Skip to content

Improve accessibility#14414

Draft
us-ravindra wants to merge 7 commits intotidev:mainfrom
us-ravindra:fix-accessibility
Draft

Improve accessibility#14414
us-ravindra wants to merge 7 commits intotidev:mainfrom
us-ravindra:fix-accessibility

Conversation

@us-ravindra
Copy link
Copy Markdown

@us-ravindra us-ravindra commented Mar 28, 2026

Here's the updated PR description with the latest commit details added:


This PR adds full cross-platform accessibility support to the Titanium SDK, introducing new properties on Ti.UI.View, a new cross-platform Ti.Accessibility module, and a fontScaleChanged event on Ti.App.

Changes

1. Cross-Platform Accessibility Properties on Ti.UI.View

  • accessibilityRole — semantic role (e.g., button, header, link).
  • accessibilityState — current state (e.g., disabled, checked).
  • accessibilityActions — custom accessibility actions.
  • accessibilityDisableLongPress — suppress "Double tap and hold" announcement.
  • accessibilityDisableClick — suppress "Double tap to activate" announcement (Android).
  • accessibilityViewIsModal — marks a view as a modal for accessibility, hiding sibling content from screen readers (VoiceOver/TalkBack).

2. Ti.Accessibility Module (iOS & Android)

  • Added new core module to provide programmatic access to accessibility APIs natively across both platforms.
  • announce(message): Programmatically reads out a string via VoiceOver (iOS) or TalkBack (Android).
  • focus(viewProxy): Immediately routes focus to a specific element without causing bounce/race conditions (fixed by removing synthetic delays and input-focus emulation).
  • Fixed iOS JSValue unwrapping issues when calling focus directly with UI views.

3. fontScaleChanged Event on Ti.App

  • iOS: Listens for UIContentSizeCategoryDidChangeNotification, fires with { category } (e.g., "UICTContentSizeCategoryXL").
  • Android: Monitors Configuration.fontScale via ConfigurationChangedListener, fires with { value } (e.g., 1.3).

Files Changed

Area Files
Android Core TiC.java, TiViewProxy.java, TiUIView.java, titanium.js
Android Modules AppModule.java, AccessibilityModule.java
iOS Core TiUIView.h, TiUIView.m, TiViewProxy.m, TiWindowProxy.m, AppModule.m, KrollModule.m
iOS Modules AccessibilityModule.h, AccessibilityModule.m
Project Configs project.pbxproj, project.xcconfig, build.gradle
API Docs Accessibility.yml, App.yml, View.yml
Tests ti.app.test.js, ti.ui.accessibility.test.js

Testing

  • ✅ iOS SDK builds successfully
  • ✅ Android SDK builds successfully
  • ✅ Java style checks pass
  • ✅ ObjC clang-format passes
  • ✅ JS oxlint passes
  • ✅ Unit tests added for new properties and events
  • ✅ Verified TalkBack/VoiceOver focus stability across platform window transitions

- Added announce() and focus() methods for Android
- Registered module in the kernel for both platforms
- Fixed iOS JSValue unwrapping race conditions
@m1ga
Copy link
Copy Markdown
Contributor

m1ga commented Mar 31, 2026

Nice PR 👍 It's adding/changing a lot so it will take some time to get it fully reviewed and tested. One thing you could change already: check how the comments are done for other methods e.g. in TiUIView and use the same structure.

@hansemannn
Copy link
Copy Markdown
Collaborator

Looking at the changes and cross-platform coverage, this could better be a module:

  • The changes are in an own module namespace already, separated from other core code
  • Good cross platform coverage for a proper module
  • Keeps the core free from new namespace => keep app build time short

@us-ravindra
Copy link
Copy Markdown
Author

Thanks for the feedback @m1ga, @hansemannn

I can work on implementing this as a separate module, but I wanted to confirm a few things first.

  1. We already have accessibilityLabel, accessibilityValue, accessibilityHint, and accessibilityHidden available on Ti.UI.View. I’m proposing to add additional properties such as accessibilityRole, accessibilityState, accessibilityActions, accessibilityDisableClick, and accessibilityViewIsModal. Would it be acceptable to include these directly in the SDK?The reason I’m asking is due to how Titanium handles view creation. Since views are lazily instantiated at the native level, setting these properties at the time of Ti.UI.createView() in a separate module may fail silently because the native view may not yet exist. This would require developers to defer applying these properties until after the view is attached or rendered (e.g., using the postlayout event), like in the example below:

win.addEventListener('postlayout', () => {
  TiAccessibility.applyProperties(myView, {
    accessibilityRole: 'button',
    accessibilityState: { selected: true },
    accessibilityViewIsModal: true
  });
});
  1. Additionally, I’ve added a fontScaleChanged event to the existing AppModule. I had initially implemented this as a separate module, but felt it would be more appropriate to include it directly in the SDK. Should I remove this from sdk code?

  2. At the moment, In Ti.Accessibility Module I have added only two methods—focus and announce. I can move these into a separate module if needed, which would also help reduce build time.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants