4
4
// the LICENSE-MIT file), at your option.
5
5
6
6
use accesskit:: { FrozenNode as NodeData , NodeId , Tree as TreeData , TreeUpdate } ;
7
- use alloc:: { sync :: Arc , vec} ;
7
+ use alloc:: vec;
8
8
use core:: fmt;
9
9
use hashbrown:: { HashMap , HashSet } ;
10
- use immutable_chunkmap:: map:: MapM as ChunkMap ;
11
10
12
11
use crate :: node:: { Node , NodeState , ParentAndIndex } ;
13
12
14
13
#[ derive( Clone , Debug ) ]
15
14
pub struct State {
16
- pub ( crate ) nodes : ChunkMap < NodeId , NodeState > ,
15
+ pub ( crate ) nodes : HashMap < NodeId , NodeState > ,
17
16
pub ( crate ) data : TreeData ,
18
17
pub ( crate ) focus : NodeId ,
19
18
is_host_focused : bool ,
@@ -28,10 +27,10 @@ struct InternalChanges {
28
27
29
28
impl State {
30
29
fn validate_global ( & self ) {
31
- if self . nodes . get_key ( & self . data . root ) . is_none ( ) {
30
+ if ! self . nodes . contains_key ( & self . data . root ) {
32
31
panic ! ( "Root id #{} is not in the node list" , self . data. root. 0 ) ;
33
32
}
34
- if self . nodes . get_key ( & self . focus ) . is_none ( ) {
33
+ if ! self . nodes . contains_key ( & self . focus ) {
35
34
panic ! ( "Focused id #{} is not in the node list" , self . focus. 0 ) ;
36
35
}
37
36
}
@@ -56,17 +55,17 @@ impl State {
56
55
let mut pending_children = HashMap :: new ( ) ;
57
56
58
57
fn add_node (
59
- nodes : & mut ChunkMap < NodeId , NodeState > ,
58
+ nodes : & mut HashMap < NodeId , NodeState > ,
60
59
changes : & mut Option < & mut InternalChanges > ,
61
60
parent_and_index : Option < ParentAndIndex > ,
62
61
id : NodeId ,
63
62
data : NodeData ,
64
63
) {
65
64
let state = NodeState {
66
65
parent_and_index,
67
- data : Arc :: new ( data ) ,
66
+ data,
68
67
} ;
69
- nodes. insert_cow ( id, state) ;
68
+ nodes. insert ( id, state) ;
70
69
if let Some ( changes) = changes {
71
70
changes. added_node_ids . insert ( id) ;
72
71
}
@@ -87,9 +86,12 @@ impl State {
87
86
}
88
87
unreachable. remove ( child_id) ;
89
88
let parent_and_index = ParentAndIndex ( node_id, child_index) ;
90
- if let Some ( child_state) = self . nodes . get_mut_cow ( child_id) {
89
+ if let Some ( child_state) = self . nodes . get_mut ( child_id) {
91
90
if child_state. parent_and_index != Some ( parent_and_index) {
92
91
child_state. parent_and_index = Some ( parent_and_index) ;
92
+ if let Some ( changes) = & mut changes {
93
+ changes. updated_node_ids . insert ( * child_id) ;
94
+ }
93
95
}
94
96
} else if let Some ( child_data) = pending_nodes. remove ( child_id) {
95
97
add_node (
@@ -105,7 +107,7 @@ impl State {
105
107
seen_child_ids. insert ( * child_id) ;
106
108
}
107
109
108
- if let Some ( node_state) = self . nodes . get_mut_cow ( & node_id) {
110
+ if let Some ( node_state) = self . nodes . get_mut ( & node_id) {
109
111
if node_id == root {
110
112
node_state. parent_and_index = None ;
111
113
}
@@ -114,8 +116,8 @@ impl State {
114
116
unreachable. insert ( * child_id) ;
115
117
}
116
118
}
117
- if * node_state. data != node_data {
118
- node_state. data = Arc :: new ( node_data) ;
119
+ if node_state. data != node_data {
120
+ node_state. data . clone_from ( & node_data) ;
119
121
if let Some ( changes) = & mut changes {
120
122
changes. updated_node_ids . insert ( node_id) ;
121
123
}
@@ -147,14 +149,14 @@ impl State {
147
149
148
150
if !unreachable. is_empty ( ) {
149
151
fn traverse_unreachable (
150
- nodes : & mut ChunkMap < NodeId , NodeState > ,
152
+ nodes : & mut HashMap < NodeId , NodeState > ,
151
153
changes : & mut Option < & mut InternalChanges > ,
152
154
id : NodeId ,
153
155
) {
154
156
if let Some ( changes) = changes {
155
157
changes. removed_node_ids . insert ( id) ;
156
158
}
157
- let node = nodes. remove_cow ( & id) . unwrap ( ) ;
159
+ let node = nodes. remove ( & id) . unwrap ( ) ;
158
160
for child_id in node. data . children ( ) . iter ( ) {
159
161
traverse_unreachable ( nodes, changes, * child_id) ;
160
162
}
@@ -240,6 +242,7 @@ pub trait ChangeHandler {
240
242
#[ derive( Debug ) ]
241
243
pub struct Tree {
242
244
state : State ,
245
+ next_state : State ,
243
246
}
244
247
245
248
impl Tree {
@@ -248,17 +251,16 @@ impl Tree {
248
251
panic ! ( "Tried to initialize the accessibility tree without a root tree. TreeUpdate::tree must be Some." ) ;
249
252
} ;
250
253
let mut state = State {
251
- nodes : ChunkMap :: new ( ) ,
254
+ nodes : HashMap :: new ( ) ,
252
255
data : tree,
253
256
focus : initial_state. focus ,
254
257
is_host_focused,
255
258
} ;
256
259
state. update ( initial_state, is_host_focused, None ) ;
257
- Self { state }
258
- }
259
-
260
- pub fn update ( & mut self , update : TreeUpdate ) {
261
- self . state . update ( update, self . state . is_host_focused , None ) ;
260
+ Self {
261
+ next_state : state. clone ( ) ,
262
+ state,
263
+ }
262
264
}
263
265
264
266
pub fn update_and_process_changes (
@@ -267,14 +269,9 @@ impl Tree {
267
269
handler : & mut impl ChangeHandler ,
268
270
) {
269
271
let mut changes = InternalChanges :: default ( ) ;
270
- let old_state = self . state . clone ( ) ;
271
- self . state
272
+ self . next_state
272
273
. update ( update, self . state . is_host_focused , Some ( & mut changes) ) ;
273
- self . process_changes ( old_state, changes, handler) ;
274
- }
275
-
276
- pub fn update_host_focus_state ( & mut self , is_host_focused : bool ) {
277
- self . state . update_host_focus_state ( is_host_focused, None ) ;
274
+ self . process_changes ( changes, handler) ;
278
275
}
279
276
280
277
pub fn update_host_focus_state_and_process_changes (
@@ -283,55 +280,69 @@ impl Tree {
283
280
handler : & mut impl ChangeHandler ,
284
281
) {
285
282
let mut changes = InternalChanges :: default ( ) ;
286
- let old_state = self . state . clone ( ) ;
287
- self . state
283
+ self . next_state
288
284
. update_host_focus_state ( is_host_focused, Some ( & mut changes) ) ;
289
- self . process_changes ( old_state , changes, handler) ;
285
+ self . process_changes ( changes, handler) ;
290
286
}
291
287
292
- fn process_changes (
293
- & self ,
294
- old_state : State ,
295
- changes : InternalChanges ,
296
- handler : & mut impl ChangeHandler ,
297
- ) {
288
+ fn process_changes ( & mut self , changes : InternalChanges , handler : & mut impl ChangeHandler ) {
298
289
for id in & changes. added_node_ids {
299
- let node = self . state . node_by_id ( * id) . unwrap ( ) ;
290
+ let node = self . next_state . node_by_id ( * id) . unwrap ( ) ;
300
291
handler. node_added ( & node) ;
301
292
}
302
293
for id in & changes. updated_node_ids {
303
- let old_node = old_state . node_by_id ( * id) . unwrap ( ) ;
304
- let new_node = self . state . node_by_id ( * id) . unwrap ( ) ;
294
+ let old_node = self . state . node_by_id ( * id) . unwrap ( ) ;
295
+ let new_node = self . next_state . node_by_id ( * id) . unwrap ( ) ;
305
296
handler. node_updated ( & old_node, & new_node) ;
306
297
}
307
- if old_state . focus_id ( ) != self . state . focus_id ( ) {
308
- let old_node = old_state . focus ( ) ;
298
+ if self . state . focus_id ( ) != self . next_state . focus_id ( ) {
299
+ let old_node = self . state . focus ( ) ;
309
300
if let Some ( old_node) = & old_node {
310
301
let id = old_node. id ( ) ;
311
302
if !changes. updated_node_ids . contains ( & id)
312
303
&& !changes. removed_node_ids . contains ( & id)
313
304
{
314
- if let Some ( old_node_new_version) = self . state . node_by_id ( id) {
305
+ if let Some ( old_node_new_version) = self . next_state . node_by_id ( id) {
315
306
handler. node_updated ( old_node, & old_node_new_version) ;
316
307
}
317
308
}
318
309
}
319
- let new_node = self . state . focus ( ) ;
310
+ let new_node = self . next_state . focus ( ) ;
320
311
if let Some ( new_node) = & new_node {
321
312
let id = new_node. id ( ) ;
322
313
if !changes. added_node_ids . contains ( & id) && !changes. updated_node_ids . contains ( & id)
323
314
{
324
- if let Some ( new_node_old_version) = old_state . node_by_id ( id) {
315
+ if let Some ( new_node_old_version) = self . state . node_by_id ( id) {
325
316
handler. node_updated ( & new_node_old_version, new_node) ;
326
317
}
327
318
}
328
319
}
329
320
handler. focus_moved ( old_node. as_ref ( ) , new_node. as_ref ( ) ) ;
330
321
}
331
322
for id in & changes. removed_node_ids {
332
- let node = old_state . node_by_id ( * id) . unwrap ( ) ;
323
+ let node = self . state . node_by_id ( * id) . unwrap ( ) ;
333
324
handler. node_removed ( & node) ;
334
325
}
326
+ for id in changes. added_node_ids {
327
+ self . state
328
+ . nodes
329
+ . insert ( id, self . next_state . nodes . get ( & id) . unwrap ( ) . clone ( ) ) ;
330
+ }
331
+ for id in changes. updated_node_ids {
332
+ self . state
333
+ . nodes
334
+ . get_mut ( & id)
335
+ . unwrap ( )
336
+ . clone_from ( self . next_state . nodes . get ( & id) . unwrap ( ) ) ;
337
+ }
338
+ for id in changes. removed_node_ids {
339
+ self . state . nodes . remove ( & id) ;
340
+ }
341
+ if self . state . data != self . next_state . data {
342
+ self . state . data . clone_from ( & self . next_state . data ) ;
343
+ }
344
+ self . state . focus = self . next_state . focus ;
345
+ self . state . is_host_focused = self . next_state . is_host_focused ;
335
346
}
336
347
337
348
pub fn state ( & self ) -> & State {
0 commit comments