所以我已经为我的地图应用程序实现了searchBar
,它给了我一些奇怪的结果。如果我搜索"奥斯陆"例如,它指向了一个位于城市北部的一个非常具体但奇怪的地方,并且远远地缩小了。在这里,我必须在代码中做错。有人能发现这个问题吗?
// When user submits search query
func searchBarSearchButtonClicked(searchBar: UISearchBar){
// resign first responder and dismiss the searchbar.
searchBar.resignFirstResponder()
dismissViewControllerAnimated(true, completion: nil)
// Create and start search request
localSearchRequest = MKLocalSearchRequest()
localSearchRequest.naturalLanguageQuery = searchBar.text
localSearch = MKLocalSearch(request: localSearchRequest)
localSearch.startWithCompletionHandler { (localSearchResponse, error) -> Void in
if localSearchResponse == nil{
let alertController = UIAlertController(title: nil, message: "Place Not Found", preferredStyle: UIAlertControllerStyle.Alert)
alertController.addAction(UIAlertAction(title: "Dismiss", style: UIAlertActionStyle.Default, handler: nil))
self.presentViewController(alertController, animated: true, completion: nil)
return
}
let center = CLLocationCoordinate2D(latitude: localSearchResponse!.boundingRegion.center.latitude, longitude: localSearchResponse!.boundingRegion.center.longitude)
self.updateCurrentMapRegion(center, distance: 5000)
NSNotificationCenter.defaultCenter().postNotificationName("LocationUpdate", object: nil, userInfo: ["latitude": center.latitude, "longitude": center.longitude])
}
}
另外,一个问题是我在获得搜索结果后更新地图区域时将距离硬编码为5000米。我怎样才能以更动态的方式处理这个问题?
什么是使用MKLocalSearchRequest()的替代品,在我看来,这听起来像是在寻找附近的东西时应该使用的东西,而不是像城市等更大的实体。
答案 0 :(得分:3)
首先要做的事情是:MKLocalSearch
是您使用的正确API,即使它对您正在做的事情听起来有点奇怪!
MKLocalSearch会为您提供一个位置列表,然后返回位置周围的边界框,以最符合您认为自己正在寻找的内容。我尝试运行你的代码并在奥斯陆找到了这个:
您遇到的问题是您使用边框的中心作为引脚位置,而不是奥斯陆地标。
所以代替你的代码行:
let center = CLLocationCoordinate2D(latitude: localSearchResponse!.boundingRegion.center.latitude,
longitude: localSearchResponse!.boundingRegion.center.longitude)
你会使用:
let center = localSearchResponse?.mapItems.first?.placemark.coordinate
(这是一个可选项,但您可以选择如何处理它。我会稍微向您展示我的首选方式。)
此外,这解决了您放大多远的问题。简单来说,您可以使用区域的边界框作为缩放级别。我不确定您的updateCurrentMapRegion:distance
方法是如何工作的,但MKMapView有一个方便的setRegion:animated
方法,您可以使用(如果您有权访问)。
mapView.setRegion(localSearchResponse!.boundingRegion, animated: true)
总结一下,如果你有一个MapView的引用,你应该可以用这个替换你的完成块并让它工作:
guard let localSearchResponse = localSearchResponse, mapItem = localSearchResponse.mapItems.first else {
let alertController = UIAlertController(title: nil, message: "Place Not Found", preferredStyle: UIAlertControllerStyle.Alert)
alertController.addAction(UIAlertAction(title: "Dismiss", style: UIAlertActionStyle.Default, handler: nil))
self.presentViewController(alertController, animated: true, completion: nil)
return
}
let center = mapItem.placemark.coordinate
self.mapView.setRegion(localSearchResponse.boundingRegion, animated: true)
NSNotificationCenter.defaultCenter().postNotificationName("LocationUpdate", object: nil, userInfo: ["latitude": center.latitude, "longitude": center.longitude])
在此块中,我还将if
语句替换为guard
以设置两个值,因此我们不再需要强制解包选项。如果您无法在此方法中访问mapView
,则可以切换updateCurrentMapRegion:center
以使其更适合,或者进行一些数学运算以使边界区域适合这些值。
答案 1 :(得分:-1)
您不应该使用MKLocalSearchRequest()而是使用MKLocalSearchCompleter,它可以提供更好的结果,并且可以在当前的Apple Maps中使用。
您可以在
中了解如何实现此操作
answer