25 ``` |
25 ``` |
26 |
26 |
27 The macro `cx_tree_node_base_layout` expands to the offsets of the above-mentioned pointers. |
27 The macro `cx_tree_node_base_layout` expands to the offsets of the above-mentioned pointers. |
28 It will become handy when calling the low-level tree functions which expect all offsets to be passed as arguments. |
28 It will become handy when calling the low-level tree functions which expect all offsets to be passed as arguments. |
29 |
29 |
|
30 <warning> |
|
31 TODO: forgot to mention that loc_last_child and loc_prev are optional in all functions. |
|
32 </warning> |
|
33 |
30 Before diving into the function definitions, there are four function pointer declarations you should know. |
34 Before diving into the function definitions, there are four function pointer declarations you should know. |
31 |
35 |
32 ```C |
36 ```C |
33 #include <cx/tree.h> |
37 #include <cx/tree.h> |
34 |
38 |
56 |
60 |
57 A `cx_tree_search_func` behaves exactly the same, except that it does expect a pointer to the `data` but a pointer to a node structure. |
61 A `cx_tree_search_func` behaves exactly the same, except that it does expect a pointer to the `data` but a pointer to a node structure. |
58 In combination with the `cx_tree_node_create_func`, when inserting nodes with the high-level functions, a `new_node` is created first, |
62 In combination with the `cx_tree_node_create_func`, when inserting nodes with the high-level functions, a `new_node` is created first, |
59 and then an appropriate insertion point is searched with the `cx_tree_search_func`. |
63 and then an appropriate insertion point is searched with the `cx_tree_search_func`. |
60 |
64 |
61 A `cx_tree_relink_func` is used when an intermediate node is removed from the tree and it's children need to be detached from |
65 A `cx_tree_relink_func` is called when an intermediate node was removed from the tree and it's children need to be detached from |
62 the removed `old_parent` and attached to a `new_parent`. |
66 the removed `old_parent` and attached to a `new_parent`. |
|
67 The function is called for every child of the removed node and can be used, for example, to update the contents of the node when needed. |
63 |
68 |
64 ## Create |
69 ## Create |
65 |
70 |
66 ```C |
71 ```C |
67 #include <cx/tree.h> |
72 #include <cx/tree.h> |
254 cx_tree_relink_func relink_func); |
259 cx_tree_relink_func relink_func); |
255 |
260 |
256 void cxTreeRemoveSubtree(CxTree *tree, void *node); |
261 void cxTreeRemoveSubtree(CxTree *tree, void *node); |
257 ``` |
262 ``` |
258 |
263 |
259 <warning> |
264 The low-level function `cx_tree_unlink()` removes the specified `node`, |
260 TODO: document |
265 as well as the entire subtree beneath that node, from its parent. |
261 </warning> |
266 The high-level counterpart is `cxTreeRemoveSubtree()`. |
|
267 |
|
268 The function `cxTreeRemoveNode()`, on the other hand, _only_ removes the `node` from the tree, |
|
269 links all children of `node` to the former parent of `node`, |
|
270 and calls the optional `relink_func` for every former child of `node` which will be relinked to a new parent. |
|
271 Therefore, calling `cxTreeRemoveNode()` on the `root` node is an error and the function returns non-zero. |
|
272 In all other cases, the function returns zero. |
|
273 |
|
274 > When your tree is storing a scene graph, for example, a possible use-case for the `relink_func` might be updating |
|
275 > the world transform matrices in the subtree of the removed node. |
262 |
276 |
263 ## Dispose |
277 ## Dispose |
264 |
278 |
265 ```C |
279 ```C |
266 #include <cx/tree.h> |
280 #include <cx/tree.h> |
273 void cxTreeClear(CxTree *tree); |
287 void cxTreeClear(CxTree *tree); |
274 |
288 |
275 void cxTreeFree(CxTree *tree); |
289 void cxTreeFree(CxTree *tree); |
276 ``` |
290 ``` |
277 |
291 |
278 <warning> |
292 The function `cxTreeDestroyNode()` first [removes](#remove) the `node` from the tree, like `cxTreeRemoveNode()`, |
279 TODO: document and mention the destructor support |
293 and then invokes the [destructor functions](collection.h.md#destructor-functions). |
280 </warning> |
294 It is guaranteed, that the simple destructor is called before the advanced destructor. |
|
295 If no destructor function is registered at all, the behavior is identical to `cxTreeRemoveNode()`. |
|
296 That means, this function does not deallocate the memory for the node on its own and leaves that entirely to the destructor functions. |
|
297 |
|
298 The function `cxTreeDestroySubtree()` performs the above actions for the entire subtree starting with `node`. |
|
299 The order in which the destructor functions for the nodes of the subtree are called are determined by a [tree iterator](#iterator-and-visitor). |
|
300 |
|
301 The function `cxTreeClear()` is a shorthand for invoking `cxTreeDestroySubtree()` on the root node of the tree. |
|
302 |
|
303 The function `cxTreeFree()` behaves like `cxTreeClear()` and then deallocates the memory for the `CxTree` structure. |
|
304 |
|
305 > Although `CxTree` supports the general concept of [destructor functions](collection.h.md#destructor-functions), |
|
306 > it is not based on `CX_COLLECTION_BASE`. |
|
307 > Therefore, the `cxDefineDestructor()` and `cxDefineAdvancedDestructor()` macros cannot be used on a `CxTree` and |
|
308 > the fields must be set manually. |
|
309 >{style="note"} |
281 |
310 |
282 <seealso> |
311 <seealso> |
283 <category ref="apidoc"> |
312 <category ref="apidoc"> |
284 <a href="https://ucx.sourceforge.io/api/tree_8h.html">tree.h</a> |
313 <a href="https://ucx.sourceforge.io/api/tree_8h.html">tree.h</a> |
285 </category> |
314 </category> |