Skip to main content

cursive_tree/model/
iterator.rs

1use super::{super::backend::*, list::*, node::*};
2
3//
4// NodeIterator
5//
6
7/// Tree node iterator.
8///
9/// Iterates the nodes in visual order from top to bottom.
10pub struct NodeIterator<'model, BackendT>
11where
12    BackendT: TreeBackend,
13{
14    current_node_list: &'model NodeList<BackendT>,
15    next_index: usize,
16    only_expanded: bool,
17    stack: Vec<(&'model NodeList<BackendT>, usize)>,
18}
19
20impl<'model, BackendT> NodeIterator<'model, BackendT>
21where
22    BackendT: TreeBackend,
23{
24    /// Constructor.
25    ///
26    /// When only_expanded is true will skip the children of collapsed branches.
27    pub fn new(roots: &'model NodeList<BackendT>, only_expanded: bool) -> Self {
28        Self { current_node_list: roots, next_index: 0, only_expanded, stack: Default::default() }
29    }
30}
31
32impl<'model, BackendT> Iterator for NodeIterator<'model, BackendT>
33where
34    BackendT: TreeBackend,
35{
36    type Item = &'model Node<BackendT>;
37
38    fn next(&mut self) -> Option<Self::Item> {
39        match self.current_node_list.0.get(self.next_index) {
40            Some(node) => {
41                self.next_index += 1;
42
43                if (!self.only_expanded || (node.kind.is_branch() && node.branch_state.is_expanded()))
44                    && let Some(children) = &node.children
45                {
46                    // Remember our place for later
47                    self.stack.push((self.current_node_list, self.next_index));
48
49                    // Continue into children
50                    self.current_node_list = children;
51                    self.next_index = 0;
52                }
53
54                Some(node)
55            }
56
57            None => match self.stack.pop() {
58                Some((current_nodes, next_index)) => {
59                    // Go back to where we were before
60                    self.current_node_list = current_nodes;
61                    self.next_index = next_index;
62                    self.next()
63                }
64
65                None => None,
66            },
67        }
68    }
69}