问题描述
我在以前的项目中使用过这个功能,这对我有用,因为用户位置是事先确定的。
现在在我的应用程序中有点不同,因为必须在登录主页后立即过滤事件,而且用户位置仍有待确定。
因此,将我的代码放在 asynchronous
下方,以便在 userLat
和 userLon
包含这些值之后开始计算
const [userLat,setUserLat] = useState(localStorage.getItem('userLat'))
const [userLon,setUserLon] = useState(localStorage.getItem('userLon'))
useEffect(() => {
data?.forEach((el) => {
Geocode.fromAddress(
`${el.street} ${el.houseNumber},${el.zip} ${el.city}`
)
.then((res) => {
let dis = getdistance(
{
latitude: parseFloat(res.results[0].geometry.location.lat),longitude: parseFloat(res.results[0].geometry.location.lon),},{
latitude: parseFloat(userLat),// Not available right away
longitude: parseFloat(userLon),// Not available right away
}
);
console.log(dis); // this return NaN since userLat & userLon values aren't available yet
})
.catch((err) => console.log(err));
});
},[data]);
所以 geocode function
应该在 userLat
和 userLon
可用时立即执行。
我尝试了一些方法将其转换为 async function
并尝试 await
userLat
en userLon
值但没有成功。
有人能指出我如何为 wait
Geocode.fromAddress
直到 userLat
en userLon
值已由地理定位 api 确定的正确方向吗?
提前致谢!
解决方法
虽然您不能 call hooks within conditionals,但您可以在钩子中包含条件检查!
如果您有一个需要基于 data
、userLat
和 userLon
运行的效果,请将它们作为依赖项并在您的效果中包含检查:
const [userLat,setUserLat] = useState(localStorage.getItem('userLat'));
const [userLon,setUserLon] = useState(localStorage.getItem('userLon'));
useEffect(
() => {
// Only calculate distance if coords are available
if (userLat && userLon) {
data?.forEach((el) => {
Geocode.fromAddress(`${el.street} ${el.houseNumber},${el.zip} ${el.city}`)
.then((res) => {
let dis = getDistance(
{
latitude: parseFloat(res.results[0].geometry.location.lat),longitude: parseFloat(res.results[0].geometry.location.lon),},{
latitude: parseFloat(userLat),longitude: parseFloat(userLon),}
);
// Do something with `dis` here...
})
.catch((err) => console.log(err));
});
}
},// Re-run effect when these variables update
[data,userLat,userLon]
);