Ярлык доступности обновления iOS

У меня есть кнопка с меткой доступности @"a". Когда кнопка нажата, у меня есть обратный вызов, который устанавливает метку доступности button.accessibilityLabel = @"b". Я знаю, что эта строка кода работает. Однако, если я нажму кнопку еще раз, VoiceOver все равно будет читать. К сожалению, код, с которым я работаю, является проприетарным, поэтому я не могу поделиться им напрямую.

Однако в целом я хотел бы знать, из-за каких проблем VoiceOver может не распознавать обновление метки.


person kmell96    schedule 23.08.2017    source источник
comment
Ваш вопрос непонятен, попробуйте опубликовать свой код и то, что вы пробовали   -  person Caplin YT    schedule 23.08.2017
comment
Ваш вопрос непонятен   -  person Arun sharma    schedule 23.08.2017
comment
Любая неясность в том, о чем спрашивают, происходит из-за незнания читателя. Это хороший вопрос, на который есть ценный ответ.   -  person ChrisCM    schedule 24.08.2017


Ответы (4)


НАИЛУЧШИЙ способ обработки меток динамической доступности - переопределить функции свойств для представлений, на которых выполняется фокус (например, для UIButton). Это позволяет ДВЕ вещи. О: это намного проще поддерживать, чем устанавливать свойство везде, где оно может измениться. B: вы можете регистрировать информацию и видеть, когда система запрашивает эту информацию, чтобы вы могли лучше понять, ПОЧЕМУ что-то происходит. Поэтому, даже если это напрямую не решает вашу проблему, видеть КОГДА система запрашивает ваше значение и регистрировать эти данные по своей сути.

Делаем это в Objective C

@implementation YourUIButton

-(NSString*)accessibilityLabel {
    if(someCondition) {
        return @"a";
    } else {
        return @"b";
    }
}

@end

В быстром

public class YourUIButton : UIButton
    override public var accessibilityLabel: String? {
        get {
            if (someCondition) {
                return "a"
            } else {
                return "b"
            }
        }

        set {
            NSException.raise(NSException("AccessibilityLabelException", "You should not set this accessibility label.", blah))
        }
    }
}

Вы также можете использовать эту логику ТОЛЬКО для отладки, разрешить настройку и тому подобное.

Здесь много потенциальных проблем. Условия соревнования, какое представление фактически получает фокус, существуют ли какие-то родительские дочерние отношения и т. Д. Переопределение свойства и добавление операторов регистрации в приведенный выше код поможет вам понять, какое представление на самом деле получает запрошенную метку доступности и когда. Супер ценная информация!

person ChrisCM    schedule 24.08.2017

Попробуйте добавить UIAccessibilityTraitUpdatesFrequently в свойство кнопок accessibilityTraits

- (void)viewDidLoad {
    myButton.accessibilityTraits |= UIAccessibilityTraitUpdatesFrequently
}

Кроме того, при изменении accessibilityLabel убедитесь, что вы находитесь в основном потоке.

dispatch_async(dispatch_get_main_queue(), ^{
    myButton.accessibilityLabel = @"b";
});
person GRiMe2D    schedule 23.08.2017
comment
Спасибо за предложение. На самом деле я звонил не из основного потока. Однако, когда я использую блок dispatch_async, как вы предложили, VoiceOver по-прежнему считывает старую метку. Есть другие идеи? - person kmell96; 24.08.2017
comment
@ kmell96, VoiceOver считывает метку сразу после касания (как вы можете видеть в приложении «Калькулятор»), попробуйте установить accessibilityLabel на nil сразу после касания, а в обратном вызове установите для него значение @"b" - person GRiMe2D; 24.08.2017
comment
Ссылка на UIAccessibilityTraitUpdatesFre всегда вводит в заблуждение относительно назначения этой черты. Остальная часть этого поста разумна. - person ChrisCM; 24.08.2017

Используйте это при изменении текста кнопки

UIAccessibility.post(notification: .layoutChanged, argument: yourButton)
person Shivam Singh    schedule 19.11.2019

Вам действительно не нужен способ обновить голос поверх ярлыков. Это делается автоматически. Я пробовал это, и он работает, как ожидалось.

class ViewController: UIViewController {

    var tapCount = 0

    var button: UIButton!

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        button = UIButton(type: .system)
        button.setTitle("Hello", for: .normal)
        button.frame = CGRect(x: 10, y: 10, width: 100, height: 50)
        view.addSubview(button)

        button.accessibilityLabel = "Hello Button"
        button.accessibilityHint = "Tap here to start the action"
        button.accessibilityIdentifier = "hello_button"
        button.addTarget(self, action: #selector(buttonTap(sender:)), for: .touchUpInside)
    }

    @IBAction func buttonTap(sender:UIButton) {
        tapCount = tapCount + 1
        sender.accessibilityLabel = "Hello button, tapped \(tapCount) times"
    }
}

Что говорит голос:

Кнопка "Привет" -пауза- Кнопка -пауза- Нажмите здесь, чтобы начать действие

При нажатии кнопки

Кнопка "Привет", нажатие один раз

Еще одно нажатие

Кнопка "Привет", нажатие два раза

person BangOperator    schedule 23.08.2017
comment
Topicstarter делает то же самое, но VoiceOver не улавливает правку - person GRiMe2D; 24.08.2017
comment
Голосующие против Мне нужны ваши ценные комментарии, чтобы улучшить это. - person BangOperator; 25.08.2017
comment
@ GRiMe2D, откуда вы знаете, что topicstarter сделал то же самое? Я вставил простой фрагмент, как это работает, поэтому OP не упускает ничего существенного. Если случай OP отличается, мы можем обновить вопрос, а также ответить. - person BangOperator; 25.08.2017