javascript - React Hooks:从同步到异步的范式转换问题
问题描述
我刚开始使用 React 钩子,但遇到了问题。在下面的组件中,我通过 react 钩子更新了一个值,并将其用作函数的参数。问题是钩子是异步的,所以当我调用函数时,值是未定义的。这是代码:
反应钩子:
const [selectedLocation, setSelectedLocation] = React.useState()
我需要更新的功能selectedLocation
:
const sendLocationToDevice = (loader = true) => {
props.dispatch({type: "CLEAR_ERROR"})
const resObj = CalculateBearing({
a: {lat: props.store.position.latitude, long: props.store.position.longitude},
b: {lat: selectedLocation.coordinates.lat, long: selectedLocation.coordinates.lng} // -> here's the value is undefined
})
我更新值的表格selectedLocation
:
<View>
{ selectedLocation === null ? (
<GooglePlacesAutocomplete
placeholder='Enter Location'
minLength={2}
autoFocus={false}
returnKeyType={'default'}
fetchDetails={true}
onPress={(data, details = null) => {
setSelectedLocation({name: details.formatted_address, coordinates: details.geometry.location})
sendLocationToDevice()
}}
流程是:用户使用表格选择位置并调用函数计算方位。旧的this.setState
一切都是同步的,所以我没有问题,现在我不确定什么是最好的模式,或者我是否滥用了钩子......我应该如何解决这个问题?
解决方案
你可以使用一个React.useEffect
钩子来监听你的selectedLocation
状态的变化,然后sendLocationToDevice
在那里调用。
例如,
function MyComponent() {
const [selectedLocation, setSelectedLocation] = React.useState(null)
React.useEffect(() => {
if (selectedLocation === null) return
function sendLocationToDevice() {
// ...
}
sendLocationToDevice()
}, [selectedLocation])
return (
<GooglePlacesAutocomplete
onPress={(data, details = null) =>
setSelectedLocation({
name: details.formatted_address,
coordinates: details.geometry.location})
})
}
/>
)
}
内部的回调React.useEffect
将始终在selectedLocation
更改时调用,并且它将具有selectedLocation
.
编辑:
作为替代方案,您也可以将回调传递给setSelectedLocation
并调用其中的其他函数。唯一的缺点是你不会再使用你的state
了,所以这可能会也可能不会导致问题。
function MyComponent() {
const [selectedLocation, setSelectedLocation] = React.useState(null)
function sendLocationToDevice(locationData) {
// ...
}
return (
<GooglePlacesAutocomplete
onPress={(data, details = null) => {
const locationData = {
name: details.formatted_address,
coordinates: details.geometry.location
}
sendLocationToDevice(locationData)
return locationData // updates state
}}
/>
)
}
但是,我认为第一个解决方案在我看来更干净,更好,所以我会选择一个useEffect
钩子。
推荐阅读
- javascript - 我想将此 Flatlist 反应本机代码转换为类文件
- java - 使用 AsyncTask 读取 Firestore 文档
- postgresql-9.6 - 一个父表可以参与多少个子表?
- swift - FileManager.replaceItem 删除原始项目
- javascript - columDefs 和 columns 是互斥的吗?
- google-cloud-platform - 在bigquery中将多列变成一行
- cplex - 基准测试中不同答案的原因
- python - 在 MongoEngine 中批量写入
- r - 根据特定标点符号拆分字符串
- python - Python 串行失败“设备的 ioctl 不合适”