【问题标题】:Custom Delegate Filter VC Swift5自定义委托过滤器 VC Swift5
【发布时间】:2019-12-01 10:57:02
【问题描述】:

我正在向我的应用程序添加一个自定义委托,但由于某种原因,它无法正常工作。 我的应用程序有一张地图,其中显示了不同公司类型的几个标记。还有一个按钮,一旦按下,就会带我到另一个视图控制器,用户可以在其中输入一些过滤器。然后用户按下“应用”,这会将过滤数据传递给地图视图控制器。 这里的问题是没有数据被传递。 作为参考,我遵循了https://medium.com/@jamesrochabrun/implementing-delegates-in-swift-step-by-step-d3211cbac3ef 的指导方针,它工作得很好。

这里是完整的项目代码https://github.com/afernandes0001/Custom-Delegate

我使用 Firebase,但下面的代码只显示了与委托相关的部分。

mapViewController - 你会注意到我在 prepareForSegue 中添加了一个打印。首次加载应用程序并单击“搜索”按钮时,它将 nav1 显示为 nil(这是预期的),但是,如果我单击搜索并应用(在 filterVC 中),则打印永远不会完成。

import UIKit
import MapKit

class MapViewController: UIViewController, MKMapViewDelegate, CLLocationManagerDelegate, FilterVCDelegate {

    @IBOutlet weak var map: MKMapView!

    override func viewDidLoad() {
        super.viewDidLoad()

        map.register(MyAnnotationView.self, forAnnotationViewWithReuseIdentifier: MKMapViewDefaultAnnotationViewReuseIdentifier)

    }

    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        if segue.identifier == "clinicDetailsSegue" {
            let clinicsDetailsViewController = segue.destination as! ClinicsDetailsViewController
            clinicsDetailsViewController.id = self.note.mapId
        } else if segue.identifier == "searchSegue" {
            print("segue call")
            let nav1 = segue.destination as? UINavigationController
            print("nav1 \(nav1)")
            if let nav = segue.destination as? UINavigationController, let filterVC = nav.topViewController as? FilterViewController {
                filterVC.delegate = self
            }
      }
    }

    func chosenData(clinicNameFilter: String, stateFilter: String, cityFilter: String, esp1Filter: String, esp2Filter: String) {
        print("Received data \(clinicNameFilter), \(stateFilter), \(cityFilter), \(esp1Filter), \(esp2Filter)")
    }
}

过滤视图控制器

import UIKit

protocol FilterVCDelegate: class {
    func chosenData(clinicNameFilter: String, stateFilter: String, cityFilter: String, esp1Filter: String, esp2Filter: String)
}


class FilterViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {

    weak var delegate: FilterVCDelegate?

    var selectedName = ""

    var statesJSON = [Estado]()
    var cities = [Cidade]()
    var state : Estate? // Selected State identifier
    var city : City? // Selected City identifier
    var selectedState = "" // Used to retrieve info from Firebase
    var selectedCity = "" // Used to retrieve info from Firebase

    var specialtiesJSON = [Specialty]()
    var specialties2 = [Specialty2]()
    var specialty1 : Specialty? // Selected Specialty1 identifier
    var specialty2 : Specialty2? // Selected Specialty2 identifier
    var selectedSpecialty1 = ""
    var selectedSpecialty2 = ""

    @IBOutlet weak var clinicName: UITextField!

    @IBOutlet weak var statePicker: UIPickerView!
    @IBOutlet weak var esp1Picker: UIPickerView!
    @IBOutlet weak var esp2Picker: UIPickerView!

    override func viewDidLoad() {
        readJsonStates()
        readJsonSpecialties()
        super.viewDidLoad()
        clinicName.text = ""
    }


