【问题标题】:Swift 2 MapKit Annotations - How to group annotations?Swift 2 MapKit Annotations - 如何对注释进行分组?
【发布时间】:2016-02-13 21:14:24
【问题描述】:

我的地图中有近 8000 个注释,我想根据用户在应用中的缩放比例对它们进行分组。

所有的经纬度都已经作为 Double 进入 CoreData。

如果我在同一点有两个不同的注释图像,我想展示两组,一组是十字架,一组是心脏。

当用户单击注释并且此注释是分组注释时,我想向用户显示此位置有多少注释,“强制”用户放大以单独查看注释。

下面是我的应用程序的图片和当前的注释。

谢谢!

【问题讨论】:

    标签: ios swift annotations mapkit latitude-longitude


    【解决方案1】:

    我已经拿到了。

    var zoomLevel = Double()
    var iphoneScaleFactorLatitude = Double()
    var iphoneScaleFactorLongitude = Double()
    var CanUpdateMap: Bool = false
    
    static func getLatitudeLongitudeLimitsFromMap(mapView: MKMapView) -> [String: Double] {
        var coord = [String: Double]()
    
        let MinLat: Double = mapView.region.center.latitude - (mapView.region.span.latitudeDelta / 2)
        let MaxLat: Double = mapView.region.center.latitude + (mapView.region.span.latitudeDelta / 2)
        let MinLon: Double = mapView.region.center.longitude - (mapView.region.span.longitudeDelta / 2)
        let MaxLon: Double = mapView.region.center.longitude + (mapView.region.span.longitudeDelta / 2)
    
        coord["MinLat"] = MinLat
        coord["MaxLat"] = MaxLat
        coord["MinLon"] = MinLon
        coord["MaxLon"] = MaxLon
    
        return coord
    }
    
    func LoadMap(mapView: MKMapView) {
        // Get the limits after move or resize the map
        let coord: [String: Double] = getLatitudeLongitudeLimitsFromMap(mapView)
        let MinLat: Double = coord["MinLat"]! as Double
        let MaxLat: Double = coord["MaxLat"]! as Double
        let MinLon: Double = coord["MinLon"]! as Double
        let MaxLon: Double = coord["MaxLon"]! as Double
        var arrAnnotations = [MKAnnotation]()
    
        let FilterMinLat = arrDicListPinsWithLatitudeLongitude.filter({
            if let item = $0["Latitude"] as? Double {
                return item > MinLat
            } else {
                return false
            }
        })
        let FilterMaxLat = FilterMinLat.filter({
            if let item = $0["Latitude"] as? Double {
                return item < MaxLat
            } else {
                return false
            }
        })
        let FilterMinLon = FilterMaxLat.filter({
            if let item = $0["Longitude"] as? Double {
                return item > MinLon
            } else {
                return false
            }
        })
        let FilterMaxLon = FilterMinLon.filter({
            if let item = $0["Longitude"] as? Double {
                return item < MaxLon
            } else {
                return false
            }
        })
    
        for Item in FilterMaxLon {
            let dic:[String:AnyObject] = Item
            var Name = String()
            var Address = String()
            var IconPNG = String()
    
            if let Latitude = dic["Latitude"] as? Double {
                if let Longitude = dic["Longitude"] as? Double {
    
                        if let item = dic["Name"] {
                            Name = item as! String
                        }
                        if let item = dic["Address"] {
                            Address = item as! String
                        }
    
                        if let item = dic["TypeID"] as? Int {
                            if item == 11 {
                                IconPNG = "icon-cross.png"
                            } else {
                                IconPNG = "icon-heart.png"
                            }
                        }
                        arrAnnotations.append(CreateAnnotation(Address, Title: Name, Latitude: Latitude, Longitude: Longitude, IconPNG: IconPNG))
                    }
                }
            }
        }
    
        // Show in the map only the annotations from that specific region
        iphoneScaleFactorLatitude = mapView.region.center.latitude
        iphoneScaleFactorLongitude = mapView.region.center.longitude
    
        if zoomLevel != mapView.region.span.longitudeDelta {
            filterAnnotations(arrAnnotations)
    
            zoomLevel = mapView.region.span.longitudeDelta
    
            CanUpdateMap = true
        }
    }
    
    func filterAnnotations(arrAnnotations: [MKAnnotation]) {
        let latDelta: Double = 0.04 / iphoneScaleFactorLatitude
        let lonDelta: Double = 0.04 / iphoneScaleFactorLongitude
        var shopsToShow = [AnyObject]()
        var arrAnnotationsNew = [MKAnnotation]()
    
        for var i = 0; i < arrAnnotations.count; i++ {
            let checkingLocation: MKAnnotation = arrAnnotations[i]
            let latitude: Double = checkingLocation.coordinate.latitude
            let longitude: Double = checkingLocation.coordinate.longitude
            var found: Bool = false
    
            for tempPlacemark: MKAnnotation in shopsToShow as! [MKAnnotation] {
                if fabs(tempPlacemark.coordinate.latitude - latitude) < fabs(latDelta) && fabs(tempPlacemark.coordinate.longitude - longitude) < fabs(lonDelta) {
                    found = true
                }
            }
    
            if !found {
                shopsToShow.append(checkingLocation)
                arrAnnotationsNew.append(checkingLocation)
            }
        }
    
        // Clean the map
        for item: MKAnnotation in self.mapRedes.annotations {
            myMap.removeAnnotation(item)
        }
    
        // Add new annotations to the map
        for item: MKAnnotation in arrAnnotationsNew {
            myMap.addAnnotation(item)
        }
    }
    
    func mapView(mapView: MKMapView, regionDidChangeAnimated animated: Bool) {
        // This validation should be added, because it will find all the annotations before the map resize
        if CanUpdateMap == true {
            LoadMap(mapView)
        }
    }
    

    【讨论】:

      【解决方案2】:

      只是对我的代码的更正:

      //....
      
      func LoadMap(mapView: MKMapView) {
          //....
      
          // Show in the map only the annotations from that specific region
          iphoneScaleFactorLatitude = Double(mapView.bounds.size.width / 30) // 30 = width of the annotation
          iphoneScaleFactorLongitude = Double(mapView.bounds.size.height / 30) // 30 = height of the annotation
      
          //....
      }
      
      func filterAnnotations(mapView: MKMapView, arrAnnotations: [MKAnnotation]) {
          let latDelta: Double = mapView.region.span.longitudeDelta / iphoneScaleFactorLatitude
          let lonDelta: Double = mapView.region.span.longitudeDelta / iphoneScaleFactorLongitude
      
          //....
      }
      
      //....
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-07-09
        • 2020-07-19
        • 2021-01-27
        • 1970-01-01
        相关资源
        最近更新 更多