From 84a10d77d9f5669b5d22369d1bcd0cdd80e6e23d Mon Sep 17 00:00:00 2001 From: JC Brand Date: Sun, 8 Jul 2018 10:13:15 +0200 Subject: [PATCH] Cancel message correction by pressing the down arrow Also, add a class `correcting` to the message being corrected, to provide a visual cue. updates #421 --- .eslintrc.json | 2 +- css/converse.css | 4 + dist/converse.js | 84 +++++++----- sass/_messages.scss | 8 ++ spec/messages.js | 249 ++++++++++++++++++++++++++--------- src/converse-chatboxes.js | 24 ++-- src/converse-chatview.js | 41 ++++-- src/converse-message-view.js | 6 +- src/converse-muc-views.js | 2 +- src/templates/message.html | 2 +- 10 files changed, 294 insertions(+), 128 deletions(-) diff --git a/.eslintrc.json b/.eslintrc.json index a4ef9ed5f..18bf914bb 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -34,7 +34,7 @@ "array-bracket-spacing": "off", "array-callback-return": "error", "arrow-body-style": "off", - "arrow-parens": "error", + "arrow-parens": "off", "arrow-spacing": "error", "block-scoped-var": "off", "block-spacing": "off", diff --git a/css/converse.css b/css/converse.css index a0a526d93..6bb6f408a 100644 --- a/css/converse.css +++ b/css/converse.css @@ -8859,6 +8859,10 @@ body.reset { -webkit-animation: colorchange-chatmessage 1s; } #conversejs .message.chat-msg:hover { background-color: rgba(0, 0, 0, 0.035); } + #conversejs .message.chat-msg.correcting.groupchat { + background-color: #fdf1ee; } + #conversejs .message.chat-msg.correcting:not(.groupchat) { + background-color: #e7f7ee; } #conversejs .message.chat-msg .spoiler { margin-top: 0.5em; } #conversejs .message.chat-msg .spoiler-hint { diff --git a/dist/converse.js b/dist/converse.js index ca042088c..3d7cac8e9 100644 --- a/dist/converse.js +++ b/dist/converse.js @@ -68675,7 +68675,6 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ return { 'fullname': fullname, - 'replace': this.correction, 'from': _converse.bare_jid, 'sender': 'me', 'time': moment().format(), @@ -68691,21 +68690,18 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ * Parameters: * (Message) message - The chat message */ - if (attrs.replace) { - const message = this.messages.findWhere({ - 'id': attrs.replace - }); + const message = this.messages.findWhere('correcting'); - if (message) { - const older_versions = message.get('older_versions') || []; - older_versions.push(message.get('message')); - message.save({ - 'message': attrs.message, - 'older_versions': older_versions, - 'edited': true - }); - return this.sendMessageStanza(message); - } + if (message) { + const older_versions = message.get('older_versions') || []; + older_versions.push(message.get('message')); + message.save({ + 'message': attrs.message, + 'older_versions': older_versions, + 'edited': true, + 'correcting': false + }); + return this.sendMessageStanza(message); } return this.sendMessageStanza(this.messages.create(attrs)); @@ -69344,6 +69340,7 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ const KEY = { ENTER: 13, UP_ARROW: 38, + DOWN_ARROW: 40, FORWARD_SLASH: 47 }; converse.plugins.add('converse-chatview', { @@ -69621,7 +69618,7 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ 'click .toggle-smiley ul.emoji-picker li': 'insertEmoji', 'click .toggle-smiley': 'toggleEmojiMenu', 'click .upload-file': 'toggleFileUpload', - 'keyup .chat-textarea': 'keyPressed', + 'keydown .chat-textarea': 'keyPressed', 'input .chat-textarea': 'inputChanged' }, @@ -70103,6 +70100,10 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ */ this.showMessage(message); + if (message.get('correcting')) { + this.insertIntoTextArea(message.get('message'), true); + } + _converse.emit('messageAdded', { 'message': message, 'chatbox': this.model @@ -70142,7 +70143,6 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ } const attrs = this.model.getOutgoingMessageAttributes(text, spoiler_hint); - delete this.model.correction; this.model.sendMessage(attrs); }, @@ -70203,10 +70203,16 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ keyPressed(ev) { /* Event handler for when a key is pressed in a chat box textarea. */ - if (ev.keyCode === KEY.ENTER && !ev.shiftKey) { + if (ev.shiftKey) { + return; + } + + if (ev.keyCode === KEY.ENTER) { this.onFormSubmitted(ev); - } else if (ev.keyCode === KEY.UP_ARROW && !ev.shiftKey) { + } else if (ev.keyCode === KEY.UP_ARROW && !ev.target.selectionEnd) { this.editPreviousMessage(); + } else if (ev.keyCode === KEY.DOWN_ARROW && ev.target.selectionEnd === ev.target.value.length) { + this.cancelMessageCorrection(); } else if (ev.keyCode !== KEY.FORWARD_SLASH && this.model.get('chat_state') !== _converse.COMPOSING) { // Set chat state to composing if keyCode is not a forward-slash // (which would imply an internal command and not a message). @@ -70214,16 +70220,19 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ } }, + cancelMessageCorrection() { + this.insertIntoTextArea('', true); + this.model.messages.where('correcting').forEach(msg => msg.save('correcting', false)); + }, + editPreviousMessage() { const msg = _.findLast(this.model.messages.models, msg => msg.get('message')); if (msg) { - const textbox_el = this.el.querySelector('.chat-textarea'); - textbox_el.value = msg.get('message'); - textbox_el.focus(); // We don't set "correcting" the Backbone-way, because + this.insertIntoTextArea(msg.get('message'), true); // We don't set "correcting" the Backbone-way, because // we don't want it to persist to storage. - this.model.correction = msg.get('id'); + msg.save('correcting', true); } }, @@ -70250,15 +70259,21 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ return this; }, - insertIntoTextArea(value) { + insertIntoTextArea(value, replace = false) { const textbox_el = this.el.querySelector('.chat-textarea'); - let existing = textbox_el.value; - if (existing && existing[existing.length - 1] !== ' ') { - existing = existing + ' '; + if (replace) { + textbox_el.value = value; + } else { + let existing = textbox_el.value; + + if (existing && existing[existing.length - 1] !== ' ') { + existing = existing + ' '; + } + + textbox_el.value = existing + value + ' '; } - textbox_el.value = existing + value + ' '; textbox_el.focus(); }, @@ -74572,10 +74587,11 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ initialize() { this.model.vcard.on('change', this.render, this); + this.model.on('change:correcting', this.render, this); + this.model.on('change:message', this.render, this); this.model.on('change:progress', this.renderFileUploadProgresBar, this); this.model.on('change:type', this.render, this); this.model.on('change:upload', this.render, this); - this.model.on('change:message', this.render, this); this.model.on('destroy', this.remove, this); this.render(); }, @@ -74746,6 +74762,10 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ } } + if (this.model.get('correcting')) { + extra_classes += ' correcting'; + } + return extra_classes; } @@ -75997,7 +76017,7 @@ var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_ 'click .toggle-smiley ul.emoji-picker li': 'insertEmoji', 'click .toggle-smiley': 'toggleEmojiMenu', 'click .upload-file': 'toggleFileUpload', - 'keypress .chat-textarea': 'keyPressed', + 'keydown .chat-textarea': 'keyPressed', 'input .chat-textarea': 'inputChanged' }, @@ -85632,13 +85652,13 @@ __p += '\n \n \n \n \n
\n '; +'\n \n '; if (o.edited) { ; __p += ' '; } ; -__p += '\n \n\n'; +__p += '\n \n
\n \n\n'; return __p }; diff --git a/sass/_messages.scss b/sass/_messages.scss index e568fb960..119297097 100644 --- a/sass/_messages.scss +++ b/sass/_messages.scss @@ -73,6 +73,14 @@ &:hover { background-color: rgba(0, 0, 0, 0.035); } + &.correcting { + &.groupchat { + background-color: lighten($chatroom-head-color, 35%); + } + &:not(.groupchat) { + background-color: lighten($chat-head-color, 50%); + } + } .spoiler { margin-top: 0.5em; diff --git a/spec/messages.js b/spec/messages.js index af9b38d31..e02a99a5d 100644 --- a/spec/messages.js +++ b/spec/messages.js @@ -19,6 +19,97 @@ describe("A Chat Message", function () { + it("can be sent as a correction", + mock.initConverseWithPromises( + null, ['rosterGroupsFetched'], {}, + function (done, _converse) { + + test_utils.createContacts(_converse, 'current', 1); + test_utils.openControlBox(); + const contact_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@localhost'; + test_utils.openChatBoxFor(_converse, contact_jid); + + const view = _converse.chatboxviews.get(contact_jid); + const textarea = view.el.querySelector('textarea.chat-textarea'); + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe(''); + + textarea.value = 'But soft, what light through yonder airlock breaks?'; + view.keyPressed({ + target: textarea, + preventDefault: _.noop, + keyCode: 13 // Enter + }); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(view.el.querySelector('.chat-msg-text').textContent) + .toBe('But soft, what light through yonder airlock breaks?'); + + const first_msg = view.model.messages.findWhere({'message': 'But soft, what light through yonder airlock breaks?'}); + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe('But soft, what light through yonder airlock breaks?'); + expect(view.model.messages.at(0).get('correcting')).toBe(true); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(true); + + spyOn(_converse.connection, 'send'); + textarea.value = 'But soft, what light through yonder window breaks?'; + view.keyPressed({ + target: textarea, + preventDefault: _.noop, + keyCode: 13 // Enter + }); + expect(_converse.connection.send).toHaveBeenCalled(); + + const msg = _converse.connection.send.calls.all()[0].args[0]; + expect(msg.toLocaleString()) + .toBe(``+ + `But soft, what light through yonder window breaks?`+ + ``+ + ``+ + ``); + expect(view.model.messages.models.length).toBe(1); + const corrected_message = view.model.messages.at(0); + expect(corrected_message.get('msgid')).toBe(first_msg.get('msgid')); + expect(corrected_message.get('correcting')).toBe(false); + expect(corrected_message.get('older_versions').length).toBe(1); + expect(corrected_message.get('older_versions')[0]).toBe('But soft, what light through yonder airlock breaks?'); + + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(false); + + // Test that pressing the down arrow cancels message correction + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe('But soft, what light through yonder window breaks?'); + expect(view.model.messages.at(0).get('correcting')).toBe(true); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(true); + expect(textarea.value).toBe('But soft, what light through yonder window breaks?'); + view.keyPressed({ + target: textarea, + keyCode: 40 // Down arrow + }); + expect(textarea.value).toBe(''); + expect(view.model.messages.at(0).get('correcting')).toBe(false); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(false); + done(); + })); + + describe("when received from someone else", function () { it("will open a chatbox and be displayed inside it", @@ -136,70 +227,6 @@ }); })); - it("can be sent as a correction", - mock.initConverseWithPromises( - null, ['rosterGroupsFetched'], {}, - function (done, _converse) { - - test_utils.createContacts(_converse, 'current', 1); - test_utils.openControlBox(); - const message = 'This is a received message'; - const contact_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@localhost'; - test_utils.openChatBoxFor(_converse, contact_jid); - - const view = _converse.chatboxviews.get(contact_jid); - const textarea = view.el.querySelector('textarea.chat-textarea'); - expect(textarea.value).toBe(''); - view.keyPressed({ - target: textarea, - keyCode: 38 - }); - expect(textarea.value).toBe(''); - - textarea.value = 'But soft, what light through yonder airlock breaks?'; - view.keyPressed({ - target: textarea, - preventDefault: _.noop, - keyCode: 13 - }); - expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); - expect(view.el.querySelector('.chat-msg-text').textContent) - .toBe('But soft, what light through yonder airlock breaks?'); - - const first_msg = view.model.messages.findWhere({'message': 'But soft, what light through yonder airlock breaks?'}); - expect(textarea.value).toBe(''); - view.keyPressed({ - target: textarea, - keyCode: 38 - }); - expect(textarea.value).toBe('But soft, what light through yonder airlock breaks?'); - - spyOn(_converse.connection, 'send'); - textarea.value = 'But soft, what light through yonder window breaks?'; - view.keyPressed({ - target: textarea, - preventDefault: _.noop, - keyCode: 13 - }); - expect(_converse.connection.send).toHaveBeenCalled(); - - const msg = _converse.connection.send.calls.all()[0].args[0]; - expect(msg.toLocaleString()) - .toBe(``+ - `But soft, what light through yonder window breaks?`+ - ``+ - ``+ - ``); - expect(view.model.messages.models.length).toBe(1); - const corrected_message = view.model.messages.at(0); - expect(corrected_message.get('msgid')).toBe(first_msg.get('msgid')); - expect(corrected_message.get('older_versions').length).toBe(1); - expect(corrected_message.get('older_versions')[0]).toBe('But soft, what light through yonder airlock breaks?'); - done(); - })); - describe("when a chatbox is opened for someone who is not in the roster", function () { it("the VCard for that user is fetched and the chatbox updated with the results", @@ -1663,7 +1690,6 @@ function (done, _converse) { let msg_id, view; - test_utils.openAndEnterChatRoom(_converse, 'lounge', 'localhost', 'dummy') .then(() => { const jid = 'lounge@localhost'; @@ -1733,5 +1759,98 @@ done(); }); })); + + it("can be sent as a correction", + mock.initConverseWithPromises( + null, ['rosterGroupsFetched'], {}, + function (done, _converse) { + + let msg_id, view; + test_utils.openAndEnterChatRoom(_converse, 'lounge', 'localhost', 'dummy') + .then(() => { + const jid = 'lounge@localhost'; + const room = _converse.api.rooms.get(jid); + view = _converse.chatboxviews.get(jid); + + const textarea = view.el.querySelector('textarea.chat-textarea'); + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe(''); + + textarea.value = 'But soft, what light through yonder airlock breaks?'; + view.keyPressed({ + target: textarea, + preventDefault: _.noop, + keyCode: 13 // Enter + }); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(view.el.querySelector('.chat-msg-text').textContent) + .toBe('But soft, what light through yonder airlock breaks?'); + + const first_msg = view.model.messages.findWhere({'message': 'But soft, what light through yonder airlock breaks?'}); + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe('But soft, what light through yonder airlock breaks?'); + expect(view.model.messages.at(0).get('correcting')).toBe(true); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(true); + + spyOn(_converse.connection, 'send'); + textarea.value = 'But soft, what light through yonder window breaks?'; + view.keyPressed({ + target: textarea, + preventDefault: _.noop, + keyCode: 13 // Enter + }); + expect(_converse.connection.send).toHaveBeenCalled(); + + const msg = _converse.connection.send.calls.all()[0].args[0]; + expect(msg.toLocaleString()) + .toBe(``+ + `But soft, what light through yonder window breaks?`+ + ``+ + ``+ + ``); + + expect(view.model.messages.models.length).toBe(1); + const corrected_message = view.model.messages.at(0); + expect(corrected_message.get('msgid')).toBe(first_msg.get('msgid')); + expect(corrected_message.get('correcting')).toBe(false); + expect(corrected_message.get('older_versions').length).toBe(1); + expect(corrected_message.get('older_versions')[0]).toBe('But soft, what light through yonder airlock breaks?'); + + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(false); + + // Test that pressing the down arrow cancels message correction + expect(textarea.value).toBe(''); + view.keyPressed({ + target: textarea, + keyCode: 38 // Up arrow + }); + expect(textarea.value).toBe('But soft, what light through yonder window breaks?'); + expect(view.model.messages.at(0).get('correcting')).toBe(true); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(true); + expect(textarea.value).toBe('But soft, what light through yonder window breaks?'); + view.keyPressed({ + target: textarea, + keyCode: 40 // Down arrow + }); + expect(textarea.value).toBe(''); + expect(view.model.messages.at(0).get('correcting')).toBe(false); + expect(view.el.querySelectorAll('.chat-msg').length).toBe(1); + expect(u.hasClass('correcting', view.el.querySelector('.chat-msg'))).toBe(false); + done(); + }); + })); }); })); diff --git a/src/converse-chatboxes.js b/src/converse-chatboxes.js index c4e3fa7f1..49bf755fc 100644 --- a/src/converse-chatboxes.js +++ b/src/converse-chatboxes.js @@ -365,7 +365,6 @@ return { 'fullname': fullname, - 'replace': this.correction, 'from': _converse.bare_jid, 'sender': 'me', 'time': moment().format(), @@ -381,18 +380,17 @@ * Parameters: * (Message) message - The chat message */ - if (attrs.replace) { - const message = this.messages.findWhere({'id': attrs.replace}) - if (message) { - const older_versions = message.get('older_versions') || []; - older_versions.push(message.get('message')); - message.save({ - 'message': attrs.message, - 'older_versions': older_versions, - 'edited': true - }); - return this.sendMessageStanza(message); - } + const message = this.messages.findWhere('correcting') + if (message) { + const older_versions = message.get('older_versions') || []; + older_versions.push(message.get('message')); + message.save({ + 'message': attrs.message, + 'older_versions': older_versions, + 'edited': true, + 'correcting': false + }); + return this.sendMessageStanza(message); } return this.sendMessageStanza(this.messages.create(attrs)); }, diff --git a/src/converse-chatview.js b/src/converse-chatview.js index e2e694496..c70ba8d2c 100644 --- a/src/converse-chatview.js +++ b/src/converse-chatview.js @@ -55,6 +55,7 @@ const KEY = { ENTER: 13, UP_ARROW: 38, + DOWN_ARROW: 40, FORWARD_SLASH: 47 }; @@ -334,7 +335,7 @@ 'click .toggle-smiley ul.emoji-picker li': 'insertEmoji', 'click .toggle-smiley': 'toggleEmojiMenu', 'click .upload-file': 'toggleFileUpload', - 'keyup .chat-textarea': 'keyPressed', + 'keydown .chat-textarea': 'keyPressed', 'input .chat-textarea': 'inputChanged' }, @@ -802,7 +803,9 @@ * (Object) message - The message Backbone object that was added. */ this.showMessage(message); - + if (message.get('correcting')) { + this.insertIntoTextArea(message.get('message'), true); + } _converse.emit('messageAdded', { 'message': message, 'chatbox': this.model @@ -848,7 +851,6 @@ return; } const attrs = this.model.getOutgoingMessageAttributes(text, spoiler_hint); - delete this.model.correction; this.model.sendMessage(attrs); }, @@ -912,10 +914,14 @@ keyPressed (ev) { /* Event handler for when a key is pressed in a chat box textarea. */ - if (ev.keyCode === KEY.ENTER && !ev.shiftKey) { + if (ev.shiftKey) { return; } + + if (ev.keyCode === KEY.ENTER) { this.onFormSubmitted(ev); - } else if (ev.keyCode === KEY.UP_ARROW && !ev.shiftKey) { + } else if (ev.keyCode === KEY.UP_ARROW && !ev.target.selectionEnd) { this.editPreviousMessage(); + } else if (ev.keyCode === KEY.DOWN_ARROW && ev.target.selectionEnd === ev.target.value.length) { + this.cancelMessageCorrection(); } else if (ev.keyCode !== KEY.FORWARD_SLASH && this.model.get('chat_state') !== _converse.COMPOSING) { // Set chat state to composing if keyCode is not a forward-slash // (which would imply an internal command and not a message). @@ -923,15 +929,18 @@ } }, + cancelMessageCorrection () { + this.insertIntoTextArea('', true); + this.model.messages.where('correcting').forEach(msg => msg.save('correcting', false)); + }, + editPreviousMessage () { const msg = _.findLast(this.model.messages.models, (msg) => msg.get('message')); if (msg) { - const textbox_el = this.el.querySelector('.chat-textarea'); - textbox_el.value = msg.get('message'); - textbox_el.focus() + this.insertIntoTextArea(msg.get('message'), true); // We don't set "correcting" the Backbone-way, because // we don't want it to persist to storage. - this.model.correction = msg.get('id'); + msg.save('correcting', true); } }, @@ -951,13 +960,17 @@ return this; }, - insertIntoTextArea (value) { + insertIntoTextArea (value, replace=false) { const textbox_el = this.el.querySelector('.chat-textarea'); - let existing = textbox_el.value; - if (existing && (existing[existing.length-1] !== ' ')) { - existing = existing + ' '; + if (replace) { + textbox_el.value = value; + } else { + let existing = textbox_el.value; + if (existing && (existing[existing.length-1] !== ' ')) { + existing = existing + ' '; + } + textbox_el.value = existing+value+' '; } - textbox_el.value = existing+value+' '; textbox_el.focus() }, diff --git a/src/converse-message-view.js b/src/converse-message-view.js index 9efbef0c3..293d8be65 100644 --- a/src/converse-message-view.js +++ b/src/converse-message-view.js @@ -91,10 +91,11 @@ initialize () { this.model.vcard.on('change', this.render, this); + this.model.on('change:correcting', this.render, this); + this.model.on('change:message', this.render, this); this.model.on('change:progress', this.renderFileUploadProgresBar, this); this.model.on('change:type', this.render, this); this.model.on('change:upload', this.render, this); - this.model.on('change:message', this.render, this); this.model.on('destroy', this.remove, this); this.render(); }, @@ -262,6 +263,9 @@ extra_classes += ' mentioned'; } } + if (this.model.get('correcting')) { + extra_classes += ' correcting'; + } return extra_classes; } }); diff --git a/src/converse-muc-views.js b/src/converse-muc-views.js index 65baf3ada..2cd521cb9 100644 --- a/src/converse-muc-views.js +++ b/src/converse-muc-views.js @@ -529,7 +529,7 @@ 'click .toggle-smiley ul.emoji-picker li': 'insertEmoji', 'click .toggle-smiley': 'toggleEmojiMenu', 'click .upload-file': 'toggleFileUpload', - 'keypress .chat-textarea': 'keyPressed', + 'keydown .chat-textarea': 'keyPressed', 'input .chat-textarea': 'inputChanged' }, diff --git a/src/templates/message.html b/src/templates/message.html index 964e47eac..379ab2a3c 100644 --- a/src/templates/message.html +++ b/src/templates/message.html @@ -9,8 +9,8 @@ + {[ if (o.edited) { ]} {[ } ]}
- {[ if (o.edited) { ]} {[ } ]}