Thanks to visit codestin.com
Credit goes to github.com

Skip to content

fix: preserve scroll position in session viewer when scrolled up#28

Merged
wesbillman merged 2 commits intomainfrom
baxen/scrollnit
Feb 11, 2026
Merged

fix: preserve scroll position in session viewer when scrolled up#28
wesbillman merged 2 commits intomainfrom
baxen/scrollnit

Conversation

@baxen
Copy link
Collaborator

@baxen baxen commented Feb 11, 2026

Problem

When viewing a live session in the session modal, polling for new messages would always auto-scroll to the bottom — even if the user had intentionally scrolled up to read earlier content. This made it impossible to review previous messages during an active session.

Solution

Commit 1: Basic scroll preservation

Track whether the user is near the bottom of the messages container. During polling, only auto-scroll if the user was already at the bottom. Intentional scrolls (initial load, user sends a message) still force scroll to bottom unconditionally.

Commit 2: Replace pixel threshold with intent tracking

The initial implementation used a fragile 80px pixel threshold to determine "near bottom." This was replaced with directional intent tracking — comparing scrollTop against lastScrollTop to detect when the user has scrolled upward.

Before After
isNearBottom — true when within 80px of bottom userScrolledUp — true when user scrolls upward
Could misfire on short/tall containers Works reliably regardless of container height
Single position check Direction-based intent detection

Key behavior:

  • userScrolledUp = true when scrollTop decreases (user scrolled up)
  • Cleared when user scrolls back to the exact bottom, or on explicit scrollToBottom() calls
  • Works across all input methods: mouse wheel, keyboard, touch, scrollbar drag

Changes

  • src/lib/SessionModal.svelte — scroll tracking logic in the messages container

Track whether the user is near the bottom of the messages container
using an onscroll handler. During polling, only auto-scroll to bottom
if the user was already near the bottom (within 80px). Intentional
scrolls (initial load, user sends a message) still force scroll to
bottom unconditionally.

- Add isNearBottom state and handleScroll listener on modal-content
- Add scrollToBottomIfNear() that gates on isNearBottom
- Replace scrollToBottom() with scrollToBottomIfNear() in poll()
- Keep unconditional scrollToBottom() in loadSession() and sendMessage()
Replace the fragile isNearBottom heuristic (< 80px from bottom) with
directional intent tracking using lastScrollTop comparison. This properly
detects user-initiated upward scrolling across all input methods (mouse
wheel, keyboard, touch, scrollbar drag).

- Track userScrolledUp flag set when scrollTop decreases (upward scroll)
- Clear flag when user scrolls back to exact bottom or on explicit
  scrollToBottom() calls (initial load, sending a message)
- Remove magic 80px threshold that could misfire on short containers
  or miss intent on long ones
Copy link
Collaborator

@wesbillman wesbillman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice! I'm always amazed at how hard this is for every chat app. 😂

@wesbillman wesbillman merged commit 70eee0c into main Feb 11, 2026
2 checks passed
@wesbillman wesbillman deleted the baxen/scrollnit branch February 11, 2026 06:46
loganj added a commit that referenced this pull request Feb 26, 2026
Adds dark mode with theme toggle and system preference detection
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants