Добавить переменную ко всем UIViewControllers

Я новичок в Swift и пытаюсь реализовать кастом UIKeyCommand архитектура в приложении практики. Я написал расширение ниже для базы UISplitViewController показать все UIKeyCommands в текущих представлениях на экране.

extension UISplitViewController {
    open override var canBecomeFirstResponder: Bool {
        return true
    }

    var BPKeyCommands: [BPKeyCommand]? {
        var commands: [BPKeyCommand] = []

        var mastervc = self.viewControllers.first
        if (mastervc is UINavigationController) {
            mastervc = (mastervc as! UINavigationController).viewControllers.last
        }
        if let masterCommands = mastervc.commands {
            for command in masterCommands {
                commands.append(command)
            }
        }

        return commands
    }

    open override var keyCommands: [UIKeyCommand]? {
        var commands: [UIKeyCommand] = []

        if let bpkeycommands = BPKeyCommands {
            for command in bpkeycommands {
                let new = UIKeyCommand(input: command.input,
                                       modifierFlags: command.modifierFlags,
                                       action: #selector(executeKeyCommand(sender:)),
                                       discoverabilityTitle: command.title)
                commands.append(new)
            }
        }

        return commands
    }

    @objc private func executeKeyCommand(sender: UIKeyCommand) {
        if let index = keyCommands?.firstIndex(of: sender) {
            if let command = BPKeyCommands?[index] {
                command.action(command)
            }
        }
    }
}

Теперь, как вы могли ожидать, это выдает ошибку в if let masterCommands = mastervc.commands {, так как UIViewController doesn't contain the commands variable out of the box. My question is: how can I haveUIViewControllerhave that variable? Just like all controllers can overridekeyCommands` по умолчанию?

2 ответа

Решение

Вы должны создать протокол с помощью переменной команды и настроить ваш контроллер представления в соответствии с ним (шаг 1). Либо вы можете предоставить значения для конкретного контроллера представления, либо вы можете предоставить реализацию по умолчанию.

Шаг 1:- Создайте протокол с нужной вам переменной.

protocol Commandable{
   var commands: [String]{set get}
}
extension Commandable{
   var commands: [String]{
        get{return ["hello","world"]}
        set{}
    }
}

Шаг 2:- Затем настройте контроллеры, которые вы используете

Шаг 3:- изменить приведенный выше код, чтобы получить команды

if let commandProtocol = masterVC as? Commandable
{
    let commands = commandProtocol.commands
}
else{
    // handle it
}

Убедитесь, что переменная уникальна, чтобы случайно не переопределить ее.

Спасибо.

Вы можете создать расширение UIViewController и добавить это свойство на этом расширении UIViewController, Тогда Вы получите это на дочерних контроллерах вида как UISplitViewController или любые другие пользовательские ViewControllers. Чтобы узнать больше о расширениях, которые можно добавить к расширению или что можно сделать с помощью расширения??

Другие вопросы по тегам