react-native - 使用 REST 中的经度和纬度获取方向
问题描述
我想从 2 个点(起点和终点)获取方向,我编写了一个简单的函数来获取经度和纬度。
看起来像这样
const GetLongitudeFromAddress = (address) =>{
var logLatApi = 'https://maps.googleapis.com/maps/api/geocode/json?address='+address+'&sensor=false&key=AIzaSyBsy6x3mTXbPQ52qk6XMI9u1NgMfn9-YNE';
var header = {
'Accept': 'application/json',
'Content-Type': 'application/json'
};
fetch(
logLatApi,{
method : 'GET',
headers : header
}
).then((response) => response.json())
.then((responseJson)=>{
if(responseJson.status ==='OK')
{
this.setState({longitude: responseJson.results[0].geometry.location.lng});
this.setState({latitude: responseJson.results[0].geometry.location.lat});
}
})
}
现在我想在 inputText 中使用它 像这样
<TextInput
style={styles.input}
placeholder="Origin"
onChangeText={text => GetLongitudeFromAddress(text)}
/>
它似乎不起作用,我得到了这个错误可能承诺处理拒绝,如下图所示
如何将它与 useState 一起使用?我的代码如下所示:
import React , {useState, useEffect} from 'react';
import {StyleSheet, View, Dimensions, TextInput} from 'react-native';
import MapView , { Marker , Polyline } from 'react-native-maps';
import MapViewDirections from 'react-native-maps-directions';
import { GooglePlacesAutocomplete } from 'react-native-google-places-autocomplete';
const ShowMap =() =>{
const GetLongitudeFromAddress = (address) =>{
var logLatApi = 'https://maps.googleapis.com/maps/api/geocode/json?address='+address+'&sensor=false&key=AIzaSyBsy6x3mTXbPQ52qk6XMI9u1NgMfn9-YNE';
var header = {
'Accept': 'application/json',
'Content-Type': 'application/json'
};
fetch(
logLatApi,{
method : 'GET',
headers : header
}
).then((response) => response.json())
.then((responseJson)=>{
if(responseJson.status ==='OK')
{
this.setState({longitude: responseJson.results[0].geometry.location.lng});
this.setState({latitude: responseJson.results[0].geometry.location.lat});
}
})
}
const [coordinates] = useState([
{
latitude: 6.450430,
longitude: 3.390460,
},
{
latitude: 6.430980,
longitude: 3.435880,
},
]);
return(
<View style={styles.container}>
<MapView
style={styles.maps}
initialRegion={{
latitude: coordinates[0].latitude,
longitude: coordinates[0].longitude,
latitudeDelta: 0.0622,
longitudeDelta: 0.0121,
}}>
<MapViewDirections
origin={coordinates[0]}
destination={coordinates[1]}
apikey="AIzaSyBsy6x3mTXbPQ52qk6XMI9u1NgMfn9-YNE"
strokeWidth={4}
strokeColor="#FD0631"
/>
<Marker coordinate={coordinates[0]} />
<Marker coordinate={coordinates[1]} />
</MapView>
<View style={styles.inputView}>
<TextInput
style={styles.input}
placeholder="Origin"
onChangeText={text => GetLongitudeFromAddress(text)}
/>
<TextInput
style={styles.input}
placeholder="Destination"
onChangeText={text => GetLongitudeFromAddress(text)}
/>
</View>
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
maps: {
width: Dimensions.get('screen').width,
height: Dimensions.get('screen').height,
},
inputView:{
backgroundColor: 'rgba(0,0,0,0)',
position: 'absolute',
top: 0,
left: 5,
right: 5
},
input: {
height: 50,
padding: 10,
marginTop: 20,
marginLeft: 10,
marginRight: 10,
fontSize: 18,
borderWidth: 1,
borderRadius: 35,
borderColor: '#EEEEEE',
backgroundColor: 'white',
}
});
export default ShowMap;
我该怎么做?我如何使用它GetLongitudeFromAddress
来获取两个领域的经度和纬度。请协助
解决方案
您需要有一个按钮,GetLongitudeFromAddress
在按下时会调用该函数。每次更改输入文本值时调用此函数的成本都会很高,因为每次调用该函数时都会调用地理编码请求。我成功地修改了您的代码以从输入文本中获取地址,然后使用该函数对其进行转换,然后将转换后的坐标用作 MapViewDirections 的输入。下面是一个示例代码和一个带有内联注释的代码片段:
import React, { useState, useEffect } from 'react';
import { StyleSheet, View, Dimensions, TextInput, Button } from 'react-native';
import MapView, { Marker, Polyline } from 'react-native-maps';
import MapViewDirections from 'react-native-maps-directions';
import { GooglePlacesAutocomplete } from 'react-native-google-places-autocomplete';
const { width, height } = Dimensions.get('window');
const ShowMap = () => {
//initial maps coordinate
const [initialCenter] = useState({
latitude: 6.45043,
longitude: 3.39046,
});
//state variables for the value of the textbox
const [originInput, setOInput] = useState(null);
const [destInput, setDInput] = useState(null);
//state variables to handle the coordinates after getting it from GetLongitudeFromAddress function
const [originReq, setOReq] = useState(null);
const [destReq, setDReq] = useState(null);
//state variable that will be one of the condition to trigger MapViewDirections once button is pressed
const [isBtnPressed, setBtn] = useState(null);
//state variable that will be a condition to show the origin and destination marker once the route was started
const [routeStarted, setRouteStarted] = useState(null);
//function that will convert the address from your inpput textbox to a coordinate(geocoding)
//coord variable will be the variable that will determine if you are converting the origin or the destination coordinates
const GetLongitudeFromAddress = (address, coord) => {
var logLatApi =
'https://maps.googleapis.com/maps/api/geocode/json?address=' +
address +
'&sensor=false&key=YOUR_KEY';
var header = {
Accept: 'application/json',
'Content-Type': 'application/json',
};
fetch(logLatApi, {
method: 'GET',
headers: header,
})
.then((response) => response.json())
.then((responseJson) => {
if (responseJson.status === 'OK') {
//check if coord value is 'origin' or destination'
if (coord == 'origin' || coord == 'destination') {
if (coord == 'origin') {
//if origin, it will change the originReq state value to the result
setOReq({
latitude: responseJson.results[0].geometry.location.lat,
longitude: responseJson.results[0].geometry.location.lng,
});
} else {
//if destination, it will change the destReq state value to the result
setDReq({
latitude: responseJson.results[0].geometry.location.lat,
longitude: responseJson.results[0].geometry.location.lng,
});
}
}
}
});
};
//function called when the button is pressed
const processAddress = () => {
//it will pass the current value of your input state and hardcoding origin or destination to mark if the address being converted to coordinates is either one of them
GetLongitudeFromAddress(originInput, 'origin');
GetLongitudeFromAddress(destInput, 'destination');
//change isBtnPressed state variable value
setBtn('Y');
};
//function called when the route is ready, it will also fit the polyline to the current view
const routeReady = (result) => {
console.log(`Distance: ${result.distance} km`);
console.log(`Duration: ${result.duration} min.`);
console.log(isBtnPressed);
this.mapView.fitToCoordinates(result.coordinates, {
edgePadding: {
right: width / 20,
bottom: height / 20,
left: width / 20,
top: height / 20,
},
});
};
return (
<View style={styles.container}>
<MapView
style={styles.maps}
ref={(c) => (this.mapView = c)}
initialRegion={{
latitude: initialCenter.latitude,
longitude: initialCenter.longitude,
latitudeDelta: 0.0622,
longitudeDelta: 0.0121,
}}>
{isBtnPressed !== null && originReq !== null && destReq !== null && (
<MapViewDirections
origin={originReq}
destination={destReq}
apikey="YOUR_KEY"
strokeWidth={4}
strokeColor="#FD0631"
onStart={() => {
setRouteStarted('Y');
}}
onReady={(result) => {
routeReady(result);
}}
onError={() => {
setRouteStarted(null);
}}
/>
)}
{routeStarted !== null && originReq != null && (
<Marker coordinate={originReq} />
)}
{routeStarted !== null && destReq != null && (
<Marker coordinate={destReq} />
)}
</MapView>
<View style={styles.inputView}>
<TextInput
style={styles.input}
placeholder="Origin"
onChangeText={(text) => setOInput(text)}
/>
<TextInput
style={styles.input}
placeholder="Destination"
onChangeText={(text) => setDInput(text)}
/>
<Button title="Press me" color="#f194ff" onPress={processAddress} />
</View>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
},
maps: {
width: Dimensions.get('screen').width,
height: Dimensions.get('screen').height,
},
inputView: {
backgroundColor: 'rgba(0,0,0,0)',
position: 'absolute',
top: 0,
left: 5,
right: 5,
},
input: {
height: 50,
padding: 10,
marginTop: 20,
marginLeft: 10,
marginRight: 10,
fontSize: 18,
borderWidth: 1,
borderRadius: 35,
borderColor: '#EEEEEE',
backgroundColor: 'white',
},
});
export default ShowMap;
注意:请在您的代码中删除您的 API 密钥,请勿将其分享到公共站点,以保护您的 API 密钥不被意外使用。
推荐阅读
- javascript - 更改嵌套对象键的值
- dart - 在列表列表中每个项目的开头插入列表项
- amazon-web-services - 通过 terraform 的客户输出
- r - 安装软件包时 Rcmd.exe 出现问题
- pandas - 在 Pandas 中按字符串和数字对 MultiIndex 列进行排序
- java - 如何将 JSON 字符串反序列化为对象放宽根值区分大小写?
- json - 将 Json 文件附加到 Postgres 表中的现有 Jsonb 字段,并在需要时更新 json 文件
- excel - 为什么 VBA 中的某些单词自动具有小写首字母?
- ruby - Puma - 没有这样的文件或目录 - connect(2)。不知道它从哪里得到这个位置
- javascript - ArangoDB AQL 片段问题