iOS 刷新辅助功能标签

Posted

技术标签:

【中文标题】iOS 刷新辅助功能标签【英文标题】:iOS Refresh Accessibility Label 【发布时间】:2017-08-23 07:08:32 【问题描述】:

我有一个带有可访问性标签@"a" 的按钮。当按下按钮时,我有一个回调来设置可访问性标签button.accessibilityLabel = @"b"。我知道这行代码运行。但是,如果我再次点击该按钮,VoiceOver 仍会读取 a。不幸的是,我正在使用的代码是专有的,所以我不能直接分享它。

但是,总的来说,我想知道哪些问题可能导致 VoiceOver 无法识别标签的更新。

【问题讨论】:

您的问题不清楚,请尝试发布您的代码和您的尝试 你的问题不清楚 所问内容的任何不清楚都是由于读者的无知。这是一个很好的问题,有一个有价值的答案。 【参考方案1】:

处理动态可访问性标签的最佳方法是覆盖正在聚焦的视图上的属性函数(例如:在 UIButton 上)。这允许两件事。 A:维护比在可以更改的任何地方设置属性要容易得多。 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))
        
    

您也可以使用此逻辑进行调试,并允许设置等。

这里有很多潜在的问题。竞争条件,哪个视图实际获得焦点,是否存在一些父子关系等。覆盖属性并将日志语句添加到上述代码将帮助您了解哪个视图实际获取了请求的可访问性标签以及何时获取。超有价值的资料!

【讨论】:

【参考方案2】:

尝试将UIAccessibilityTraitUpdatesFrequently 添加到您的按钮属性accessibilityTraits

- (void)viewDidLoad 
    myButton.accessibilityTraits |= UIAccessibilityTraitUpdatesFrequently

另外,在更改 accessibilityLabel 时,请确保您在主线程上。

dispatch_async(dispatch_get_main_queue(), ^
    myButton.accessibilityLabel = @"b";
);

【讨论】:

感谢您的建议。我实际上并没有从主线程调用。但是,当我按照您的建议使用 dispatch_async 块时,VoiceOver 仍会读取旧标签。还有其他想法吗? @kmell96,VoiceOver 在点击后立即读取标签(如您使用计算器应用程序所见),尝试在点击后立即将 accessibilityLabel 设置为 nil 并在回调中将其设置为 @ 987654328@ 对 UIAccessibilityTraitUpdatesFrequently 的引用会误导该特征的用途。这篇文章的其余部分是合理的。【参考方案3】:

在更改按钮文本时使用它

UIAccessibility.post(notification: .layoutChanged, argument: yourButton)

【讨论】:

【参考方案4】:

您真的不需要一种方法来刷新标签上的配音。它自动完成。我已经尝试过了,它按预期工作。

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"
    

什么声音超话:

Hello 按钮-pause-按钮-pause-点按此处开始操作

点击按钮

Hello 按钮,点按一次

再点一下

Hello 按钮,点按两次

【讨论】:

Topicstarter 做同样的事情,但 VoiceOver 没有捕捉到编辑 Downvoters 我需要你们有价值的 cmets 来改善这一点。 @GRiMe2D,你怎么知道 topicstarter 做了同样的事情?我已经粘贴了一个简单的 sn-p 它是如何工作的,所以这个 OP 不会错过任何重要的东西。如果 OP 的情况不同,我们可以更新问题和答案。

以上是关于iOS 刷新辅助功能标签的主要内容,如果未能解决你的问题,请参考以下文章

相机快照按钮的辅助功能标签是啥?

有没有办法在导航栏后退按钮上自定义辅助功能标签?

如何为 UIPickerView 行设置 Voice Over 辅助功能标签?

由于辅助功能设置未检测到 iOS 手势

iOS 模拟器辅助功能检查员冻结

更改焦点时不读取辅助功能提示