LoginSignup
1
2

More than 3 years have passed since last update.

【Swift】選択上限のある複数選択可能なTableViewの実装+スクロールしてもチェックマークがズレないようにする

Last updated at Posted at 2020-05-28

選択上限をつけた複数選択可能なTableViewの実装が調べても出てこなかったので、簡単に作ってみました。

今回実現したいTableView
  1. 複数選択可能
  2. 選択状態がスクロールによって他のCellにズレない
  3. 選択できる数に上限をつける

サンプルプログラム

1. 複数選択を可能にする

MultipleTableView.swift
// tableViewのisMultipleTouchEnabledをtrueにする
isMultipleTouchEnabled = true

これだけで複数選択が可能になる。

2. 選択状態がスクロールによって他のCellにズレない

Modelに選択状態を持って、その値を元にCellinitする。
(R.swift使っております)

MultipleTableView.swift
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(
                         withIdentifier: R.reuseIdentifier.multipleTableViewCell.identifier, 
                         for: indexPath) as! MultipleTableViewCell
    cell.selectionStyle = .none
    cell.kind = kinds[indexPath.row]
    return cell
}
MultipleTableViewCell.swift
var kind: KindModel? {
    didSet {
       accessoryType = kind?.isSelected ?? false ? .checkmark : .none
       initLabel()
    }
}

選択状態のsetは次の 選択できる数に上限をつける と合わせて紹介します。

3. 選択できる数に上限をつける

選択状態に上限をつけるのは、TableViewに選択数のカウンタをつけるのが1番楽かなと思います。
もっとかっこいい方法はないかと考えたのですが、特に思いつきませんでした。。

MultipleTableView.swift
var selectedIndex: [Int] = []

func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    if let row = selectedIndex.filter({ $0 == indexPath.row }).first {
        guard let removeIndex = selectedIndex.firstIndex(of: row) else { return }
        selectedIndex.remove(at: removeIndex)
        kinds[indexPath.row].isSelected.toggle()
        return
    }
    // 今回は上限を3にしました
    if selectedIndex.count > 2 { return }
    kinds[indexPath.row].isSelected.toggle()
    selectedIndex.append(indexPath.row)
}

これで上限の管理は完了です!

didDeselectRowAt 使いたかったけど、なぜか呼ばれなかった。
SOFにも同じような投稿がありましたが、解決ならずだったので諦めました。。

1
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
2