javascript - add condition with variable inside const IntersectionObserver
问题描述
I have following hook that is added on start:
const scrollObserver = useCallback(
(node) => {
new IntersectionObserver((entries) => {
entries.forEach((en) => {
if (en.intersectionRatio > 0.5) {
pagerDispatch({ type: 'ADVANCE_PAGE' }
}
})
}).observe(node)
},
[pagerDispatch]
)
useEffect(
() => {
if (bottomBoundaryRef.current) {
scrollObserver(bottomBoundaryRef.current)
}
},
[scrollObserver, bottomBoundaryRef]
)
The problem I'm facing that I want to add if
condition with a variable value that updates over time. If I add following code then data.length
is always 0
. I guess that's because it has in store the state that was on start.
if (en.intersectionRatio > 0.5) {
if (data.length <= iScrollMax) {
pagerDispatch({ type: 'ADVANCE_PAGE' })
}
}
How do I add condition with updatable variable here?
ps. I've tried making separate fuction but that did not work too. example
function upd() {
if (data.length <= iScrollMax) {
pagerDispatch({ type: 'ADVANCE_PAGE' })
}
}
const scrollObserver = useCallback(
(node) => {
new IntersectionObserver((entries) => {
entries.forEach((en) => {
if (en.intersectionRatio > 0.5) {
upd()
}
})
}).observe(node)
},
[pagerDispatch]
)
解决方案
You aren't seeing the updated data value in the function because of closure. Your function is only recreated on change on pagerDispatch
and so when the data values update, it isn't made aware of it and keeps using the old data value it had when it was created
The solution is to add data as dependency to useCallback and also ensure you cleanup your observer in useEffect
const scrollObserver = useCallback(
(node) => {
return new IntersectionObserver((entries) => {
entries.forEach((en) => {
if (en.intersectionRatio > 0.5) {
if (data.length <= iScrollMax) {
pagerDispatch({ type: 'ADVANCE_PAGE' }
}
}
})
}).observe(node)
},
[pagerDispatch, data]
)
useEffect(
() => {
let observer;
if (bottomBoundaryRef.current) {
observer=scrollObserver(bottomBoundaryRef.current)
}
return () => {
observer && observer.disconnect();
}
},
[scrollObserver, bottomBoundaryRef]
)
Approach 2: There is a getaway to this via a ref
const dataRef = useRef(data);
useEffect(() => {
dataRef.current = data;
}, [data]);
const scrollObserver = useCallback(
(node) => {
return new IntersectionObserver((entries) => {
entries.forEach((en) => {
if (en.intersectionRatio > 0.5) {
if (dataRef.current.length <= iScrollMax) {
pagerDispatch({ type: 'ADVANCE_PAGE' }
}
}
})
}).observe(node)
},
[pagerDispatch]
)
useEffect(
() => {
let observer;
if (bottomBoundaryRef.current) {
observer=scrollObserver(bottomBoundaryRef.current)
}
return () => {
observer && observer.disconnect();
}
},
[scrollObserver, bottomBoundaryRef]
)
推荐阅读
- python - How do I get "new" behavior in python?
- python - 如何更正有关单独 Python 文件的“ModuleNotFoundError”?
- service-worker - 工作箱:`ignoreUrlParametersMatching` 似乎不起作用
- python - 在 Python pyglet 中按下按钮时做一些事情
- java - Java超类变量在子类之外访问?
- node.js - 如何解析 lambda 中的事件参数?
- python - 在 pandas DataFrame 中的列表上使用 numpy.where(或 numpy.select)
- reactjs - 我的状态被填满又变空了?React-Redux
- java - 在 Java 中将 JSON 参数作为 livy 参数发送
- google-apps-script - 如何在应用脚本中获取当前用户名(邮件 ID)