scrolling!
This commit is contained in:
parent
147f34c1fd
commit
bc762a9413
6 changed files with 43 additions and 44 deletions
|
|
@ -72,6 +72,7 @@ export default (store) => {
|
||||||
() => import('src/components/chat_view/chat_view.vue'),
|
() => import('src/components/chat_view/chat_view.vue'),
|
||||||
),
|
),
|
||||||
props: true,
|
props: true,
|
||||||
|
meta: { dontScroll: true },
|
||||||
beforeEnter: validateAuthenticatedRoute,
|
beforeEnter: validateAuthenticatedRoute,
|
||||||
},
|
},
|
||||||
{ name: 'quotes', path: '/notice/:id/quotes', component: QuotesTimeline },
|
{ name: 'quotes', path: '/notice/:id/quotes', component: QuotesTimeline },
|
||||||
|
|
|
||||||
|
|
@ -184,11 +184,6 @@ const ChatMessage = {
|
||||||
menuOpened: false,
|
menuOpened: false,
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
watch: {
|
|
||||||
focused: function (value) {
|
|
||||||
this.scrollIfFocused(value)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
methods: {
|
methods: {
|
||||||
onHover(bool) {
|
onHover(bool) {
|
||||||
this.$emit('hover', {
|
this.$emit('hover', {
|
||||||
|
|
@ -224,22 +219,6 @@ const ChatMessage = {
|
||||||
this.hovered = false
|
this.hovered = false
|
||||||
this.menuOpened = false
|
this.menuOpened = false
|
||||||
},
|
},
|
||||||
scrollIfFocused(focused) {
|
|
||||||
if (this.$el.getBoundingClientRect == null) return
|
|
||||||
if (focused) {
|
|
||||||
const rect = this.$el.getBoundingClientRect()
|
|
||||||
if (rect.top < 100) {
|
|
||||||
// Post is above screen, match its top to screen top
|
|
||||||
window.scrollBy(0, rect.top - 100)
|
|
||||||
} else if (rect.height >= window.innerHeight - 50) {
|
|
||||||
// Post we want to see is taller than screen so match its top to screen top
|
|
||||||
window.scrollBy(0, rect.top - 100)
|
|
||||||
} else if (rect.bottom > window.innerHeight - 50) {
|
|
||||||
// Post is below screen, match its bottom to screen bottom
|
|
||||||
window.scrollBy(0, rect.bottom - window.innerHeight + 50)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@
|
||||||
v-if="isMessage"
|
v-if="isMessage"
|
||||||
class="chat-message-wrapper"
|
class="chat-message-wrapper"
|
||||||
:class="[classnames, { 'hovered-message-chain': hoveredMessageChain }]"
|
:class="[classnames, { 'hovered-message-chain': hoveredMessageChain }]"
|
||||||
|
:id="`chatmessage-${message.id}`"
|
||||||
@mouseover="onHover(true)"
|
@mouseover="onHover(true)"
|
||||||
@mouseleave="onHover(false)"
|
@mouseleave="onHover(false)"
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -86,9 +86,9 @@ const Chat = {
|
||||||
created() {
|
created() {
|
||||||
if (this.testMode) return
|
if (this.testMode) return
|
||||||
this.startFetching()
|
this.startFetching()
|
||||||
window.addEventListener('resize', this.handleResize)
|
|
||||||
},
|
},
|
||||||
mounted() {
|
mounted() {
|
||||||
|
window.addEventListener('resize', this.handleResize)
|
||||||
window.addEventListener('scroll', this.handleScroll)
|
window.addEventListener('scroll', this.handleScroll)
|
||||||
if (typeof document.hidden !== 'undefined') {
|
if (typeof document.hidden !== 'undefined') {
|
||||||
document.addEventListener(
|
document.addEventListener(
|
||||||
|
|
@ -122,14 +122,11 @@ const Chat = {
|
||||||
)
|
)
|
||||||
},
|
},
|
||||||
isConversation() {
|
isConversation() {
|
||||||
return this.conversationId !== null
|
return this.statusId !== null
|
||||||
},
|
},
|
||||||
recipient() {
|
recipient() {
|
||||||
return this.chat?.account
|
return this.chat?.account
|
||||||
},
|
},
|
||||||
recipientId() {
|
|
||||||
return this.$route.params.recipient_id
|
|
||||||
},
|
|
||||||
formPlaceholder() {
|
formPlaceholder() {
|
||||||
if (this.recipient) {
|
if (this.recipient) {
|
||||||
return this.$t('chats.message_user', {
|
return this.$t('chats.message_user', {
|
||||||
|
|
@ -166,7 +163,8 @@ const Chat = {
|
||||||
}),
|
}),
|
||||||
},
|
},
|
||||||
watch: {
|
watch: {
|
||||||
messages() {
|
messages(old, neu) {
|
||||||
|
if (old.length === neu.length) return
|
||||||
// We don't want to scroll to the bottom on a new message when the user is viewing older messages.
|
// We don't want to scroll to the bottom on a new message when the user is viewing older messages.
|
||||||
// Therefore we need to know whether the scroll position was at the bottom before the DOM update.
|
// Therefore we need to know whether the scroll position was at the bottom before the DOM update.
|
||||||
const bottomedOutBeforeUpdate = isBottomedOut(BOTTOMED_OUT_OFFSET)
|
const bottomedOutBeforeUpdate = isBottomedOut(BOTTOMED_OUT_OFFSET)
|
||||||
|
|
@ -180,7 +178,38 @@ const Chat = {
|
||||||
await nextTick() // wait for changes to propagate to postStatusForm
|
await nextTick() // wait for changes to propagate to postStatusForm
|
||||||
this.$refs.postStatusForm.update()
|
this.$refs.postStatusForm.update()
|
||||||
},
|
},
|
||||||
$route: function () {
|
$route: async function (newVal) {
|
||||||
|
if (this.messagesIndex[newVal.params.statusId]) {
|
||||||
|
const focused = document.getElementById(`chatmessage-${this.$route.params.statusId}`)
|
||||||
|
if (focused?.getBoundingClientRect == null) return
|
||||||
|
const bottomBoundary = window.innerHeight - this.$refs.footer.clientHeight
|
||||||
|
const topBoundary = this.$refs.header.clientHeight + document.getElementById('nav').clientHeight
|
||||||
|
const margin = Number(window.getComputedStyle(this.$refs.messageList.$el).gap.replace('px',''))
|
||||||
|
|
||||||
|
const rect = focused.getBoundingClientRect()
|
||||||
|
const scrollAmount = (() => {
|
||||||
|
if (rect.top < topBoundary) {
|
||||||
|
// Post is above screen, match its top to screen top
|
||||||
|
return rect.top - topBoundary - margin
|
||||||
|
} else if (rect.height >= bottomBoundary) {
|
||||||
|
// Post we want to see is taller than screen so match its top to screen top
|
||||||
|
return rect.top - topBoundary - margin
|
||||||
|
} else if (rect.bottom > bottomBoundary) {
|
||||||
|
// Post is below screen, match its bottom to screen bottom
|
||||||
|
return rect.bottom - bottomBoundary + margin
|
||||||
|
} else {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
})()
|
||||||
|
|
||||||
|
if (scrollAmount !== 0) {
|
||||||
|
window.scrollBy(0, scrollAmount)
|
||||||
|
}
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
this.clear()
|
||||||
this.startFetching()
|
this.startFetching()
|
||||||
},
|
},
|
||||||
mastoUserSocketStatus(newValue) {
|
mastoUserSocketStatus(newValue) {
|
||||||
|
|
@ -295,6 +324,9 @@ const Chat = {
|
||||||
this.addMessages({ messages })
|
this.addMessages({ messages })
|
||||||
|
|
||||||
await nextTick()
|
await nextTick()
|
||||||
|
if (isFirstFetch) {
|
||||||
|
this.scrollDown()
|
||||||
|
}
|
||||||
|
|
||||||
const fetchOlderMessages = !!maxId
|
const fetchOlderMessages = !!maxId
|
||||||
if (fetchOlderMessages) {
|
if (fetchOlderMessages) {
|
||||||
|
|
|
||||||
|
|
@ -18,7 +18,7 @@
|
||||||
icon="chevron-left"
|
icon="chevron-left"
|
||||||
/>
|
/>
|
||||||
</button>
|
</button>
|
||||||
<div class="title text-center">
|
<div class="title">
|
||||||
<template v-if="isConversation">
|
<template v-if="isConversation">
|
||||||
<RichContent
|
<RichContent
|
||||||
v-if="messages[0]?.summary"
|
v-if="messages[0]?.summary"
|
||||||
|
|
@ -38,6 +38,7 @@
|
||||||
<div class="chat-list-wrapper panel-body">
|
<div class="chat-list-wrapper panel-body">
|
||||||
<div class="top-spacer" />
|
<div class="top-spacer" />
|
||||||
<ChatMessageList
|
<ChatMessageList
|
||||||
|
ref="messageList"
|
||||||
header-date
|
header-date
|
||||||
:messages="messages"
|
:messages="messages"
|
||||||
:pending-messages="pendingMessages"
|
:pending-messages="pendingMessages"
|
||||||
|
|
|
||||||
|
|
@ -92,19 +92,4 @@
|
||||||
backdrop-filter: var(--__panel-backdrop-filter);
|
backdrop-filter: var(--__panel-backdrop-filter);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.chat-view-reply-form {
|
|
||||||
position: sticky;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: stretch;
|
|
||||||
bottom: 0;
|
|
||||||
padding: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.reply-to-text {
|
|
||||||
line-height: 1.2;
|
|
||||||
padding-top: 0.5em;
|
|
||||||
margin-bottom: -0.5em;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue