Element
Overview
Section titled “Overview”An Element is a single UI component drawn from the AT-SPI2 accessibility tree. Buttons, text fields, menu items, sliders, tables, and every other widget all become Element primitives. For applications without AT-SPI2 support, the compositor generates fallback elements from surface metadata.
Elements form a tree. Each element has a parent (except roots) and zero or more children. The root of the tree for a given surface is referenced by Surface.atspi2_root. When System Intelligence needs to click a button or read text from a field, it addresses the target by element ID.
JSON Schema
Section titled “JSON Schema”{ "$schema": "http://json-schema.org/draft-07/schema#", "title": "Element", "type": "object", "required": ["id", "surface_id", "app_id", "role", "states", "geometry", "actions"], "properties": { "id": { "type": "string", "description": "atspi:{bus}:{path} | surf:... | native:..." }, "surface_id": { "type": "string" }, "app_id": { "type": "string" }, "role": { "type": "string", "description": "AtspiRole name. See the role registry below." }, "name": { "type": ["string", "null"], "description": "Accessible name (label). Null for decorative elements." }, "description": { "type": ["string", "null"], "description": "Accessible description, supplementary to name." }, "states": { "type": "array", "items": { "type": "string" }, "description": "Current AT-SPI2 states." }, "geometry": { "type": "object", "required": ["x", "y", "w", "h"], "properties": { "x": { "type": "integer" }, "y": { "type": "integer" }, "w": { "type": "integer", "minimum": 0 }, "h": { "type": "integer", "minimum": 0 } } }, "parent": { "type": ["string", "null"], "description": "Parent element ID. Null for root elements." }, "children": { "type": "array", "items": { "type": "string" }, "description": "Child element IDs." }, "actions": { "type": "array", "items": { "type": "string" }, "description": "AT-SPI2 supported actions." }, "text": { "type": ["string", "null"], "description": "Current text content for text/entry/document roles." }, "text_selection": { "type": ["object", "null"], "properties": { "start": { "type": "integer" }, "end": { "type": "integer" }, "text": { "type": "string" } }, "description": "Current text selection, if any." }, "caret_position": { "type": ["integer", "null"], "description": "Current caret position in text content." }, "value": { "type": ["object", "null"], "properties": { "current": { "type": "number" }, "minimum": { "type": "number" }, "maximum": { "type": "number" }, "step": { "type": ["number", "null"] }, "text": { "type": ["string", "null"] } }, "description": "Current value for slider/progress/spin_button/checkbox roles." }, "table_info": { "type": ["object", "null"], "properties": { "rows": { "type": "integer" }, "columns": { "type": "integer" }, "selected_rows": { "type": "array", "items": { "type": "integer" } }, "selected_columns": { "type": "array", "items": { "type": "integer" } } }, "description": "Table/grid metadata for table roles." }, "relationships": { "type": "object", "properties": { "labelled_by": { "type": ["string", "null"] }, "label_for": { "type": ["string", "null"] }, "controller_of": { "type": ["string", "null"] }, "controlled_by": { "type": ["string", "null"] }, "member_of": { "type": ["array", "null"], "items": { "type": "string" } } } }, "fallback_note": { "type": ["string", "null"], "description": "Set on compositor-only fallback elements. Describes the limitation." } }}ElementId Format
Section titled “ElementId Format”Element IDs carry a source prefix that indicates where the element came from:
| Prefix | Source | Description |
|---|---|---|
atspi:{bus}:{path} |
AT-SPI2 tree | Standard toolkit applications (GTK, Qt). The daemon’s element auto-resolution splits on colons to recover the D-Bus path. |
surf:... |
Compositor fallback | Apps without accessibility support. The compositor generates these from surface metadata. |
native:... |
Tier 1 app-defined | Applications that define their own element IDs through the PcpServer trait. |
The atspi: prefix is the most common. The bus and path components come from the D-Bus accessible object path in the AT-SPI2 registry.
AtspiRole Registry (69 roles)
Section titled “AtspiRole Registry (69 roles)”Every element has exactly one role. The role determines what actions are available, what additional fields are populated, and what capability actions the Tier 2 adapter derives. The table below lists all 69 roles from core::element::role::AtspiRole along with the Tier 2 derived actions.
Window and container roles
Section titled “Window and container roles”| Role | Tier 2 derives |
|---|---|
Application |
structural root |
Window, Frame, Dialog, Alert |
focus, close, minimize, maximize, activate |
Panel, ScrollPane, Section, Embedded, Unknown |
structural |
Interactive controls
Section titled “Interactive controls”| Role | Tier 2 derives |
|---|---|
PushButton, ToggleButton |
click |
CheckBox, RadioButton |
click, set_value |
ComboBox, SpinButton, Slider, Dial, ScrollBar |
set_value |
PageTab, PageTabList |
click |
Text elements
Section titled “Text elements”| Role | Tier 2 derives |
|---|---|
Entry, Text, Paragraph, DocumentText |
set_text, get_text |
Heading, Label, Static, Icon, Image |
get_text (readable content) |
DocumentWeb, DocumentSpreadsheet, DocumentPresentation, DocumentEmail |
get_text |
Link |
click |
Terminal |
get_text |
Collection elements
Section titled “Collection elements”| Role | Tier 2 derives |
|---|---|
List, ListBox, ListItem, Tree, TreeTable, TreeItem |
structural (plus selection states) |
Table, TableCell, TableColumnHeader, TableRowHeader, Grid |
get_text (cells) |
Menu elements
Section titled “Menu elements”| Role | Tier 2 derives |
|---|---|
MenuBar, Menu, MenuItem, CheckMenuItem, RadioMenuItem, Separator |
click |
Specialized roles
Section titled “Specialized roles”| Role | Tier 2 derives |
|---|---|
Canvas, Animation, Chart |
structural |
ProgressBar |
get_value (via states) |
StatusBar, ToolBar, ToolTip |
structural |
Calendar, ColorChooser, FileChooser, FontChooser |
click, set_value (inputs) |
Any role may additionally expose toolkit-declared actions, forwarded verbatim into Element.actions and invokable through the adapter’s method-aware execution path.
AtspiState
Section titled “AtspiState”An element can have any combination of states. The states array reflects the current runtime state of the widget.
Common states include: enabled, disabled, visible, invisible, showing, hidden, focusable, focused, selected, selectable, checked, unchecked, indeterminate, editable, read_only, expandable, expanded, collapsed, multiselectable, required, invalid_entry, supports_autocompletion, transient, vertical, horizontal, modal, multiline, protected, stale, busy, resizable, movable.
States are strings in the wire format and enum variants in the Rust type. The two representations are equivalent.
Supporting Types
Section titled “Supporting Types”ElementRelationships
Section titled “ElementRelationships”pub struct ElementRelationships { pub labelled_by: Option<ElementId>, // another element provides this label pub label_for: Option<ElementId>, // this element labels another pub controller_of: Option<ElementId>, // this element controls another's state pub controlled_by: Option<ElementId>, // this element's state is controlled pub member_of: Option<Vec<ElementId>>, // belongs to a named group}Relationships express semantic connections beyond the parent/child tree structure. A slider might have a label_for pointing to the text field it controls, for example.
TableInfo
Section titled “TableInfo”pub struct TableInfo { pub rows: usize, pub columns: usize, pub selected_rows: Vec<usize>, pub selected_columns: Vec<usize>,}Populated only for Table, Grid, and TreeTable roles. Tracks dimensions and current selections.
TextSelection
Section titled “TextSelection”pub struct TextSelection { pub start: usize, pub end: usize, pub text: String,}Character offsets into the element’s text field. Only populated when a selection exists on text-entry and document roles.
ValueInfo
Section titled “ValueInfo”pub struct ValueInfo { pub current: f64, pub minimum: f64, pub maximum: f64, pub step: Option<f64>, pub text: Option<String>,}Populated for roles that represent a scalar value: Slider, ProgressBar, SpinButton, CheckBox.
Example
Section titled “Example”{ "id": "atspi:::0.5:12/document/push_button", "surface_id": "surf:12-w1", "app_id": "com.example.present", "role": "push_button", "name": "Add Slide", "description": "Insert a new slide at the end of the deck", "states": ["enabled", "visible", "focusable"], "geometry": { "x": 150, "y": 598, "w": 120, "h": 36 }, "parent": "atspi:::0.5:12/document/toolbar", "children": [], "actions": ["activate"], "text": null, "text_selection": null, "caret_position": null, "value": null, "table_info": null, "relationships": { "labelled_by": null, "label_for": null, "controller_of": null, "controlled_by": null, "member_of": null }, "fallback_note": null}This is a fully accessible button from the AT-SPI2 tree. It has one supported action (activate) and is currently enabled, visible, and focusable. The atspi: prefix in the ID means the daemon can split on colons to recover the D-Bus path for method-aware execution.
Fallback Elements
Section titled “Fallback Elements”When an application has no AT-SPI2 support, the compositor generates fallback elements with the surf: prefix. These carry a fallback_note describing the limitation. Available actions are limited to basic window management (focus, close, minimize, maximize). Interacting with anything inside a fallback surface requires input simulation rather than AT-SPI2 action invocation.