Skip to content

Commit 123126f

Browse files
authored
add list content top notice size css vars (#387)
1 parent ecadd8c commit 123126f

4 files changed

Lines changed: 84 additions & 13 deletions

File tree

src/NotificationList/Content.tsx

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,20 @@ import * as React from 'react';
44
export interface ContentProps extends React.HTMLAttributes<HTMLDivElement> {
55
listPrefixCls: string;
66
height: number;
7+
topNoticeHeight?: number;
8+
topNoticeWidth?: number;
79
}
810

911
const Content = React.forwardRef<HTMLDivElement, ContentProps>((props, ref) => {
10-
const { listPrefixCls, height, className, style, ...restProps } = props;
12+
const {
13+
listPrefixCls,
14+
height,
15+
topNoticeHeight = 0,
16+
topNoticeWidth = 0,
17+
className,
18+
style,
19+
...restProps
20+
} = props;
1121

1222
const contentPrefixCls = `${listPrefixCls}-content`;
1323

@@ -18,15 +28,23 @@ const Content = React.forwardRef<HTMLDivElement, ContentProps>((props, ref) => {
1828

1929
prevHeightRef.current = height;
2030

31+
// ========================= Style ==========================
32+
const contentStyle: React.CSSProperties & {
33+
'--top-notificiation-height': string;
34+
'--top-notificiation-width': string;
35+
} = {
36+
...style,
37+
height,
38+
'--top-notificiation-height': `${topNoticeHeight}px`,
39+
'--top-notificiation-width': `${topNoticeWidth}px`,
40+
};
41+
2142
// ========================= Render =========================
2243
return (
2344
<div
2445
{...restProps}
2546
className={clsx(contentPrefixCls, `${contentPrefixCls}-${heightStatus}`, className)}
26-
style={{
27-
...style,
28-
height,
29-
}}
47+
style={contentStyle}
3048
ref={ref}
3149
/>
3250
);

src/NotificationList/index.tsx

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -210,11 +210,8 @@ const NotificationList: React.FC<NotificationListProps> = (props) => {
210210
// ====================== List Measure ======================
211211
const [gap, setGap] = React.useState(0);
212212
const contentRef = React.useRef<HTMLDivElement>(null);
213-
const [notificationPosition, setNodeSize, totalHeight] = useListPosition(
214-
configList,
215-
stackPosition,
216-
gap,
217-
);
213+
const [notificationPosition, setNodeSize, totalHeight, topNoticeHeight, topNoticeWidth] =
214+
useListPosition(configList, stackPosition, gap);
218215
const hasConfigList = !!configList.length;
219216

220217
React.useEffect(() => {
@@ -259,6 +256,8 @@ const NotificationList: React.FC<NotificationListProps> = (props) => {
259256
<Content
260257
listPrefixCls={listPrefixCls}
261258
height={totalHeight}
259+
topNoticeHeight={topNoticeHeight}
260+
topNoticeWidth={topNoticeWidth}
262261
className={classNames?.listContent}
263262
style={styles?.listContent}
264263
ref={contentRef}

src/hooks/useListPosition/index.ts

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,11 +12,13 @@ export default function useListPosition(
1212
) {
1313
const [sizeMap, setNodeSize] = useSizes();
1414

15-
const [notificationPosition, totalHeight] = React.useMemo(() => {
15+
const [notificationPosition, totalHeight, topNoticeHeight, topNoticeWidth] = React.useMemo(() => {
1616
let offsetY = 0;
1717
let nextTotalHeight = 0;
1818
const stackThreshold = stack?.threshold ?? 0;
1919
const nextNotificationPosition = new Map<string, number>();
20+
let nextTopNoticeHeight: number | undefined;
21+
let nextTopNoticeWidth: number | undefined;
2022

2123
configList
2224
.slice()
@@ -29,6 +31,11 @@ export default function useListPosition(
2931

3032
nextNotificationPosition.set(key, y);
3133

34+
if (index === 0) {
35+
nextTopNoticeHeight = height;
36+
nextTopNoticeWidth = sizeMap[key]?.width ?? 0;
37+
}
38+
3239
if (!stack || index < stackThreshold) {
3340
nextTotalHeight = Math.max(nextTotalHeight, y + height);
3441
}
@@ -40,8 +47,13 @@ export default function useListPosition(
4047
}
4148
});
4249

43-
return [nextNotificationPosition, nextTotalHeight] as const;
50+
return [
51+
nextNotificationPosition,
52+
nextTotalHeight,
53+
nextTopNoticeHeight,
54+
nextTopNoticeWidth,
55+
] as const;
4456
}, [configList, gap, sizeMap, stack]);
4557

46-
return [notificationPosition, setNodeSize, totalHeight] as const;
58+
return [notificationPosition, setNodeSize, totalHeight, topNoticeHeight, topNoticeWidth] as const;
4759
}

tests/index.test.tsx

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -866,6 +866,48 @@ describe('Notification.Basic', () => {
866866
expect(document.querySelector('.rc-notification-list-content')).toHaveClass('bamboo');
867867
});
868868

869+
it('should expose top notice size on listContent', () => {
870+
const offsetHeightSpy = vi
871+
.spyOn(HTMLElement.prototype, 'offsetHeight', 'get')
872+
.mockImplementation(function offsetHeight(this: HTMLElement) {
873+
if (this.classList.contains('rc-notification-notice')) {
874+
return this.textContent === 'second' ? 18 : 10;
875+
}
876+
877+
return 0;
878+
});
879+
const offsetWidthSpy = vi
880+
.spyOn(HTMLElement.prototype, 'offsetWidth', 'get')
881+
.mockImplementation(function offsetWidth(this: HTMLElement) {
882+
if (this.classList.contains('rc-notification-notice')) {
883+
return this.textContent === 'second' ? 28 : 20;
884+
}
885+
886+
return 0;
887+
});
888+
889+
const { instance } = renderDemo();
890+
891+
act(() => {
892+
instance.open({
893+
description: 'first',
894+
duration: false,
895+
});
896+
instance.open({
897+
description: 'second',
898+
duration: false,
899+
});
900+
});
901+
902+
expect(document.querySelector('.rc-notification-list-content')).toHaveStyle({
903+
'--top-notificiation-height': '18px',
904+
'--top-notificiation-width': '28px',
905+
});
906+
907+
offsetHeightSpy.mockRestore();
908+
offsetWidthSpy.mockRestore();
909+
});
910+
869911
it('placement', () => {
870912
const { instance } = renderDemo();
871913

0 commit comments

Comments
 (0)