UIAlertController asyn c? - PullRequest
       7

UIAlertController asyn c?

1 голос
/ 24 апреля 2020

У меня есть UITableView с некоторыми действиями смахивания. Один из них представляет лист действий через UIAlertController и позволяет пользователю изменять категорию UITableViewCell, заставляя ячейку появляться в другом разделе.

Я пытаюсь добиться перезагрузки tableView после выбор был сделан, но кажется, что предупреждение вызывается асинхронно. Может ли кто-нибудь помочь мне понять стек вызовов и куда поставить вызов tableview.reloadData()?

        let switchTypeAction = UIContextualAction(style: .normal, title: nil) { [weak self] (_,_,success) in

            let ac = UIAlertController(title: "Change type", message: nil, preferredStyle: .actionSheet)
            for type in orderItem.orderItemType.allValues where type != item.type {
                ac.addAction(UIAlertAction(title: "\(type.prettyName)", style: .default, handler: self?.handleChangeType(item: item, type: type)))
            }
            ac.addAction(UIAlertAction(title: "Cancel", style: .cancel))
            self?.present(ac, animated: true)
            tableview.reloadData()
            success(true)
        }

    func handleChangeType(item: orderItem, type: orderItem.orderItemType) -> (_ alertAction:UIAlertAction) -> (){
        return { alertAction in
            item.type = type
        }
    }

Я бы предположил, что вызовы выполнялись в этом порядке, но при отладке я вижу, что self?.present(ac, animated: true) фактически выполняется после блока, поэтому сначала выполняется перезагрузка и ответ об успешном выполнении. Имеет ли это какое-либо отношение к закрытию, являющемуся @escaping?

1 Ответ

1 голос
/ 24 апреля 2020

Да, UIAlertController - это "asyn c", в том смысле, что V C, который представляет предупреждение, все равно будет выполнять код, пока отображается предупреждение. На самом деле это, как правило, верно для любого V C, представляющего другой V C.

. Вы должны позвонить reloadData в закрытии handler, которое принимает UIAlertAction.init. Это закрытие, которое будет вызываться, когда пользователь выбирает действие. Здесь вы передаете возвращаемое значение handleChangeType, поэтому вы должны записать его здесь:

func handleChangeType(item: orderItem, type: orderItem.orderItemType) -> (_ alertAction:UIAlertAction) -> (){
    return { alertAction in
        item.type = type
        self.tableView.reloadData()
    }
}

Если вам известны пути индекса, к которому и из которого перемещается элемент, вы можете использовать moveTow(at:to:) вместо этого, чтобы перезагрузить только эти две строки, вместо все .

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