Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/swift/17.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Swift 我的sender.tag返回零_Swift_Uibutton_Mkmapview_Mkannotation - Fatal编程技术网

Swift 我的sender.tag返回零

Swift 我的sender.tag返回零,swift,uibutton,mkmapview,mkannotation,Swift,Uibutton,Mkmapview,Mkannotation,我的注释上有两个按钮,一个用于导航,一个用于调用。但是当我单击按钮时,它根本不起作用,因为sender.tag返回nil。我在网上找不到如何正确设置批注的sender.tag func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? { if annotation is MKUserLocation {return nil} let

我的注释上有两个按钮,一个用于导航,一个用于调用。但是当我单击按钮时,它根本不起作用,因为sender.tag返回nil。我在网上找不到如何正确设置批注的sender.tag

 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


        let annotitle = annotation.title ?? ""
        let annosubtitle = annotation.subtitle ?? ""
        let title = annotitle ?? ""
        let phone = annosubtitle ?? ""
        let type = annotation.description
        let hostel = Hostel(location: annotation.coordinate, title: title, phone: phone, type: type)
        let hostelTag = hostelsHelper.getTagForHostel(hostel)

        if pinView == nil {
            pinView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: reuseId)
            pinView!.canShowCallout = true
            pinView!.animatesDrop = true
            pinView!.pinTintColor = UIColor.black
            let mapsButton = UIButton(frame: CGRect(origin: CGPoint.zero, size: CGSize(width: 30, height: 30)))
            mapsButton.setBackgroundImage(UIImage(named: "Maps-icon"), for: UIControlState())
            mapsButton.tag = hostelTag
            pinView!.leftCalloutAccessoryView = mapsButton
            pinView!.leftCalloutAccessoryView?.tintColor = UIColor.black
            mapsButton.addTarget(self, action: #selector (MapViewController.didClickRouteButton(sender: )), for: .touchUpInside)


            if !phone.isEmpty {
                let callButton = UIButton(frame: CGRect(origin: CGPoint.zero, size: CGSize(width: 30, height: 30)))
                callButton.setBackgroundImage(UIImage(named: "call icon round"), for: UIControlState())
                callButton.tag = hostelTag
                pinView!.rightCalloutAccessoryView = callButton
                pinView!.rightCalloutAccessoryView?.tintColor = UIColor.black
                callButton.addTarget(self, action: #selector (MapViewController.didClickCallButton(sender: )), for: .touchUpInside)
            }
            pinView!.sizeToFit()
        }
        else {
            pinView!.annotation = annotation
        }
        return pinView
    }

    // pinButton actions
    @objc func didClickRouteButton(sender: UIButton) {
        let placemark : MKPlacemark = MKPlacemark(coordinate: hostelsHelper.getLocationFor(sender.tag))
        let mapItem:MKMapItem = MKMapItem(placemark: placemark)
        mapItem.name = hostelsHelper.getTitleFor(sender.tag)
        mapItem.phoneNumber = hostelsHelper.getPhoneFor(sender.tag)
        let launchOptions:NSDictionary = NSDictionary(object: MKLaunchOptionsDirectionsModeDriving, forKey: MKLaunchOptionsDirectionsModeKey as NSCopying)
        let currentLocationMapItem:MKMapItem = MKMapItem.forCurrentLocation()
        MKMapItem.openMaps(with: [currentLocationMapItem, mapItem], launchOptions: launchOptions as? [String : Any])
        print ("Navigation to:\(hostelsHelper.getTitleFor(sender.tag))")
    }

    @objc func didClickCallButton(sender: UIButton) -> Void {

        if let url = URL(string: "tel://\(hostelsHelper.getPhoneFor(sender.tag))") {
            UIApplication.shared.open(url, options: [:])
        }
        print ("calling:\(hostelsHelper.getTitleFor(sender.tag))")
    }
如果有人能帮我,那太棒了

我的hostelHelper函数看起来是这样的:

import Foundation
import MapKit

struct Hostel {
    var location: CLLocationCoordinate2D
    var title: String
    var phone: String
    var type: String
}

extension Hostel: Equatable {}

func ==(lhs: Hostel, rhs: Hostel) -> Bool {
    return lhs.location.latitude == rhs.location.latitude && lhs.location.longitude == rhs.location.longitude && lhs.title == rhs.title && lhs.phone == rhs.phone && lhs.type == rhs.type
}

class HostelsHelper {

    private var hostels: [Hostel]

    init() {

        hostels = [Hostel]()

        if let cityDetailsPath = Bundle.main.path(forResource: "Hostels", ofType: "plist") {
            guard let cityDetails = NSArray(contentsOfFile: cityDetailsPath) as? [[String: String]] else {return}

            for city in cityDetails
            {
                guard let latStr = city["latitude"] else { continue }
                guard let lonStr = city["longitude"] else { continue }
                guard let titleStr = city["title"] else { continue }
                guard let phoneStr = city["subTitle"] else { continue }
                guard let typeStr = city["type"] else { continue }

                if let lat = Double(latStr) {
                    if let lon = Double(lonStr) {
                        let coordinate = CLLocationCoordinate2DMake(lat,lon)
                        hostels.append(Hostel(location: coordinate, title: titleStr, phone: phoneStr, type: typeStr))

                    }
                }
            }
        }
    }

    func getTagForHostel(_ hostel: Hostel) -> Int {
        return hostels.index(of: hostel ) ?? -1
    }

    func getHostelsCount() -> Int {
        return hostels.count
    }

    func getPhoneFor(_ tag: Int) -> String {
        return tag != -1 ? hostels[tag].phone : ""
    }

    func getTypeFor(_ tag: Int) -> String {
        return tag != -1 ? hostels[tag].type : ""
    }

    func getTitleFor(_ tag: Int) -> String {
        return tag != -1 ? hostels[tag].title : ""
    }

    func getLocationFor(_ tag: Int) -> CLLocationCoordinate2D {
        return tag != -1 ? hostels[tag].location : kCLLocationCoordinate2DInvalid
    }
}

而hotels是从.plist加载的,这是因为注释被加载到地图中

,以便将标签设置为
ui按钮
需要以下步骤

在我的例子中,我正在
viewDidLoad()
中为我的按钮设置标记,您可以在任何地方设置它

@IBOutlet weak var btnAgenda: UIButton!

 override func viewDidLoad() {
        super.viewDidLoad()

        btnAgenda.tag = 5
    // Do any additional setup after loading the view.

    }

@IBAction func btnAgendaClicked(_ sender: UIButton) {
        print(sender.tag) // 5
    }
输出:

if let hostelTag = hostelsHelper.getTagForHostel(hostel){
   mapsButton.tag = hostelTag as? Int
}

在完成上述所有步骤后,确认您的产品线:

let hostelTag = hostelsHelper.getTagForHostel(hostel)
print(hostelTag)
您将获得一个
Int
值,如果不符合,则将其转换为正确的格式。我猜它将是nil,所以没有标记传递给按钮,您将得到nil作为输出

以后要养成这样检查空条件的习惯:

if let hostelTag = hostelsHelper.getTagForHostel(hostel){
   mapsButton.tag = hostelTag as? Int
}
这将阻止您为其指定nil


希望这有帮助。

您能告诉我您是如何设置“hostelTag”的吗?让hostelTag=hostelsHelper.getTagForHostel(hostel)。你能解释一下吗?我更新了描述