更新MapView接点位置



所以我有一个MapView,它在当前用户位置添加了一个pin。此外,我有两个文本字段,显示引脚的坐标。我想添加两个功能:

  1. 当我拖放引脚时,我想更新文本字段内的坐标。

  2. 当我编辑文本字段中的坐标时,它应该将引脚移动到文本字段中更新的坐标。

这里是我的代码,我在这里处理MapView的一切。我对编码还很陌生,所以代码可能会让人困惑,很抱歉。

class LocateVC: UIViewController, CLLocationManagerDelegate, MKMapViewDelegate {
@IBOutlet weak var mapView: MKMapView!
@IBOutlet weak var finishedLocateButton: UIButton!
@IBOutlet weak var relocateButton: UIButton!
var coordinates: [[Double]]!
var latTitleLabel:[String]!
var latValueLabel:[String]!
var lngTitleLabel:[String]!
var lngValueLabel: [String]!
var isEdited = false
var customCallout: UIView?
//Important to track location
let locationManager = CLLocationManager()

override func viewDidLoad() {
super.viewDidLoad()
view.layer.backgroundColor = Colors.grey.cgColor
//button titles
relocateButton.isHidden = true
relocateButton.setTitle("Relocate", for: .normal)
finishedLocateButton.setTitle("Continue", for: .normal)
navigationItem.title = "Location"
// Ask for Authorisation from the User.
self.locationManager.requestAlwaysAuthorization()
self.locationManager.requestWhenInUseAuthorization()
locationManager.delegate = self
self.mapView.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters
if isEdited == false {
if CLLocationManager.locationServicesEnabled() {
addPin()
}
}
// Latitude,Longitude
coordinates = [
[ProductData.shared.latitude!, ProductData.shared.longitude!],
]
} //end of viewDidLoad
override func viewWillAppear(_ animated: Bool) {
super.dismiss(animated: animated)
}

public func removePin() {

}
func dropPinFor(placemark: MKPlacemark) {
for annotation in mapView.annotations {
if annotation.isKind(of: MKPointAnnotation.self) {
// mapView.removeAnnotation(annotation) // removing the pins from the map
}
}
let annotation = MKPointAnnotation()
annotation.coordinate = placemark.coordinate
mapView.addAnnotation(annotation)
}
//1
public func addPin() {
if isEdited == false {
ProductData.shared.latitude = locationManager.location?.coordinate.latitude
ProductData.shared.longitude = locationManager.location?.coordinate.longitude
}
self.mapView.delegate = self
// adds an annotation to coordinates from productData
let point = ProductAnnotation(coordinate: CLLocationCoordinate2D(latitude: ProductData.shared.latitude! , longitude: ProductData.shared.longitude!))
self.mapView.addAnnotation(point)
// 3
let region = MKCoordinateRegion(center: CLLocationCoordinate2D(latitude: ProductData.shared.latitude!, longitude: ProductData.shared.longitude!), span: MKCoordinateSpan(latitudeDelta: 0.1, longitudeDelta: 0.1))
self.mapView.setRegion(region, animated: true)
}
public func editCoord() {
performSegue(withIdentifier: "editCoord", sender: CustomCalloutView.self)
}
@IBAction func relocateButtonClicked(_ sender: Any) {
addPin()
}
@IBAction func finishedLocateButtonClicked(_ sender: Any) {
performSegue(withIdentifier: "finishedLocateSegue2", sender: self)
}
//4
func mapView(_ mapView: MKMapView, didDeselect view: MKAnnotationView) {
if view.isKind(of: CustomCalloutView.self ) || view.isKind(of: AnnotationView.self) || view.isKind(of: ProductAnnotation.self) {
return
} else {
customCallout?.removeFromSuperview()
}
}
//3
func mapView(_ mapView: MKMapView, didSelect view: MKAnnotationView) {
if view.annotation is MKUserLocation {
return
}
//this creates the callout
let views = Bundle.main.loadNibNamed("CustomCalloutView", owner: nil, options: nil)
let calloutView =  views?[0] as! CustomCalloutView
calloutView.delegate = self
calloutView.lngTitleLabel.text = "Lng"
calloutView.latTitleLabel.text = "Lat"
calloutView.lngTextField.text = String(format:"%f", ProductData.shared.longitude!)
calloutView.latTextField.text = String(format:"%f", ProductData.shared.latitude!)
calloutView.latTextField.layer.borderWidth = 0.0
calloutView.lngTextField.layer.borderWidth = 0.0
calloutView.latTextField.isEnabled = false
calloutView.lngTextField.isEnabled = false
calloutView.latTextField.keyboardType = .numberPad
calloutView.lngTextField.keyboardType = .numberPad
calloutView.alpha = 1.0
calloutView.layer.cornerRadius = 8
calloutView.center = CGPoint(x: view.bounds.size.width / 2, y: -calloutView.bounds.size.height*0.52)
customCallout = calloutView
view.addSubview(calloutView)
mapView.setCenter((view.annotation?.coordinate)!, animated: true)
}

//2
func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
if annotation is MKUserLocation {
return nil
}
var annotationView = self.mapView.dequeueReusableAnnotationView(withIdentifier: "Pin")
if annotationView == nil{
annotationView = AnnotationView(annotation: annotation, reuseIdentifier: "Pin")
annotationView?.isDraggable = true
annotationView?.canShowCallout = false
} else {
annotationView?.annotation = annotation
}
annotationView?.image = UIImage(named: "dot")
return annotationView
}
func saveButtonTapped() {
customCallout?.removeFromSuperview()
}
}

