Ios 如何检测在Swift和更新缩放中移动的地图视图
我正在尝试在Swift 2中设置地图的最小缩放级别。我找不到任何关于如何限制地图被放大太远的文档。我决定尝试监视地图的移动(如拖动或缩放),然后将Ios 如何检测在Swift和更新缩放中移动的地图视图,ios,swift,mkmapview,Ios,Swift,Mkmapview,我正在尝试在Swift 2中设置地图的最小缩放级别。我找不到任何关于如何限制地图被放大太远的文档。我决定尝试监视地图的移动(如拖动或缩放),然后将MKZoomScale设置回最小值 我找到的大部分关于regionDidChangeAnimated的答案都是在Objective C中,我不知道,我很难将它们转换成Swift 我尝试实现@hEADcRASH的答案:,但当地图在模拟器中移动时,它不会触发并向控制台打印任何内容 谁能告诉我我做错了什么?我是Swift新手,所以这可能是个小错误。另外,请告
MKZoomScale
设置回最小值
我找到的大部分关于regionDidChangeAnimated
的答案都是在Objective C中,我不知道,我很难将它们转换成Swift
我尝试实现@hEADcRASH的答案:,但当地图在模拟器中移动时,它不会触发并向控制台打印任何内容
谁能告诉我我做错了什么?我是Swift新手,所以这可能是个小错误。另外,请告诉我是否有一种轻量级方法可以解决限制地图缩放级别的问题。我担心“运动监视器”会使贴图动画的速度减慢一点。谢谢你的帮助
这是我的视图控制器。
导入UIKit
导入解析
导入地图套件
class SearchRadiusViewController: UIViewController, CLLocationManagerDelegate, MKMapViewDelegate {
@IBOutlet weak var map: MKMapView!
@IBOutlet weak var menuBtn: UIBarButtonItem!
var locationManager = CLLocationManager()
override func viewDidLoad() {
super.viewDidLoad()
//menu button control
if self.revealViewController() != nil {
menuBtn.target = self.revealViewController()
menuBtn.action = "revealToggle:"
self.view.addGestureRecognizer(self.revealViewController().panGestureRecognizer())
}
//user location
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.requestWhenInUseAuthorization()
locationManager.startUpdatingLocation()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func locationManager(manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
//set map
let location:CLLocationCoordinate2D = manager.location!.coordinate
let latitude = location.latitude
let longitude = location.longitude
let latDelta:CLLocationDegrees = 0.1
let longDelta:CLLocationDegrees = 0.1
let span:MKCoordinateSpan = MKCoordinateSpanMake(latDelta, longDelta)
let maplocation:CLLocationCoordinate2D = CLLocationCoordinate2DMake(latitude, longitude)
let region:MKCoordinateRegion = MKCoordinateRegionMake(maplocation, span)
map.setRegion(region, animated: true)
//stop updating location, only need user location once to position map.
manager.stopUpdatingLocation()
}
//Attempt to monitor for map movement based on hEADcRASH's answer.
private var mapChangedFromUserInteraction = false
private func mapViewRegionDidChangeFromUserInteraction() -> Bool {
let view = self.map.subviews[0]
// Look through gesture recognizers to determine whether this region change is from user interaction
if let gestureRecognizers = view.gestureRecognizers {
for recognizer in gestureRecognizers {
if( recognizer.state == UIGestureRecognizerState.Began || recognizer.state == UIGestureRecognizerState.Ended ) {
return true
}
}
}
return false
}
func mapView(mapView: MKMapView, regionWillChangeAnimated animated: Bool) {
print("yes")
mapChangedFromUserInteraction = mapViewRegionDidChangeFromUserInteraction()
if (mapChangedFromUserInteraction) {
// user changed map region
print("user changed map in WILL")
}
}
func mapView(mapView: MKMapView, regionDidChangeAnimated animated: Bool) {
print("yes ddd")
if (mapChangedFromUserInteraction) {
// user changed map region
print("user changed map in Did")
}
}
}
在回顾并结合了许多其他问题/答案以及@lorenzoliveto的帮助后,我已经在Swift中使用了它。如果有更好/更轻量级的方法来实现同样的目标,请留下评论 我在viewDidLoad函数中添加了
self.map.delegate=self
下面是我如何监控地图移动的代码,当用户放大“太远”且地图宽度小于2英里时,我使用mapView.setRegion
缩小地图
private var mapChangedFromUserInteraction = false
private func mapViewRegionDidChangeFromUserInteraction() -> Bool {
let view = self.map.subviews[0]
// Look through gesture recognizers to determine whether this region change is from user interaction
if let gestureRecognizers = view.gestureRecognizers {
for recognizer in gestureRecognizers {
if( recognizer.state == UIGestureRecognizerState.Began || recognizer.state == UIGestureRecognizerState.Ended ) {
return true
}
}
}
return false
}
func mapView(mapView: MKMapView, regionWillChangeAnimated animated: Bool) {
mapChangedFromUserInteraction = mapViewRegionDidChangeFromUserInteraction()
if (mapChangedFromUserInteraction) {
// user will change map region
print("user WILL change map.")
// calculate the width of the map in miles.
let mRect: MKMapRect = mapView.visibleMapRect
let eastMapPoint = MKMapPointMake(MKMapRectGetMinX(mRect), MKMapRectGetMidY(mRect))
let westMapPoint = MKMapPointMake(MKMapRectGetMaxX(mRect), MKMapRectGetMidY(mRect))
let currentDistWideInMeters = MKMetersBetweenMapPoints(eastMapPoint, westMapPoint)
let milesWide = currentDistWideInMeters / 1609.34 // number of meters in a mile
print(milesWide)
print("^miles wide")
// check if user zoomed in too far and zoom them out.
if milesWide < 2.0 {
var region:MKCoordinateRegion = mapView.region
var span:MKCoordinateSpan = mapView.region.span
span.latitudeDelta = 0.04
span.longitudeDelta = 0.04
region.span = span;
mapView.setRegion(region, animated: true)
print("map zoomed back out")
}
}
}
func mapView(mapView: MKMapView, regionDidChangeAnimated animated: Bool) {
if (mapChangedFromUserInteraction) {
// user changed map region
print("user CHANGED map.")
print(mapView.region.span.latitudeDelta)
print(mapView.region.span.longitudeDelta)
// calculate the width of the map in miles.
let mRect: MKMapRect = mapView.visibleMapRect
let eastMapPoint = MKMapPointMake(MKMapRectGetMinX(mRect), MKMapRectGetMidY(mRect))
let westMapPoint = MKMapPointMake(MKMapRectGetMaxX(mRect), MKMapRectGetMidY(mRect))
let currentDistWideInMeters = MKMetersBetweenMapPoints(eastMapPoint, westMapPoint)
let milesWide = currentDistWideInMeters / 1609.34 // number of meters in a mile
print(milesWide)
print("^miles wide")
// check if user zoomed in too far and zoom them out.
if milesWide < 2.0 {
var region:MKCoordinateRegion = mapView.region
var span:MKCoordinateSpan = mapView.region.span
span.latitudeDelta = 0.04
span.longitudeDelta = 0.04
region.span = span;
mapView.setRegion(region, animated: true)
print("map zoomed back out")
}
}
是否在情节提要中设置地图视图的代理?如果没有,您应该在viewDidLoad方法中添加self.map.delegate=self。谢谢@lorenzoliveto,将
self.map.delegate=self
添加到viewDidLoad中是可行的。mapViewRegionDidChangeAnimated正在工作!您对设置最大缩放级别的最佳方法有何看法?我是否应该观察地图移动/缩放并重置地图缩放?是的,我认为这是您唯一的选择。regionWillChangeAnimated:在滚动期间调用多次,RegionIDChangeAnimated:仅在滚动后调用一次。尝试在两者中添加重置代码,看看性能是如何受到影响的。我正在寻找如何检测映射更改,发现了这个问题。似乎我只需要func mapViewRegionDidChangeFromUserInteraction()
谢谢分享!
dispatch_async(dispatch_get_main_queue(), {
var region:MKCoordinateRegion = mapView.region
var span:MKCoordinateSpan = mapView.region.span
span.latitudeDelta = 0.04
span.longitudeDelta = 0.04
region.span = span;
mapView.setRegion(region, animated: true)
print("map zoomed back out")
})