瀏覽代碼

fix #1963 - Mentions are visually incorrect when used in message replies (#1968)

* fix #1963 - Mentions are visually incorrect when used in message replies
Dele Olajide 5 年之前
父節點
當前提交
f97d827280
共有 3 個文件被更改,包括 50 次插入3 次删除
  1. 1 0
      CHANGES.md
  2. 41 0
      spec/muc_messages.js
  3. 8 3
      src/utils/html.js

+ 1 - 0
CHANGES.md

@@ -19,6 +19,7 @@ Soon we'll deprecate the latter, so prepare now.
 - #1839: Headline messages are shown in controlbox
 - #1896: Don't send receipts for messages fetched from the archive 
 - #1937: Editing a message removes the mentions highlight
+- #1963: Mentions are visually incorrect when used in message replies
 - Allow ignoring of bootstrap modules at build using environment variable. For xample: `export BOOTSTRAP_IGNORE_MODULES="Modal,Dropdown" && make dist`
 - Bugfix. Handle stanza that clears the MUC subject
 - New config option [modtools_disable_assign](https://conversejs.org/docs/html/configuration.html#modtools-disable-assign)

+ 41 - 0
spec/muc_messages.js

@@ -902,6 +902,47 @@
                     '<span class="mention">mr.robot</span>, how are you?');
                 done();
             }));
+
+            it("highlights all users mentioned via XEP-0372 references in a quoted message",
+                mock.initConverse(
+                    ['rosterGroupsFetched'], {},
+                    async function (done, _converse) {
+
+                const muc_jid = 'lounge@montague.lit';
+                await test_utils.openAndEnterChatRoom(_converse, muc_jid, 'tom');
+                const view = _converse.api.chatviews.get(muc_jid);
+                ['z3r0', 'mr.robot', 'gibson', 'sw0rdf1sh'].forEach((nick) => {
+                    _converse.connection._dataRecv(test_utils.createRequest(
+                        $pres({
+                            'to': 'tom@montague.lit/resource',
+                            'from': `lounge@montague.lit/${nick}`
+                        })
+                        .c('x', {xmlns: Strophe.NS.MUC_USER})
+                        .c('item', {
+                            'affiliation': 'none',
+                            'jid': `${nick}@montague.lit/resource`,
+                            'role': 'participant'
+                        }))
+                    );
+                });
+                const msg = $msg({
+                        from: 'lounge@montague.lit/gibson',
+                        id: u.getUniqueId(),
+                        to: 'romeo@montague.lit',
+                        type: 'groupchat'
+                    }).c('body').t('>hello z3r0 tom mr.robot, how are you?').up()
+                        .c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'7', 'end':'11', 'type':'mention', 'uri':'xmpp:z3r0@montague.lit'}).up()
+                        .c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'12', 'end':'15', 'type':'mention', 'uri':'xmpp:romeo@montague.lit'}).up()
+                        .c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'16', 'end':'24', 'type':'mention', 'uri':'xmpp:mr.robot@montague.lit'}).nodeTree;
+                await view.model.queueMessage(msg);
+                const message = await u.waitUntil(() => view.el.querySelector('.chat-msg__text'));
+                expect(message.classList.length).toEqual(1);
+                expect(message.innerHTML).toBe(
+                    '&gt;hello <span class="mention">z3r0</span> '+
+                    '<span class="mention mention--self badge badge-info">tom</span> '+
+                    '<span class="mention">mr.robot</span>, how are you?');
+                done();
+            }));
         });
 
         describe("in which someone is mentioned", function () {

+ 8 - 3
src/utils/html.js

@@ -372,12 +372,17 @@ u.addMentionsMarkup = function (text, references, chatbox) {
     references
         .sort((a, b) => b.begin - a.begin)
         .forEach(ref => {
-            const mention = text.slice(ref.begin, ref.end)
+            const prefix = text.slice(0, ref.begin);
+            const offset = ((prefix.match(/&lt;/g) || []).length + (prefix.match(/&gt;/g) || []).length) * 3;
+            const begin = parseInt(ref.begin, 10) + parseInt(offset, 10);
+            const end = parseInt(ref.end, 10) + parseInt(offset, 10);
+            const mention = text.slice(begin, end)
             chatbox;
+
             if (mention === nick) {
-                text = text.slice(0, ref.begin) + `<span class="mention mention--self badge badge-info">${mention}</span>` + text.slice(ref.end);
+                text = text.slice(0, begin) + `<span class="mention mention--self badge badge-info">${mention}</span>` + text.slice(end);
             } else {
-                text = text.slice(0, ref.begin) + `<span class="mention">${mention}</span>` + text.slice(ref.end);
+                text = text.slice(0, begin) + `<span class="mention">${mention}</span>` + text.slice(end);
             }
         });
     return text;