Skip to content

[@mantine/core] ScrollArea: Fix scrollbar never visible with offsetScrollbars="present" #8844

Merged
rtivital merged 1 commit into
mantinedev:masterfrom
semimikoh:fix/scroll-area-offset-scrollbars-present
Apr 22, 2026
Merged

[@mantine/core] ScrollArea: Fix scrollbar never visible with offsetScrollbars="present" #8844
rtivital merged 1 commit into
mantinedev:masterfrom
semimikoh:fix/scroll-area-offset-scrollbars-present

Conversation

@semimikoh

Copy link
Copy Markdown
Contributor

Summary

  • useResizeObserver received ref.current (null at first render) as its element argument — since ref assignment doesn't cause
    re-render, the ResizeObserver was never attached
  • Replaced with callback ref + useState so the effect dependency updates after mount, correctly attaching the observer
  • Applied the same fix to ScrollArea.Autosize's onOverflowChange detection which had the identical bug

Fixes #8839

Test plan

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull request overview

Fixes ScrollArea/ScrollArea.Autosize ResizeObserver attachment when ref.current is null on first render (notably impacting offsetScrollbars="present"), ensuring scrollbar visibility/overflow detection updates correctly after mount.

Changes:

  • Switch ResizeObserver target from ref.current to a callback-ref-backed state element so the observer reliably attaches after mount.
  • Apply the same callback-ref/state pattern to ScrollArea.Autosize overflow detection.
  • Add a unit test asserting the viewport is observed when offsetScrollbars="present".

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 4 comments.

File Description
packages/@mantine/core/src/components/ScrollArea/ScrollArea.tsx Uses callback refs + state to provide stable, post-mount elements to useResizeObserver for offsetScrollbars="present" and Autosize overflow detection.
packages/@mantine/core/src/components/ScrollArea/ScrollArea.test.tsx Adds a test that mocks ResizeObserver to verify observation occurs when offsetScrollbars="present".

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

const combinedViewportRef = useMergeRefs([viewportRef, localViewportRef]);
const [viewportElement, setViewportElement] = useState<HTMLDivElement | null>(null);
const viewportCallbackRef = useCallback((node: HTMLDivElement | null) => {
setViewportElement(node);

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Thanks, addressed all comments.

Changes:

  • Guarded ref callback state updates against identical nodes.
  • Made the ResizeObserver test mock restore safely via try/finally.
  • Added Autosize coverage for observing the viewport when onOverflowChange is provided.

Verified with the ScrollArea Jest suite and oxfmt check.

Comment on lines +196 to +209
window.ResizeObserver = jest.fn().mockImplementation(() => ({
observe,
unobserve,
}));

render(
<ScrollArea h={100} offsetScrollbars="present">
<div style={{ height: 500 }}>Content</div>
</ScrollArea>
);

expect(observe).toHaveBeenCalled();

window.ResizeObserver = originalResizeObserver;

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Thanks, addressed all comments.

Comment on lines +196 to +199
window.ResizeObserver = jest.fn().mockImplementation(() => ({
observe,
unobserve,
}));

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Thanks, addressed all comments.

Comment on lines 396 to +400
overflowingRef.current = isOverflowing;
}
});

useResizeObserver(onOverflowChange ? viewportObserverRef.current : null, handleOverflowCheck);
useResizeObserver(onOverflowChange ? viewportObserverElement : null, handleOverflowCheck);

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Thanks, addressed all comments.

@semimikoh semimikoh force-pushed the fix/scroll-area-offset-scrollbars-present branch from 1063109 to 8cc23a1 Compare April 18, 2026 03:26
@rtivital rtivital merged commit 36a2350 into mantinedev:master Apr 22, 2026
1 check passed
@rtivital

Copy link
Copy Markdown
Member

Thanks!

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.

Scrollbar in select component never visible with offsetScrollbars: "present"

3 participants