aboutsummaryrefslogtreecommitdiff
path: root/client/js/views
diff options
context:
space:
mode:
authorrr-2016-10-22 10:03:38 +0200
committerrr-2016-10-22 14:05:56 +0200
commitf1445b9c24b286a9f74a2fead655ab5c169bc74b (patch)
treeeba026eb8dcd53f8d4db58e9dc50af1b857d92ed /client/js/views
parent8c0fa7f49ea24606e1887b76e89c2bfd155b1776 (diff)
client/posts: add post merging
Diffstat (limited to 'client/js/views')
-rw-r--r--client/js/views/post_detail_view.js80
-rw-r--r--client/js/views/post_main_view.js (renamed from client/js/views/post_view.js)6
-rw-r--r--client/js/views/post_merge_view.js129
3 files changed, 212 insertions, 3 deletions
diff --git a/client/js/views/post_detail_view.js b/client/js/views/post_detail_view.js
new file mode 100644
index 0000000..4c19059
--- /dev/null
+++ b/client/js/views/post_detail_view.js
@@ -0,0 +1,80 @@
+'use strict';
+
+const events = require('../events.js');
+const views = require('../util/views.js');
+const PostMergeView = require('./post_merge_view.js');
+const EmptyView = require('../views/empty_view.js');
+
+const template = views.getTemplate('post-detail');
+
+class PostDetailView extends events.EventTarget {
+ constructor(ctx) {
+ super();
+
+ this._ctx = ctx;
+ ctx.post.addEventListener('change', e => this._evtChange(e));
+ ctx.section = ctx.section || 'summary';
+
+ this._hostNode = document.getElementById('content-holder');
+ this._install();
+ }
+
+ _install() {
+ const ctx = this._ctx;
+ views.replaceContent(this._hostNode, template(ctx));
+
+ for (let item of this._hostNode.querySelectorAll('[data-name]')) {
+ item.classList.toggle(
+ 'active', item.getAttribute('data-name') === ctx.section);
+ }
+
+ ctx.hostNode = this._hostNode.querySelector('.post-content-holder');
+ if (ctx.section === 'merge') {
+ if (!this._ctx.canMerge) {
+ this._view = new EmptyView();
+ this._view.showError(
+ 'You don\'t have privileges to merge posts.');
+ } else {
+ this._view = new PostMergeView(ctx);
+ events.proxyEvent(this._view, this, 'select');
+ events.proxyEvent(this._view, this, 'submit', 'merge');
+ }
+
+ } else {
+ // this._view = new PostSummaryView(ctx);
+ }
+
+ views.syncScrollPosition();
+ }
+
+ clearMessages() {
+ this._view.clearMessages();
+ }
+
+ enableForm() {
+ this._view.enableForm();
+ }
+
+ disableForm() {
+ this._view.disableForm();
+ }
+
+ showSuccess(message) {
+ this._view.showSuccess(message);
+ }
+
+ showError(message) {
+ this._view.showError(message);
+ }
+
+ selectPost(post) {
+ this._view.selectPost(post);
+ }
+
+ _evtChange(e) {
+ this._ctx.post = e.detail.post;
+ this._install(this._ctx);
+ }
+}
+
+module.exports = PostDetailView;
diff --git a/client/js/views/post_view.js b/client/js/views/post_main_view.js
index 256eb2d..446297d 100644
--- a/client/js/views/post_view.js
+++ b/client/js/views/post_main_view.js
@@ -13,9 +13,9 @@ const PostEditSidebarControl =
const CommentListControl = require('../controls/comment_list_control.js');
const CommentFormControl = require('../controls/comment_form_control.js');
-const template = views.getTemplate('post');
+const template = views.getTemplate('post-main');
-class PostView {
+class PostMainView {
constructor(ctx) {
this._hostNode = document.getElementById('content-holder');
@@ -118,4 +118,4 @@ class PostView {
}
}
-module.exports = PostView;
+module.exports = PostMainView;
diff --git a/client/js/views/post_merge_view.js b/client/js/views/post_merge_view.js
new file mode 100644
index 0000000..fb17527
--- /dev/null
+++ b/client/js/views/post_merge_view.js
@@ -0,0 +1,129 @@
+'use strict';
+
+const config = require('../config.js');
+const events = require('../events.js');
+const views = require('../util/views.js');
+
+const KEY_RETURN = 13;
+const template = views.getTemplate('post-merge');
+const sideTemplate = views.getTemplate('post-merge-side');
+
+class PostMergeView extends events.EventTarget {
+ constructor(ctx) {
+ super();
+
+ this._ctx = ctx;
+ this._post = ctx.post;
+ this._hostNode = ctx.hostNode;
+
+ this._leftPost = ctx.post;
+ this._rightPost = null;
+ views.replaceContent(this._hostNode, template(this._ctx));
+ views.decorateValidator(this._formNode);
+
+ this._refreshLeftSide();
+ this._refreshRightSide();
+
+ this._formNode.addEventListener('submit', e => this._evtSubmit(e));
+ }
+
+ clearMessages() {
+ views.clearMessages(this._hostNode);
+ }
+
+ enableForm() {
+ views.enableForm(this._formNode);
+ }
+
+ disableForm() {
+ views.disableForm(this._formNode);
+ }
+
+ showSuccess(message) {
+ views.showSuccess(this._hostNode, message);
+ }
+
+ showError(message) {
+ views.showError(this._hostNode, message);
+ }
+
+ selectPost(post) {
+ this._rightPost = post;
+ this._refreshRightSide();
+ }
+
+ _refreshLeftSide() {
+ views.replaceContent(
+ this._leftSideNode,
+ sideTemplate(Object.assign({}, this._ctx, {
+ post: this._leftPost,
+ name: 'left',
+ editable: false})));
+ }
+
+ _refreshRightSide() {
+ views.replaceContent(
+ this._rightSideNode,
+ sideTemplate(Object.assign({}, this._ctx, {
+ post: this._rightPost,
+ name: 'right',
+ editable: true})));
+
+ if (this._targetPostFieldNode) {
+ this._targetPostFieldNode.addEventListener(
+ 'keydown', e => this._evtTargetPostFieldKeyDown(e));
+ }
+ }
+
+ _evtSubmit(e) {
+ e.preventDefault();
+ const checkedTargetPost = this._formNode.querySelector(
+ '.target-post :checked').value;
+ const checkedTargetPostContent = this._formNode.querySelector(
+ '.target-post-content :checked').value;
+ this.dispatchEvent(new CustomEvent('submit', {
+ detail: {
+ post: checkedTargetPost == 'left' ?
+ this._rightPost :
+ this._leftPost,
+ targetPost: checkedTargetPost == 'left' ?
+ this._leftPost :
+ this._rightPost,
+ useOldContent: checkedTargetPostContent !== checkedTargetPost,
+ },
+ }));
+ }
+
+ _evtTargetPostFieldKeyDown(e) {
+ const key = e.which;
+ if (key !== KEY_RETURN) {
+ return;
+ }
+ e.target.blur();
+ e.preventDefault();
+ this.dispatchEvent(new CustomEvent('select', {
+ detail: {
+ postId: this._targetPostFieldNode.value,
+ },
+ }));
+ }
+
+ get _formNode() {
+ return this._hostNode.querySelector('form');
+ }
+
+ get _leftSideNode() {
+ return this._hostNode.querySelector('.left-post-container');
+ }
+
+ get _rightSideNode() {
+ return this._hostNode.querySelector('.right-post-container');
+ }
+
+ get _targetPostFieldNode() {
+ return this._formNode.querySelector(
+ '.post-mirror input:not([readonly])[type=text]');
+ }
+}
+
+module.exports = PostMergeView;

© 2015 - 2026 Jakob L. Kreuze