代码之家  ›  专栏  ›  技术社区  ›  Adrian Le Roy Devezin

在MapView for SwiftUI中检测longpress

  •  0
  • Adrian Le Roy Devezin  · 技术社区  · 5 年前

    我在SwiftUi中有一个地图视图,当用户长按地图上的某个位置时,我试图在其中添加一个pin注释。我看到这可以很容易地在swift中完成,但我使用的是SwiftUI。我不知道如何添加长压力检测器。一个代码示例会很好。

    struct MapView: UIViewRepresentable {
    
    @Binding
    var annotations: [PinAnnotation]
    let addAnnotationListener: (PinAnnotation) -> Void
    
    func makeUIView(context: Context) -> MKMapView {
        let mapView = MKMapView()
        mapView.delegate = context.coordinator
        return mapView
    }
    
    func updateUIView(_ view: MKMapView, context: Context) {
        view.delegate = context.coordinator
        view.addAnnotations(annotations)
        if annotations.count == 1 {
            let coords = annotations.first!.coordinate
            let region = MKCoordinateRegion(center: coords, span: MKCoordinateSpan(latitudeDelta: 0.1, longitudeDelta: 0.1))
            view.setRegion(region, animated: true)
        }
    
    }
    
    
    func makeCoordinator() -> MapViewCoordinator {
        MapViewCoordinator(self)
    }
    

    }

    class MapViewCoordinator: NSObject, MKMapViewDelegate {
    
    var mapViewController: MapView
    
    init(_ control: MapView) {
        self.mapViewController = control
    }
    
    func mapView(_ mapView: MKMapView, annotationView view: MKAnnotationView, calloutAccessoryControlTapped control: UIControl) {
        let annotation = view.annotation
        guard let placemark = annotation as? MKPointAnnotation else { return }
    }
    
    func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView?{
        //Custom View for Annotation
        let identifier = "Placemark"
        if  let annotationView = mapView.dequeueReusableAnnotationView(withIdentifier: identifier) {
            annotationView.annotation = annotation
            return annotationView
        } else {
            let annotationView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: identifier)
            annotationView.isEnabled = true
            annotationView.canShowCallout = true
            let button = UIButton(type: .infoDark)
            annotationView.rightCalloutAccessoryView = button
            return annotationView
        }
    }
    }
    

    将接点添加到地图视图的方法

        func addPinBasedOnGesture(gestureRecognizer:UIGestureRecognizer){
            var touchPoint = gestureRecognizer.locationInView(mapView)
            var newCoordinates = self.convertPoint(touchPoint, toCoordinateFromView: mapView)
            let annotation = MKPointAnnotation()
            annotation.coordinate = newCoordinates
            mapView.addAnnotation(annotation)
        }
    
    0 回复  |  直到 5 年前
        1
  •  4
  •   user832    5 年前

    下面的解决方案在用户长按地图的位置添加一个pin。

    在中添加以下方法 MapViewCoordinator

    @objc func addPinBasedOnGesture(_ gestureRecognizer:UIGestureRecognizer) {
        let touchPoint = gestureRecognizer.location(in: gestureRecognizer.view)
        let newCoordinates = (gestureRecognizer.view as? MKMapView)?.convert(touchPoint, toCoordinateFrom: gestureRecognizer.view)
        let annotation = PinAnnotation()
        guard let _newCoordinates = newCoordinates else { return }
        annotation.coordinate = _newCoordinates
        mapViewController.annotations.append(annotation)
    }
    

    func makeUIView(context: Context) -> MKMapView {}

        func makeUIView(context: Context) -> MKMapView {
        let mapView = MKMapView()
        mapView.delegate = context.coordinator
        let longPressed = UILongPressGestureRecognizer(target: context.coordinator,
                                                       action: #selector(context.coordinator.addPinBasedOnGesture(_:)))
        mapView.addGestureRecognizer(longPressed)
        return mapView
    }
    
        2
  •  0
  •   Asperi    5 年前

    查找所提供代码的以下修改部分,以获得所需的行为:

    struct SUMapView: UIViewRepresentable {
    
        // ... other your code here
    
        func makeUIView(context: Context) -> MKMapView {
            let mapView = MKMapView()
            mapView.delegate = context.coordinator
    
            let longPressed = UILongPressGestureRecognizer(target: 
                  context.coordinator, action: #selector(addPin(gesture:)))
            mapView.addGestureRecognizer(longPressed)
    
            return mapView
        }
    
        // ... other your code here
    }
    
    class MapViewCoordinator: NSObject, MKMapViewDelegate {
    
        // ... other your code here
    
        @objc func addPin(gesture: UILongPressGestureRecognizer) {
            // do whatever needed here
        }
    
        // ... other your code here
    
    }