From c22a28aafccd56304126f2a99fe743eee7130175 Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Thu, 25 Jun 2026 18:47:53 +0200 Subject: [PATCH 1/6] Create ARCHITECTURE.md --- ARCHITECTURE.md | 142 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 142 insertions(+) create mode 100644 ARCHITECTURE.md diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md new file mode 100644 index 00000000..79763a9c --- /dev/null +++ b/ARCHITECTURE.md @@ -0,0 +1,142 @@ +# ARCHITECTURE + +AccessKit is a cross-platform, cross-language abstraction over accessibility APIs, so toolkit developers only have to implement accessibility once. + +The expected userbase of AccessKit is developers who are writing a UI toolkit and want their toolkit to communicate with screen readers and other assistive technologies so that apps developed with the toolkit are accessible to a wider audience. + + +## Data schema + +The heart of AccessKit is a data schema that defines all the data required to render an accessible UI for screen readers and other assistive technologies. + +The schema represents a tree structure, in which each node is either a single UI element or an element cluster such as a window or document. Each node has an integer ID, a role (e.g. button, label, or text input), and a variety of optional attributes. + +The schema also defines actions that can be requested by assistive technologies, such as moving the keyboard focus, invoking a button, or selecting text. The schema is based largely on Chromium's cross-platform accessibility abstraction. + + +## File structure + +- `common/` is the main accesskit crate, it's where there is what you need to import accesskit. You use this crate to build a representation for your accessibility tree. +- `platforms/` is where you'll find the backends, crates that expose the constructed accessibility trees to the platform APIs. +- `consumer/` defines common code used by backends. Most accesskit users don't need to use that crate. + +### `consumer/` + +This folder holds the `accesskit_consumer` crate, which defines types and functions used by backend. + +You're unlikely to need to look at `accesskit_consumer` unless you're writing a platform backend or a testing system for accesskit. + +`accesskit_consumer::Tree` is the type that retains the accessibility tree in memory and updates it when a new `TreeUpdate` is emitted (see `accesskit` section). + +### `platforms/` + +Crates in the `platforms/` folder are what we call "adapters". + +Adapters translate between accesskit's tree format and a given platform's accessibility API. + +Adapters are best-effort implementations and may not cover all the accessibility APIs of their platform. + +Anecdotally, adapters have very similar code; the main difference between platform APIs is the threading model. + + +## `accesskit` crate + +This is the repository's, main crate, stored in the `common/` folder. + +The main types exported by the crate are: + +- `Node` +- `Role` +- `TreeUpdate` +- `Action` + +### `Node` + +A `Node` represents the frozen state of a semantic UI element. + +A node can be a button, a date input, a widget group, a text run, a window, etc. + +A node is defined by: + +- A `Role`, which indicates how accessibility APIs should interpret the node. +- A list of properties, semantic information about the node. +- A list of actions that the node can receive. + +For instance, a button will have the role `Button`, may have properties like "label", "disabled", "bounds", etc, and can receive the actions `Focus`, `Blur` and `Click`. + +The exact list of which properties and actions apply to which roles is vague and undocumented, but mostly matches ARIA guidelines for equivalent roles. + + +### `TreeUpdate` + +A `TreeUpdate` is a list of changes that applies to your accessibility tree. Its definition looks like: + +```rust +pub struct TreeUpdate { + pub nodes: Vec<(NodeId, Node)>, + pub tree: Option, + pub tree_id: TreeId, + pub focus: NodeId, +} +``` + +`nodes` is the important field here. + +If `nodes` is an empty `Vec`, the node tree will stay unchanged. Otherwise, each included node will be updated. + +You add new nodes by updating the parent with a children list that includes the id of new node, and you remove nodes by updating the parent with a children list without the if of the removed node. + +`tree_id` indicates which tree is affected (see **Sub-trees** section). + +The other two `TreeUpdate` fields (`tree`, `focus`) affect basic tree metadata. + +(If you include a node, you have to re-specify everything, otherwise you erase all properties) + + + +### `Action` + +Each node has a set of actions that it accepts. + +When you register that a node accepts certain actions, accesskit may give you `ActionRequest` values: + +```rust +pub struct ActionRequest { + pub action: Action, + pub target_tree: TreeId, + pub target_node: NodeId, + pub data: Option, +} +``` + +Action requests are usually sent based on user input. + +For instance, if you register a node with a `Button` role, an `"Apply"` label and that the node accepts `Action::Click`, if the user uses some voice control software and says "Click the 'Apply' button", your application will receive an `ActionRequest` with `Action::Click` targetting that node. + + +### Sub-trees + +An app's accessibility tree can be composed of several subtrees. + +The idea behind subtrees is to allow different actors to produce accessibility trees without coordinating (for example, because they're separate processes in a browser), and let the main application submit them to the adapters, which take care of combining them. + +The main way this separation manifests is in namespacing: each subtree can pick whatever `NodeId`s it wants without worrying about colliding with other subtree's `NodeId`s. +`NodeId(123)` in one subtree and `NodeId(123)` in another subtree refer to completely different nodes + +Subtrees are composed through "graft nodes", `Node` instances with a "tree_id" property set to the id of the subtree. + +Each sub-tree has to be submitted to the adapter with a separate `TreeUpdate`. When presented to the platform's accessibility APIs, the sub trees will be stitched together and submitted as a single accessibility tree. + + +## Specification + +Accesskit is currently sparsely documented (see accesskit#402), and some values are subject to interpretation. AccessKit is inspired by Chromium's accessibility API, which is undocumented, and by the ARIA standard. + +In the short term, we plan on documenting which items match the ARIA standard exactly and which have a different or not-in-ARIA meaning. + + +## Testing + +When working on AccesstKit or a project using it, it's important to check the user experience with an actual screen reader (or whatever assistive technology you're trying to support). + +README-APPLICATION-DEVELOPERS.md gives some information about how to do it. From f72a6ac57824962ace5ed7452274290aab0bc9a7 Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Tue, 14 Jul 2026 11:44:57 +0200 Subject: [PATCH 2/6] Regularize spacing --- ARCHITECTURE.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md index 79763a9c..12c7eecb 100644 --- a/ARCHITECTURE.md +++ b/ARCHITECTURE.md @@ -20,6 +20,7 @@ The schema also defines actions that can be requested by assistive technologies, - `platforms/` is where you'll find the backends, crates that expose the constructed accessibility trees to the platform APIs. - `consumer/` defines common code used by backends. Most accesskit users don't need to use that crate. + ### `consumer/` This folder holds the `accesskit_consumer` crate, which defines types and functions used by backend. @@ -28,6 +29,7 @@ You're unlikely to need to look at `accesskit_consumer` unless you're writing a `accesskit_consumer::Tree` is the type that retains the accessibility tree in memory and updates it when a new `TreeUpdate` is emitted (see `accesskit` section). + ### `platforms/` Crates in the `platforms/` folder are what we call "adapters". @@ -50,6 +52,7 @@ The main types exported by the crate are: - `TreeUpdate` - `Action` + ### `Node` A `Node` represents the frozen state of a semantic UI element. @@ -93,7 +96,6 @@ The other two `TreeUpdate` fields (`tree`, `focus`) affect basic tree metadata. (If you include a node, you have to re-specify everything, otherwise you erase all properties) - ### `Action` Each node has a set of actions that it accepts. From e2a8c7d180fe39f4db790e0e8d80ab9784b0a43c Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Tue, 14 Jul 2026 11:48:03 +0200 Subject: [PATCH 3/6] Add TODO about data schema doc. --- ARCHITECTURE.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md index 12c7eecb..e3881c67 100644 --- a/ARCHITECTURE.md +++ b/ARCHITECTURE.md @@ -7,6 +7,8 @@ The expected userbase of AccessKit is developers who are writing a UI toolkit an ## Data schema + + The heart of AccessKit is a data schema that defines all the data required to render an accessible UI for screen readers and other assistive technologies. The schema represents a tree structure, in which each node is either a single UI element or an element cluster such as a window or document. Each node has an integer ID, a role (e.g. button, label, or text input), and a variety of optional attributes. From 177659ab593555677fb8b8cf5e79bb830e2d579f Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Tue, 14 Jul 2026 11:48:34 +0200 Subject: [PATCH 4/6] Remove mentions of "backends" where it should say "adapters" --- ARCHITECTURE.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md index e3881c67..0cd32d14 100644 --- a/ARCHITECTURE.md +++ b/ARCHITECTURE.md @@ -19,15 +19,15 @@ The schema also defines actions that can be requested by assistive technologies, ## File structure - `common/` is the main accesskit crate, it's where there is what you need to import accesskit. You use this crate to build a representation for your accessibility tree. -- `platforms/` is where you'll find the backends, crates that expose the constructed accessibility trees to the platform APIs. -- `consumer/` defines common code used by backends. Most accesskit users don't need to use that crate. +- `platforms/` is where you'll find the adapters, crates that expose the constructed accessibility trees to the platform APIs. +- `consumer/` defines common code used by adapters. Most accesskit users don't need to use that crate. ### `consumer/` -This folder holds the `accesskit_consumer` crate, which defines types and functions used by backend. +This folder holds the `accesskit_consumer` crate, which defines types and functions used by adapters. -You're unlikely to need to look at `accesskit_consumer` unless you're writing a platform backend or a testing system for accesskit. +You're unlikely to need to look at `accesskit_consumer` unless you're writing a platform adapter or a testing system for accesskit. `accesskit_consumer::Tree` is the type that retains the accessibility tree in memory and updates it when a new `TreeUpdate` is emitted (see `accesskit` section). @@ -36,7 +36,7 @@ You're unlikely to need to look at `accesskit_consumer` unless you're writing a Crates in the `platforms/` folder are what we call "adapters". -Adapters translate between accesskit's tree format and a given platform's accessibility API. +Adapters translate between accesskit's tree format and a given platform's accessibility API; you can think of them as backends for accesskit. Adapters are best-effort implementations and may not cover all the accessibility APIs of their platform. From 66c0aa2310aa42dd85988b7ccfac67021a906160 Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Tue, 14 Jul 2026 11:53:11 +0200 Subject: [PATCH 5/6] Tweak descriptions --- ARCHITECTURE.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md index 0cd32d14..289863c5 100644 --- a/ARCHITECTURE.md +++ b/ARCHITECTURE.md @@ -34,7 +34,7 @@ You're unlikely to need to look at `accesskit_consumer` unless you're writing a ### `platforms/` -Crates in the `platforms/` folder are what we call "adapters". +This folder stores a list of crates that we call "adapters". Adapters translate between accesskit's tree format and a given platform's accessibility API; you can think of them as backends for accesskit. @@ -54,6 +54,8 @@ The main types exported by the crate are: - `TreeUpdate` - `Action` +Most of these types are defined in the `lib.rs` file. + ### `Node` From dd47dcb7f0f7004dce7116c70b61714b54b37910 Mon Sep 17 00:00:00 2001 From: Olivier FAURE Date: Tue, 14 Jul 2026 18:28:07 +0200 Subject: [PATCH 6/6] Tweak documentation --- ARCHITECTURE.md | 29 ++++++++++++++++++----------- 1 file changed, 18 insertions(+), 11 deletions(-) diff --git a/ARCHITECTURE.md b/ARCHITECTURE.md index 289863c5..f3f8a3d5 100644 --- a/ARCHITECTURE.md +++ b/ARCHITECTURE.md @@ -18,18 +18,27 @@ The schema also defines actions that can be requested by assistive technologies, ## File structure -- `common/` is the main accesskit crate, it's where there is what you need to import accesskit. You use this crate to build a representation for your accessibility tree. -- `platforms/` is where you'll find the adapters, crates that expose the constructed accessibility trees to the platform APIs. -- `consumer/` defines common code used by adapters. Most accesskit users don't need to use that crate. +The main folders are: + +- `common/` stores the main accesskit crate. +- `consumer/` stores utility code for platform adapters. +- `platforms/` stores platform adapters. + + +### `common/` + +This folder stores the `accesskit` crate, which defines the types you need to build your accessibility tree. + +See **`accesskit` crate overview** section for details. ### `consumer/` -This folder holds the `accesskit_consumer` crate, which defines types and functions used by adapters. +This folder stores the `accesskit_consumer` crate, which defines types and functions used by platform adapters (see next section). You're unlikely to need to look at `accesskit_consumer` unless you're writing a platform adapter or a testing system for accesskit. -`accesskit_consumer::Tree` is the type that retains the accessibility tree in memory and updates it when a new `TreeUpdate` is emitted (see `accesskit` section). +`accesskit_consumer::Tree` is the type that retains the accessibility tree in memory and updates it when a new `TreeUpdate` is emitted (see **`accesskit` crate overview**). ### `platforms/` @@ -40,12 +49,10 @@ Adapters translate between accesskit's tree format and a given platform's access Adapters are best-effort implementations and may not cover all the accessibility APIs of their platform. -Anecdotally, adapters have very similar code; the main difference between platform APIs is the threading model. - +(Anecdotally, adapters have very similar code; the main difference between platform APIs is the threading model.) -## `accesskit` crate -This is the repository's, main crate, stored in the `common/` folder. +## `accesskit` crate overview The main types exported by the crate are: @@ -91,13 +98,13 @@ pub struct TreeUpdate { If `nodes` is an empty `Vec`, the node tree will stay unchanged. Otherwise, each included node will be updated. -You add new nodes by updating the parent with a children list that includes the id of new node, and you remove nodes by updating the parent with a children list without the if of the removed node. +You add new nodes by updating the parent with a children list that includes the id of the new node, and you remove nodes by updating the parent with a children list without the id of the removed node. `tree_id` indicates which tree is affected (see **Sub-trees** section). The other two `TreeUpdate` fields (`tree`, `focus`) affect basic tree metadata. -(If you include a node, you have to re-specify everything, otherwise you erase all properties) +(If you include a node in a `TreeUpdate`, you have to re-specify all its properties, otherwise you erase the ones you haven't specified.) ### `Action`