From 77b2c86db3be0aed68e746cc30048770e58401c9 Mon Sep 17 00:00:00 2001 From: "Ronald M. Clifford" Date: Wed, 25 Feb 2015 22:03:13 -0600 Subject: [PATCH] Modified how the default controller and its views work. --- .../app/controllers/default_controller.js | 15 +- .../app/controllers/music_controller.js | 2 +- roncli.com/app/templates/default/index.hbs | 9 - roncli.com/app/views/default/index.js | 241 ------------------ roncli.com/app/views/error/404.js | 9 + roncli.com/app/views/error/other.js | 9 + roncli.com/app/views/page/index.js | 223 ++++++++++++++++ 7 files changed, 250 insertions(+), 258 deletions(-) delete mode 100644 roncli.com/app/templates/default/index.hbs delete mode 100644 roncli.com/app/views/default/index.js create mode 100644 roncli.com/app/views/error/404.js create mode 100644 roncli.com/app/views/error/other.js create mode 100644 roncli.com/app/views/page/index.js diff --git a/roncli.com/app/controllers/default_controller.js b/roncli.com/app/controllers/default_controller.js index 08f9ae9d..bc1bf53b 100644 --- a/roncli.com/app/controllers/default_controller.js +++ b/roncli.com/app/controllers/default_controller.js @@ -2,7 +2,7 @@ module.exports = { /** * The default view. * @param {object} params The parameters to use in the controller. - * @param {function((null | object), object=)} callback The callback to run upon completion of the controller running. + * @param {function} callback The callback to run upon completion of the controller running. */ index: function(params, callback) { "use strict"; @@ -21,15 +21,17 @@ module.exports = { } if (err) { - result = {error: true}; if (err.status) { // This is a known error. if (app && app.req && app.req.res) { app.req.res.status(err.status); } - result["status" + err.status] = true; - callback(null, result); + if (err.status === 404) { + callback(null, "error/404", result); + } else { + callback(null, "error/other", result); + } return; } @@ -37,12 +39,11 @@ module.exports = { if (app && app.req && app.req.res) { app.req.res.status(500); } - callback(null, result); + callback(null, "error/other", result); return; } // This matched a page. - result.error = false; if (app.req) { page = result.page.get("page"); content = page.content.replace("\n", " ").replace("\r", " ").replace(/<[^>]*>/g, " ").replace(/\s+/g, " ").trim(); @@ -68,7 +69,7 @@ module.exports = { }; } - callback(err, result); + callback(err, "page/index", result); }); } }; diff --git a/roncli.com/app/controllers/music_controller.js b/roncli.com/app/controllers/music_controller.js index 602f187b..1cd6778c 100644 --- a/roncli.com/app/controllers/music_controller.js +++ b/roncli.com/app/controllers/music_controller.js @@ -82,7 +82,7 @@ module.exports = { app.fetch({ page: {model: "PageOptional", params: {url: "/" + params[0]}}, song: {model: "Song_GetFromUrl", params: {url: "/" + params[0]}} - }, function(err, result) { + }, function(err, result) {console.log(app); var content; if (app.req) { diff --git a/roncli.com/app/templates/default/index.hbs b/roncli.com/app/templates/default/index.hbs deleted file mode 100644 index 73102869..00000000 --- a/roncli.com/app/templates/default/index.hbs +++ /dev/null @@ -1,9 +0,0 @@ -{{#if error}} - {{#if status404}} - {{partial "error/404"}} - {{else}} - {{partial "error/other"}} - {{/if}} -{{else}} - {{partial "page/index"}} -{{/if}} diff --git a/roncli.com/app/views/default/index.js b/roncli.com/app/views/default/index.js deleted file mode 100644 index c9aee579..00000000 --- a/roncli.com/app/views/default/index.js +++ /dev/null @@ -1,241 +0,0 @@ -/*global tinyMCE, bootbox*/ -var BaseView = require("rendr/shared/base/view"), - PageComment = require("../../models/page_comment"), - PageComments = require("../../collections/page_comments"), - $ = require("jquery"), - moment = require("moment"), - sanitizeHtml = require("sanitize-html"); - -// Sets up the default view. -module.exports = BaseView.extend({ - className: "default_index_view", - - events: { - "click img.thumb": "thumbClick", - "click #add-page-comment": "addPageComment", - "click button.comment-reply": "commentReply" - }, - - postRender: function() { - "use strict"; - - if (this.options.page) { - if ($("#sibling-pages-wrapper").length > 0) { - this.app.addPageScroller("#sibling-pages-wrapper", {mouseWheel: true, scrollbars: true}); - } - if ($("#children-pages-wrapper").length > 0) { - this.app.addPageScroller("#children-pages-wrapper", {mouseWheel: true, scrollbars: true}); - } - - $("div.page-content img").each(function() { - var image = $(this); - image.load(function() { - var width = this.width; - $("").attr("src", $(this).attr("src")).load(function() { - if (width !== this.width) { - image.addClass("thumb").attr("title", "Click to view full image in a new window"); - } - }); - }); - }); - } - }, - - thumbClick: function(ev) { - "use strict"; - - window.open($(ev.target).attr("src"), "fullImage", "menubar=0,status=0,titlebar=0,toolbar=0"); - }, - - onScroll: function() { - "use strict"; - - if (this.options.page) { - var windowTop = $(window).scrollTop(), - windowBottom = windowTop + $(window).height(), - commentsUnloaded = $("div.comments-unloaded"), - divTop = commentsUnloaded.offset().top, - divBottom = divTop + commentsUnloaded.height(); - - if (windowTop <= divBottom && windowBottom >= divTop) { - this.loadComments(); - } - } else { - this.onScroll = null; - } - }, - - loadComments: function() { - "use strict"; - - var view = this, - app = this.app; - - if (this.options.page) { - this.onScroll = null; - - // Delay 1s in case the user is rapidly moving through the pages. - setTimeout(function() { - var comments; - - if (view !== app.router.currentView) { - return; - } - - $("div.comments-unloaded").removeClass("comments-unloaded").addClass("comments"); - - comments = new PageComments(); - comments.pageId = view.options.page.attributes.page.id; - comments.fetch({ - success: function() { - if (view !== app.router.currentView) { - return; - } - - var commentsDiv = $("div.comments"); - commentsDiv.find("div.loader").remove(); - commentsDiv.append(app.templateAdapter.getTemplate("page/comment")({comments: comments.models})); - - tinyMCE.init({ - selector: "textarea.tinymce", - toolbar: [ - "formatselect | fontsizeselect | removeformat | bold italic underline | strikethrough subscript superscript", - "undo redo | alignleft aligncenter alignright | alignjustify blockquote | bullist numlist | outdent indent " - ], - menubar: false, - statusbar: false, - content_css: "/css/tinymce.min.css", - fontsize_formats: "12px 15px 18px 24px 36px 48px 72px", - init_instance_callback: function(editor) { - view.app.loadFonts(editor.iframeElement.contentWindow); - } - }); - }, - error: function(xhr, error) { - var commentsDiv = $("div.comments"), - message; - - if (error && error.body && error.body.error) { - message = error.body.error; - } else { - message = "A server error occurred while loading this post's comments. Please try again later."; - } - - commentsDiv.find("div.loader").remove(); - commentsDiv.append(app.templateAdapter.getTemplate("page/commentLoadingError")({error: message})); - } - }); - }, 1000); - } else { - this.loadComments = null; - } - }, - - addPageComment: function() { - "use strict"; - - var view = this, - attributes = sanitizeHtml.defaults.allowedAttributes, - addPageCommentButton, comment, content; - - if (this.options.page) { - if (view !== view.app.router.currentView) { - return; - } - - content = sanitizeHtml(tinyMCE.activeEditor.getContent(), { - allowedTags: sanitizeHtml.defaults.allowedTags.concat(["h1", "h2", "u", "sup", "sub", "strike", "address", "span"]), - allowedAttributes: attributes - }); - - if (content.length === 0) { - return; - } - - addPageCommentButton = $("#add-page-comment"); - addPageCommentButton.attr("disabled", ""); - tinyMCE.activeEditor.getBody().setAttribute("contenteditable", false); - - if (!this.app.user) { - this.onLogin = this.addPageComment; - $("#login").click(); - return; - } - this.onLogin = null; - - attributes.p = ["style"]; - attributes.span = ["style"]; - - comment = new PageComment(); - comment.fetch({ - url: "/page-comment", - data: JSON.stringify({ - pageId: view.options.page.attributes.page.id, - content: content - }), - type: "POST", - contentType: "application/json", - dataType: "json", - success: function() { - if (view !== view.app.router.currentView) { - return; - } - - $("#page-comment-server-errors").html(""); - $("#page-comment-server-error-list").hide(); - - tinyMCE.activeEditor.setContent(""); - addPageCommentButton.removeAttr("disabled"); - tinyMCE.activeEditor.getBody().setAttribute("contenteditable", true); - - // Display the dialog box. - bootbox.dialog({ - title: "Comment Awaiting Moderation", - message: view.app.templateAdapter.getTemplate("page/commentAwaitingModeration")(), - buttons: {ok: {label: "OK"}}, - show: false - }).off("shown.bs.modal").modal("show"); - }, - error: function(xhr, error) { - var list = $("#page-comment-server-error-list"), - message; - - console.log(xhr, error); - if (error && error.body && error.body.error) { - message = error.body.error; - } else { - message = "There was a server error posting your comment. Please try again later."; - } - $("#page-comment-server-errors").html(message); - list.show(); - addPageCommentButton.removeAttr("disabled"); - tinyMCE.activeEditor.getBody().setAttribute("contenteditable", true); - $(window).scrollTop(list.offset().top); - } - }); - } else { - this.addPageComment = null; - } - }, - - commentReply: function(ev) { - "use strict"; - - var commentPost, content, author, date; - - if (this.options.page) { - commentPost = $(ev.target).closest(".comment-post"); - content = commentPost.find(".comment-body").html().trim(); - author = commentPost.find(".comment-author").text(); - date = moment(new Date(commentPost.find(".comment-date").data("published") * 1000)); - - tinyMCE.activeEditor.setContent(""); - tinyMCE.activeEditor.execCommand("mceInsertContent", false, "

On " + date.format("M/D/YYYY") + " at " + date.format("h:mm:ss a (Z)") + ", " + author + " wrote:

" + content + "

{$caret}

"); - tinyMCE.activeEditor.focus(); - } else { - this.commentReply = null; - } - } -}); - -module.exports.id = "default/index"; diff --git a/roncli.com/app/views/error/404.js b/roncli.com/app/views/error/404.js new file mode 100644 index 00000000..93cd559c --- /dev/null +++ b/roncli.com/app/views/error/404.js @@ -0,0 +1,9 @@ +/*global bootbox*/ +var BaseView = require("rendr/shared/base/view"); + +// Sets up the 404 view. +module.exports = BaseView.extend({ + className: "error_404_view" +}); + +module.exports.id = "error/404"; diff --git a/roncli.com/app/views/error/other.js b/roncli.com/app/views/error/other.js new file mode 100644 index 00000000..e4995442 --- /dev/null +++ b/roncli.com/app/views/error/other.js @@ -0,0 +1,9 @@ +/*global bootbox*/ +var BaseView = require("rendr/shared/base/view"); + +// Sets up the other error view. +module.exports = BaseView.extend({ + className: "error_other_view" +}); + +module.exports.id = "error/other"; diff --git a/roncli.com/app/views/page/index.js b/roncli.com/app/views/page/index.js new file mode 100644 index 00000000..bc01a9c0 --- /dev/null +++ b/roncli.com/app/views/page/index.js @@ -0,0 +1,223 @@ +/*global tinyMCE, bootbox*/ +var BaseView = require("rendr/shared/base/view"), + PageComment = require("../../models/page_comment"), + PageComments = require("../../collections/page_comments"), + $ = require("jquery"), + moment = require("moment"), + sanitizeHtml = require("sanitize-html"); + +// Sets up the page view. +module.exports = BaseView.extend({ + className: "page_index_view", + + events: { + "click img.thumb": "thumbClick", + "click #add-page-comment": "addPageComment", + "click button.comment-reply": "commentReply" + }, + + postRender: function() { + "use strict"; + + if ($("#sibling-pages-wrapper").length > 0) { + this.app.addPageScroller("#sibling-pages-wrapper", {mouseWheel: true, scrollbars: true}); + } + if ($("#children-pages-wrapper").length > 0) { + this.app.addPageScroller("#children-pages-wrapper", {mouseWheel: true, scrollbars: true}); + } + + $("div.page-content img").each(function() { + var image = $(this); + image.load(function() { + var width = this.width; + $("").attr("src", $(this).attr("src")).load(function() { + if (width !== this.width) { + image.addClass("thumb").attr("title", "Click to view full image in a new window"); + } + }); + }); + }); + }, + + thumbClick: function(ev) { + "use strict"; + + window.open($(ev.target).attr("src"), "fullImage", "menubar=0,status=0,titlebar=0,toolbar=0"); + }, + + onScroll: function() { + "use strict"; + + var windowTop = $(window).scrollTop(), + windowBottom = windowTop + $(window).height(), + commentsUnloaded = $("div.comments-unloaded"), + divTop = commentsUnloaded.offset().top, + divBottom = divTop + commentsUnloaded.height(); + + if (windowTop <= divBottom && windowBottom >= divTop) { + this.loadComments(); + } + }, + + loadComments: function() { + "use strict"; + + var view = this, + app = this.app; + + this.onScroll = null; + + // Delay 1s in case the user is rapidly moving through the pages. + setTimeout(function() { + var comments; + + if (view !== app.router.currentView) { + return; + } + + $("div.comments-unloaded").removeClass("comments-unloaded").addClass("comments"); + + comments = new PageComments(); + comments.pageId = view.options.page.attributes.page.id; + comments.fetch({ + success: function() { + if (view !== app.router.currentView) { + return; + } + + var commentsDiv = $("div.comments"); + commentsDiv.find("div.loader").remove(); + commentsDiv.append(app.templateAdapter.getTemplate("page/comment")({comments: comments.models})); + + tinyMCE.init({ + selector: "textarea.tinymce", + toolbar: [ + "formatselect | fontsizeselect | removeformat | bold italic underline | strikethrough subscript superscript", + "undo redo | alignleft aligncenter alignright | alignjustify blockquote | bullist numlist | outdent indent " + ], + menubar: false, + statusbar: false, + content_css: "/css/tinymce.min.css", + fontsize_formats: "12px 15px 18px 24px 36px 48px 72px", + init_instance_callback: function(editor) { + view.app.loadFonts(editor.iframeElement.contentWindow); + } + }); + }, + error: function(xhr, error) { + var commentsDiv = $("div.comments"), + message; + + if (error && error.body && error.body.error) { + message = error.body.error; + } else { + message = "A server error occurred while loading this post's comments. Please try again later."; + } + + commentsDiv.find("div.loader").remove(); + commentsDiv.append(app.templateAdapter.getTemplate("page/commentLoadingError")({error: message})); + } + }); + }, 1000); + }, + + addPageComment: function() { + "use strict"; + + var view = this, + attributes = sanitizeHtml.defaults.allowedAttributes, + addPageCommentButton, comment, content; + + if (view !== view.app.router.currentView) { + return; + } + + content = sanitizeHtml(tinyMCE.activeEditor.getContent(), { + allowedTags: sanitizeHtml.defaults.allowedTags.concat(["h1", "h2", "u", "sup", "sub", "strike", "address", "span"]), + allowedAttributes: attributes + }); + + if (content.length === 0) { + return; + } + + addPageCommentButton = $("#add-page-comment"); + addPageCommentButton.attr("disabled", ""); + tinyMCE.activeEditor.getBody().setAttribute("contenteditable", false); + + if (!this.app.user) { + this.onLogin = this.addPageComment; + $("#login").click(); + return; + } + this.onLogin = null; + + attributes.p = ["style"]; + attributes.span = ["style"]; + + comment = new PageComment(); + comment.fetch({ + url: "/page-comment", + data: JSON.stringify({ + pageId: view.options.page.attributes.page.id, + content: content + }), + type: "POST", + contentType: "application/json", + dataType: "json", + success: function() { + if (view !== view.app.router.currentView) { + return; + } + + $("#page-comment-server-errors").html(""); + $("#page-comment-server-error-list").hide(); + + tinyMCE.activeEditor.setContent(""); + addPageCommentButton.removeAttr("disabled"); + tinyMCE.activeEditor.getBody().setAttribute("contenteditable", true); + + // Display the dialog box. + bootbox.dialog({ + title: "Comment Awaiting Moderation", + message: view.app.templateAdapter.getTemplate("page/commentAwaitingModeration")(), + buttons: {ok: {label: "OK"}}, + show: false + }).off("shown.bs.modal").modal("show"); + }, + error: function(xhr, error) { + var list = $("#page-comment-server-error-list"), + message; + + console.log(xhr, error); + if (error && error.body && error.body.error) { + message = error.body.error; + } else { + message = "There was a server error posting your comment. Please try again later."; + } + $("#page-comment-server-errors").html(message); + list.show(); + addPageCommentButton.removeAttr("disabled"); + tinyMCE.activeEditor.getBody().setAttribute("contenteditable", true); + $(window).scrollTop(list.offset().top); + } + }); + }, + + commentReply: function(ev) { + "use strict"; + + var commentPost, content, author, date; + + commentPost = $(ev.target).closest(".comment-post"); + content = commentPost.find(".comment-body").html().trim(); + author = commentPost.find(".comment-author").text(); + date = moment(new Date(commentPost.find(".comment-date").data("published") * 1000)); + + tinyMCE.activeEditor.setContent(""); + tinyMCE.activeEditor.execCommand("mceInsertContent", false, "

On " + date.format("M/D/YYYY") + " at " + date.format("h:mm:ss a (Z)") + ", " + author + " wrote:

" + content + "

{$caret}

"); + tinyMCE.activeEditor.focus(); + } +}); + +module.exports.id = "page/index";