如何将按钮添加到 Swift 中的 MKPointAnnotation
How do I add button to MKPointAnnotation in Swift
我想添加一个按钮,当用户点击标记时,该按钮将出现在注释的右侧。这是我目前正在做的事情。
- 从我的网站下载 json 文件。
- 打开文件并解析它。
- 使用 json 文件
中的坐标绘制所有标记
- 但是现在..如何在我的注释右侧添加一个按钮,当用户点击它时会移动到 detailViewController?
这是我的 ViewDidLoad
//Retrieve the existing JSON from document directory
let defaults = UserDefaults.standard
let fileUrl = defaults.url(forKey: "pathForJSON")
do {
let jsonData = try Data(contentsOf: fileUrl!, options: [])
let myJson = try JSONSerialization.jsonObject(with: jsonData, options: .mutableContainers) as! [Dictionary<String,AnyObject>]
// print out the content
// print("My JSON: ", myJson)
createAnnotation(locations: myJson)
} catch {
print(error)
}
我的 createAnnotation 函数。
func createAnnotation(locations: [Dictionary<String, AnyObject>]) {
for location in locations {
let annotation = MKPointAnnotation()
annotation.title = location["name"] as? String
let lat = (location["latitude"] as! NSString).doubleValue
let lon = (location["longitude"] as! NSString).doubleValue
annotation.coordinate = CLLocationCoordinate2D(latitude: lat, longitude: lon)
mapView.addAnnotation(annotation)
// print(annotation)
}
}
试试下面的代码
func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
if annotation is MKUserLocation {
return nil
}
let reuseId = "pin"
var pinView = mapView.dequeueReusableAnnotationView(withIdentifier: reuseId) as? MKPinAnnotationView
if pinView == nil {
pinView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: reuseId)
pinView?.canShowCallout = true
let rightButton: AnyObject! = UIButton(type: UIButton.ButtonType.detailDisclosure)
pinView?.rightCalloutAccessoryView = rightButton as? UIView
}
else {
pinView?.annotation = annotation
}
return pinView
}
不要忘记设置 mapView 的委托
mapView.delegate = self
顺便说一下,如果目标是 iOS 11 或更高版本,您可以进一步简化它,特别是:
完全删除你的mapView(_:viewFor:)
;
注册默认注释视图class;
定义注释视图class,根据需要配置注释及其标注。
例如:
class CustomAnnotationView: MKPinAnnotationView {
override init(annotation: MKAnnotation?, reuseIdentifier: String?) {
super.init(annotation: annotation, reuseIdentifier: reuseIdentifier)
canShowCallout = true
rightCalloutAccessoryView = UIButton(type: .detailDisclosure)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
并且,在您的视图控制器中:
override func viewDidLoad() {
super.viewDidLoad()
mapView.register(CustomAnnotationView.self, forAnnotationViewWithReuseIdentifier: MKMapViewDefaultAnnotationViewReuseIdentifier)
}
我想添加一个按钮,当用户点击标记时,该按钮将出现在注释的右侧。这是我目前正在做的事情。
- 从我的网站下载 json 文件。
- 打开文件并解析它。
- 使用 json 文件 中的坐标绘制所有标记
- 但是现在..如何在我的注释右侧添加一个按钮,当用户点击它时会移动到 detailViewController?
这是我的 ViewDidLoad
//Retrieve the existing JSON from document directory
let defaults = UserDefaults.standard
let fileUrl = defaults.url(forKey: "pathForJSON")
do {
let jsonData = try Data(contentsOf: fileUrl!, options: [])
let myJson = try JSONSerialization.jsonObject(with: jsonData, options: .mutableContainers) as! [Dictionary<String,AnyObject>]
// print out the content
// print("My JSON: ", myJson)
createAnnotation(locations: myJson)
} catch {
print(error)
}
我的 createAnnotation 函数。
func createAnnotation(locations: [Dictionary<String, AnyObject>]) {
for location in locations {
let annotation = MKPointAnnotation()
annotation.title = location["name"] as? String
let lat = (location["latitude"] as! NSString).doubleValue
let lon = (location["longitude"] as! NSString).doubleValue
annotation.coordinate = CLLocationCoordinate2D(latitude: lat, longitude: lon)
mapView.addAnnotation(annotation)
// print(annotation)
}
}
试试下面的代码
func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
if annotation is MKUserLocation {
return nil
}
let reuseId = "pin"
var pinView = mapView.dequeueReusableAnnotationView(withIdentifier: reuseId) as? MKPinAnnotationView
if pinView == nil {
pinView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: reuseId)
pinView?.canShowCallout = true
let rightButton: AnyObject! = UIButton(type: UIButton.ButtonType.detailDisclosure)
pinView?.rightCalloutAccessoryView = rightButton as? UIView
}
else {
pinView?.annotation = annotation
}
return pinView
}
不要忘记设置 mapView 的委托
mapView.delegate = self
顺便说一下,如果目标是 iOS 11 或更高版本,您可以进一步简化它,特别是:
完全删除你的
mapView(_:viewFor:)
;注册默认注释视图class;
定义注释视图class,根据需要配置注释及其标注。
例如:
class CustomAnnotationView: MKPinAnnotationView {
override init(annotation: MKAnnotation?, reuseIdentifier: String?) {
super.init(annotation: annotation, reuseIdentifier: reuseIdentifier)
canShowCallout = true
rightCalloutAccessoryView = UIButton(type: .detailDisclosure)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
并且,在您的视图控制器中:
override func viewDidLoad() {
super.viewDidLoad()
mapView.register(CustomAnnotationView.self, forAnnotationViewWithReuseIdentifier: MKMapViewDefaultAnnotationViewReuseIdentifier)
}