diff options
author | John Molakvoæ (skjnldsv) <skjnldsv@protonmail.com> | 2019-09-25 18:19:42 +0200 |
---|---|---|
committer | John Molakvoæ (skjnldsv) <skjnldsv@protonmail.com> | 2019-10-01 17:16:09 +0200 |
commit | b9bc2417e7a8dc81feb0abe20359bedaf864f790 (patch) | |
tree | 61b47fbf37c1d168da8625224debde9e6a985348 /apps/comments/src | |
parent | 7fb651235128dcbca8a6683b5cdafdf835f46300 (diff) | |
download | nextcloud-server-b9bc2417e7a8dc81feb0abe20359bedaf864f790.tar.gz nextcloud-server-b9bc2417e7a8dc81feb0abe20359bedaf864f790.zip |
Comply to eslint
Signed-off-by: John Molakvoæ (skjnldsv) <skjnldsv@protonmail.com>
Diffstat (limited to 'apps/comments/src')
-rw-r--r-- | apps/comments/src/activitytabviewplugin.js | 31 | ||||
-rw-r--r-- | apps/comments/src/app.js | 5 | ||||
-rw-r--r-- | apps/comments/src/commentcollection.js | 186 | ||||
-rw-r--r-- | apps/comments/src/commentmodel.js | 104 | ||||
-rw-r--r-- | apps/comments/src/comments.js | 2 | ||||
-rw-r--r-- | apps/comments/src/commentsmodifymenu.js | 55 | ||||
-rw-r--r-- | apps/comments/src/commentstabview.js | 1260 | ||||
-rw-r--r-- | apps/comments/src/commentsummarymodel.js | 60 | ||||
-rw-r--r-- | apps/comments/src/filesplugin.js | 86 | ||||
-rw-r--r-- | apps/comments/src/search.js | 101 |
10 files changed, 944 insertions, 946 deletions
diff --git a/apps/comments/src/activitytabviewplugin.js b/apps/comments/src/activitytabviewplugin.js index b6195b80c45..2afee4c2be5 100644 --- a/apps/comments/src/activitytabviewplugin.js +++ b/apps/comments/src/activitytabviewplugin.js @@ -1,4 +1,4 @@ -/* +/** * @author Joas Schilling <coding@schilljs.com> * Copyright (c) 2016 * @@ -18,18 +18,18 @@ * @param {jQuery} $el jQuery handle for this activity * @param {string} view The view that displayes this activity */ - prepareModelForDisplay: function (model, $el, view) { + prepareModelForDisplay: function(model, $el, view) { if (model.get('app') !== 'comments' || model.get('type') !== 'comments') { - return; + return } if (view === 'ActivityTabView') { - $el.addClass('comment'); + $el.addClass('comment') if (model.get('message') && this._isLong(model.get('message'))) { - $el.addClass('collapsed'); - var $overlay = $('<div>').addClass('message-overlay'); - $el.find('.activitymessage').after($overlay); - $el.on('click', this._onClickCollapsedComment); + $el.addClass('collapsed') + var $overlay = $('<div>').addClass('message-overlay') + $el.find('.activitymessage').after($overlay) + $el.on('click', this._onClickCollapsedComment) } } }, @@ -38,22 +38,21 @@ * Copy of CommentsTabView._onClickComment() */ _onClickCollapsedComment: function(ev) { - var $row = $(ev.target); + var $row = $(ev.target) if (!$row.is('.comment')) { - $row = $row.closest('.comment'); + $row = $row.closest('.comment') } - $row.removeClass('collapsed'); + $row.removeClass('collapsed') }, /* * Copy of CommentsTabView._isLong() */ _isLong: function(message) { - return message.length > 250 || (message.match(/\n/g) || []).length > 1; + return message.length > 250 || (message.match(/\n/g) || []).length > 1 } - }; + } +})() -})(); - -OC.Plugins.register('OCA.Activity.RenderingPlugins', OCA.Comments.ActivityTabViewPlugin); +OC.Plugins.register('OCA.Activity.RenderingPlugins', OCA.Comments.ActivityTabViewPlugin) diff --git a/apps/comments/src/app.js b/apps/comments/src/app.js index 547059393a5..626d7703a3e 100644 --- a/apps/comments/src/app.js +++ b/apps/comments/src/app.js @@ -13,8 +13,7 @@ /** * @namespace */ - OCA.Comments = {}; + OCA.Comments = {} } -})(); - +})() diff --git a/apps/comments/src/commentcollection.js b/apps/comments/src/commentcollection.js index a15039cf484..8e7f9e37d56 100644 --- a/apps/comments/src/commentcollection.js +++ b/apps/comments/src/commentcollection.js @@ -1,3 +1,4 @@ +/* eslint-disable */ /* * Copyright (c) 2016 * @@ -20,148 +21,147 @@ var CommentCollection = OC.Backbone.Collection.extend( /** @lends OCA.Comments.CommentCollection.prototype */ { - sync: OC.Backbone.davSync, + sync: OC.Backbone.davSync, - model: OCA.Comments.CommentModel, + model: OCA.Comments.CommentModel, - /** + /** * Object type * * @type string */ - _objectType: 'files', + _objectType: 'files', - /** + /** * Object id * * @type string */ - _objectId: null, + _objectId: null, - /** + /** * True if there are no more page results left to fetch * * @type bool */ - _endReached: false, + _endReached: false, - /** + /** * Number of comments to fetch per page * * @type int */ - _limit : 20, + _limit: 20, - /** + /** * Initializes the collection * * @param {string} [options.objectType] object type * @param {string} [options.objectId] object id */ - initialize: function(models, options) { - options = options || {}; - if (options.objectType) { - this._objectType = options.objectType; - } - if (options.objectId) { - this._objectId = options.objectId; - } - }, + initialize: function(models, options) { + options = options || {} + if (options.objectType) { + this._objectType = options.objectType + } + if (options.objectId) { + this._objectId = options.objectId + } + }, - url: function() { - return OC.linkToRemote('dav') + '/comments/' + - encodeURIComponent(this._objectType) + '/' + - encodeURIComponent(this._objectId) + '/'; - }, + url: function() { + return OC.linkToRemote('dav') + '/comments/' + + encodeURIComponent(this._objectType) + '/' + + encodeURIComponent(this._objectId) + '/' + }, - setObjectId: function(objectId) { - this._objectId = objectId; - }, + setObjectId: function(objectId) { + this._objectId = objectId + }, - hasMoreResults: function() { - return !this._endReached; - }, + hasMoreResults: function() { + return !this._endReached + }, - reset: function() { - this._endReached = false; - this._summaryModel = null; - return OC.Backbone.Collection.prototype.reset.apply(this, arguments); - }, + reset: function() { + this._endReached = false + this._summaryModel = null + return OC.Backbone.Collection.prototype.reset.apply(this, arguments) + }, - /** + /** * Fetch the next set of results */ - fetchNext: function(options) { - var self = this; - if (!this.hasMoreResults()) { - return null; - } + fetchNext: function(options) { + var self = this + if (!this.hasMoreResults()) { + return null + } - var body = '<?xml version="1.0" encoding="utf-8" ?>\n' + - '<oc:filter-comments xmlns:D="DAV:" xmlns:oc="http://owncloud.org/ns">\n' + + var body = '<?xml version="1.0" encoding="utf-8" ?>\n' + + '<oc:filter-comments xmlns:D="DAV:" xmlns:oc="http://owncloud.org/ns">\n' // load one more so we know there is more - ' <oc:limit>' + (this._limit + 1) + '</oc:limit>\n' + - ' <oc:offset>' + this.length + '</oc:offset>\n' + - '</oc:filter-comments>\n'; - - options = options || {}; - var success = options.success; - options = _.extend({ - remove: false, - parse: true, - data: body, - davProperties: CommentCollection.prototype.model.prototype.davProperties, - success: function(resp) { - if (resp.length <= self._limit) { + + ' <oc:limit>' + (this._limit + 1) + '</oc:limit>\n' + + ' <oc:offset>' + this.length + '</oc:offset>\n' + + '</oc:filter-comments>\n' + + options = options || {} + var success = options.success + options = _.extend({ + remove: false, + parse: true, + data: body, + davProperties: CommentCollection.prototype.model.prototype.davProperties, + success: function(resp) { + if (resp.length <= self._limit) { // no new entries, end reached - self._endReached = true; - } else { + self._endReached = true + } else { // remove last entry, for next page load - resp = _.initial(resp); - } - if (!self.set(resp, options)) { - return false; + resp = _.initial(resp) + } + if (!self.set(resp, options)) { + return false + } + if (success) { + success.apply(null, arguments) + } + self.trigger('sync', 'REPORT', self, options) } - if (success) { - success.apply(null, arguments); - } - self.trigger('sync', 'REPORT', self, options); - } - }, options); + }, options) - return this.sync('REPORT', this, options); - }, + return this.sync('REPORT', this, options) + }, - /** + /** * Returns the matching summary model * - * @return {OCA.Comments.CommentSummaryModel} summary model + * @returns {OCA.Comments.CommentSummaryModel} summary model */ - getSummaryModel: function() { - if (!this._summaryModel) { - this._summaryModel = new OCA.Comments.CommentSummaryModel({ - id: this._objectId, - objectType: this._objectType - }); - } - return this._summaryModel; - }, + getSummaryModel: function() { + if (!this._summaryModel) { + this._summaryModel = new OCA.Comments.CommentSummaryModel({ + id: this._objectId, + objectType: this._objectType + }) + } + return this._summaryModel + }, - /** + /** * Updates the read marker for this comment thread * * @param {Date} [date] optional date, defaults to now * @param {Object} [options] backbone options */ - updateReadMarker: function(date, options) { - options = options || {}; - - return this.getSummaryModel().save({ - readMarker: (date || new Date()).toUTCString() - }, options); - } - }); + updateReadMarker: function(date, options) { + options = options || {} - OCA.Comments.CommentCollection = CommentCollection; -})(OC, OCA); + return this.getSummaryModel().save({ + readMarker: (date || new Date()).toUTCString() + }, options) + } + }) + OCA.Comments.CommentCollection = CommentCollection +})(OC, OCA) diff --git a/apps/comments/src/commentmodel.js b/apps/comments/src/commentmodel.js index 3711e53c9f3..804fbdfd3cb 100644 --- a/apps/comments/src/commentmodel.js +++ b/apps/comments/src/commentmodel.js @@ -12,7 +12,7 @@ _.extend(OC.Files.Client, { PROPERTY_FILEID: '{' + OC.Files.Client.NS_OWNCLOUD + '}id', - PROPERTY_MESSAGE: '{' + OC.Files.Client.NS_OWNCLOUD + '}message', + PROPERTY_MESSAGE: '{' + OC.Files.Client.NS_OWNCLOUD + '}message', PROPERTY_ACTORTYPE: '{' + OC.Files.Client.NS_OWNCLOUD + '}actorType', PROPERTY_ACTORID: '{' + OC.Files.Client.NS_OWNCLOUD + '}actorId', PROPERTY_ISUNREAD: '{' + OC.Files.Client.NS_OWNCLOUD + '}isUnread', @@ -21,7 +21,7 @@ PROPERTY_ACTORDISPLAYNAME: '{' + OC.Files.Client.NS_OWNCLOUD + '}actorDisplayName', PROPERTY_CREATIONDATETIME: '{' + OC.Files.Client.NS_OWNCLOUD + '}creationDateTime', PROPERTY_MENTIONS: '{' + OC.Files.Client.NS_OWNCLOUD + '}mentions' - }); + }) /** * @class OCA.Comments.CommentModel @@ -32,62 +32,62 @@ */ var CommentModel = OC.Backbone.Model.extend( /** @lends OCA.Comments.CommentModel.prototype */ { - sync: OC.Backbone.davSync, + sync: OC.Backbone.davSync, - defaults: { - actorType: 'users', - objectType: 'files' - }, + defaults: { + actorType: 'users', + objectType: 'files' + }, - davProperties: { - 'id': OC.Files.Client.PROPERTY_FILEID, - 'message': OC.Files.Client.PROPERTY_MESSAGE, - 'actorType': OC.Files.Client.PROPERTY_ACTORTYPE, - 'actorId': OC.Files.Client.PROPERTY_ACTORID, - 'actorDisplayName': OC.Files.Client.PROPERTY_ACTORDISPLAYNAME, - 'creationDateTime': OC.Files.Client.PROPERTY_CREATIONDATETIME, - 'objectType': OC.Files.Client.PROPERTY_OBJECTTYPE, - 'objectId': OC.Files.Client.PROPERTY_OBJECTID, - 'isUnread': OC.Files.Client.PROPERTY_ISUNREAD, - 'mentions': OC.Files.Client.PROPERTY_MENTIONS - }, + davProperties: { + 'id': OC.Files.Client.PROPERTY_FILEID, + 'message': OC.Files.Client.PROPERTY_MESSAGE, + 'actorType': OC.Files.Client.PROPERTY_ACTORTYPE, + 'actorId': OC.Files.Client.PROPERTY_ACTORID, + 'actorDisplayName': OC.Files.Client.PROPERTY_ACTORDISPLAYNAME, + 'creationDateTime': OC.Files.Client.PROPERTY_CREATIONDATETIME, + 'objectType': OC.Files.Client.PROPERTY_OBJECTTYPE, + 'objectId': OC.Files.Client.PROPERTY_OBJECTID, + 'isUnread': OC.Files.Client.PROPERTY_ISUNREAD, + 'mentions': OC.Files.Client.PROPERTY_MENTIONS + }, - parse: function(data) { - return { - id: data.id, - message: data.message, - actorType: data.actorType, - actorId: data.actorId, - actorDisplayName: data.actorDisplayName, - creationDateTime: data.creationDateTime, - objectType: data.objectType, - objectId: data.objectId, - isUnread: (data.isUnread === 'true'), - mentions: this._parseMentions(data.mentions) - }; - }, + parse: function(data) { + return { + id: data.id, + message: data.message, + actorType: data.actorType, + actorId: data.actorId, + actorDisplayName: data.actorDisplayName, + creationDateTime: data.creationDateTime, + objectType: data.objectType, + objectId: data.objectId, + isUnread: (data.isUnread === 'true'), + mentions: this._parseMentions(data.mentions) + } + }, - _parseMentions: function(mentions) { - if(_.isUndefined(mentions)) { - return {}; - } - var result = {}; - for(var i in mentions) { - var mention = mentions[i]; - if(_.isUndefined(mention.localName) || mention.localName !== 'mention') { - continue; + _parseMentions: function(mentions) { + if (_.isUndefined(mentions)) { + return {} } - result[i] = {}; - for (var child = mention.firstChild; child; child = child.nextSibling) { - if(_.isUndefined(child.localName) || !child.localName.startsWith('mention')) { - continue; + var result = {} + for (var i in mentions) { + var mention = mentions[i] + if (_.isUndefined(mention.localName) || mention.localName !== 'mention') { + continue + } + result[i] = {} + for (var child = mention.firstChild; child; child = child.nextSibling) { + if (_.isUndefined(child.localName) || !child.localName.startsWith('mention')) { + continue + } + result[i][child.localName] = child.textContent } - result[i][child.localName] = child.textContent; } + return result } - return result; - } - }); + }) - OCA.Comments.CommentModel = CommentModel; -})(OC, OCA); + OCA.Comments.CommentModel = CommentModel +})(OC, OCA) diff --git a/apps/comments/src/comments.js b/apps/comments/src/comments.js index f0d4433674b..e632936c770 100644 --- a/apps/comments/src/comments.js +++ b/apps/comments/src/comments.js @@ -15,4 +15,4 @@ import './vendor/At.js/dist/js/jquery.atwho.min' import './style/autocomplete.scss' import './style/comments.scss' -window.OCA.Comments = OCA.Comments; +window.OCA.Comments = OCA.Comments diff --git a/apps/comments/src/commentsmodifymenu.js b/apps/comments/src/commentsmodifymenu.js index 2640dcf4201..7c9470f13b2 100644 --- a/apps/comments/src/commentsmodifymenu.js +++ b/apps/comments/src/commentsmodifymenu.js @@ -8,7 +8,6 @@ * */ -/* global Handlebars */ (function() { /** @@ -23,7 +22,7 @@ _scopes: [ { name: 'edit', - displayName: t('comments', 'Edit comment'), + displayName: t('comments', 'Edit comment'), iconClass: 'icon-rename' }, { @@ -45,14 +44,14 @@ * @param {Object} event event object */ _onClickAction: function(event) { - var $target = $(event.currentTarget); + var $target = $(event.currentTarget) if (!$target.hasClass('menuitem')) { - $target = $target.closest('.menuitem'); + $target = $target.closest('.menuitem') } - OC.hideMenus(); + OC.hideMenus() - this.trigger('select:menu-item-clicked', event, $target.data('action')); + this.trigger('select:menu-item-clicked', event, $target.data('action')) }, /** @@ -61,49 +60,49 @@ render: function() { this.$el.html(OCA.Comments.Templates['commentsmodifymenu']({ items: this._scopes - })); + })) }, /** * Displays the menu + * @param {Event} context the click event */ show: function(context) { - this._context = context; + this._context = context - for(var i in this._scopes) { - this._scopes[i].active = false; + for (var i in this._scopes) { + this._scopes[i].active = false } - - var $el = $(context.target); - var offsetIcon = $el.offset(); - var offsetContainer = $el.closest('.authorRow').offset(); + var $el = $(context.target) + var offsetIcon = $el.offset() + var offsetContainer = $el.closest('.authorRow').offset() // adding some extra top offset to push the menu below the button. var position = { top: offsetIcon.top - offsetContainer.top + 48, left: '', right: '' - }; + } - position.left = offsetIcon.left - offsetContainer.left; + position.left = offsetIcon.left - offsetContainer.left if (position.left > 200) { // we need to position the menu to the right. - position.left = ''; - position.right = this.$el.closest('.comment').find('.date').width(); - this.$el.removeClass('menu-left').addClass('menu-right'); + position.left = '' + position.right = this.$el.closest('.comment').find('.date').width() + this.$el.removeClass('menu-left').addClass('menu-right') } else { - this.$el.removeClass('menu-right').addClass('menu-left'); + this.$el.removeClass('menu-right').addClass('menu-left') } - this.$el.css(position); - this.render(); - this.$el.removeClass('hidden'); + this.$el.css(position) + this.render() + this.$el.removeClass('hidden') - OC.showMenu(null, this.$el); + OC.showMenu(null, this.$el) } - }); + }) - OCA.Comments = OCA.Comments || {}; - OCA.Comments.CommentsModifyMenu = CommentsModifyMenu; -})(OC, OCA); + OCA.Comments = OCA.Comments || {} + OCA.Comments.CommentsModifyMenu = CommentsModifyMenu +})(OC, OCA) diff --git a/apps/comments/src/commentstabview.js b/apps/comments/src/commentstabview.js index 8b71fc1f87b..a638f46a2c6 100644 --- a/apps/comments/src/commentstabview.js +++ b/apps/comments/src/commentstabview.js @@ -1,3 +1,4 @@ +/* eslint-disable */ /* * Copyright (c) 2016 * @@ -17,252 +18,252 @@ */ var CommentsTabView = OCA.Files.DetailTabView.extend( /** @lends OCA.Comments.CommentsTabView.prototype */ { - id: 'commentsTabView', - className: 'tab commentsTabView', - _autoCompleteData: undefined, - _commentsModifyMenu: undefined, - - events: { - 'submit .newCommentForm': '_onSubmitComment', - 'click .showMore': '_onClickShowMore', - 'click .cancel': '_onClickCloseComment', - 'click .comment': '_onClickComment', - 'keyup div.message': '_onTextChange', - 'change div.message': '_onTextChange', - 'input div.message': '_onTextChange', - 'paste div.message': '_onPaste' - }, - - _commentMaxLength: 1000, - - initialize: function() { - OCA.Files.DetailTabView.prototype.initialize.apply(this, arguments); - this.collection = new OCA.Comments.CommentCollection(); - this.collection.on('request', this._onRequest, this); - this.collection.on('sync', this._onEndRequest, this); - this.collection.on('add', this._onAddModel, this); - this.collection.on('change:message', this._onChangeModel, this); - - this._commentMaxThreshold = this._commentMaxLength * 0.9; - - // TODO: error handling - _.bindAll(this, '_onTypeComment', '_initAutoComplete', '_onAutoComplete'); - }, - - template: function(params) { - var currentUser = OC.getCurrentUser(); - return OCA.Comments.Templates['view'](_.extend({ - actorId: currentUser.uid, - actorDisplayName: currentUser.displayName - }, params)); - }, - - editCommentTemplate: function(params) { - var currentUser = OC.getCurrentUser(); - return OCA.Comments.Templates['edit_comment'](_.extend({ - actorId: currentUser.uid, - actorDisplayName: currentUser.displayName, - newMessagePlaceholder: t('comments', 'New comment …'), - submitText: t('comments', 'Post'), - cancelText: t('comments', 'Cancel'), - tag: 'li' - }, params)); - }, - - commentTemplate: function(params) { - params = _.extend({ - editTooltip: t('comments', 'Edit comment'), - isUserAuthor: OC.getCurrentUser().uid === params.actorId, - isLong: this._isLong(params.message) - }, params); - - if (params.actorType === 'deleted_users') { + id: 'commentsTabView', + className: 'tab commentsTabView', + _autoCompleteData: undefined, + _commentsModifyMenu: undefined, + + events: { + 'submit .newCommentForm': '_onSubmitComment', + 'click .showMore': '_onClickShowMore', + 'click .cancel': '_onClickCloseComment', + 'click .comment': '_onClickComment', + 'keyup div.message': '_onTextChange', + 'change div.message': '_onTextChange', + 'input div.message': '_onTextChange', + 'paste div.message': '_onPaste' + }, + + _commentMaxLength: 1000, + + initialize: function() { + OCA.Files.DetailTabView.prototype.initialize.apply(this, arguments) + this.collection = new OCA.Comments.CommentCollection() + this.collection.on('request', this._onRequest, this) + this.collection.on('sync', this._onEndRequest, this) + this.collection.on('add', this._onAddModel, this) + this.collection.on('change:message', this._onChangeModel, this) + + this._commentMaxThreshold = this._commentMaxLength * 0.9 + + // TODO: error handling + _.bindAll(this, '_onTypeComment', '_initAutoComplete', '_onAutoComplete') + }, + + template: function(params) { + var currentUser = OC.getCurrentUser() + return OCA.Comments.Templates['view'](_.extend({ + actorId: currentUser.uid, + actorDisplayName: currentUser.displayName + }, params)) + }, + + editCommentTemplate: function(params) { + var currentUser = OC.getCurrentUser() + return OCA.Comments.Templates['edit_comment'](_.extend({ + actorId: currentUser.uid, + actorDisplayName: currentUser.displayName, + newMessagePlaceholder: t('comments', 'New comment …'), + submitText: t('comments', 'Post'), + cancelText: t('comments', 'Cancel'), + tag: 'li' + }, params)) + }, + + commentTemplate: function(params) { + params = _.extend({ + editTooltip: t('comments', 'Edit comment'), + isUserAuthor: OC.getCurrentUser().uid === params.actorId, + isLong: this._isLong(params.message) + }, params) + + if (params.actorType === 'deleted_users') { // makes the avatar a X - params.actorId = null; - params.actorDisplayName = t('comments', '[Deleted user]'); - } + params.actorId = null + params.actorDisplayName = t('comments', '[Deleted user]') + } - return OCA.Comments.Templates['comment'](params); - }, - - getLabel: function() { - return t('comments', 'Comments'); - }, - - getIcon: function() { - return 'icon-comment'; - }, - - setFileInfo: function(fileInfo) { - if (fileInfo) { - this.model = fileInfo; - - this.render(); - this._initAutoComplete($('#commentsTabView').find('.newCommentForm .message')); - this.collection.setObjectId(this.model.id); - // reset to first page - this.collection.reset([], {silent: true}); - this.nextPage(); - } else { - this.model = null; - this.render(); - this.collection.reset(); - } - }, - - render: function() { - this.$el.html(this.template({ - emptyResultLabel: t('comments', 'No comments yet, start the conversation!'), - moreLabel: t('comments', 'More comments …') - })); - this.$el.find('.comments').before(this.editCommentTemplate({ tag: 'div'})); - this.$el.find('.has-tooltip').tooltip(); - this.$container = this.$el.find('ul.comments'); - this.$el.find('.avatar').avatar(OC.getCurrentUser().uid, 32); - this.delegateEvents(); - this.$el.find('.message').on('keydown input change', this._onTypeComment); - - autosize(this.$el.find('.newCommentRow .message')) - this.$el.find('.newCommentForm .message').focus(); - }, - - _initAutoComplete: function($target) { - var s = this; - var limit = 10; - if(!_.isUndefined(OC.appConfig.comments)) { - limit = OC.appConfig.comments.maxAutoCompleteResults; - } - $target.atwho({ - at: '@', - limit: limit, - callbacks: { - remoteFilter: s._onAutoComplete, - highlighter: function (li) { + return OCA.Comments.Templates['comment'](params) + }, + + getLabel: function() { + return t('comments', 'Comments') + }, + + getIcon: function() { + return 'icon-comment' + }, + + setFileInfo: function(fileInfo) { + if (fileInfo) { + this.model = fileInfo + + this.render() + this._initAutoComplete($('#commentsTabView').find('.newCommentForm .message')) + this.collection.setObjectId(this.model.id) + // reset to first page + this.collection.reset([], { silent: true }) + this.nextPage() + } else { + this.model = null + this.render() + this.collection.reset() + } + }, + + render: function() { + this.$el.html(this.template({ + emptyResultLabel: t('comments', 'No comments yet, start the conversation!'), + moreLabel: t('comments', 'More comments …') + })) + this.$el.find('.comments').before(this.editCommentTemplate({ tag: 'div' })) + this.$el.find('.has-tooltip').tooltip() + this.$container = this.$el.find('ul.comments') + this.$el.find('.avatar').avatar(OC.getCurrentUser().uid, 32) + this.delegateEvents() + this.$el.find('.message').on('keydown input change', this._onTypeComment) + + autosize(this.$el.find('.newCommentRow .message')) + this.$el.find('.newCommentForm .message').focus() + }, + + _initAutoComplete: function($target) { + var s = this + var limit = 10 + if (!_.isUndefined(OC.appConfig.comments)) { + limit = OC.appConfig.comments.maxAutoCompleteResults + } + $target.atwho({ + at: '@', + limit: limit, + callbacks: { + remoteFilter: s._onAutoComplete, + highlighter: function(li) { // misuse the highlighter callback to instead of // highlighting loads the avatars. - var $li = $(li); - $li.find('.avatar').avatar(undefined, 32); - return $li; + var $li = $(li) + $li.find('.avatar').avatar(undefined, 32) + return $li + }, + sorter: function(q, items) { return items } + }, + displayTpl: function(item) { + return '<li>' + + '<span class="avatar-name-wrapper">' + + '<span class="avatar" ' + + 'data-username="' + escapeHTML(item.id) + '" ' // for avatars + + 'data-user="' + escapeHTML(item.id) + '" ' // for contactsmenu + + 'data-user-display-name="' + escapeHTML(item.label) + '">' + + '</span>' + + '<strong>' + escapeHTML(item.label) + '</strong>' + + '</span></li>' }, - sorter: function (q, items) { return items; } - }, - displayTpl: function (item) { - return '<li>' + - '<span class="avatar-name-wrapper">' + - '<span class="avatar" ' + - 'data-username="' + escapeHTML(item.id) + '" ' + // for avatars - 'data-user="' + escapeHTML(item.id) + '" ' + // for contactsmenu - 'data-user-display-name="' + escapeHTML(item.label) + '">' + - '</span>' + - '<strong>' + escapeHTML(item.label) + '</strong>' + - '</span></li>'; - }, - insertTpl: function (item) { - return '' + - '<span class="avatar-name-wrapper">' + - '<span class="avatar" ' + - 'data-username="' + escapeHTML(item.id) + '" ' + // for avatars - 'data-user="' + escapeHTML(item.id) + '" ' + // for contactsmenu - 'data-user-display-name="' + escapeHTML(item.label) + '">' + - '</span>' + - '<strong>' + escapeHTML(item.label) + '</strong>' + - '</span>'; - }, - searchKey: "label" - }); - $target.on('inserted.atwho', function (je, $el) { - var editionMode = true; - s._postRenderItem( + insertTpl: function(item) { + return '' + + '<span class="avatar-name-wrapper">' + + '<span class="avatar" ' + + 'data-username="' + escapeHTML(item.id) + '" ' // for avatars + + 'data-user="' + escapeHTML(item.id) + '" ' // for contactsmenu + + 'data-user-display-name="' + escapeHTML(item.label) + '">' + + '</span>' + + '<strong>' + escapeHTML(item.label) + '</strong>' + + '</span>' + }, + searchKey: 'label' + }) + $target.on('inserted.atwho', function(je, $el) { + var editionMode = true + s._postRenderItem( // we need to pass the parent of the inserted element // passing the whole comments form would re-apply and request // avatars from the server - $(je.target).find( - 'span[data-username="' + $el.find('[data-username]').data('username') + '"]' - ).parent(), - editionMode - ); - }); - }, - - _onAutoComplete: function(query, callback) { - var s = this; - if(!_.isUndefined(this._autoCompleteRequestTimer)) { - clearTimeout(this._autoCompleteRequestTimer); - } - this._autoCompleteRequestTimer = _.delay(function() { - if(!_.isUndefined(this._autoCompleteRequestCall)) { - this._autoCompleteRequestCall.abort(); + $(je.target).find( + 'span[data-username="' + $el.find('[data-username]').data('username') + '"]' + ).parent(), + editionMode + ) + }) + }, + + _onAutoComplete: function(query, callback) { + var s = this + if (!_.isUndefined(this._autoCompleteRequestTimer)) { + clearTimeout(this._autoCompleteRequestTimer) } - this._autoCompleteRequestCall = $.ajax({ - url: OC.linkToOCS('core', 2) + 'autocomplete/get', - data: { - search: query, - itemType: 'files', - itemId: s.model.get('id'), - sorter: 'commenters|share-recipients', - limit: OC.appConfig.comments.maxAutoCompleteResults - }, - beforeSend: function (request) { - request.setRequestHeader('Accept', 'application/json'); - }, - success: function (result) { - callback(result.ocs.data); + this._autoCompleteRequestTimer = _.delay(function() { + if (!_.isUndefined(this._autoCompleteRequestCall)) { + this._autoCompleteRequestCall.abort() } - }); - }, 400); - }, - - _formatItem: function(commentModel) { - var timestamp = new Date(commentModel.get('creationDateTime')).getTime(); - var data = _.extend({ - timestamp: timestamp, - date: OC.Util.relativeModifiedDate(timestamp), - altDate: OC.Util.formatDate(timestamp), - formattedMessage: this._formatMessage(commentModel.get('message'), commentModel.get('mentions')) - }, commentModel.attributes); - return data; - }, - - _toggleLoading: function(state) { - this._loading = state; - this.$el.find('.loading').toggleClass('hidden', !state); - }, - - _onRequest: function(type) { - if (type === 'REPORT') { - this._toggleLoading(true); - this.$el.find('.showMore').addClass('hidden'); - } - }, + this._autoCompleteRequestCall = $.ajax({ + url: OC.linkToOCS('core', 2) + 'autocomplete/get', + data: { + search: query, + itemType: 'files', + itemId: s.model.get('id'), + sorter: 'commenters|share-recipients', + limit: OC.appConfig.comments.maxAutoCompleteResults + }, + beforeSend: function(request) { + request.setRequestHeader('Accept', 'application/json') + }, + success: function(result) { + callback(result.ocs.data) + } + }) + }, 400) + }, + + _formatItem: function(commentModel) { + var timestamp = new Date(commentModel.get('creationDateTime')).getTime() + var data = _.extend({ + timestamp: timestamp, + date: OC.Util.relativeModifiedDate(timestamp), + altDate: OC.Util.formatDate(timestamp), + formattedMessage: this._formatMessage(commentModel.get('message'), commentModel.get('mentions')) + }, commentModel.attributes) + return data + }, + + _toggleLoading: function(state) { + this._loading = state + this.$el.find('.loading').toggleClass('hidden', !state) + }, + + _onRequest: function(type) { + if (type === 'REPORT') { + this._toggleLoading(true) + this.$el.find('.showMore').addClass('hidden') + } + }, - _onEndRequest: function(type) { - var fileInfoModel = this.model; - this._toggleLoading(false); - this.$el.find('.emptycontent').toggleClass('hidden', !!this.collection.length); - this.$el.find('.showMore').toggleClass('hidden', !this.collection.hasMoreResults()); + _onEndRequest: function(type) { + var fileInfoModel = this.model + this._toggleLoading(false) + this.$el.find('.emptycontent').toggleClass('hidden', !!this.collection.length) + this.$el.find('.showMore').toggleClass('hidden', !this.collection.hasMoreResults()) - if (type !== 'REPORT') { - return; - } + if (type !== 'REPORT') { + return + } - // find first unread comment - var firstUnreadComment = this.collection.findWhere({isUnread: true}); - if (firstUnreadComment) { + // find first unread comment + var firstUnreadComment = this.collection.findWhere({ isUnread: true }) + if (firstUnreadComment) { // update read marker - this.collection.updateReadMarker( - null, - { - success: function() { - fileInfoModel.set('commentsUnread', 0); + this.collection.updateReadMarker( + null, + { + success: function() { + fileInfoModel.set('commentsUnread', 0) + } } - } - ); - } - this.$el.find('.newCommentForm .message').focus(); - - }, + ) + } + this.$el.find('.newCommentForm .message').focus() + + }, - /** + /** * takes care of post-rendering after a new comment was added to the * collection * @@ -271,322 +272,321 @@ * @param options * @private */ - _onAddModel: function(model, collection, options) { + _onAddModel: function(model, collection, options) { // we need to render it immediately, to ensure that the right // order of comments is kept on opening comments tab - var $comment = $(this.commentTemplate(this._formatItem(model))); - if (!_.isUndefined(options.at) && collection.length > 1) { - this.$container.find('li').eq(options.at).before($comment); - } else { - this.$container.append($comment); - } - this._postRenderItem($comment); - $('#commentsTabView').find('.newCommentForm div.message').text('').prop('contenteditable', true); - - // we need to update the model, because it consists of client data - // only, but the server might add meta data, e.g. about mentions - var oldMentions = model.get('mentions'); - var self = this; - model.fetch({ - success: function (model) { - if(_.isEqual(oldMentions, model.get('mentions'))) { + var $comment = $(this.commentTemplate(this._formatItem(model))) + if (!_.isUndefined(options.at) && collection.length > 1) { + this.$container.find('li').eq(options.at).before($comment) + } else { + this.$container.append($comment) + } + this._postRenderItem($comment) + $('#commentsTabView').find('.newCommentForm div.message').text('').prop('contenteditable', true) + + // we need to update the model, because it consists of client data + // only, but the server might add meta data, e.g. about mentions + var oldMentions = model.get('mentions') + var self = this + model.fetch({ + success: function(model) { + if (_.isEqual(oldMentions, model.get('mentions'))) { // don't attempt to render if unnecessary, avoids flickering - return; + return + } + var $updated = $(self.commentTemplate(self._formatItem(model))) + $comment.html($updated.html()) + self._postRenderItem($comment) } - var $updated = $(self.commentTemplate(self._formatItem(model))); - $comment.html($updated.html()); - self._postRenderItem($comment); - } - }) + }) - }, + }, - /** + /** * takes care of post-rendering after a new comment was edited * * @param model * @private */ - _onChangeModel: function (model) { - if(model.get('message').trim() === model.previous('message').trim()) { - return; - } + _onChangeModel: function(model) { + if (model.get('message').trim() === model.previous('message').trim()) { + return + } - var $form = this.$container.find('.comment[data-id="' + model.id + '"] form'); - var $row = $form.closest('.comment'); - var $target = $row.data('commentEl'); - if(_.isUndefined($target)) { + var $form = this.$container.find('.comment[data-id="' + model.id + '"] form') + var $row = $form.closest('.comment') + var $target = $row.data('commentEl') + if (_.isUndefined($target)) { // ignore noise – this is only set after editing a comment and hitting post - return; - } - var self = this; - - // we need to update the model, because it consists of client data - // only, but the server might add meta data, e.g. about mentions - model.fetch({ - success: function (model) { - $target.removeClass('hidden'); - $row.remove(); - - var $message = $target.find('.message'); - $message - .html(self._formatMessage(model.get('message'), model.get('mentions'))) - .find('.avatar') - .each(function () { $(this).avatar(); }); - self._postRenderItem($message); + return } - }); - }, - - _postRenderItem: function($el, editionMode) { - $el.find('.has-tooltip').tooltip(); - var inlineAvatars = $el.find('.message .avatar'); - if ($($el.context).hasClass('message')) { - inlineAvatars = $el.find('.avatar'); - } - inlineAvatars.each(function () { - var $this = $(this); - $this.avatar($this.attr('data-username'), 16); - }); - $el.find('.authorRow .avatar').each(function () { - var $this = $(this); - $this.avatar($this.attr('data-username'), 32); - }); - - var username = $el.find('.avatar').data('username'); - if (username !== OC.getCurrentUser().uid) { - $el.find('.authorRow .avatar, .authorRow .author').contactsMenu( - username, 0, $el.find('.authorRow')); - } + var self = this - var $message = $el.find('.message'); - if($message.length === 0) { - // it is the case when writing a comment and mentioning a person - $message = $el; - } - - - if (!editionMode) { - var self = this; - // add the dropdown menu to display the edit and delete option - var modifyCommentMenu = new OCA.Comments.CommentsModifyMenu(); - $el.find('.authorRow').append(modifyCommentMenu.$el); - $el.find('.more').on('click', _.bind(modifyCommentMenu.show, modifyCommentMenu)); - - self.listenTo(modifyCommentMenu, 'select:menu-item-clicked', function(ev, action) { - if (action === 'edit') { - self._onClickEditComment(ev); - } else if (action === 'delete') { - self._onClickDeleteComment(ev); + // we need to update the model, because it consists of client data + // only, but the server might add meta data, e.g. about mentions + model.fetch({ + success: function(model) { + $target.removeClass('hidden') + $row.remove() + + var $message = $target.find('.message') + $message + .html(self._formatMessage(model.get('message'), model.get('mentions'))) + .find('.avatar') + .each(function() { $(this).avatar() }) + self._postRenderItem($message) } - }); - } + }) + }, + + _postRenderItem: function($el, editionMode) { + $el.find('.has-tooltip').tooltip() + var inlineAvatars = $el.find('.message .avatar') + if ($($el.context).hasClass('message')) { + inlineAvatars = $el.find('.avatar') + } + inlineAvatars.each(function() { + var $this = $(this) + $this.avatar($this.attr('data-username'), 16) + }) + $el.find('.authorRow .avatar').each(function() { + var $this = $(this) + $this.avatar($this.attr('data-username'), 32) + }) + + var username = $el.find('.avatar').data('username') + if (username !== OC.getCurrentUser().uid) { + $el.find('.authorRow .avatar, .authorRow .author').contactsMenu( + username, 0, $el.find('.authorRow')) + } - this._postRenderMessage($message, editionMode); - }, + var $message = $el.find('.message') + if ($message.length === 0) { + // it is the case when writing a comment and mentioning a person + $message = $el + } - _postRenderMessage: function($el, editionMode) { - if (editionMode) { - return; - } + if (!editionMode) { + var self = this + // add the dropdown menu to display the edit and delete option + var modifyCommentMenu = new OCA.Comments.CommentsModifyMenu() + $el.find('.authorRow').append(modifyCommentMenu.$el) + $el.find('.more').on('click', _.bind(modifyCommentMenu.show, modifyCommentMenu)) + + self.listenTo(modifyCommentMenu, 'select:menu-item-clicked', function(ev, action) { + if (action === 'edit') { + self._onClickEditComment(ev) + } else if (action === 'delete') { + self._onClickDeleteComment(ev) + } + }) + } - $el.find('.avatar-name-wrapper').each(function() { - var $this = $(this); - var $avatar = $this.find('.avatar'); + this._postRenderMessage($message, editionMode) + }, - var user = $avatar.data('user'); - if (user !== OC.getCurrentUser().uid) { - $this.contactsMenu(user, 0, $this); + _postRenderMessage: function($el, editionMode) { + if (editionMode) { + return } - }); - }, - /** + $el.find('.avatar-name-wrapper').each(function() { + var $this = $(this) + var $avatar = $this.find('.avatar') + + var user = $avatar.data('user') + if (user !== OC.getCurrentUser().uid) { + $this.contactsMenu(user, 0, $this) + } + }) + }, + + /** * Convert a message to be displayed in HTML, * converts newlines to <br> tags. */ - _formatMessage: function(message, mentions, editMode) { - message = escapeHTML(message).replace(/\n/g, '<br/>'); + _formatMessage: function(message, mentions, editMode) { + message = escapeHTML(message).replace(/\n/g, '<br/>') - for(var i in mentions) { - if(!mentions.hasOwnProperty(i)) { - return; - } - var mention = '@' + mentions[i].mentionId; - if (mentions[i].mentionId.indexOf(' ') !== -1) { - mention = _.escape('@"' + mentions[i].mentionId + '"'); - } + for (var i in mentions) { + if (!mentions.hasOwnProperty(i)) { + return + } + var mention = '@' + mentions[i].mentionId + if (mentions[i].mentionId.indexOf(' ') !== -1) { + mention = _.escape('@"' + mentions[i].mentionId + '"') + } - // escape possible regex characters in the name - mention = mention.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); - var regex = new RegExp("(^|\\s)(" + mention + ")\\b", 'g'); - if (mentions[i].mentionId.indexOf(' ') !== -1) { - regex = new RegExp("(^|\\s)(" + mention + ")", 'g'); - } + // escape possible regex characters in the name + mention = mention.replace(/[.*+?^${}()|[\]\\]/g, '\\$&') + var regex = new RegExp('(^|\\s)(' + mention + ')\\b', 'g') + if (mentions[i].mentionId.indexOf(' ') !== -1) { + regex = new RegExp('(^|\\s)(' + mention + ')', 'g') + } - var displayName = this._composeHTMLMention(mentions[i].mentionId, mentions[i].mentionDisplayName); + var displayName = this._composeHTMLMention(mentions[i].mentionId, mentions[i].mentionDisplayName) - // replace every mention either at the start of the input or after a whitespace - // followed by a non-word character. - message = message.replace(regex, - function(match, p1) { + // replace every mention either at the start of the input or after a whitespace + // followed by a non-word character. + message = message.replace(regex, + function(match, p1) { // to get number of whitespaces (0 vs 1) right - return p1+displayName; - } - ); - } - if(editMode !== true) { - message = OCP.Comments.plainToRich(message); - } - return message; - }, - - _composeHTMLMention: function(uid, displayName) { - var avatar = '' + - '<span class="avatar" ' + - 'data-username="' + _.escape(uid) + '" ' + - 'data-user="' + _.escape(uid) + '" ' + - 'data-user-display-name="' + _.escape(displayName) + '">' + - '</span>'; - - var isCurrentUser = (uid === OC.getCurrentUser().uid); - - return '' + - '<span class="atwho-inserted" contenteditable="false">' + - '<span class="avatar-name-wrapper' + (isCurrentUser ? ' currentUser' : '') + '">' + - avatar + - '<strong>' + _.escape(displayName) + '</strong>' + - '</span>' + - '</span>'; - }, - - nextPage: function() { - if (this._loading || !this.collection.hasMoreResults()) { - return; - } + return p1 + displayName + } + ) + } + if (editMode !== true) { + message = OCP.Comments.plainToRich(message) + } + return message + }, + + _composeHTMLMention: function(uid, displayName) { + var avatar = '' + + '<span class="avatar" ' + + 'data-username="' + _.escape(uid) + '" ' + + 'data-user="' + _.escape(uid) + '" ' + + 'data-user-display-name="' + _.escape(displayName) + '">' + + '</span>' + + var isCurrentUser = (uid === OC.getCurrentUser().uid) + + return '' + + '<span class="atwho-inserted" contenteditable="false">' + + '<span class="avatar-name-wrapper' + (isCurrentUser ? ' currentUser' : '') + '">' + + avatar + + '<strong>' + _.escape(displayName) + '</strong>' + + '</span>' + + '</span>' + }, + + nextPage: function() { + if (this._loading || !this.collection.hasMoreResults()) { + return + } - this.collection.fetchNext(); - }, - - _onClickEditComment: function(ev) { - ev.preventDefault(); - var $comment = $(ev.target).closest('.comment'); - var commentId = $comment.data('id'); - var commentToEdit = this.collection.get(commentId); - var $formRow = $(this.editCommentTemplate(_.extend({ - isEditMode: true, - submitText: t('comments', 'Save') - }, commentToEdit.attributes))); - - $comment.addClass('hidden').removeClass('collapsed'); - // spawn form - $comment.after($formRow); - $formRow.data('commentEl', $comment); - $formRow.find('.message').on('keydown input change', this._onTypeComment); - - // copy avatar element from original to avoid flickering - $formRow.find('.avatar:first').replaceWith($comment.find('.avatar:first').clone()); - $formRow.find('.has-tooltip').tooltip(); - - var $message = $formRow.find('.message'); - $message - .html(this._formatMessage(commentToEdit.get('message'), commentToEdit.get('mentions'), true)) - .find('.avatar') - .each(function () { $(this).avatar(); }); - var editionMode = true; - this._postRenderItem($message, editionMode); - - // Enable autosize - autosize($formRow.find('.message')); - - // enable autocomplete - this._initAutoComplete($formRow.find('.message')); - - return false; - }, - - _onTypeComment: function(ev) { - var $field = $(ev.target); - var len = $field.text().length; - var $submitButton = $field.data('submitButtonEl'); - if (!$submitButton) { - $submitButton = $field.closest('form').find('.submit'); - $field.data('submitButtonEl', $submitButton); - } - $field.tooltip('hide'); - if (len > this._commentMaxThreshold) { - $field.attr('data-original-title', t('comments', 'Allowed characters {count} of {max}', {count: len, max: this._commentMaxLength})); - $field.tooltip({trigger: 'manual'}); - $field.tooltip('show'); - $field.addClass('error'); - } + this.collection.fetchNext() + }, + + _onClickEditComment: function(ev) { + ev.preventDefault() + var $comment = $(ev.target).closest('.comment') + var commentId = $comment.data('id') + var commentToEdit = this.collection.get(commentId) + var $formRow = $(this.editCommentTemplate(_.extend({ + isEditMode: true, + submitText: t('comments', 'Save') + }, commentToEdit.attributes))) + + $comment.addClass('hidden').removeClass('collapsed') + // spawn form + $comment.after($formRow) + $formRow.data('commentEl', $comment) + $formRow.find('.message').on('keydown input change', this._onTypeComment) + + // copy avatar element from original to avoid flickering + $formRow.find('.avatar:first').replaceWith($comment.find('.avatar:first').clone()) + $formRow.find('.has-tooltip').tooltip() + + var $message = $formRow.find('.message') + $message + .html(this._formatMessage(commentToEdit.get('message'), commentToEdit.get('mentions'), true)) + .find('.avatar') + .each(function() { $(this).avatar() }) + var editionMode = true + this._postRenderItem($message, editionMode) + + // Enable autosize + autosize($formRow.find('.message')) + + // enable autocomplete + this._initAutoComplete($formRow.find('.message')) + + return false + }, + + _onTypeComment: function(ev) { + var $field = $(ev.target) + var len = $field.text().length + var $submitButton = $field.data('submitButtonEl') + if (!$submitButton) { + $submitButton = $field.closest('form').find('.submit') + $field.data('submitButtonEl', $submitButton) + } + $field.tooltip('hide') + if (len > this._commentMaxThreshold) { + $field.attr('data-original-title', t('comments', 'Allowed characters {count} of {max}', { count: len, max: this._commentMaxLength })) + $field.tooltip({ trigger: 'manual' }) + $field.tooltip('show') + $field.addClass('error') + } - var limitExceeded = (len > this._commentMaxLength); - $field.toggleClass('error', limitExceeded); - $submitButton.prop('disabled', limitExceeded); - - // Submits form with Enter, but Shift+Enter is a new line. If the - // autocomplete popover is being shown Enter does not submit the - // form either; it will be handled by At.js which will add the - // currently selected item to the message. - if (ev.keyCode === 13 && !ev.shiftKey && !$field.atwho('isSelecting')) { - $submitButton.click(); - ev.preventDefault(); - } - }, + var limitExceeded = (len > this._commentMaxLength) + $field.toggleClass('error', limitExceeded) + $submitButton.prop('disabled', limitExceeded) + + // Submits form with Enter, but Shift+Enter is a new line. If the + // autocomplete popover is being shown Enter does not submit the + // form either; it will be handled by At.js which will add the + // currently selected item to the message. + if (ev.keyCode === 13 && !ev.shiftKey && !$field.atwho('isSelecting')) { + $submitButton.click() + ev.preventDefault() + } + }, - _onClickComment: function(ev) { - var $row = $(ev.target); - if (!$row.is('.comment')) { - $row = $row.closest('.comment'); - } - $row.removeClass('collapsed'); - }, - - _onClickCloseComment: function(ev) { - ev.preventDefault(); - var $row = $(ev.target).closest('.comment'); - $row.data('commentEl').removeClass('hidden'); - $row.remove(); - return false; - }, - - _onClickDeleteComment: function(ev) { - ev.preventDefault(); - var $comment = $(ev.target).closest('.comment'); - var commentId = $comment.data('id'); - var $loading = $comment.find('.deleteLoading'); - var $moreIcon = $comment.find('.more'); - - $comment.addClass('disabled'); - $loading.removeClass('hidden'); - $moreIcon.addClass('hidden'); - - $comment.data('commentEl', $comment); - - this.collection.get(commentId).destroy({ - success: function() { - $comment.data('commentEl').remove(); - $comment.remove(); - }, - error: function() { - $loading.addClass('hidden'); - $moreIcon.removeClass('hidden'); - $comment.removeClass('disabled'); - - OC.Notification.showTemporary(t('comments', 'Error occurred while retrieving comment with ID {id}', {id: commentId})); + _onClickComment: function(ev) { + var $row = $(ev.target) + if (!$row.is('.comment')) { + $row = $row.closest('.comment') } - }); + $row.removeClass('collapsed') + }, + + _onClickCloseComment: function(ev) { + ev.preventDefault() + var $row = $(ev.target).closest('.comment') + $row.data('commentEl').removeClass('hidden') + $row.remove() + return false + }, + + _onClickDeleteComment: function(ev) { + ev.preventDefault() + var $comment = $(ev.target).closest('.comment') + var commentId = $comment.data('id') + var $loading = $comment.find('.deleteLoading') + var $moreIcon = $comment.find('.more') + + $comment.addClass('disabled') + $loading.removeClass('hidden') + $moreIcon.addClass('hidden') + + $comment.data('commentEl', $comment) + + this.collection.get(commentId).destroy({ + success: function() { + $comment.data('commentEl').remove() + $comment.remove() + }, + error: function() { + $loading.addClass('hidden') + $moreIcon.removeClass('hidden') + $comment.removeClass('disabled') + + OC.Notification.showTemporary(t('comments', 'Error occurred while retrieving comment with ID {id}', { id: commentId })) + } + }) - return false; - }, + return false + }, - _onClickShowMore: function(ev) { - ev.preventDefault(); - this.nextPage(); - }, + _onClickShowMore: function(ev) { + ev.preventDefault() + this.nextPage() + }, - /** + /** * takes care of updating comment element states after submit (either new * comment or edit). * @@ -594,106 +594,106 @@ * @param {jQuery} $form * @private */ - _onSubmitSuccess: function(model, $form) { - var $submit = $form.find('.submit'); - var $loading = $form.find('.submitLoading'); - - $submit.removeClass('hidden'); - $loading.addClass('hidden'); - }, - - _commentBodyHTML2Plain: function($el) { - var $comment = $el.clone(); - - $comment.find('.avatar-name-wrapper').each(function () { - var $this = $(this), - $inserted = $this.parent(), - userId = $this.find('.avatar').data('username'); - if (userId.indexOf(' ') !== -1) { - $inserted.html('@"' + userId + '"'); - } else { - $inserted.html('@' + userId); - } - }); + _onSubmitSuccess: function(model, $form) { + var $submit = $form.find('.submit') + var $loading = $form.find('.submitLoading') + + $submit.removeClass('hidden') + $loading.addClass('hidden') + }, + + _commentBodyHTML2Plain: function($el) { + var $comment = $el.clone() + + $comment.find('.avatar-name-wrapper').each(function() { + var $this = $(this) + var $inserted = $this.parent() + var userId = $this.find('.avatar').data('username') + if (userId.indexOf(' ') !== -1) { + $inserted.html('@"' + userId + '"') + } else { + $inserted.html('@' + userId) + } + }) - $comment.html(OCP.Comments.richToPlain($comment.html())); + $comment.html(OCP.Comments.richToPlain($comment.html())) - var oldHtml; - var html = $comment.html(); - do { + var oldHtml + var html = $comment.html() + do { // replace works one by one - oldHtml = html; - html = oldHtml.replace("<br>", "\n"); // preserve line breaks - } while(oldHtml !== html); - $comment.html(html); - - return $comment.text(); - }, - - _onSubmitComment: function(e) { - var self = this; - var $form = $(e.target); - var commentId = $form.closest('.comment').data('id'); - var currentUser = OC.getCurrentUser(); - var $submit = $form.find('.submit'); - var $loading = $form.find('.submitLoading'); - var $commentField = $form.find('.message'); - var message = $commentField.text().trim(); - e.preventDefault(); - - if (!message.length || message.length > this._commentMaxLength) { - return; - } + oldHtml = html + html = oldHtml.replace('<br>', '\n') // preserve line breaks + } while (oldHtml !== html) + $comment.html(html) + + return $comment.text() + }, + + _onSubmitComment: function(e) { + var self = this + var $form = $(e.target) + var commentId = $form.closest('.comment').data('id') + var currentUser = OC.getCurrentUser() + var $submit = $form.find('.submit') + var $loading = $form.find('.submitLoading') + var $commentField = $form.find('.message') + var message = $commentField.text().trim() + e.preventDefault() + + if (!message.length || message.length > this._commentMaxLength) { + return + } - $commentField.prop('contenteditable', false); - $submit.addClass('hidden'); - $loading.removeClass('hidden'); + $commentField.prop('contenteditable', false) + $submit.addClass('hidden') + $loading.removeClass('hidden') - message = this._commentBodyHTML2Plain($commentField); - if (commentId) { + message = this._commentBodyHTML2Plain($commentField) + if (commentId) { // edit mode - var comment = this.collection.get(commentId); - comment.save({ - message: message - }, { - success: function(model) { - self._onSubmitSuccess(model, $form); - if(model.get('message').trim() === model.previous('message').trim()) { + var comment = this.collection.get(commentId) + comment.save({ + message: message + }, { + success: function(model) { + self._onSubmitSuccess(model, $form) + if (model.get('message').trim() === model.previous('message').trim()) { // model change event doesn't trigger, manually remove the row. - var $row = $form.closest('.comment'); - $row.data('commentEl').removeClass('hidden'); - $row.remove(); + var $row = $form.closest('.comment') + $row.data('commentEl').removeClass('hidden') + $row.remove() + } + }, + error: function() { + self._onSubmitError($form, commentId) } - }, - error: function() { - self._onSubmitError($form, commentId); - } - }); - } else { - this.collection.create({ - actorId: currentUser.uid, - actorDisplayName: currentUser.displayName, - actorType: 'users', - verb: 'comment', - message: message, - creationDateTime: (new Date()).toUTCString() - }, { - at: 0, - // wait for real creation before adding - wait: true, - success: function(model) { - self._onSubmitSuccess(model, $form); - }, - error: function() { - self._onSubmitError($form, undefined); - } - }); - } + }) + } else { + this.collection.create({ + actorId: currentUser.uid, + actorDisplayName: currentUser.displayName, + actorType: 'users', + verb: 'comment', + message: message, + creationDateTime: (new Date()).toUTCString() + }, { + at: 0, + // wait for real creation before adding + wait: true, + success: function(model) { + self._onSubmitSuccess(model, $form) + }, + error: function() { + self._onSubmitError($form, undefined) + } + }) + } - return false; - }, + return false + }, - /** + /** * takes care of updating the UI after an error on submit (either new * comment or edit). * @@ -701,51 +701,51 @@ * @param {string|undefined} commentId * @private */ - _onSubmitError: function($form, commentId) { - $form.find('.submit').removeClass('hidden'); - $form.find('.submitLoading').addClass('hidden'); - $form.find('.message').prop('contenteditable', true); - - if(!_.isUndefined(commentId)) { - OC.Notification.show(t('comments', 'Error occurred while updating comment with id {id}', {id: commentId}), {type: 'error'}); - } else { - OC.Notification.show(t('comments', 'Error occurred while posting comment'), {type: 'error'}); - } - }, + _onSubmitError: function($form, commentId) { + $form.find('.submit').removeClass('hidden') + $form.find('.submitLoading').addClass('hidden') + $form.find('.message').prop('contenteditable', true) - /** + if (!_.isUndefined(commentId)) { + OC.Notification.show(t('comments', 'Error occurred while updating comment with id {id}', { id: commentId }), { type: 'error' }) + } else { + OC.Notification.show(t('comments', 'Error occurred while posting comment'), { type: 'error' }) + } + }, + + /** * ensures the contenteditable div is really empty, when user removed * all input, so that the placeholder will be shown again * * @private */ - _onTextChange: function() { - var $message = $('#commentsTabView').find('.newCommentForm div.message'); - if(!$message.text().trim().length) { - $message.empty(); - } - }, + _onTextChange: function() { + var $message = $('#commentsTabView').find('.newCommentForm div.message') + if (!$message.text().trim().length) { + $message.empty() + } + }, - /** + /** * Limit pasting to plain text * * @param e * @private */ - _onPaste: function (e) { - e.preventDefault(); - var text = e.originalEvent.clipboardData.getData("text/plain"); - document.execCommand('insertText', false, text); - }, + _onPaste: function(e) { + e.preventDefault() + var text = e.originalEvent.clipboardData.getData('text/plain') + document.execCommand('insertText', false, text) + }, - /** + /** * Returns whether the given message is long and needs * collapsing */ - _isLong: function(message) { - return message.length > 250 || (message.match(/\n/g) || []).length > 1; - } - }); + _isLong: function(message) { + return message.length > 250 || (message.match(/\n/g) || []).length > 1 + } + }) - OCA.Comments.CommentsTabView = CommentsTabView; -})(OC, OCA); + OCA.Comments.CommentsTabView = CommentsTabView +})(OC, OCA) diff --git a/apps/comments/src/commentsummarymodel.js b/apps/comments/src/commentsummarymodel.js index ffabbc30fb4..1a3002a9f78 100644 --- a/apps/comments/src/commentsummarymodel.js +++ b/apps/comments/src/commentsummarymodel.js @@ -12,7 +12,7 @@ _.extend(OC.Files.Client, { PROPERTY_READMARKER: '{' + OC.Files.Client.NS_OWNCLOUD + '}readMarker' - }); + }) /** * @class OCA.Comments.CommentSummaryModel @@ -24,45 +24,47 @@ */ var CommentSummaryModel = OC.Backbone.Model.extend( /** @lends OCA.Comments.CommentSummaryModel.prototype */ { - sync: OC.Backbone.davSync, + sync: OC.Backbone.davSync, - /** + /** * Object type * * @type string */ - _objectType: 'files', + _objectType: 'files', - /** + /** * Object id * * @type string */ - _objectId: null, + _objectId: null, - davProperties: { - 'readMarker': OC.Files.Client.PROPERTY_READMARKER - }, + davProperties: { + 'readMarker': OC.Files.Client.PROPERTY_READMARKER + }, - /** - * Initializes the summary model - * - * @param {string} [options.objectType] object type - * @param {string} [options.objectId] object id - */ - initialize: function(attrs, options) { - options = options || {}; - if (options.objectType) { - this._objectType = options.objectType; - } - }, + /** + * Initializes the summary model + * + * @param {any} [attrs] ignored + * @param {Object} [options] destructuring object + * @param {string} [options.objectType] object type + * @param {string} [options.objectId] object id + */ + initialize: function(attrs, options) { + options = options || {} + if (options.objectType) { + this._objectType = options.objectType + } + }, - url: function() { - return OC.linkToRemote('dav') + '/comments/' + - encodeURIComponent(this._objectType) + '/' + - encodeURIComponent(this.id) + '/'; - } - }); + url: function() { + return OC.linkToRemote('dav') + '/comments/' + + encodeURIComponent(this._objectType) + '/' + + encodeURIComponent(this.id) + '/' + } + }) - OCA.Comments.CommentSummaryModel = CommentSummaryModel; -})(OC, OCA); + OCA.Comments.CommentSummaryModel = CommentSummaryModel +})(OC, OCA) diff --git a/apps/comments/src/filesplugin.js b/apps/comments/src/filesplugin.js index 2073be09b69..e315dd2fef8 100644 --- a/apps/comments/src/filesplugin.js +++ b/apps/comments/src/filesplugin.js @@ -8,20 +8,18 @@ * */ -/* global Handlebars */ - (function() { _.extend(OC.Files.Client, { PROPERTY_COMMENTS_UNREAD: '{' + OC.Files.Client.NS_OWNCLOUD + '}comments-unread' - }); + }) - OCA.Comments = _.extend({}, OCA.Comments); + OCA.Comments = _.extend({}, OCA.Comments) if (!OCA.Comments) { /** * @namespace */ - OCA.Comments = {}; + OCA.Comments = {} } /** @@ -38,43 +36,43 @@ count: count, countMessage: n('comments', '%n unread comment', '%n unread comments', count), iconUrl: OC.imagePath('core', 'actions/comment') - }); + }) }, attach: function(fileList) { - var self = this; + var self = this if (this.ignoreLists.indexOf(fileList.id) >= 0) { - return; + return } - fileList.registerTabView(new OCA.Comments.CommentsTabView('commentsTabView')); + fileList.registerTabView(new OCA.Comments.CommentsTabView('commentsTabView')) - var oldGetWebdavProperties = fileList._getWebdavProperties; + var oldGetWebdavProperties = fileList._getWebdavProperties fileList._getWebdavProperties = function() { - var props = oldGetWebdavProperties.apply(this, arguments); - props.push(OC.Files.Client.PROPERTY_COMMENTS_UNREAD); - return props; - }; + var props = oldGetWebdavProperties.apply(this, arguments) + props.push(OC.Files.Client.PROPERTY_COMMENTS_UNREAD) + return props + } fileList.filesClient.addFileInfoParser(function(response) { - var data = {}; - var props = response.propStat[0].properties; - var commentsUnread = props[OC.Files.Client.PROPERTY_COMMENTS_UNREAD]; + var data = {} + var props = response.propStat[0].properties + var commentsUnread = props[OC.Files.Client.PROPERTY_COMMENTS_UNREAD] if (!_.isUndefined(commentsUnread) && commentsUnread !== '') { - data.commentsUnread = parseInt(commentsUnread, 10); + data.commentsUnread = parseInt(commentsUnread, 10) } - return data; - }); + return data + }) - fileList.$el.addClass('has-comments'); - var oldCreateRow = fileList._createRow; + fileList.$el.addClass('has-comments') + var oldCreateRow = fileList._createRow fileList._createRow = function(fileData) { - var $tr = oldCreateRow.apply(this, arguments); + var $tr = oldCreateRow.apply(this, arguments) if (fileData.commentsUnread) { - $tr.attr('data-comments-unread', fileData.commentsUnread); + $tr.attr('data-comments-unread', fileData.commentsUnread) } - return $tr; - }; + return $tr + } // register "comment" action for reading comments fileList.fileActions.registerAction({ @@ -94,35 +92,35 @@ permissions: OC.PERMISSION_READ, type: OCA.Files.FileActions.TYPE_INLINE, render: function(actionSpec, isDefault, context) { - var $file = context.$file; - var unreadComments = $file.data('comments-unread'); + var $file = context.$file + var unreadComments = $file.data('comments-unread') if (unreadComments) { - var $actionLink = $(self._formatCommentCount(unreadComments)); - context.$file.find('a.name>span.fileactions').append($actionLink); - return $actionLink; + var $actionLink = $(self._formatCommentCount(unreadComments)) + context.$file.find('a.name>span.fileactions').append($actionLink) + return $actionLink } - return ''; + return '' }, actionHandler: function(fileName, context) { - context.$file.find('.action-comment').tooltip('hide'); + context.$file.find('.action-comment').tooltip('hide') // open sidebar in comments section - context.fileList.showDetailsView(fileName, 'commentsTabView'); + context.fileList.showDetailsView(fileName, 'commentsTabView') } - }); + }) // add attribute to "elementToFile" - var oldElementToFile = fileList.elementToFile; + var oldElementToFile = fileList.elementToFile fileList.elementToFile = function($el) { - var fileInfo = oldElementToFile.apply(this, arguments); - var commentsUnread = $el.data('comments-unread'); + var fileInfo = oldElementToFile.apply(this, arguments) + var commentsUnread = $el.data('comments-unread') if (commentsUnread) { - fileInfo.commentsUnread = commentsUnread; + fileInfo.commentsUnread = commentsUnread } - return fileInfo; - }; + return fileInfo + } } - }; + } -})(); +})() -OC.Plugins.register('OCA.Files.FileList', OCA.Comments.FilesPlugin); +OC.Plugins.register('OCA.Files.FileList', OCA.Comments.FilesPlugin) diff --git a/apps/comments/src/search.js b/apps/comments/src/search.js index 8e0a35ff6ed..c62726d9082 100644 --- a/apps/comments/src/search.js +++ b/apps/comments/src/search.js @@ -1,3 +1,4 @@ +/* eslint-disable */ /* * Copyright (c) 2014 * @@ -8,15 +9,15 @@ * */ (function(OC, OCA, $) { - "use strict"; + 'use strict' /** * Construct a new FileActions instance * @constructs Files */ var Comment = function() { - this.initialize(); - }; + this.initialize() + } Comment.prototype = { @@ -27,25 +28,25 @@ */ initialize: function() { - var self = this; + var self = this this.fileAppLoaded = function() { - return !!OCA.Files && !!OCA.Files.App; - }; + return !!OCA.Files && !!OCA.Files.App + } function inFileList($row, result) { - return false; + return false - if (! self.fileAppLoaded()) { - return false; + if (!self.fileAppLoaded()) { + return false } - var dir = self.fileList.getCurrentDirectory().replace(/\/+$/,''); - var resultDir = OC.dirname(result.path); - return dir === resultDir && self.fileList.inList(result.name); + var dir = self.fileList.getCurrentDirectory().replace(/\/+$/, '') + var resultDir = OC.dirname(result.path) + return dir === resultDir && self.fileList.inList(result.name) } function hideNoFilterResults() { - var $nofilterresults = $('.nofilterresults'); - if ( ! $nofilterresults.hasClass('hidden') ) { - $nofilterresults.addClass('hidden'); + var $nofilterresults = $('.nofilterresults') + if (!$nofilterresults.hasClass('hidden')) { + $nofilterresults.addClass('hidden') } } @@ -64,73 +65,73 @@ */ this.renderCommentResult = function($row, result) { if (inFileList($row, result)) { - return null; + return null } - hideNoFilterResults(); - /*render preview icon, show path beneath filename, + hideNoFilterResults() + /* render preview icon, show path beneath filename, show size and last modified date on the right */ - this.updateLegacyMimetype(result); + this.updateLegacyMimetype(result) - var $pathDiv = $('<div>').addClass('path').text(result.path); + var $pathDiv = $('<div>').addClass('path').text(result.path) - var $avatar = $('<div>'); + var $avatar = $('<div>') $avatar.addClass('avatar') .css('display', 'inline-block') .css('vertical-align', 'middle') - .css('margin', '0 5px 2px 3px'); + .css('margin', '0 5px 2px 3px') if (result.authorName) { - $avatar.avatar(result.authorId, 21, undefined, false, undefined, result.authorName); + $avatar.avatar(result.authorId, 21, undefined, false, undefined, result.authorName) } else { - $avatar.avatar(result.authorId, 21); + $avatar.avatar(result.authorId, 21) } - $row.find('td.info div.name').after($pathDiv).text(result.comment).prepend($('<span>').addClass('path').css('margin-right', '5px').text(result.authorName)).prepend($avatar); - $row.find('td.result a').attr('href', result.link); + $row.find('td.info div.name').after($pathDiv).text(result.comment).prepend($('<span>').addClass('path').css('margin-right', '5px').text(result.authorName)).prepend($avatar) + $row.find('td.result a').attr('href', result.link) $row.find('td.icon') .css('background-image', 'url(' + OC.imagePath('core', 'actions/comment') + ')') - .css('opacity', '.4'); - var dir = OC.dirname(result.path); + .css('opacity', '.4') + var dir = OC.dirname(result.path) // "result.path" does not include a leading "/", so "OC.dirname" // returns the path itself for files or folders in the root. if (dir === result.path) { - dir = '/'; + dir = '/' } $row.find('td.info a').attr('href', - OC.generateUrl('/apps/files/?dir={dir}&scrollto={scrollto}', {dir: dir, scrollto: result.fileName}) - ); + OC.generateUrl('/apps/files/?dir={dir}&scrollto={scrollto}', { dir: dir, scrollto: result.fileName }) + ) - return $row; - }; + return $row + } this.handleCommentClick = function($row, result, event) { if (self.fileAppLoaded() && self.fileList.id === 'files') { - self.fileList.changeDirectory(OC.dirname(result.path)); - self.fileList.scrollTo(result.name); - return false; + self.fileList.changeDirectory(OC.dirname(result.path)) + self.fileList.scrollTo(result.name) + return false } else { - return true; + return true } - }; + } - this.updateLegacyMimetype = function (result) { + this.updateLegacyMimetype = function(result) { // backward compatibility: if (!result.mime && result.mime_type) { - result.mime = result.mime_type; + result.mime = result.mime_type } - }; - this.setFileList = function (fileList) { - this.fileList = fileList; - }; + } + this.setFileList = function(fileList) { + this.fileList = fileList + } - OC.Plugins.register('OCA.Search.Core', this); + OC.Plugins.register('OCA.Search.Core', this) }, attach: function(search) { - search.setRenderer('comment', this.renderCommentResult.bind(this)); - search.setHandler('comment', this.handleCommentClick.bind(this)); + search.setRenderer('comment', this.renderCommentResult.bind(this)) + search.setHandler('comment', this.handleCommentClick.bind(this)) } - }; + } - OCA.Search.comment = new Comment(); -})(OC, OCA, $); + OCA.Search.comment = new Comment() +})(OC, OCA, $) |