11import type { DElementSelector } from '../../hooks/element-ref' ;
2- import type { DStateBackflowContextData } from '../../hooks/state-backflow ' ;
2+ import type { Draft } from 'immer ' ;
33
44import { isUndefined } from 'lodash' ;
55import React , { useCallback , useEffect , useMemo , useState } from 'react' ;
@@ -13,11 +13,12 @@ import {
1313 useRefCallback ,
1414 useRootContentConfig ,
1515 useValueChange ,
16- DStateBackflowContext ,
1716} from '../../hooks' ;
1817import { getClassName , CustomScroll } from '../../utils' ;
1918
2019export interface DAnchorContextData {
20+ updateLinks : ( identity : string , href : string | undefined , el : HTMLLIElement | null ) => void ;
21+ removeLinks : ( identity : string ) => void ;
2122 anchorActiveHref : string | null ;
2223 onLinkClick : ( href : string ) => void ;
2324}
@@ -55,7 +56,7 @@ export function DAnchor(props: DAnchorProps) {
5556 const asyncCapture = useAsync ( ) ;
5657 const [ customScroll ] = useState ( ( ) => new CustomScroll ( ) ) ;
5758 const [ dotStyle , setDotStyle ] = useImmer < React . CSSProperties > ( { } ) ;
58- const [ links , setLinks ] = useImmer ( new Map < string , { href : string ; el : HTMLLIElement | null } > ( ) ) ;
59+ const [ links , setLinks ] = useImmer ( new Map < string , { href : string ; el : HTMLLIElement } > ( ) ) ;
5960 const [ activeHref , setActiveHref ] = useState < string | null > ( null ) ;
6061
6162 const pageRef = useRefSelector ( dPage ?? null ) ;
@@ -97,8 +98,8 @@ export function DAnchor(props: DAnchorProps) {
9798 if ( newHref ) {
9899 for ( const { href, el } of links . values ( ) ) {
99100 if ( href === newHref ) {
100- const rect = el ? .getBoundingClientRect ( ) ;
101- if ( rect && anchorEl ) {
101+ const rect = el . getBoundingClientRect ( ) ;
102+ if ( anchorEl ) {
102103 draft . top = rect . top + rect . height / 2 - anchorEl . getBoundingClientRect ( ) . top ;
103104 }
104105 break ;
@@ -157,51 +158,46 @@ export function DAnchor(props: DAnchorProps) {
157158 } , [ asyncCapture , rootContentRef , updateAnchor ] ) ;
158159 //#endregion
159160
160- const contextValue = useMemo < DAnchorContextData > (
161- ( ) => ( {
162- anchorActiveHref : activeHref ,
163- onLinkClick,
164- } ) ,
165- [ activeHref , onLinkClick ]
166- ) ;
167-
168- const stateBackflowContextValue = useMemo < DStateBackflowContextData > (
161+ const stateBackflow = useMemo < Pick < DAnchorContextData , 'updateLinks' | 'removeLinks' > > (
169162 ( ) => ( {
170- addState : ( identity , href , el ) => {
171- setLinks ( ( draft ) => {
172- draft . set ( identity , { href, el } ) ;
173- } ) ;
174- } ,
175- updateState : ( identity , href , el ) => {
176- setLinks ( ( draft ) => {
177- draft . set ( identity , { href, el } ) ;
178- } ) ;
163+ updateLinks : ( identity , href , el ) => {
164+ if ( href && el ) {
165+ setLinks ( ( draft ) => {
166+ draft . set ( identity , { href, el : el as Draft < HTMLLIElement > } ) ;
167+ } ) ;
168+ }
179169 } ,
180- removeState : ( identity ) => {
170+ removeLinks : ( identity ) => {
181171 setLinks ( ( draft ) => {
182172 draft . delete ( identity ) ;
183173 } ) ;
184174 } ,
185175 } ) ,
186176 [ setLinks ]
187177 ) ;
178+ const contextValue = useMemo < DAnchorContextData > (
179+ ( ) => ( {
180+ ...stateBackflow ,
181+ anchorActiveHref : activeHref ,
182+ onLinkClick,
183+ } ) ,
184+ [ activeHref , onLinkClick , stateBackflow ]
185+ ) ;
188186
189187 return (
190- < DStateBackflowContext . Provider value = { stateBackflowContextValue } >
191- < DAnchorContext . Provider value = { contextValue } >
192- < ul { ...restProps } ref = { anchorRef } className = { getClassName ( className , `${ dPrefix } anchor` ) } >
193- < div className = { `${ dPrefix } anchor__indicator` } >
194- { dIndicator === 'dot' ? (
195- < span className = { `${ dPrefix } anchor__dot-indicator` } style = { dotStyle } > </ span >
196- ) : dIndicator === 'line' ? (
197- < span className = { `${ dPrefix } anchor__line-indicator` } style = { dotStyle } > </ span >
198- ) : (
199- dIndicator
200- ) }
201- </ div >
202- { children }
203- </ ul >
204- </ DAnchorContext . Provider >
205- </ DStateBackflowContext . Provider >
188+ < DAnchorContext . Provider value = { contextValue } >
189+ < ul { ...restProps } ref = { anchorRef } className = { getClassName ( className , `${ dPrefix } anchor` ) } >
190+ < div className = { `${ dPrefix } anchor__indicator` } >
191+ { dIndicator === 'dot' ? (
192+ < span className = { `${ dPrefix } anchor__dot-indicator` } style = { dotStyle } > </ span >
193+ ) : dIndicator === 'line' ? (
194+ < span className = { `${ dPrefix } anchor__line-indicator` } style = { dotStyle } > </ span >
195+ ) : (
196+ dIndicator
197+ ) }
198+ </ div >
199+ { children }
200+ </ ul >
201+ </ DAnchorContext . Provider >
206202 ) ;
207203}
0 commit comments