From 8f1a1c63fd02a699b8af2e8c2f3e1025d6a38742 Mon Sep 17 00:00:00 2001 From: Jack Hsu Date: Fri, 15 Sep 2023 13:09:24 -0400 Subject: [PATCH] feat(nx-dev): improve auto-scrolling so it does not interfere with users reading the content --- nx-dev/feature-ai/src/lib/feed-container.tsx | 38 ++++++++++++-------- nx-dev/nx-dev/pages/ai-chat/index.tsx | 2 +- 2 files changed, 24 insertions(+), 16 deletions(-) diff --git a/nx-dev/feature-ai/src/lib/feed-container.tsx b/nx-dev/feature-ai/src/lib/feed-container.tsx index d4f9c038d0c8b4..0e5405e9e7ff29 100644 --- a/nx-dev/feature-ai/src/lib/feed-container.tsx +++ b/nx-dev/feature-ai/src/lib/feed-container.tsx @@ -4,7 +4,6 @@ import { type JSX, RefObject, useEffect, - useMemo, useRef, useState, } from 'react'; @@ -28,8 +27,6 @@ export function FeedContainer(): JSX.Element { const [startedReply, setStartedReply] = useState(false); const [isStopped, setStopped] = useState(false); - const feedContainer: RefObject | undefined = useRef(null); - const { messages, setMessages, @@ -57,14 +54,28 @@ export function FeedContainer(): JSX.Element { }, }); - const hasReply = useMemo(() => messages.length > 0, [messages]); - + /* + * Determine whether we should scroll to the bottom of new messages. + * Scroll if: + * 1. New message has come in (length > previous length) + * 2. User is close to the bottom of the messages + * + * Otherwise, user is probably reading messages, so don't scroll. + */ + const scrollableWrapperRef: RefObject | undefined = + useRef(null); + const currentMessagesLength = useRef(0); useEffect(() => { - if (feedContainer.current) { - const elements = - feedContainer.current.getElementsByClassName('feed-item'); - elements[elements.length - 1].scrollIntoView({ behavior: 'smooth' }); + if (!scrollableWrapperRef.current) return; + const el = scrollableWrapperRef.current; + let shouldScroll = false; + if (messages.length > currentMessagesLength.current) { + currentMessagesLength.current = messages.length; + shouldScroll = true; + } else if (el.scrollTop + el.clientHeight + 50 >= el.scrollHeight) { + shouldScroll = true; } + if (shouldScroll) el.scrollTo(0, el.scrollHeight); }, [messages, isLoading]); const handleSubmit = (event: FormEvent) => { @@ -100,6 +111,7 @@ export function FeedContainer(): JSX.Element { <> {/*WRAPPER*/}
{/*MAIN CONTENT*/} -
+
0} showRegenerateCta={isStopped} />
diff --git a/nx-dev/nx-dev/pages/ai-chat/index.tsx b/nx-dev/nx-dev/pages/ai-chat/index.tsx index 6c229d8ffcd48f..e965363a2e469c 100644 --- a/nx-dev/nx-dev/pages/ai-chat/index.tsx +++ b/nx-dev/nx-dev/pages/ai-chat/index.tsx @@ -21,7 +21,7 @@ export default function AiDocs(): JSX.Element { maxVideoPreview: -1, }} /> -
+