diff --git a/conversejs/custom/plugins/poll/index.js b/conversejs/custom/plugins/poll/index.js index 1f4953b7..2f32be8d 100644 --- a/conversejs/custom/plugins/poll/index.js +++ b/conversejs/custom/plugins/poll/index.js @@ -74,8 +74,11 @@ converse.plugins.add('livechat-converse-poll', { } // We will also translate some strings here. - // eslint-disable-next-line no-undef - const body = (attrs.body ?? '').replace(LOC_poll_is_over, __(LOC_poll_is_over)) + const body = (attrs.body ?? '') + // eslint-disable-next-line no-undef + .replace(LOC_poll_is_over, __(LOC_poll_is_over)) + // eslint-disable-next-line no-undef + .replace(LOC_poll_vote_instructions_xmpp, __(LOC_poll_vote_instructions)) // changing instructions on the fly return Object.assign( attrs, @@ -93,15 +96,11 @@ converse.plugins.add('livechat-converse-poll', { if (!attrs.current_poll) { return this.__super__.onMessage(attrs) } + // We intercept poll messages, to show the banner. - // Note: we also show poll end messages in the chat, so that the user don't loose the result. - if (attrs.is_delayed || attrs.is_archived) { - if (attrs.current_poll.over) { - console.info('Got a delayed/archived poll message for an poll that is over, just displaying in the chat') - return this.__super__.onMessage(attrs) - } - console.info('Got a delayed/archived poll message, just dropping') - return + // We just drop archived messages, to not show the banner for finished polls. + if (attrs.is_archived) { + return this.__super__.onMessage(attrs) } console.info('Got a poll message, setting it as the current_poll') @@ -109,11 +108,7 @@ converse.plugins.add('livechat-converse-poll', { // which is inserted in the DOM by the muc.js template overload. this.set('current_poll', attrs.current_poll) - if (attrs.current_poll.over) { - console.info('The poll is over, displaying the message in the chat') - return this.__super__.onMessage(attrs) - } - // Dropping the message. + return this.__super__.onMessage(attrs) } } } diff --git a/conversejs/loc.keys.js b/conversejs/loc.keys.js index c209e67d..7a6f9283 100644 --- a/conversejs/loc.keys.js +++ b/conversejs/loc.keys.js @@ -46,6 +46,7 @@ const locKeys = [ 'poll_end', 'poll', 'poll_vote_instructions', + 'poll_vote_instructions_xmpp', 'poll_is_over', 'poll_choice_invalid', 'poll_anonymous_vote_ok' diff --git a/languages/en.yml b/languages/en.yml index 9dde54d3..34211eb4 100644 --- a/languages/en.yml +++ b/languages/en.yml @@ -575,6 +575,8 @@ poll_choice_n: 'Choice {{N}}:' poll_end: 'Poll ends at:' poll_vote_instructions: | To vote, click on your choice or send a message with an exclamation mark followed by your choice number (Example: !1). +poll_vote_instructions_xmpp: | + Send a message with an exclamation mark followed by your choice number to vote. Example: !1 poll_is_over: This poll is now over. poll_choice_invalid: This choice is not valid. poll_anonymous_vote_ok: Your vote is taken into account. Votes are anonymous, they will not be shown to other participants. diff --git a/prosody-modules/mod_muc_poll/message.lib.lua b/prosody-modules/mod_muc_poll/message.lib.lua index ea17b88a..93612a0b 100644 --- a/prosody-modules/mod_muc_poll/message.lib.lua +++ b/prosody-modules/mod_muc_poll/message.lib.lua @@ -20,13 +20,12 @@ local scheduled_updates = {}; local string_poll_over = module:get_option_string("poll_string_over") or "This poll is now over."; local string_poll_vote_instructions = module:get_option_string("poll_string_vote_instructions") or "Send a message with an exclamation mark followed by your choice number to vote. Example: !1"; --- construct the poll message stanza -local function build_poll_message(room, message_id, is_end_message) +-- Build the content for poll start and end messages (that will go to the message
) +local function build_poll_message_content(room, is_end_message) local current_poll = room._data.current_poll; if not current_poll then return nil; end - local from = current_poll.occupant_nick; -- this is in fact room.jid/nickname local content = current_poll["muc#roompoll_question"] .. "\n"; @@ -41,7 +40,8 @@ local function build_poll_message(room, message_id, is_end_message) for _, choice_desc in ipairs(current_poll.choices_ordered) do local choice, label = choice_desc.number, choice_desc.label; content = content .. choice .. ': ' .. label; - if total > 0 then + -- if vote over, and at least 1 vote, we add the results. + if is_end_message and total > 0 then local nb = current_poll.votes_by_choices[choice] or 0; local percent = string.format("%.2f", nb * 100 / total); content = content .. " (" .. nb .. "/" .. total .. " = " .. percent .. "%)"; @@ -53,10 +53,23 @@ local function build_poll_message(room, message_id, is_end_message) content = content .. string_poll_vote_instructions .. "\n"; end + return content; +end + +-- construct the poll message stanza. +-- Note: content can be nil, for updates messages. +local function build_poll_message(room, content) + local current_poll = room._data.current_poll; + if not current_poll then + return nil; + end + + local from = current_poll.occupant_nick; -- this is in fact room.jid/nickname + local msg = st.message({ type = "groupchat", from = from, - id = message_id + id = id.long() }, content); msg:tag("occupant-id", { @@ -64,6 +77,14 @@ local function build_poll_message(room, message_id, is_end_message) id = current_poll.occupant_id }):up(); + if content == nil then + -- No content, this is an update message. + -- Adding some hints (XEP-0334): + msg:tag("no-copy", { xmlns = "urn:xmpp:hints" }):up(); + msg:tag("no-store", { xmlns = "urn:xmpp:hints" }):up(); + msg:tag("no-permanent-store", { xmlns = "urn:xmpp:hints" }):up(); + end + -- now we must add some custom XML data, so that compatible clients can display the poll as they want: --