//ViewControllerクラスでUIPickerViewのデリゲートメソッドを使用するため
//UIPickerViewDelegate, UIPickerViewDataSourceの2つのプロトコルを採用する
class ViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource {
@IBOutlet weak var myPicker: UIPickerView!
let compos = [["月","火","水","木","金"], ["午前","午後"]]
override func viewDidLoad() {
super.viewDidLoad()
//ViewControllerクラスをmyPickerのデリゲート、データソースに指定
//これでViewControllerクラス内でUIPickerViewのデリゲートメソッドが使用できる
myPicker.delegate = self
myPicker.dataSource = self
}
//---------------データソース----------------------------
//ピッカーの個数の指定
public func numberOfComponents(in pickerView: UIPickerView) -> Int{
return compos.count
}
//各ピッカーの行数の指定
//第2引数(component):配列のインデックス
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int{
let compo = compos[component]
return compo.count
}
//---------------デリゲート------------------------------
//各ピッカーの横幅の指定
//第2引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, widthForComponent component: Int) -> CGFloat {
if component == 0 {
return 50
}else {
return 100
}
}
//各ピッカーに配列の項目を指定(設定)する
//第2引数(row):配列の配列の値のインデックス
//第3引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
let item = compos[component][row]
return item
}
//選択された項目を調べる
//第2引数(row):選択された値(配列の配列の値)のインデックス
//第3引数(component):選択された項目(配列)のインデックス
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
//選択された値
let item = compos[component][row]
print(item, "が選ばれた")
//1つ目のコンポーネント(ピッカー)の行
let row1 = pickerView.selectedRow(inComponent: 0)
//2つ目のコンポーネント(ピッカー)の行
let row2 = pickerView.selectedRow(inComponent: 1)
print("現在選択されている行番号: \(row1, row2)")
//選択されている項目名
//1つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item1 = self.pickerView(pickerView, titleForRow:row1, forComponent:0)
//2つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item2 = self.pickerView(pickerView, titleForRow:row2, forComponent:1)
print("現在選択されている項目名: \(item1, item2)")
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
プロトコルの採用
ViewControllerクラスでUIPickerViewのデリゲートメソッドを使用するため
UIPickerViewDelegate, UIPickerViewDataSourceの2つのプロトコルを採用します。
この箇所についてはUIPickerViewクラスに限らず、その他のイベント発生においても、イベント発生時の処理を設定したい場合はそのイベント(クラス)のデリゲート及びデータソースのプロトコルををデリゲートメソッドを記述したクラス(今回はViewControllerクラス)に採用します。
デリゲートメソッド、データソースメソッドを記述するクラスを指定
override func viewDidLoad() {
super.viewDidLoad()
//ViewControllerクラスをmyPickerのデリゲート、データソースに指定
//これでViewControllerクラス内でUIPickerViewのデリゲートメソッドが使用できる
myPicker.delegate = self
myPicker.dataSource = self
}
storyboard上に配置してあるmyPicker(outlet接続した)のイベント発生時の処理を記述する(デリゲートメソッド、データソースメソッド)クラスを設定します。
今回はViewControllerクラスを使用するためselfを設定しています。
UIPickerViewDelegate, UIPickerViewDataSourceのプロトコルを採用しているクラスであれば設定できます。
この箇所も上記と同じく、その他のイベント発生においても、同様の記述設定をします。
データソースメドッド
基本的にはデータに関することを取り扱うメソッドです。
//---------------データソース----------------------------
//ピッカーの個数の指定
public func numberOfComponents(in pickerView: UIPickerView) -> Int{
return compos.count
}
//各ピッカーの行数の指定
//第2引数(component):配列のインデックス
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int{
let compo = compos[component]
return compo.count
}
ピッカーの個数の指定
//ピッカーの個数の指定
public func numberOfComponents(in pickerView: UIPickerView) -> Int{
return compos.count
}
ピッカーの個数を設定します。
今回は下記のような配列の内容をピッカーに反映させるので、配置するピッカーの数は
「月〜金」を表示させるピッカーと「午前、午後」を表示させるピッカーの2個です。
let compos = [["月","火","水","木","金"], ["午前","午後"]]
各ピッカーの行数の指定
//各ピッカーの行数の指定
//第2引数(component):配列のインデックス
public func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int{
let compo = compos[component]
return compo.count
}
第2引数(component): ピッカーのインデックス
各ピッカーの行数の設定します。
第2引数はピッカーのインデックス番号になります。
今回の場合はピッカーの個数は2個なので、pickerView( numberOfRowsInComponent)が最初に呼び出され時はcomponentには「0」が2回目に呼び出された時には「1」が入ります。
下記でピッカーを一つずつ配列composから取り出しcompo.countで各ピッカーの要素(値)を指定します。
let compo = compos[component]
return compo.count
今回の場合は、
compos[0]・・・・[“月”,”火”,”水”,”木”,”金”]
compos[1]・・・・[“午前”,”午後”]
となり、そのcountなので「5」と「2」になります。
デリゲートメソッド
基本的にはイベント処理に関することを取り扱うメソッドです。
//---------------デリゲート------------------------------
//各ピッカーの横幅の指定
//第2引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, widthForComponent component: Int) -> CGFloat {
if component == 0 {
return 50
}else {
return 100
}
}
//各ピッカーに配列の項目を指定(設定)する
//第2引数(row):配列の配列の値のインデックス
//第3引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
let item = compos[component][row]
return item
}
//選択された項目を調べる
//第2引数(row):選択された値(配列の配列の値)のインデックス
//第3引数(component):選択された項目(配列)のインデックス
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
//選択された値
let item = compos[component][row]
print(item, "が選ばれた")
//1つ目のコンポーネント(ピッカー)の行
let row1 = pickerView.selectedRow(inComponent: 0)
//2つ目のコンポーネント(ピッカー)の行
let row2 = pickerView.selectedRow(inComponent: 1)
print("現在選択されている行番号: \(row1, row2)")
//選択されている項目名
//1つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item1 = self.pickerView(pickerView, titleForRow:row1, forComponent:0)
//2つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item2 = self.pickerView(pickerView, titleForRow:row2, forComponent:1)
print("現在選択されている項目名: \(item1, item2)")
}
今回使用するデリゲートメソッドは上記の3つです。
ピッカーの横幅の指定
//各ピッカーの横幅の指定
//第2引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, widthForComponent component: Int) -> CGFloat {
if component == 0 {
return 50
}else {
return 100
}
}
今回はピッカーは2個なので第2引数(component)の値(インデックス)は「0」と「1」です。
compos[0]・・・・[“月”,”火”,”水”,”木”,”金”]
compos[1]・・・・[“午前”,”午後”]
なので、
●[“月”,”火”,”水”,”木”,”金”]の配列が反映されるピッカーの横幅は「50」
●[“午前”,”午後”]の配列が反映されるピッカーの横幅は「100」
になります。
各ピッカーに配列の項目を指定(反映)する
//各ピッカーに配列の項目を指定(設定)する
//第2引数(row):配列の配列の値のインデックス
//第3引数(component):配列のインデックス
func pickerView(_ pickerView: UIPickerView, titleForRow row: Int, forComponent component: Int) -> String? {
let item = compos[component][row]
return item
}
● 第2引数(row):配列の配列の値のインデックス
・・・今回は[“月”,”火”,”水”,”木”,”金”]と[“午前”,”午後”]なので「0〜4」と「0〜1」。
● 第3引数(component):配列のインデックス
・・・・各ピッカーのインデックス。今回は2個なので「0」と「1」。
組み合わせは(0、0〜4)と(1、0〜1)。
選択された項目を調べる
func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
//選択された値
let item = compos[component][row]
print(item, "が選ばれた")
//1つ目のコンポーネント(ピッカー)の行
let row1 = pickerView.selectedRow(inComponent: 0)
//2つ目のコンポーネント(ピッカー)の行
let row2 = pickerView.selectedRow(inComponent: 1)
print("現在選択されている行番号: \(row1, row2)")
//選択されている項目名
//1つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item1 = self.pickerView(pickerView, titleForRow:row1, forComponent:0)
//2つ目のコンポーネント(ピッカー)の現在選択されている項目名
let item2 = self.pickerView(pickerView, titleForRow:row2, forComponent:1)
print("現在選択されている項目名: \(item1, item2)")
print("------------------")
}
ドラムが回転して項目が選ばれると上記のpickerView(_ didSelectRow: inComponent:)メソッドが呼び出さ、コンポーネントで選ばれた行とコンポーネント番号が引数で送られてきます。
selectedRow(inComponent:)メソッドを使えばコンポーネントで選ばれている行を調べることもできます。
pickerView(_:titleForRow)メソッドを使えば、コンポーネントで現在選ばれている項目名を調べることができます。
上記スクリプトの出力結果
//1つ目のピッカーを回した結果
火 が選ばれた
現在選択されている行番号: (1, 0)
現在選択されている項目名: ("火", "午前")
------------------
//2つ目のピッカーを回した結果
昼間 が選ばれた
現在選択されている行番号: (1, 1)
現在選択されている項目名: ("火", "昼間")
------------------
