Now learning that UIStackView's accessibility behaves by default reads the arrangedSubviews in order when voice over is on. Assume I have this hierarchy:
UIView
- UIStackView
-view1
-view2
-view3
-view4
- collapsibleSpecialView
collapsibleSpecialView
is anchored on top of view4:
etc
|------------------|
| view3 |
|------------------|
| collapsible | <- when collapsed overlaps with vw3 to vw1
|------------------|
| view4 |
|------------------|
I need voice over to read my elements in such order above. But since stackView needs to finish first all its accessible subviews my collapsible view is read last but I need it read before view4.
I cannot add it to stackview because when collapsibleView collapse it will push up everything above it. and I don't want to hack around auto-layout to get around that problem.
What I thought that could work is insert an invisible proxy UIView
just before view4 and in that ProxyView override its methods to return accessible elements .
public class ProxyView: UIView {
private var view: UIView?
/// view is the collapsibleView
@objc public convenience init(view: UIView) {
self.init()
self.isAccessibilityElement = true
self.view = view
}
public override func accessibilityElementCount() -> Int {
return 1
}
public override func accessibilityElement(at index: Int) -> Any? {
guard let menu = view else { return nil }
return menu
}
public override func index(ofAccessibilityElement element: Any) -> Int {
return 0
}
}
With this voiceover is able to read my ProxyView before the view4
but for some reason it does not enter the collapsibleView, swiping right shifts the focus to view4.
If my understanding with UIAccessibilityContainer is correct this should theoretically work but it's not. What am I missing? Thanks