Swift - Table View Cell にチェックボックスを追加する方法
「Swift でチェックボックスを作る方法」では、Swift で View Controller にチェックボックスを追加する方法をご説明しました。
ここでは、Table View の Table View Cell にチェックボックスを追加して使う方法をご説明します。
Table View を使う準備をする
まずは Table View と Table View Cell を使う準備をします。
手順は 「 Table View の使い方 」 と全く同じですので、やった方はそのプロジェクトを開いて、そのまま次に進んでください。
「 Table View の使い方 」 をやっていない方は、Table View の使い方 の 3-1 から 3-4 を参考に Table View と Table View Cell を使う準備をしておいてください。
表示する Item データを準備する
今回は Item という構造体を定義してデータを保存しておき、それを Table View Cell に表示します。
ひとつのセルに表示したい Item の情報は、選択状態(チェックボックス)、商品の名前、色の三つです。
itemID, itemName, color, selected を格納できる Item という名前の構造体を作ります。
Item 構造体を作る
メニューバーの File > New > File... で iOS の Swift File を選択し Next をクリックして、Item.swift ファイルを生成します。
そして、Item.swift ファイルを開いて、その中に以下のコードを追加します。
struct Item {
var itemID: Int
var itemName: String
var color: String
var selected: Bool
init(itemID: Int, itemName: String, color: String, selected: Bool) {
self.itemID = itemID
self.itemName = itemName
self.color = color
self.selected = selected
}
}
Item の Array データを作っておく
続けて、データを表示するための Item 構造体の配列データを作っておきます。
ViewController.swift ファイルを開いて、以下のコードを追加してください。
まずは、上のほうで items という名前の Item 型の配列を定義します。
var items: [Item] = []
loadData() というメソッドで、それぞれの Item オブジェクトを作って、items に追加しています。
func loadData() {
items.append(Item(itemID: 1, itemName: "Item Name 1", color: "Red", selected: false))
items.append(Item(itemID: 2, itemName: "Item Name 2", color: "Blue", selected: false))
items.append(Item(itemID: 3, itemName: "Item Name 3", color: "Green", selected: false))
items.append(Item(itemID: 4, itemName: "Item Name 4", color: "Yellow", selected: false))
items.append(Item(itemID: 5, itemName: "Item Name 5", color: "Pink", selected: false))
items.append(Item(itemID: 6, itemName: "Item Name 6", color: "Red", selected: false))
items.append(Item(itemID: 7, itemName: "Item Name 7", color: "Blue", selected: false))
items.append(Item(itemID: 8, itemName: "Item Name 8", color: "Green", selected: false))
items.append(Item(itemID: 9, itemName: "Item Name 9", color: "Yellow", selected: false))
items.append(Item(itemID: 10, itemName: "Item Name 10", color: "Pink", selected: false))
}
そして、viewDidLoad() の下のほうで、先ほどの loadData() を呼び出しデータを生成するようにしておきます。
loadData()
tableView(_:numberOfRowsInSection:) では、items.count を返すようにしておきます。
return items.count
チェックボックスを使う準備をする
Table View Cell でチェックボックスを使う準備をします。
以下のようなチェックされていない状態の画像と、チェックされている状態の画像を準備します。
二つの画像を、Assets.xcassets にドラッグ&ドロップして追加しておきます。
次に、UIButton クラスを元に CheckboxButton クラスをつくります。
メニューの File > New > File... から CheckboxButton.swift という名前の Swift File を追加します。
CheckboxButton.swift に以下のコードを追加します。
import UIKit
final class CheckboxButton: UIButton {
let checkedImage = UIImage(named: "checked")! as UIImage
let uncheckedImage = UIImage(named: "unchecked")! as UIImage
var isChecked: Bool = false {
didSet{
if isChecked {
self.setImage(checkedImage, for: .normal)
} else {
self.setImage(uncheckedImage, for: .normal)
}
}
}
}
アセットに追加した checked と unchecked から、UIImage を定義しています。
isChecked というプロパティを追加し、isChecked がセットされた時に true であれば、image を checkedImage に、false の時は uncheckedImage に設定するようにしています。
Table View Cell にチェックボックスを追加する方法
ItemTableViewCell クラスを作る
まずは、カスタムの UITableViewCell のクラスをつくります。
メニューバーの File > New > File... で iOS の Cocoa Touch Class を選択し Next をクリックして、Class に ItemTableViewCell、Subclass of に UITableViewCell を選択しファイルを生成します。
Table View Cell のクラスを設定する
Item の情報を表示する Table View Cell を設定します。
ここではざっとご説明しますので、詳細は「 Table View Cell をカスタマイズする方法 」をご覧ください。
次に、Table View Cell のクラスを ItemTableViewCell を設定します。
左側のプロジェクトナビゲーターで Main.storyboard を選択します。
Table View Cell を選択した状態で、右側のユーティリティエリアの Identity インスペクターを選択します。
上のほうにある Custom Class のクラスの Class のドロップダウンリストから ItemTableViewCell を選んでおきます。
Table View Cell にオブジェクトを配置する
Table View Cell にチェックボックスや Label などのオブジェクトを配置していきます。
まずは、Table View と Table View Cell の 1 行の高さを 100 に設定します。
Table View を選択した状態で Size インスペクターを開きます。
一番上の Table View の Row Height に 100 を設定します。
そのまま、Table View Cell を選択し、Size インスペクターで Table View Cell の Row Height も 100 に設定します。
次に Table View Cell を選択したまま、Attribute インスペクターを開き、Style を Custom に変更し、Identifier を ItemTableViewCell に変更しておきます。
それでは、Table View Cell にチェックボックス用のボタンやラベルなどのオブジェクトを配置していきましょう。
Table View Cell の左側にボタンを追加し、Image に unchecked を選択し、文字を削除します。
ボタンの class に CheckboxButton を指定します。
その右側に Item Name と Color を表示するための Label を、ヘッダー用・値用の二つを 2 セット配置します。
フォントや配置などは、お好みで変更してください。
Table View Cell のアウトレットを生成する
次に Table View Cell のアウトレットを生成します。
ストーリーボードで、ItemTableViewCell の中のチェックボックスなど選択した状態で、メニューから Editor > Assistant Editor を選択するか、Adjust Editor Options ボタンの Assistant から Assistant Editor を開きます。
Assistant Editor が開いたら、開かれたファイルが ItemTableViewCell.swift であることを確認してください。
違う場合は、Assistant Editor の上の Automatic をクリックして、ItemTableViewCell.swift に変更してください。
そして、チェックボックスボタンと Item Name、Color の値用のラベルから、以下のように 3 つのアウトレットを生成しておいてください。
@IBOutlet weak var itemNameLabel: UILabel!
@IBOutlet weak var colorLabel: UILabel!
@IBOutlet weak var selectCheckboxButton: CheckboxButton!
選択されているチェックボックスを確認するために、Table View の下のほうに SAVE ボタンを追加して、ViewController.swift に saveTapped という TouchUpInside のアクションを作っておきます。
@IBAction func saveTapped(_ sender: Any) {
}
これで、カスタムの Table View Cell を使う下準備は完了です。
Table View でチェックボックスのデータを表示・更新する
それでは、カスタムの Table View Cell にデータを表示してみましょう。
tableView(_:cellForRowAt:) インスタンスメソッドに次のようにコードを追加して、selectTapped() メソッドも追加します。
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let cell = myTableView.dequeueReusableCell(withIdentifier: "ItemTableViewCell", for: indexPath) as? ItemTableViewCell else {
fatalError("Dequeue failed: ItemTableViewCell.")
}
cell.selectionStyle = .none
cell.itemNameLabel.text = items[indexPath.row].itemName
cell.colorLabel.text = items[indexPath.row].color
cell.selectCheckboxButton.isChecked = items[indexPath.row].selected
cell.selectCheckboxButton.addTarget(self, action: #selector(selectTapped(sender:)), for: .touchUpInside)
cell.selectCheckboxButton.tag = indexPath.row
return cell
}
@objc func selectTapped(sender: CheckboxButton){
let row = sender.tag as Int
sender.isChecked = !items[row].selected
items[row].selected = !items[row].selected
}
まず、dequeueReusableCell で得られた UITableViewCell を guard let で ItemTableViewCell 型にキャストし、失敗した時は fatalError で実行を終了するようにしています。
そして、items 配列の indexPath.row 番目の Item オブジェクトの itemName、color、selected の値を cell の itemNameLabel.text、colorLabel.text、selectCheckboxButton.isChecked に設定しています。
続けて、selectCheckboxButton の addTarget() メソッドを使って、チェックボックスボタンの touchUpInside のイベントで、selectTapped() メソッドが実行されるようにしています。
selectTapped() メソッドの中で、どの row だったかわかるように tag プロパティに indexPath.row を入れています。
selectTapped() メソッドでは、タグから row 番号の値を取り出し、その row 番号の Item オブジェクトの selected の値を反転させて、sender.isChecked に設定してチェックボックスの画像のON/OFFを切り替えています。
row 番号の Item オブジェクトの selected の値も反転させています。
最後に saveTapped() に以下のコードを追加して、SAVE ボタンがタップされた時にチェックされている Item Name を print するようにしました。
@IBAction func saveTapped(_ sender: Any) {
for item in items {
if item.selected {
print("\(item.itemName) selected")
}
}
print("-----------------------------------")
}
これでカスタム Table View Cell にデータを表示する為のコードを書き終わりました。
念のため ViewController.swift の全体のコードを載せておきます。
import UIKit
class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
@IBOutlet weak var myTableView: UITableView!
var items: [Item] = []
override func viewDidLoad() {
super.viewDidLoad()
myTableView.dataSource = self
myTableView.delegate = self
loadData()
}
func loadData() {
items.append(Item(itemID: 1, itemName: "Item Name 1", color: "Red", selected: false))
items.append(Item(itemID: 2, itemName: "Item Name 2", color: "Blue", selected: false))
items.append(Item(itemID: 3, itemName: "Item Name 3", color: "Green", selected: false))
items.append(Item(itemID: 4, itemName: "Item Name 4", color: "Yellow", selected: false))
items.append(Item(itemID: 5, itemName: "Item Name 5", color: "Pink", selected: false))
items.append(Item(itemID: 6, itemName: "Item Name 6", color: "Red", selected: false))
items.append(Item(itemID: 7, itemName: "Item Name 7", color: "Blue", selected: false))
items.append(Item(itemID: 8, itemName: "Item Name 8", color: "Green", selected: false))
items.append(Item(itemID: 9, itemName: "Item Name 9", color: "Yellow", selected: false))
items.append(Item(itemID: 10, itemName: "Item Name 10", color: "Pink", selected: false))
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return items.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let cell = myTableView.dequeueReusableCell(withIdentifier: "ItemTableViewCell", for: indexPath) as? ItemTableViewCell else {
fatalError("Dequeue failed: ItemTableViewCell.")
}
cell.selectionStyle = .none
cell.itemNameLabel.text = items[indexPath.row].itemName
cell.colorLabel.text = items[indexPath.row].color
cell.selectCheckboxButton.isChecked = items[indexPath.row].selected
cell.selectCheckboxButton.addTarget(self, action: #selector(selectTapped(sender:)), for: .touchUpInside)
cell.selectCheckboxButton.tag = indexPath.row
return cell
}
@objc func selectTapped(sender: CheckboxButton){
let row = sender.tag as Int
sender.isChecked = !items[row].selected
items[row].selected = !items[row].selected
}
@IBAction func saveTapped(_ sender: Any) {
for item in items {
if item.selected {
print("\(item.itemName) selected")
}
}
print("-----------------------------------")
}
}
iOS アプリをシミュレーターでテストする
それでは、作った iOS アプリをビルド・実行して確認してみます。
画面が表示されるので、適当にチェックをつけ、SAVEボタンをタップします。
チェックボックスで選択した、Item Name が取得できていますね。
以上、Table View Cell にチェックボックスを追加して使う方法をご説明しました。