Skip to content

Commit bb45daf

Browse files
committed
Address PR Feedback
- remove unneeded css class - respect reduced motion settings in scrollTo function - use lazy ref for sticky manager - fix: scroll hint happens at max once per mount - fix: invoke callback when scrolled to bottom of container
1 parent e2beb61 commit bb45daf

File tree

2 files changed

+20
-15
lines changed

2 files changed

+20
-15
lines changed

polaris-react/src/components/Scrollable/Scrollable.scss

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -25,10 +25,6 @@
2525
overflow-y: auto;
2626
}
2727

28-
.verticalHasScrolling {
29-
overflow-y: scroll;
30-
}
31-
3228
.hasTopShadow {
3329
box-shadow: var(--pc-scrollable-shadow-top);
3430
}

polaris-react/src/components/Scrollable/Scrollable.tsx

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import {
77
StickyManagerContext,
88
} from '../../utilities/sticky-manager';
99
import {scrollable} from '../shared';
10+
import {useLazyRef} from '../../utilities/use-lazy-ref';
11+
import {useComponentDidMount} from '../../utilities/use-component-did-mount';
1012

1113
import {ScrollTo} from './components';
1214
import {ScrollableContext} from './context';
@@ -45,17 +47,18 @@ export function Scrollable({
4547
}: ScrollableProps) {
4648
const [topShadow, setTopShadow] = useState(false);
4749
const [bottomShadow, setBottomShadow] = useState(false);
48-
const stickyManager = useRef(new StickyManager());
50+
const stickyManager = useLazyRef(() => new StickyManager());
4951
const scrollArea = useRef<HTMLDivElement>(null);
5052
const scrollTo = useCallback((scrollY: number) => {
51-
scrollArea.current?.scrollTo({top: scrollY, behavior: 'smooth'});
53+
const behavior = prefersReducedMotion() ? 'auto' : 'smooth';
54+
scrollArea.current?.scrollTo({top: scrollY, behavior});
5255
}, []);
5356

54-
useEffect(() => {
57+
useComponentDidMount(() => {
5558
if (hint) {
5659
performScrollHint(scrollArea.current);
5760
}
58-
}, [hint]);
61+
});
5962

6063
useEffect(() => {
6164
const currentScrollArea = scrollArea.current;
@@ -66,11 +69,17 @@ export function Scrollable({
6669

6770
const handleScroll = () => {
6871
const {scrollTop, clientHeight, scrollHeight} = currentScrollArea;
69-
70-
setBottomShadow(
71-
Boolean(shadow && !(scrollTop + clientHeight >= scrollHeight)),
72+
const isBelowTopOfScroll = Boolean(scrollTop > 0);
73+
const isAtBottomOfScroll = Boolean(
74+
scrollTop + clientHeight >= scrollHeight - LOW_RES_BUFFER,
7275
);
73-
setTopShadow(Boolean(shadow && scrollTop > 0));
76+
77+
setTopShadow(isBelowTopOfScroll);
78+
setBottomShadow(!isAtBottomOfScroll);
79+
80+
if (isAtBottomOfScroll && onScrolledToBottom) {
81+
onScrolledToBottom();
82+
}
7483
};
7584

7685
const handleResize = debounce(handleScroll, 50, {trailing: true});
@@ -85,15 +94,15 @@ export function Scrollable({
8594
currentScrollArea.removeEventListener('scroll', handleScroll);
8695
globalThis.removeEventListener('resize', handleResize);
8796
};
88-
}, [shadow]);
97+
}, [stickyManager, onScrolledToBottom]);
8998

9099
const finalClassName = classNames(
91100
className,
92101
styles.Scrollable,
93102
vertical && styles.vertical,
94103
horizontal && styles.horizontal,
95-
topShadow && styles.hasTopShadow,
96-
bottomShadow && styles.hasBottomShadow,
104+
shadow && topShadow && styles.hasTopShadow,
105+
shadow && bottomShadow && styles.hasBottomShadow,
97106
);
98107

99108
return (

0 commit comments

Comments
 (0)