changed traverse_iter to return a pair of handle and ref

- much more convenient when there's a need to handle a handle with a reference at the same time, no need to do re-borrow which is double work anyway
This commit is contained in:
Dmitry Stepanov
2024-11-01 11:50:29 +03:00
parent 388bb46c1b
commit 29113b58e0
10 changed files with 31 additions and 60 deletions
+1 -1
View File
@@ -245,7 +245,7 @@ impl CameraController {
pub fn fit_object(&mut self, scene: &mut Scene, handle: Handle<Node>) {
// Combine AABBs from the descendants.
let mut aabb = AxisAlignedBoundingBox::default();
for descendant in scene.graph.traverse_iter(handle) {
for (_, descendant) in scene.graph.traverse_iter(handle) {
let descendant_aabb = descendant.local_bounding_box();
if !descendant_aabb.is_invalid_or_degenerate() {
aabb.add_box(descendant_aabb.transform(&descendant.global_transform()))
+4 -5
View File
@@ -22,7 +22,7 @@ use crate::{
fyrox::{
core::{color::Color, pool::Handle, sstorage::ImmutableString},
fxhash::FxHashSet,
graph::{BaseSceneGraph, SceneGraph},
graph::BaseSceneGraph,
renderer::{
bundle::{BundleRenderContext, ObserverInfo, RenderContext, RenderDataBundleStorage},
framework::{
@@ -46,6 +46,7 @@ use crate::{
},
Editor,
};
use fyrox::graph::SceneGraph;
use std::{any::TypeId, cell::RefCell, rc::Rc};
struct EdgeDetectShader {
@@ -213,10 +214,8 @@ impl SceneRenderPass for HighlightRenderPass {
for &root_node_handle in self.nodes_to_highlight.iter() {
if ctx.scene.graph.is_valid_handle(root_node_handle) {
for node_handle in ctx.scene.graph.traverse_handle_iter(root_node_handle) {
if let Some(node) = ctx.scene.graph.try_get(node_handle) {
node.collect_render_data(&mut render_context);
}
for (_, node) in ctx.scene.graph.traverse_iter(root_node_handle) {
node.collect_render_data(&mut render_context);
}
}
}
+1 -2
View File
@@ -159,8 +159,7 @@ impl NodeRemovalDialog {
let selection = selection_to_delete(editor_selection, game_scene);
for root in selection.nodes.iter() {
for node_handle in graph.traverse_handle_iter(*root) {
let node = &graph[node_handle];
for (node_handle, node) in graph.traverse_iter(*root) {
for reference_handle in graph.find_references_to(node_handle) {
let reference = &graph[reference_handle];
text += &format!(
+5 -4
View File
@@ -420,8 +420,8 @@ impl GameScene {
) -> bool {
if let Some(selection) = editor_selection.as_graph() {
for node in selection.nodes() {
for descendant in graph.traverse_handle_iter(*node) {
for reference in graph.find_references_to(descendant) {
for (descendant_handle, _) in graph.traverse_iter(*node) {
for reference in graph.find_references_to(descendant_handle) {
if !selection.contains(reference) {
return true;
}
@@ -611,7 +611,8 @@ impl SceneController for GameScene {
let nodes = scene
.graph
.traverse_handle_iter(instance)
.traverse_iter(instance)
.map(|(handle, _)| handle)
.collect::<FxHashSet<Handle<Node>>>();
self.preview_instance = Some(PreviewInstance { instance, nodes });
@@ -912,7 +913,7 @@ impl SceneController for GameScene {
}
let node_overrides = self.graph_switches.node_overrides.as_mut().unwrap();
for handle in scene.graph.traverse_handle_iter(self.editor_objects_root) {
for (handle, _) in scene.graph.traverse_iter(self.editor_objects_root) {
node_overrides.insert(handle);
}
+6 -35
View File
@@ -981,7 +981,7 @@ pub trait SceneGraph: BaseSceneGraph {
fn traverse_iter(
&self,
from: Handle<Self::Node>,
) -> GraphTraverseIterator<'_, Self, Self::Node> {
) -> impl Iterator<Item = (Handle<Self::Node>, &Self::Node)> {
GraphTraverseIterator {
graph: self,
stack: vec![from],
@@ -993,11 +993,8 @@ pub trait SceneGraph: BaseSceneGraph {
fn traverse_handle_iter(
&self,
from: Handle<Self::Node>,
) -> GraphHandleTraverseIterator<'_, Self, Self::Node> {
GraphHandleTraverseIterator {
graph: self,
stack: vec![from],
}
) -> impl Iterator<Item = Handle<Self::Node>> {
self.traverse_iter(from).map(|(handle, _)| handle)
}
/// This method checks integrity of the graph and restores it if needed. For example, if a node
@@ -1034,7 +1031,7 @@ pub trait SceneGraph: BaseSceneGraph {
for (instance_root, resource) in instances.iter().cloned() {
// Step 1. Find and remove orphaned nodes.
let mut nodes_to_delete = Vec::new();
for node in self.traverse_iter(instance_root) {
for (_, node) in self.traverse_iter(instance_root) {
if let Some(resource) = node.resource() {
let kind = resource.kind().clone();
if let Some(model) = resource.state().data() {
@@ -1318,7 +1315,7 @@ where
G: SceneGraph<Node = N>,
N: SceneGraphNode,
{
type Item = &'a N;
type Item = (Handle<N>, &'a N);
#[inline]
fn next(&mut self) -> Option<Self::Item> {
@@ -1329,39 +1326,13 @@ where
self.stack.push(*child_handle);
}
return Some(node);
return Some((handle, node));
}
None
}
}
/// Iterator that traverses tree in depth and returns handles to nodes.
pub struct GraphHandleTraverseIterator<'a, G: ?Sized, N> {
graph: &'a G,
stack: Vec<Handle<N>>,
}
impl<'a, G, N> Iterator for GraphHandleTraverseIterator<'a, G, N>
where
G: SceneGraph<Node = N>,
N: SceneGraphNode,
{
type Item = Handle<N>;
#[inline]
fn next(&mut self) -> Option<Self::Item> {
if let Some(handle) = self.stack.pop() {
for child_handle in self.graph.node(handle).children() {
self.stack.push(*child_handle);
}
return Some(handle);
}
None
}
}
#[cfg(test)]
mod test {
use crate::{
+6 -1
View File
@@ -125,7 +125,12 @@ pub trait LayerMaskExt {
impl LayerMaskExt for LayerMask {
fn from_hierarchy(graph: &Graph, root: Handle<Node>) -> Self {
Self::from(graph.traverse_handle_iter(root).collect::<Vec<_>>())
Self::from(
graph
.traverse_iter(root)
.map(|(handle, _)| handle)
.collect::<Vec<_>>(),
)
}
}
+2 -2
View File
@@ -556,8 +556,8 @@ impl Graph {
let mut old_new_mapping = NodeHandleMap::default();
let to_copy = self
.traverse_handle_iter(node_handle)
.map(|node| (node, self.pool[node].children.clone()))
.traverse_iter(node_handle)
.map(|(descendant_handle, descendant)| (descendant_handle, descendant.children.clone()))
.collect::<Vec<_>>();
let mut root_handle = Handle::NONE;
+1 -2
View File
@@ -165,12 +165,11 @@ struct BatchContainer {
impl BatchContainer {
fn fill(&mut self, from: Handle<Node>, ctx: &mut RenderContext) {
for descendant_handle in ctx.graph.traverse_handle_iter(from) {
for (descendant_handle, descendant) in ctx.graph.traverse_iter(from) {
if descendant_handle == from {
continue;
}
let descendant = &ctx.graph[descendant_handle];
descendant.collect_render_data(&mut RenderContext {
observer_info: ctx.observer_info,
frustum: None,
+2 -3
View File
@@ -783,10 +783,9 @@ impl PropertyFilter {
fn assign_tab_indices(container: Handle<UiNode>, ui: &mut UserInterface) {
let mut counter = 0;
let mut widgets_list = Vec::new();
for descendant in ui.traverse_handle_iter(container) {
let descendant_ref = ui.node(descendant);
for (descendant_handle, descendant_ref) in ui.traverse_iter(container) {
if descendant_ref.accepts_input {
widgets_list.push((descendant, counter));
widgets_list.push((descendant_handle, counter));
counter += 1;
}
}
+3 -5
View File
@@ -33,7 +33,7 @@ use crate::{
widget::{Widget, WidgetBuilder, WidgetMessage},
BuildContext, Control, UiNode, UserInterface,
};
use fyrox_graph::{BaseSceneGraph, SceneGraph};
use fyrox_graph::SceneGraph;
use std::ops::{Deref, DerefMut};
/// A widget, that handles keyboard navigation on its descendant widgets using Tab key. It should
@@ -104,14 +104,12 @@ impl Control for NavigationLayer {
// Collect all descendant widgets, that supports Tab navigation.
let mut tab_list = Vec::new();
for &child in self.children() {
for descendant in ui.traverse_handle_iter(child) {
let descendant_ref = ui.node(descendant);
for (descendant_handle, descendant_ref) in ui.traverse_iter(child) {
if !*descendant_ref.tab_stop && descendant_ref.is_globally_visible() {
if let Some(tab_index) = *descendant_ref.tab_index {
tab_list.push(OrderedHandle {
tab_index,
handle: descendant,
handle: descendant_handle,
});
}
}