From 29965efe6a09816eba238e3d5c04d856c82a855c Mon Sep 17 00:00:00 2001 From: dimden Date: Wed, 13 Sep 2023 02:13:03 +0300 Subject: [PATCH] add support for reactions --- layouts/header/script.js | 104 +++++++++++++++++++++++++++++---------- layouts/header/style.css | 18 +++++++ scripts/apis.js | 2 +- 3 files changed, 97 insertions(+), 27 deletions(-) diff --git a/layouts/header/script.js b/layouts/header/script.js index 440449e3..3b1e48b3 100644 --- a/layouts/header/script.js +++ b/layouts/header/script.js @@ -811,23 +811,46 @@ let userDataFunction = async user => { } else { messageElement.classList.add('message-element-self'); } - messageElement.id = `message-${m.id}`; - messageElement.innerHTML = ` - ${sender.id_str !== user.id_str ? ` -
-
${escapeHTML(m.message_data.text).replace(/((http|https|ftp):\/\/[\w?=&.\/-;#~%-]+(?![\w\s?&.\/;#~%"=-]*>))/g, '$1').replace(/(?@$1`)}
- ` : ` -
- ${escapeHTML(m.message_data.text).replace(/((http|https|ftp):\/\/[\w?=&.\/-;#~%-]+(?![\w\s?&.\/;#~%"=-]*>))/g, '$1').replace(/(?@$1`)}
-
- + messageElement.dataset.messageId = m.id; + messageElement.innerHTML = /*html*/` + ${sender.id_str !== user.id_str ? /*html*/` +
+ + + +
+
+
+ ${escapeHTML(m.message_data.text).replace(/((http|https|ftp):\/\/[\w?=&.\/-;#~%-]+(?![\w\s?&.\/;#~%"=-]*>))/g, '$1').replace(/(?@$1`)} +
+
+
+
+ ` : /*html*/` +
+
+ + ${escapeHTML(m.message_data.text).replace(/((http|https|ftp):\/\/[\w?=&.\/-;#~%-]+(?![\w\s?&.\/;#~%"=-]*>))/g, '$1').replace(/(?@$1`)} + +
+
+
+
+
+ + + +
`} `; let messageBlockInner = messageElement.querySelector('.message-block-inner'); let messageBlock = messageElement.querySelector('.message-block'); let menuOpen = messageBlockInner.querySelector('.message-menu-open'); + let messageAttachments = messageElement.querySelector('.message-attachments'); + let messageReactions = messageElement.querySelector('.message-reactions'); + if(menuOpen) { let menu = messageBlockInner.querySelector('.message-menu'); let menuDelete = messageBlockInner.querySelector('.message-menu-delete'); @@ -900,11 +923,7 @@ let userDataFunction = async user => { }); e.target.click(); }) - if(span.innerHTML === '' || span.innerHTML === ' ') - messageBlockInner.append(photoElement); - else - messageBlockInner.append(document.createElement('br'), photoElement); - + messageAttachments.append(photoElement); } if(attachment.animated_gif) { let gif = attachment.animated_gif; @@ -917,10 +936,7 @@ let userDataFunction = async user => { gifElement.width = w; gifElement.height = h; gifElement.classList.add('message-element-media'); - if(span.innerHTML === '' || span.innerHTML === ' ') - messageBlockInner.append(gifElement); - else - messageBlockInner.append(document.createElement('br'), gifElement); + messageAttachments.append(gifElement); } if(attachment.video) { let video = attachment.video; @@ -931,10 +947,17 @@ let userDataFunction = async user => { videoElement.width = w; videoElement.height = h; videoElement.classList.add('message-element-media'); - if(span.innerHTML === '' || span.innerHTML === ' ') - messageBlockInner.append(videoElement); - else - messageBlockInner.append(document.createElement('br'), videoElement); + messageAttachments.append(videoElement); + } + } + if(m.message_reactions) { + for(let reaction of m.message_reactions) { + let reactionElement = document.createElement('span'); + reactionElement.classList.add('message-reaction'); + reactionElement.innerText = reaction.emoji_reaction; + reactionElement.dataset.userId = reaction.sender_id; + if(vars.enableTwemoji) twemoji.parse(reactionElement); + messageReactions.append(reactionElement); } } timestamp=document.createElement('span'); @@ -1332,13 +1355,42 @@ let userDataFunction = async user => { let messages = e.message_delete.messages; for(let j in messages) { let message = messages[j]; - let messageElement = document.getElementById(`message-${message.message_id}`); + let messageElement = document.querySelector(`div.message-element[data-message-id="${message.message_id}"]`); if(messageElement) { messageElement.remove(); } } } }); + for(let i in updates.user_events.entries) { + let e = updates.user_events.entries[i]; + if(e.reaction_create) { + let reaction = e.reaction_create; + let messageElement = document.querySelector(`div.message-element[data-message-id="${reaction.message_id}"]`); + if(messageElement) { + let reactionElement = document.createElement('span'); + reactionElement.classList.add('message-reaction'); + reactionElement.innerText = reaction.emoji_reaction; + reactionElement.dataset.userId = reaction.sender_id; + + if(vars.enableTwemoji) twemoji.parse(reactionElement); + let oldReaction = messageElement.querySelector(`span.message-reaction[data-user-id="${reaction.sender_id}"]`); + if(oldReaction) { + oldReaction.remove(); + } + messageElement.getElementsByClassName('message-reactions')[0].append(reactionElement); + } + } else if(e.reaction_delete) { + let reaction = e.reaction_delete; + let messageElement = document.querySelector(`div.message-element[data-message-id="${reaction.message_id}"]`); + if(messageElement) { + let reactionElement = messageElement.querySelector(`span.message-reaction[data-user-id="${reaction.sender_id}"]`); + if(reactionElement) { + reactionElement.remove(); + } + } + } + } updates.user_events.entries = updates.user_events.entries.filter(m => m.message && m.message.conversation_id === lastConvo.conversation_id); renderConversation(updates.user_events, lastConvo.conversation_id, true, false); } diff --git a/layouts/header/style.css b/layouts/header/style.css index 07468182..5bf28e72 100644 --- a/layouts/header/style.css +++ b/layouts/header/style.css @@ -2198,6 +2198,24 @@ emoji-picker { vertical-align: text-bottom; margin-right: 5px; } +.message-reactions { + position: relative; + display: block; +} +.message-reactions > span { + margin-top: -13px; + display: inline-block; + font-size: 24px; + user-select: none; + margin-left: -15px; +} +.message-element-other .message-reactions > span { + margin-left: 0; +} +.message-reaction .emoji { + width: 24px; + height: 24px; +} .tweet-media-cws { color: var(--cw); font-size: 12px; diff --git a/scripts/apis.js b/scripts/apis.js index 30e1f05d..75d84f33 100644 --- a/scripts/apis.js +++ b/scripts/apis.js @@ -4083,7 +4083,7 @@ const API = { }, getConversation: (id, max_id) => { return new Promise((resolve, reject) => { - fetch(`https://api.twitter.com/1.1/dm/conversation/${id}.json?ext=altText${max_id ? `&max_id=${max_id}` : ''}&count=100&cards_platform=Web-13&include_entities=1&include_user_entities=1&include_cards=1&send_error_codes=1&tweet_mode=extended&include_ext_alt_text=true&include_reply_count=true&include_conversation_info=true`, { + fetch(`https://twitter.com/i/api/1.1/dm/conversation/${id}.json?${max_id ? `max_id=${max_id}&` : ''}count=100&context=FETCH_DM_CONVERSATION_HISTORY&include_profile_interstitial_type=1&include_blocking=1&include_blocked_by=1&include_followed_by=1&include_want_retweets=1&include_mute_edge=1&include_can_dm=1&include_can_media_tag=1&include_ext_has_nft_avatar=1&include_ext_is_blue_verified=1&include_ext_verified_type=1&include_ext_profile_image_shape=1&skip_status=1&dm_secret_conversations_enabled=false&krs_registration_enabled=true&cards_platform=Web-12&include_cards=1&include_ext_alt_text=true&include_ext_limited_action_results=true&include_quote_count=true&include_reply_count=1&tweet_mode=extended&include_ext_views=true&dm_users=false&include_groups=true&include_inbox_timelines=true&include_ext_media_color=true&supports_reactions=true&include_conversation_info=true&ext=mediaColor%2CaltText%2CmediaStats%2ChighlightedLabel%2ChasNftAvatar%2CvoiceInfo%2CbirdwatchPivot%2CsuperFollowMetadata%2CunmentionInfo%2CeditControl`, { headers: { "authorization": OLDTWITTER_CONFIG.oauth_key, "x-csrf-token": OLDTWITTER_CONFIG.csrf,