Google maps Xamarin谷歌地图自动完成
我正试图在Xamarin表单上为我的Xamarin表单映射添加一个自动完成服务到我的自定义搜索栏(我正在使用一个条目),但我一直无法这样做 我已经尝试过XLabs,但没有成功,到目前为止,我还没有找到任何其他解决方案 Xamarin.formsmap是否包含任何自动完成功能?或者Xamarin上已经有我可能缺少的自动完成功能了吗?Google maps Xamarin谷歌地图自动完成,google-maps,xamarin,autocomplete,xamarin.forms,Google Maps,Xamarin,Autocomplete,Xamarin.forms,我正试图在Xamarin表单上为我的Xamarin表单映射添加一个自动完成服务到我的自定义搜索栏(我正在使用一个条目),但我一直无法这样做 我已经尝试过XLabs,但没有成功,到目前为止,我还没有找到任何其他解决方案 Xamarin.formsmap是否包含任何自动完成功能?或者Xamarin上已经有我可能缺少的自动完成功能了吗? 你给我推荐什么?如果您需要任何代码或其他信息,请告诉我。这是一个很长的代码,但这里有。。。。显然,您希望将服务调用代码放在服务类中,并将所有其他代码放在视图模型中。您
你给我推荐什么?如果您需要任何代码或其他信息,请告诉我。这是一个很长的代码,但这里有。。。。显然,您希望将服务调用代码放在服务
类中,并将所有其他代码放在视图模型中。您可能还希望在服务调用方法中或周围添加更多null和错误检查
我没有提到的一个重要部分是谷歌要求在执行搜索时显示谷歌徽标。因此,下载并将其添加到UI。我仅在用户关注条目时显示它
以下是我的位置模型和我自己的地址模型:
public class AddressInfo {
public string Address { get; set; }
public string City { get; set; }
public string State { get; set; }
public string ZipCode { get; set; }
public double Longitude { get; set; }
public double Latitude { get; set; }
}
public class PlacesMatchedSubstring {
[Newtonsoft.Json.JsonProperty("length")]
public int Length { get; set; }
[Newtonsoft.Json.JsonProperty("offset")]
public int Offset { get; set; }
}
public class PlacesTerm {
[Newtonsoft.Json.JsonProperty("offset")]
public int Offset { get; set; }
[Newtonsoft.Json.JsonProperty("value")]
public string Value { get; set; }
}
public class Prediction {
[Newtonsoft.Json.JsonProperty("id")]
public string Id { get; set; }
[Newtonsoft.Json.JsonProperty("description")]
public string Description { get; set; }
[Newtonsoft.Json.JsonProperty("matched_substrings")]
public List<PlacesMatchedSubstring> MatchedSubstrings { get; set; }
[Newtonsoft.Json.JsonProperty("place_id")]
public string PlaceId { get; set; }
[Newtonsoft.Json.JsonProperty("reference")]
public string Reference { get; set; }
[Newtonsoft.Json.JsonProperty("terms")]
public List<PlacesTerm> Terms { get; set; }
[Newtonsoft.Json.JsonProperty("types")]
public List<string> Types { get; set; }
}
public class PlacesLocationPredictions {
[Newtonsoft.Json.JsonProperty("predictions")]
public List<Prediction> Predictions { get; set; }
[Newtonsoft.Json.JsonProperty("status")]
public string Status { get; set; }
}
可能是@hvaughan3的复制品我已经看过了,但它是android的独家产品,所以这个问题没有答案。谢谢。这正是我需要的。如果我可以问一下,你是如何得到坐标的?您是否使用geocoder?@MauricioCárdenas坐标来自预测类?如果是,是的。我使用谷歌地理编码API。除了我使用服务调用的地理代码URL,并将响应反序列化为不同的模型之外,代码几乎相同。@hvaughan3是这样一行:wait ViewModel.GetAddressCoordinatesAsync();是否应该调用GetPlacesPredictionsAsync?@hvaughan3您是真正的MVPIn用户界面代码中有一个单词“Text”,它给出了一个错误“无法将'Xamarin.Forms.Xaml.ListNode'类型的对象强制转换为'Xamarin.Forms.Xaml.IElementNode'”哦,花了大约3小时才弄清楚为什么会出现这个错误!
public const string GooglePlacesApiAutoCompletePath = "https://maps.googleapis.com/maps/api/place/autocomplete/json?key={0}&input={1}&components=country:us"; //Adding country:us limits results to us
public const string GooglePlacesApiKey = "bTafrOPmO4LpPgAl34r5wQ6LFRWhgTxBW80-3GK";
private static HttpClient _httpClientInstance;
public static HttpClient HttpClientInstance => _httpClientInstance ?? (_httpClientInstance = new HttpClient());
private ObservableCollection<AddressInfo> _addresses;
public ObservableCollection<AddressInfo> Addresses {
get => _addresses ?? (_addresses = new ObservableCollection<AddressInfo>());
set {
if(_addresses != value) {
_addresses = value;
OnPropertyChanged();
}
};
}
private string _addressText;
public string AddressText {
get => _addressText;
set {
if(_addressText != value) {
_addressText = value;
OnPropertyChanged();
}
};
}
public async Task GetPlacesPredictionsAsync() {
// TODO: Add throttle logic, Google begins denying requests if too many are made in a short amount of time
CancellationToken cancellationToken = new CancellationTokenSource(TimeSpan.FromMinutes(2)).Token;
using(HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, string.Format(GooglePlacesApiAutoCompletePath, ConstantKeys.GooglePlacesApiKey, WebUtility.UrlEncode(_addressText)))) { //Be sure to UrlEncode the search term they enter
using(HttpResponseMessage message = await HttpClientInstance.SendAsync(request, HttpCompletionOption.ResponseContentRead, cancellationToken).ConfigureAwait(false)) {
if(message.IsSuccessStatusCode) {
string json = await message.Content.ReadAsStringAsync().ConfigureAwait(false);
PlacesLocationPredictions predictionList = await Task.Run(() => JsonConvert.DeserializeObject<PlacesLocationPredictions>(json)).ConfigureAwait(false);
if(predictionList.Status == "OK") {
Addresses.Clear();
if(predictionList.Predictions.Count > 0) {
foreach(Prediction prediction in predictionList.Predictions) {
Addresses.Add(new AddressInfo {
Address = prediction.Description
});
}
}
} else {
throw new Exception(predictionList.Status);
}
}
}
}
}
<Entry Text="{Binding AddressText}"
TextChanged="OnTextChanged" />
<ListView ItemsSource="{Binding Addresses}">
<ListView.ItemTemplate>
<DataTemplate>
<TextCell Text="{Binding Address}"/>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
private async void OnTextChanged(object sender, EventArgs eventArgs) {
if(!string.IsNullOrWhiteSpace(ViewModel.AddressText)) {
await ViewModel.GetPlacesPredictionsAsync();
}
}