Skip to content

Commit ecbeb95

Browse files
authored
feat: dynamic width (#313)
* fix: height flick * feat: dynamic width * fix: top and bottom * chore: code clean
1 parent b0eb1fd commit ecbeb95

File tree

1 file changed

+24
-15
lines changed

1 file changed

+24
-15
lines changed

src/NoticeList.tsx

Lines changed: 24 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ const NoticeList: FC<NoticeListProps> = (props) => {
4545

4646
const { classNames: ctxCls } = useContext(NotificationContext);
4747

48-
const listRef = useRef<HTMLDivElement[]>([]);
48+
const dictRef = useRef<Record<React.Key, HTMLDivElement>>({});
4949
const [latestNotice, setLatestNotice] = useState<HTMLDivElement>(null);
5050
const [hoverCount, setHoverCount] = useState(0);
5151

@@ -91,21 +91,30 @@ const NoticeList: FC<NoticeListProps> = (props) => {
9191
// If dataIndex is -1, that means this notice has been removed in data, but still in dom
9292
// Should minus (motionIndex - 1) to get the correct index because keys.length is not the same as dom length
9393
const index = keys.length - 1 - (dataIndex > -1 ? dataIndex : motionIndex - 1);
94+
const transformX = placement === 'top' || placement === 'bottom' ? '-50%' : '0';
9495
const stackStyle: CSSProperties = {};
9596
if (stack) {
9697
if (index > 0) {
9798
stackStyle.height = expanded
98-
? listRef.current[index]?.offsetHeight
99+
? dictRef.current[key]?.offsetHeight
99100
: latestNotice?.offsetHeight;
100-
stackStyle.transform = `translateY(${
101-
(expanded
102-
? listRef.current.reduce(
103-
(acc, item, refIndex) => acc + (refIndex < index ? item?.offsetHeight ?? 0 : 0),
104-
0,
105-
) +
106-
index * gap
107-
: index * offset) * (placement.startsWith('top') ? 1 : -1)
108-
}px)`;
101+
102+
// Transform
103+
let verticalOffset = 0;
104+
for (let i = 0; i < index; i++) {
105+
verticalOffset += dictRef.current[keys[keys.length - 1 - i].key]?.offsetHeight + gap;
106+
}
107+
108+
const transformY =
109+
(expanded ? verticalOffset : index * offset) * (placement.startsWith('top') ? 1 : -1);
110+
const scaleX =
111+
!expanded && latestNotice?.offsetWidth && dictRef.current[key]?.offsetWidth
112+
? (latestNotice?.offsetWidth - offset * 2 * (index < 3 ? index : 3)) /
113+
dictRef.current[key]?.offsetWidth
114+
: 1;
115+
stackStyle.transform = `translate3d(${transformX}, ${transformY}px, 0) scaleX(${scaleX})`;
116+
} else {
117+
stackStyle.transform = `translate3d(${transformX}, 0, 0)`;
109118
}
110119
}
111120

@@ -116,6 +125,7 @@ const NoticeList: FC<NoticeListProps> = (props) => {
116125
style={{
117126
...motionStyle,
118127
...stackStyle,
128+
...configStyle,
119129
}}
120130
onMouseEnter={() => setHoverCount((c) => c + 1)}
121131
onMouseLeave={() => setHoverCount((c) => c - 1)}
@@ -124,14 +134,13 @@ const NoticeList: FC<NoticeListProps> = (props) => {
124134
{...config}
125135
ref={(node) => {
126136
if (dataIndex > -1) {
127-
listRef.current[index] = node;
137+
dictRef.current[key] = node;
138+
} else {
139+
delete dictRef.current[key];
128140
}
129141
}}
130142
prefixCls={prefixCls}
131143
className={clsx(configClassName, ctxCls?.notice)}
132-
style={{
133-
...configStyle,
134-
}}
135144
times={times}
136145
key={key}
137146
eventKey={key}

0 commit comments

Comments
 (0)