    @IBAction func applyFilter(_ sender: Any) {
        if clinicName.text == nil {
            clinicName.text = ""
        }

        if selectedState != "" {
            if selectedCity != "" {
                if selectedSpecialty1 != ""{
                    if selectedSpecialty2 != "" {

                       delegate?.chosenData(clinicNameFilter: clinicName.text!, stateFilter: selectedState, cityFilter: selectedCity, esp1Filter: selectedSpecialty1, esp2Filter: selectedSpecialty2)
                        let viewControllers: [UIViewController] = self.navigationController!.viewControllers as [UIViewController]
                        self.navigationController?.popToViewController(viewControllers[viewControllers.count - 2], animated: true)
                    } else {
                        print("Fill in all filter data")
                    }
                } else {
                        print("Fill in all filter data")
                }
            } else {
                         print("Fill in all filter data")
            }
        } else {
                        print("Fill in all filter data")
        }
    }


    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {

        esp1Picker.reloadComponent(0)
        esp2Picker.reloadComponent(0)
        statePicker.reloadAllComponents()

        if pickerView == statePicker {
            if component == 0 {
                self.state = self.statesJSON[row]
                self.coties = self.statesJSON[row].cities
                statePicker.reloadComponent(1)
                statePicker.selectRow(0, inComponent: 1, animated: true)
            } else {
                self.city = self.cities[row]
                statePicker.reloadAllComponents()
            }
        } else if pickerView == esp1Picker {
            self.specialty1 = self.specialtiesJSON[row]
            self.specialties2 = self.specialtiesJSON[row].specialty2
            esp1Picker.reloadComponent(0)
            esp2Picker.reloadComponent(0)
            esp2Picker.selectRow(0, inComponent: 0, animated: true)

        } else if pickerView == esp2Picker {
            self.specialty2 = self.specialties2[row]
            esp1Picker.reloadComponent(0)
            esp2Picker.reloadComponent(0)
        }

        let indexSelectedState = statePicker.selectedRow(inComponent: 0)
        let indexSelectedCity = statePicker.selectedRow(inComponent: 1)
        let indexSelectedEsp1 = esp1Picker.selectedRow(inComponent: 0)
        let indexSelectedEsp2 = esp2Picker.selectedRow(inComponent: 0)

        if indexSelectedState >= 0 {
            if indexSelectedCity >= 0 {
                selectedState = estadosJSON[indexSelectedState].name
                selectedCity = cidades[indexSelectedCity].name
            }
        }

        if indexSelectedEsp1 >= 0 {
            if indexSelectedEsp2 >= 0 {
                selectedSpecialty1 = specialtiesJSON[indexSelectedEsp1].name
                selectedSpecialty2 = specialtiesJSON[indexSelectedEsp1].specialty2[indexSelectedEsp2].name
            }
        }
    }

    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        if pickerView == statePicker {
            return 2
        } else if pickerView == esp1Picker {
            return 1
        } else if pickerView == esp2Picker {
            return 1
        }
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        if pickerView == statePicker {
            if component == 0 {
                return statesJSON.count
            } else {
                return cities.count
            }
        } else if pickerView == esp1Picker {
            return self.specialtiesJSON.count

        } else if pickerView == esp2Picker {
            return specialties2.count
        }
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, viewForRow row: Int, forComponent component: Int, reusing view: UIView?) -> UIView {
        var rowTitle = ""
        let pickerLabel = UILabel()

        pickerLabel.textColor = UIColor.black

        if pickerView == statePicker {
            if component == 0 {
                rowTitle = statesJSON[row].name
            } else {
                rowTitle = cities[row].name
            }
        } else if pickerView == esp1Picker {
            rowTitle = specialtiesJSON[row].name
        } else if pickerView == esp2Picker {
            rowTitle = specialties2[row].name
        }

        pickerLabel.text = rowTitle
        pickerLabel.font = UIFont(name: fontName, size: 16.0)
        pickerLabel.textAlignment = .center

        return pickerLabel
    }

    func pickerView(_ pickerView: UIPickerView, widthForComponent component: Int) -> CGFloat {
        if pickerView == statePicker {
            if component == 0 {
                return 50
            } else {
                return 300
            }
        }
        return 300
    }

    override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
        view.endEditing(true)
    }

    func readJsonStates() {
        let url = Bundle.main.url(forResource: "StatesAndCities", withExtension: "json")!
        do {
            let data = try Data(contentsOf: url)
            let jsonResult = try JSONDecoder().decode(RootState.self, from: data)

            //handles the array of countries on your json file.
            self.statesJSON = jsonResult.state
            self.cities = self.statesJSON.first!.cities

        } catch {

        }
    }

    func readJsonSpecialties() {
        let url = Bundle.main.url(forResource: "Specialties", withExtension: "json")!
        do {
            let data = try Data(contentsOf: url)
            let jsonResult = try JSONDecoder().decode(RootEsp.self, from: data)

            //handles the array of specialties on your json file.
            self.specialtiesJSON = jsonResult.specialty
            self.specialties2 = self.specialtiesJSON.first!.specialty2
        } catch {
        }
    }

}

知道为什么当我单击 ApplyFilter 时,MapViewController 中的委托没有更新吗?

谢谢

【问题讨论】:

    标签: delegates swift5


    【解决方案1】:

    我在我的项目中发现了错误。 问题出在我的导航控制器上。

    当我发布上面的错误时,我的故事板如下所示

    为了让它工作,我将导航控制器添加到过滤视图控制器中,如下所示

    完成了工作,协议按预期工作。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-07-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-08-12
      • 2021-08-29
      • 2020-03-23
      相关资源
      最近更新 更多