extension LocateVC: CustomCalloutViewDelegate {
func didClickEditButton() {
editCoord()
}
func didClickSaveButton() {
saveButtonTapped()
}
}

这里是我的自定义标注:

class CustomCalloutView: UIView {
@IBOutlet weak var latTitleLabel: UILabel!
@IBOutlet weak var lngTitleLabel: UILabel!
@IBOutlet weak var editButton: UIButton!
@IBOutlet weak var saveButton: UIButton!
@IBOutlet weak var latTextField: UITextField!
@IBOutlet weak var lngTextField: UITextField!
var delegate: CustomCalloutViewDelegate?
var isEditing: Bool = false
@IBAction func didClickEditButton(_ sender: Any) {
//        delegate?.didClickEditButton()

isEditing = true

latTextField.layer.borderWidth = 1.0
lngTextField.layer.borderWidth = 1.0
latTextField.isEnabled = true
lngTextField.isEnabled = true
saveButton.isHidden = false
}
@IBAction func saveButtonTapped(_ sender: Any) {
if isEditing == true {
if let lat = latTextField.text {
ProductData.shared.latitude = Double(lat)
}
if let lng = lngTextField.text {
ProductData.shared.longitude = Double(lng)
}
latTextField.layer.borderWidth = 0.0
lngTextField.layer.borderWidth = 0.0
latTextField.isEnabled = false
lngTextField.isEnabled = false
self.saveButton.setTitle("Save", for: .normal)
isEditing = false
} else {
self.saveButton.setTitle("Cancel", for: .normal)
delegate?.didClickSaveButton()
}
}
override func point(inside point: CGPoint, with event: UIEvent?) -> Bool {
if self.bounds.contains(point) {
return true
} else {
return self.subviews.contains { $0.frame.contains(point) }
}
}
}
protocol CustomCalloutViewDelegate {
func didClickEditButton()
func didClickSaveButton()
}

知道我该怎么做到吗?也许在一般情况下。

提前感谢

这里有一个到DSCenterPinMapView的链接。我建议你使用CocoaPod。

它是一个自定义MapView,具有一个动画和可自定义的中心销,可用于选择地图中的位置。

如果你是新手,这里还有一个安装CocoaPods的指南。

你应该安装Pod,然后,作为你的问题的解决方案:

  1. 实现委托,以便您可以获得引脚掉落的位置
pinMapView.delegate = self
extension MyViewController: DSCenterPinMapViewDelegate {
func didStartDragging() {
// My custom actions
}
func didEndDragging() {
// My custom actions
selectedLocation = pinMapView.mapview.centerCoordinate
// Update Text field
}
}
  1. 在TextFields上添加完坐标后,您应该调用
pinMapView.center(on coordinate: myTextFieldCoordinate)

以将地图集中在所需位置。

更改标记位置后,获取类似的坐标

let latitude = marker.coordinate.latitude
let longitude = marker.coordinate.longitude

并设置坐标

let coordinate = CLLocationCoordinate2D(latitude: "your lat", longitude: "your long")
marker.coordinate = coordinate
mapView.setCenter(coordinate, animated: true)

如果你没有保留标记参考,那么

guard let marker = self.appleMap.annotations.first else {return}
let latitude = marker.coordinate.latitude
let longitude = marker.coordinate.longitude

并设置坐标

guard let marker = self.appleMap.annotations.first else {return}
let coordinate = CLLocationCoordinate2D(latitude: "your lat", longitude: "your long")
marker.coordinate = coordinate
mapView.setCenter(coordinate, animated: true)

希望这会有所帮助。

最新更新