web-dev-qa-db-ja.com

1つのView Controllerで2つのUIPickerViewを使用する方法は?

1つのView Controllerに2つのUIPickerControllerがあります。 1つを機能させることはできますが、2つ目を追加すると、アプリがクラッシュします。 1つのピッカービューに使用するコードは次のとおりです。

import UIKit

class RegisterJobPosition: UIViewController, UIPickerViewDelegate {

    @IBOutlet weak var positionLabel: UILabel!

    var position = ["Lifeguard", "Instructor", "Supervisor"]

    override func viewDidLoad() {
        super.viewDidLoad()
    }

    func numberOfComponentsInPickerView(PickerView: UIPickerView!) -> Int
    {
        return 1
    }

    func pickerView(pickerView: UIPickerView!, numberOfRowsInComponent component: Int) -> Int
    {
        return position.count
    }

    func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String!
    {
        return position[row]
    }

    func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {        
        positionLabel.text = position[row]
    }
}

さて、2番目のピッカーを機能させるにはどうすればよいですか? 2番目のピッカービューはlocation(もう1つはpositionと呼ばれます)と呼ばれます。 locationのピッカービューメソッド内でコードを複製しようとしましたが、機能しません。

25
dom999999

私が質問に持っている情報に基づいて、どのピッカーインスタンスが呼び出しているかを区別する機能を処理するために、データソースとデリゲートメソッドをセットアップする必要があると思います。

タグプロパティの使用 ピッカービューでの1つの戦略です。

参照されているのが位置ピッカーであるか位置ピッカーであるかによってロジックが異なるメソッドには、if/elseまたはswitchステートメントがいくつかあるはずです。

26
andrewcbancroft

ここに私の解決策があります:

  • ストーリーボードで、ビューに2つのUIPickerViewインスタンスを追加します
  • 最初のピッカーのタグを_1_に設定し、「属性インスペクター」の下の2番目のピッカーに_2_を設定します
  • control +各ピッカーから一番上の黄色のView Controllerアイコンにドラッグして、dataSourceを選択します。同じ選択delegateを繰り返します
  • view ControllerにUIPickerViewDataSourceUIPickerViewDelegateを追加します:

    _class ViewController: UIViewController, UIPickerViewDataSource, UIPickerViewDelegate {
    _
  • view Controllerクラスで、ピッカー用の空の配列を作成します。

    _var picker1Options = []
    var picker2Options = []
    _
  • viewDidLoad()で、配列にコンテンツを入力します。

    _picker1Options = ["Option 1","Option 2","Option 3","Option 4","Option 5"]
    picker2Options = ["Item 1","Item 2","Item 3","Item 4","Item 5"]
    _
  • デリゲートメソッドとデータソースメソッドを実装します。

    _func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
        return 1
    }
    
    func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        if pickerView.tag == 1 {
            return picker1Options.count
        } else {
            return picker2Options.count
        }
    }
    
    func pickerView(pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String! {
        if pickerView.tag == 1 {
            return "\(picker1Options[row])"
        } else {
            return "\(picker2Options[row])"
        }
    }
    _
67
LAOMUSIC ARTS

これが機能することがわかりました。

class SecondViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {

    @IBOutlet weak var textbox1: UILabel!
    @IBOutlet weak var textbox2: UILabel!

    @IBOutlet weak var dropdown1: UIPickerView!
    @IBOutlet weak var dropdown2: UIPickerView!

    var age = ["10-20", "20-30", "30-40"]
    var Gender = ["Male", "Female"]

    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return 1
    }

    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        var countrows : Int = age.count
        if pickerView == dropdown2 {
            countrows = self.Gender.count
        }

        return countrows
    }

    func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
        if pickerView == dropdown1 {
            let titleRow = age[row]
             return titleRow
        } else if pickerView == dropdown2 {
            let titleRow = Gender[row]
            return titleRow
        }

        return ""
    }

    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        if pickerView == dropdown1 {
            self.textbox1.text = self.age[row]
        } else if pickerView == dropdown2 {            
            self.textbox2.text = self.Gender[row]
        }
    }
}
4
Diavel Rider

私の背景はAndroidですが、私の答えは非常にOOPです。このようにDataSourceとDelegateを実装するために異なるクラスを作成することをお勧めします。

class PositionDataSourceDelegate : NSObject, UIPickerViewDelegate, UIPickerViewDataSource {
   var position = ["Lifeguard", "Instructor", "Supervisor"]
   var selectedPosition : String?

    func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
       return 1
    }

    func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
      return position.count
    }

    func pickerView(pickerView: UIPickerView, attributedTitleForRow row: Int, forComponent component: Int) -> NSAttributedString? {
       return position[row]
    }

    func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
       selectedPosition = position[row]
    }
}

次に、場所の別のもの:

class LocationDataSourceDelegate : NSObject, UIPickerViewDelegate, UIPickerViewDataSource {
   var location = ["Up", "Down", "Everywhere"]
   var selectedLocation : String?

    func numberOfComponentsInPickerView(pickerView: UIPickerView) -> Int {
        return 1
    }

    func pickerView(pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        return location.count
    }

    func pickerView(pickerView: UIPickerView, attributedTitleForRow row: Int, forComponent component: Int) -> NSAttributedString? {
         return location[row]
    }

    func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        selectedLocation = location[row]
   }
}

registerJobPositionで、それぞれのインスタンスを作成する必要があります。

let positionDSD = PositionDataSourceDelegate()
let locationDSD = LocationDataSourceDelegate()

次のようにそれらをピッカーに割り当てます。

positionPicker.dataSource = positionDSD
positionPicker.delegate = positionDSD
locationPicker.dataSource = locationDSD
locationPicker.delegate = locationDSD

また、次を使用して、選択した位置と場所にアクセスできます。

positionDSD.selectedPosition 
locationDSD.selectedLocation

これがあなたや他の人に役立つことを願っています。また、なぜこれが「迅速」ではないのかについての建設的なコメントも期待しています。

0
Matei Suica

最大の問題は、Javaとは異なることだと思います。Javaは、コンストラクタを介して属性を簡単に渡すことができます。たとえば、クラスLocationDataSourceDelegateをジェネリックおよびそれをgenericDataSourceDelegateと呼び、コンストラクターがArray public genericDataSourceDelegate(String data [])を受け入れて、単純にオブジェクトを作成できる1つのクラスを作成できるようにします。

モデルの問題は、1つのプログラムでできるだけ多くのデリゲートクラスを作成する必要があるため、コンパイラーにとって負担となります。

0
Dula Al-Zakwani