當 table view 或 collection view 進入編輯模式時顯示不同樣式的 cell
我們時常在 iOS App 看到點選 Edit 按鈕進入編輯模式的畫面設計,比方下圖的 Clock App,點選 Edit 後 cell 會出現刪除跟調整順序的按鈕。
不過上圖還有個特別的設計,進入編輯模式時 cell 的內容也改變了,為了節省空間,它的時間不見了。這是怎麼做到的呢 ?
接下來我們將示範實作的方法,關鍵在讓 table view 或 collection view 在編輯模式時顯示不同樣式的 cell,在正常模式顯示有時間的 cell,在編輯模式拿掉時間。
App 畫面設計
table view controller 的類別為繼承 UITableViewController 的 TimeTableViewController,cell 的類別為繼承 UITableViewCell 的 TimeTableViewCell。
TimeTableViewCell
class TimeTableViewCell: UITableViewCell {
static let reuseIdentifier = "\(TimeTableViewCell.self)"
@IBOutlet weak var locationLabel: UILabel!
@IBOutlet weak var timeLabel: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
} override func setSelected(_ selected: Bool, animated: Bool) {
super.setSelected(selected, animated: animated) }}
TimeTableViewController
利用 TimeZone.knownTimeZoneIdentifiers 找出世界各地的時區代號,在表格顯示城市名跟時間。(ps: 以下範例不會自動更新時間,因為它不是此篇文章的重點)
class TimeTableViewController: UITableViewController {
let timeZoneIdentifiers = TimeZone.knownTimeZoneIdentifiers.filter {
$0.contains("/") }
let dateFormatter: DateFormatter = {
let dateFormatter = DateFormatter()
dateFormatter.timeStyle = .short
return dateFormatter
}()
override func viewDidLoad() {
super.viewDidLoad()
navigationItem.leftBarButtonItem = editButtonItem
}
// MARK: - Table view data source
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return timeZoneIdentifiers.count
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: TimeTableViewCell.reuseIdentifier, for: indexPath) as! TimeTableViewCell
let id = timeZoneIdentifiers[indexPath.row]
let city = id.components(separatedBy: "/")[1]
cell.locationLabel.text = city
dateFormatter.timeZone = TimeZone(identifier: id)
cell.timeLabel.text = dateFormatter.string(from: .now)
return cell
}
}
執行 App
點選 Edit 進入編輯模式,左邊出現刪除按鈕。
不過因為縮排的關係,右邊的時間有的會變成 …。接下來我們將模仿 iOS 的 Clock App,在編輯模式時將時間隱藏。
在編輯模式切換時更新表格
當畫面進入或結束編輯模式時,會觸發 UIViewController 的 setEditing(_:animated:),因此我們可覆寫它,在裡面呼叫 reloadData 更新表格。
override func setEditing(_ editing: Bool, animated: Bool) {
super.setEditing(editing, animated: animated)
tableView.reloadData()
}
在編輯模式時將時間隱藏
檢查 isEditing 判斷是否處於編輯模式,isEditing true 時將時間隱藏。
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: TimeTableViewCell.reuseIdentifier, for: indexPath) as! TimeTableViewCell
let id = timeZoneIdentifiers[indexPath.row]
let city = id.components(separatedBy: "/")[1]
cell.locationLabel.text = city
dateFormatter.timeZone = TimeZone(identifier: id)
if isEditing {
cell.timeLabel.isHidden = true
} else {
cell.timeLabel.text = dateFormatter.string(from: .now)
cell.timeLabel.isHidden = false
}
return cell
}
Cool,現在正常模式跟編輯模式的表格長不一樣了,只有正常模式會顯示時間。
其它範例參考
Apple 的 Today App,範例裡定義 ReminderDetailViewDataSource & ReminderDetailEditDataSource,當 table 在正常模式時 data source 是 ReminderDetailViewDataSource,當 table 在編輯模式時 data source 是 ReminderDetailEditDataSource。