diff --git a/src/plugins/sib-history-scroll.js b/src/plugins/sib-history-scroll.js new file mode 100644 index 0000000000000000000000000000000000000000..f514a52dd5a28b58a2c1492d5f9fed950489cc0a --- /dev/null +++ b/src/plugins/sib-history-scroll.js @@ -0,0 +1,68 @@ +converse.plugins.add('sib-history-scroll', { + overrides: { + ChatRoomView: { + events: { + 'wheel .chat-content__messages': 'onScrolledUp', + }, + }, + ChatBoxView: { + events: { + 'wheel .chat-content__messages': 'onScrolledUp', + }, + + /** + * Fetch the old messages if there is no scroll available. + * @param {WheelEvent} ev + */ + onScrolledUp(ev) { + const scrollable = this.msgs_container.clientHeight < this.msgs_container.scrollHeight + if (ev.deltaY < 0 && !scrollable) { + const _converse = this.__super__._converse; + _converse.api.trigger('chatBoxScrolledUp', this); + converse.env.utils.safeSave(this.model, { + scrolled: true, + scrollTop: 0, + }); + } + }, + + /** + * Fix the scroll event when contained in the <solid-xmpp-chat> element. + * Replace the ev.target with the first element in composed path. + * + * @param {Event} ev + * @private + */ + _markScrolled: function (ev) { + const _converse = this.__super__._converse; + + let scrolled = true; + let scrollTop = null; + const is_at_bottom = this.msgs_container.scrollTop + this.msgs_container.clientHeight >= this.msgs_container.scrollHeight; + + // TODO: use composed path + const target = ev.target || ev.path[0]; + + if (is_at_bottom) { + scrolled = false; + this.onScrolledDown(); + } else if (this.msgs_container.scrollTop === 0) { + /** + * Triggered once the chat's message area has been scrolled to the top + * @event _converse#chatBoxScrolledUp + * @property { _converse.ChatBoxView | _converse.ChatRoomView } view + * @example _converse.api.listen.on('chatBoxScrolledUp', obj => { ... }); + */ + _converse.api.trigger('chatBoxScrolledUp', this); + } else { + scrollTop = target?.scrollTop; + } + + converse.env.utils.safeSave(this.model, { + scrolled, + scrollTop + }); + } + } + } +}); diff --git a/src/solid-xmpp-chat.js b/src/solid-xmpp-chat.js index 5e14d12f9fae4b54b266c159856c475e980d9556..b80778abd878384f918c97b2d45c04785762f91a 100644 --- a/src/solid-xmpp-chat.js +++ b/src/solid-xmpp-chat.js @@ -1,6 +1,7 @@ import './conversejs/converse.min.js'; import './conversejs/emojis.js'; import './plugins/converse-rai.js'; +import './plugins/sib-history-scroll.js' import { Sib, store, StoreMixin } from 'https://cdn.skypack.dev/@startinblox/core@0.15'; import ComponentPath from './path.js'; @@ -426,7 +427,17 @@ export const SolidXMPPChat = { fileupload: true, // Not working in current Converse toggle_occupants: false }, - 'whitelisted_plugins': ['rai', 'conversejs-sib-disconnected', 'conversejs-sib-connected', 'conversejs-sib-focused', 'conversejs-changechat', 'conversejs-rai', 'custom-hats', 'remove-notifications'], + 'whitelisted_plugins': [ + 'rai', + 'sib-history-scroll', + 'conversejs-sib-disconnected', + 'conversejs-sib-connected', + 'conversejs-sib-focused', + 'conversejs-changechat', + 'conversejs-rai', + 'custom-hats', + 'remove-notifications', + ], }); converse_sib.loaded_deferred.resolve();