@@ -146,12 +146,8 @@ export function genCSSMotion(config: CSSMotionConfig) {
146146 return getDOM ( nodeRef . current ) as HTMLElement ;
147147 }
148148
149- const [ getStatus , statusStep , statusStyle , mergedVisible ] = useStatus (
150- supportMotion ,
151- visible ,
152- getDomElement ,
153- props ,
154- ) ;
149+ const [ getStatus , statusStep , statusStyle , mergedVisible , styleReady ] =
150+ useStatus ( supportMotion , visible , getDomElement , props ) ;
155151 const status = getStatus ( ) ;
156152
157153 // Record whether content has rendered
@@ -186,73 +182,85 @@ export function genCSSMotion(config: CSSMotionConfig) {
186182 React . useImperativeHandle ( ref , ( ) => refObj , [ ] ) ;
187183
188184 // ===================== Render =====================
189- let motionChildren : React . ReactNode ;
190- const mergedProps = { ...eventProps , visible } ;
191-
192- if ( ! children ) {
193- // No children
194- motionChildren = null ;
195- } else if ( status === STATUS_NONE ) {
196- // Stable children
197- if ( mergedVisible ) {
198- motionChildren = children ( { ...mergedProps } , nodeRef ) ;
199- } else if ( ! removeOnLeave && renderedRef . current && leavedClassName ) {
200- motionChildren = children (
201- { ...mergedProps , className : leavedClassName } ,
202- nodeRef ,
203- ) ;
204- } else if ( forceRender || ( ! removeOnLeave && ! leavedClassName ) ) {
205- motionChildren = children (
206- { ...mergedProps , style : { display : 'none' } } ,
207- nodeRef ,
208- ) ;
209- } else {
210- motionChildren = null ;
211- }
212- } else {
213- // In motion
214- let statusSuffix : string ;
215- if ( statusStep === STEP_PREPARE ) {
216- statusSuffix = 'prepare' ;
217- } else if ( isActive ( statusStep ) ) {
218- statusSuffix = 'active' ;
219- } else if ( statusStep === STEP_START ) {
220- statusSuffix = 'start' ;
221- }
222-
223- const motionCls = getTransitionName (
224- motionName ,
225- `${ status } -${ statusSuffix } ` ,
226- ) ;
227-
228- motionChildren = children (
229- {
230- ...mergedProps ,
231- className : clsx ( getTransitionName ( motionName , status ) , {
232- [ motionCls ] : motionCls && statusSuffix ,
233- [ motionName as string ] : typeof motionName === 'string' ,
234- } ) ,
235- style : statusStyle ,
236- } ,
237- nodeRef ,
238- ) ;
185+ // return motionChildren as React.ReactElement;
186+ const idRef = React . useRef ( 0 ) ;
187+ if ( styleReady ) {
188+ idRef . current += 1 ;
239189 }
240190
241- // Auto inject ref if child node not have `ref` props
242- if ( React . isValidElement ( motionChildren ) && supportRef ( motionChildren ) ) {
243- const originNodeRef = getNodeRef ( motionChildren ) ;
191+ // We should render children when motionStyle is sync with stepStatus
192+ return React . useMemo ( ( ) => {
193+ let motionChildren : React . ReactNode ;
194+ const mergedProps = { ...eventProps , visible } ;
195+
196+ if ( ! children ) {
197+ // No children
198+ motionChildren = null ;
199+ } else if ( status === STATUS_NONE ) {
200+ // Stable children
201+ if ( mergedVisible ) {
202+ motionChildren = children ( { ...mergedProps } , nodeRef ) ;
203+ } else if ( ! removeOnLeave && renderedRef . current && leavedClassName ) {
204+ motionChildren = children (
205+ { ...mergedProps , className : leavedClassName } ,
206+ nodeRef ,
207+ ) ;
208+ } else if ( forceRender || ( ! removeOnLeave && ! leavedClassName ) ) {
209+ motionChildren = children (
210+ { ...mergedProps , style : { display : 'none' } } ,
211+ nodeRef ,
212+ ) ;
213+ } else {
214+ motionChildren = null ;
215+ }
216+ } else {
217+ // In motion
218+ let statusSuffix : string ;
219+ if ( statusStep === STEP_PREPARE ) {
220+ statusSuffix = 'prepare' ;
221+ } else if ( isActive ( statusStep ) ) {
222+ statusSuffix = 'active' ;
223+ } else if ( statusStep === STEP_START ) {
224+ statusSuffix = 'start' ;
225+ }
226+
227+ const motionCls = getTransitionName (
228+ motionName ,
229+ `${ status } -${ statusSuffix } ` ,
230+ ) ;
244231
245- if ( ! originNodeRef ) {
246- motionChildren = React . cloneElement (
247- motionChildren as React . ReactElement ,
232+ motionChildren = children (
248233 {
249- ref : nodeRef ,
234+ ...mergedProps ,
235+ className : clsx ( getTransitionName ( motionName , status ) , {
236+ [ motionCls ] : motionCls && statusSuffix ,
237+ [ motionName as string ] : typeof motionName === 'string' ,
238+ } ) ,
239+ style : statusStyle ,
250240 } ,
241+ nodeRef ,
251242 ) ;
252243 }
253- }
254244
255- return motionChildren as React . ReactElement ;
245+ // Auto inject ref if child node not have `ref` props
246+ if (
247+ React . isValidElement ( motionChildren ) &&
248+ supportRef ( motionChildren )
249+ ) {
250+ const originNodeRef = getNodeRef ( motionChildren ) ;
251+
252+ if ( ! originNodeRef ) {
253+ motionChildren = React . cloneElement (
254+ motionChildren as React . ReactElement ,
255+ {
256+ ref : nodeRef ,
257+ } ,
258+ ) ;
259+ }
260+ }
261+
262+ return motionChildren ;
263+ } , [ idRef . current ] ) as React . ReactElement ;
256264 } ,
257265 ) ;
258266
0 commit comments