Свифт |UIViewTable меняет галочку при прокрутке с экрана - PullRequest
0 голосов
/ 10 марта 2019

У меня есть список TableViewCells (todoList.items) внутри TableView. Я могу легко переключать галочки, и это работает. Но когда ячейки прокручиваются за пределы представления таблицы, флажок неожиданно переключается.

На мой взгляд контроллер

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "ChecklistItem", for: indexPath)
    let item = todoList.items[indexPath.row]
    configureText(for: cell, with: item)
    configureCheckmark(for: cell, with: item)

    return cell
}

// **EDIT**
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    if let cell = tableView.cellForRow(at: indexPath) {
        let item = todoList.items[indexPath.row]
        configureCheckmark(for: cell, with: item)
        tableView.deselectRow(at: indexPath, animated: true)
    }
}

func configureCheckmark(for cell: UITableViewCell, with item: ChecklistItem) {
    cell.accessoryType = item.checked ? .checkmark : .none
    item.toggleChecked()
}

// **END EDIT**

TodoList.swift

class TodoList {

    var items: [ChecklistItem] = []

    init() {
        // Create some demo items
        items.append(ChecklistItem(text: "Take a jog"))
        items.append(ChecklistItem(text: "Watch a movie"))
        items.append(ChecklistItem(text: "Code an app"))
        items.append(ChecklistItem(text: "Walk the dog"))
        items.append(ChecklistItem(text: "Study design patterns"))
    }

    func newItem() -> ChecklistItem {
        items.append(ChecklistItem(text: "NEW ITEM"))
        return items[items.count-1]
    }

}

ChecklistItem.swift

class ChecklistItem {

    var text = ""
    var checked = true

    init(text: String) {
        self.text = text
    }

    func toggleChecked() {
        checked = !checked
    }

}

1 Ответ

1 голос
/ 10 марта 2019

Ошибка возникает из-за того, что вы переключаете состояние checked всегда в configureCheckmark. Поэтому, когда для этой строки вызывается cellForRow, состояние переключается.

На самом деле дополнительный метод configureCheckmark не нужен. Поставьте строку, чтобы установить галочку в cellForRow, но не меняйте состояние.

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "ChecklistItem", for: indexPath)
    let item = todoList.items[indexPath.row]
    configureText(for: cell, with: item)
    cell.accessoryType = item.checked ? .checkmark : .none

    return cell
}

В didSelectRowAt переключите checked в модели и перезагрузите строку

override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    todoList.items[indexPath.row].checked.toggle()
    tableView.reloadRows(at: [indexPath], with: .none)
}

Метод toggleChecked() в ChecklistItem также является избыточным. В Bool.

есть метод toggle().

И подумайте об использовании структур, а не классов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...