From c930a49ce9b705debc9444ac56bcfb8d2fc9c3ad Mon Sep 17 00:00:00 2001 From: Fermin Quant <14808645+ferminquant@users.noreply.github.com> Date: Tue, 2 Jun 2026 23:09:24 -0400 Subject: [PATCH] fix(desktop): honor upward wheel scroll in long threads --- .../assistant-ui/streaming.test.tsx | 34 +++++++++++++++++++ .../assistant-ui/thread-virtualizer.tsx | 1 + 2 files changed, 35 insertions(+) diff --git a/apps/desktop/src/components/assistant-ui/streaming.test.tsx b/apps/desktop/src/components/assistant-ui/streaming.test.tsx index 70f66040e..51edee952 100644 --- a/apps/desktop/src/components/assistant-ui/streaming.test.tsx +++ b/apps/desktop/src/components/assistant-ui/streaming.test.tsx @@ -415,6 +415,40 @@ describe('assistant-ui streaming renderer', () => { expect(viewport.scrollTop).toBe(420) }) + it('honors the first upward wheel scroll even when a programmatic bottom-pin scroll event is still pending', async () => { + const { container } = render() + + const content = container.querySelector('[data-slot="aui_thread-content"]') as HTMLDivElement + const viewport = content.parentElement as HTMLDivElement + let scrollHeight = 1_000 + + Object.defineProperty(viewport, 'clientHeight', { configurable: true, value: 200 }) + Object.defineProperty(viewport, 'scrollHeight', { + configurable: true, + get: () => scrollHeight + }) + + await wait(80) + await wait(0) + + await act(async () => { + fireEvent.wheel(viewport, { deltaY: -120 }) + viewport.scrollTop = 420 + fireEvent.scroll(viewport) + }) + + scrollHeight = 1_200 + + await act(async () => { + for (const observer of resizeObservers) { + observer.trigger(1_200) + } + }) + await wait(0) + + expect(viewport.scrollTop).toBe(420) + }) + it('renders reasoning text without a leading token space', () => { const { container } = render() diff --git a/apps/desktop/src/components/assistant-ui/thread-virtualizer.tsx b/apps/desktop/src/components/assistant-ui/thread-virtualizer.tsx index 3ee02e755..784ed71f3 100644 --- a/apps/desktop/src/components/assistant-ui/thread-virtualizer.tsx +++ b/apps/desktop/src/components/assistant-ui/thread-virtualizer.tsx @@ -237,6 +237,7 @@ function useThreadScrollAnchor({ enabled, groupCount, scrollerRef, sessionKey, v const disarm = () => { armedRef.current = false + programmaticScrollPendingRef.current = 0 } const onScroll = () => {