我在使用 useEffect 时遇到了获取 clientWidth 的问题。
有一个 lazyLoad,它会加载一个包含用户的页面。
import {Suspense, lazy} from 'react';
const UsersContainer = lazy (() => import ('./ users / users-container'));
const Index = (props) => {
return (
<Suspense fallback = {<div id = {'loading'} />}>
<UsersContainer />
</Suspense>
)
}
export default Index;
UsersContainer有一个子组件dataTooltip,当用户名称无法适应块时,该组件将显示完整的用户名称。
import React, {useEffect, useRef} from 'react';
import '../common.scss';
const DataTooltip = ({title, ... props}) => {
let ref = useRef ();
useEffect (() => {
if (ref.current.scrollWidth> ref.current.clientWidth) {
ref.current.setAttribute ('data-tooltip', title)
}
});
return (
<div ref = {ref} className = {'tooltip'}>
{
React.cloneElement (props.children, {ref: ref})
}
</div>
)
}
export default DataTooltip;
问题是什么?
UsersContainer 加载并在 DOM 中呈现后,它具有 'display: none',同时 DataTooltip 中的 useEffect 会异步触发。
结果是,DataTooltip 显示 clientWidth = 0,因为父元素具有 'display: none'。
如何让 useEffect 在 lazyLoad 删除 'display: none' 后起作用。
PS:useLayoutEffect 的效果相同,clientWidth=0
通过以下方式解决问题:
<Suspense fallback={<div id={'loading'}/>}>
<Main/>
<Acquaintance/>
<UsersContainer/>
<RegisterContainer/>
</Suspense>
to
<Suspense fallback={<div id={'loading'}/>}>
<Main/>
</Suspense>
<Suspense fallback={<div id={'loading'}/>}>
<Acquaintance/>
</Suspense>
<Suspense fallback={<div id={'loading'}/>}>
<UsersContainer/>
</Suspense>
<Suspense fallback={<div id={'loading'}/>}>
<RegisterContainer/>
</Suspense>