diff --git a/src/vvedit/s_editor_ui.rs b/src/vvedit/s_editor_ui.rs index e862ca3..6521001 100644 --- a/src/vvedit/s_editor_ui.rs +++ b/src/vvedit/s_editor_ui.rs @@ -1,7 +1,7 @@ use bevy::{ app::{Startup, Update}, asset::{AssetServer, Assets, Handle}, ecs::{ entity::Entity, event::EventWriter, query::With, system::{Commands, Query, Res, ResMut, Resource} - }, hierarchy::BuildChildren, math::Vec3, pbr::{PointLight, PointLightBundle}, prelude::{default, SpatialBundle}, render::{camera::Camera, color::Color, view::Visibility}, transform::{commands, components::{GlobalTransform, Transform}, TransformBundle}, window::{PrimaryWindow, Window, WindowResolution} + }, hierarchy::BuildChildren, math::Vec3, pbr::{PointLight, PointLightBundle}, prelude::{default, SpatialBundle}, render::{camera::Camera, color::Color, view::Visibility}, transform::{commands, components::{GlobalTransform, Transform}, TransformBundle}, utils::{hashbrown::hash_map::Entry, HashMap}, window::{PrimaryWindow, Window, WindowResolution} }; use bevy_egui::{ egui::{self, color_picker, epaint::Hsva, Id, Pos2, Rect, ScrollArea}, @@ -48,16 +48,54 @@ pub struct EditWindowUIState { pub structures: Vec, pub egui: EditWindowEguiState, pub popup: PopupWindowMode, - pub selected_structure_element: String, - pub selected_structure: String, - pub selected_grid: String, + //pub selected_structure_element: String, + //pub selected_structure: String, + //pub selected_grid: String, pub display_state: DisplayState, pub display_root: Entity, + pub selection: Selection, + pub struct_element_selections: HashMap, } // SELECTION REWORK: // hashmap keeps track of what the selected element was per-structure // Option (Enum(Grid OR Structure)) < early fail out support +#[derive(Default, Clone, PartialEq)] +pub enum Selection { + #[default] + None, + Structure(String), + Grid(String), +} +impl Selection { + pub fn is_none(&self) -> bool { + match self { + Selection::None => { true} + _ => {false} + } + } + pub fn selection_structure(&self) -> Option { + match self { + Selection::Structure(name) =>{ + Some(name.clone()) + } + _ => { + None + } + } + } + pub fn selection_grid(&self) -> Option { + match self { + Selection::Grid(name) =>{ + Some(name.clone()) + } + _ => { + None + } + } + } +} + impl Default for EditWindowUIState { fn default() -> Self { Self { @@ -66,15 +104,14 @@ impl Default for EditWindowUIState { structures: Default::default(), egui: Default::default(), popup: Default::default(), - selected_structure_element: "".into(), - selected_structure: "".into(), - selected_grid: "".into(), display_root: Entity::PLACEHOLDER, display_state: Default::default(), + selection: Selection::None, + struct_element_selections: Default::default(), } } } -#[derive(Default)] +#[derive(Default, Clone)] pub enum PopupWindowMode { #[default] None, @@ -559,8 +596,17 @@ pub fn edit_window_ui( } } }); + if !shared_ui_state.selection.is_none() { + if ui.button("Deselect Asset").clicked() { + shared_ui_state.selection = Selection::None; + } + } ui.collapsing("grid assets", |ui| { - // + if !shared_ui_state.selection.is_none() { + if ui.button("Deselect Asset").clicked() { + shared_ui_state.selection = Selection::None; + } + } for (id, _asset) in (&grid_assets).iter() { let path = asset_server.get_path(id.untyped()); if let Some(path) = path { @@ -569,18 +615,19 @@ pub fn edit_window_ui( } }); ui.collapsing("structure assets", |ui| { - ui.radio_value( - &mut shared_ui_state.selected_structure, - "".to_string(), - "Deselect", - ); + if !shared_ui_state.selection.is_none() { + if ui.button("Deselect Asset").clicked() { + shared_ui_state.selection = Selection::None; + } + } + for (id, _asset) in (&structure_assets).iter() { let path = asset_server.get_path(id.untyped()); if let Some(path) = path { //ui.label(path.to_string().as_str()); ui.radio_value( - &mut shared_ui_state.selected_structure, - path.to_string(), + &mut shared_ui_state.selection, + Selection::Structure(path.to_string()), path.to_string().as_str(), ); } @@ -588,9 +635,9 @@ pub fn edit_window_ui( }); let mut selected_structure = false; let mut selection = Option::::None; - if shared_ui_state.selected_structure != "" { + if let Selection::Structure(select) = &shared_ui_state.selection { for structure in &shared_ui_state.structures { - if structure.path == shared_ui_state.selected_structure { + if &structure.path == select { let asset = structure_assets.get_mut(structure.id.clone()); if asset.is_some() { selection = Some(asset.unwrap().layout.clone()); @@ -602,90 +649,127 @@ pub fn edit_window_ui( } if selected_structure { let selection = selection.unwrap(); + //dbg!(&selection); ui.collapsing("Model Structure", |ui| { ui.vertical(|ui| { if ui.button("add element").clicked() { - shared_ui_state.popup = PopupWindowMode::CreateStructureElement( - shared_ui_state.selected_structure.clone(), - "unnamed".to_owned(), - "".to_owned(), - ); + if let Selection::Structure(select) = &shared_ui_state.selection { + shared_ui_state.popup = PopupWindowMode::CreateStructureElement( + select.clone(), + "unnamed".to_owned(), + "".to_owned(), + ); + } } ui.separator(); - if shared_ui_state.selected_structure_element != "" { - let structure_name = shared_ui_state.selected_structure.clone(); - let selection_name = shared_ui_state.selected_structure_element.clone(); - for structure in &mut shared_ui_state.structures { - if structure.path == structure_name { - let asset = structure_assets.get_mut(structure.id.clone()); - if asset.is_some() { - let mut should_reshape = false; - let selection = asset.unwrap(); - ui.collapsing("Node Data", |ui| { - let mut trans = { - if selection.default_pose_positions.contains_key(&selection_name) { - selection.default_pose_positions.get(&selection_name).unwrap().clone() - } else { - Transform::IDENTITY - } - }.clone(); - ui.label("Position"); - editable_vec3(ui, &mut trans.translation, &mut should_reshape); - ui.label("Scale"); - editable_vec3(ui, &mut trans.scale, &mut should_reshape); - ui.label("Rotation"); - editable_quat(ui, &mut trans.rotation, &mut should_reshape); - if should_reshape { + if let Selection::Structure(select) = &shared_ui_state.selection { + let structure_name = select.clone(); + if let Entry::Occupied(element_select) = shared_ui_state.struct_element_selections.clone().entry(structure_name.clone()) { + let element_select = element_select.get(); - println!("code reached 2."); - event_writer.send(StructureUpdateMessage { - update_type: StructureUpdateType::Reshape, - entity: structure.edit_entity, - }); + for structure in &mut shared_ui_state.structures { + if structure.path == structure_name { + let asset = structure_assets.get_mut(structure.id.clone()); + if asset.is_some() { + let mut should_reshape = false; + let asset_selection = asset.unwrap(); + ui.collapsing("Node Data", |ui| { + let mut trans = { + if asset_selection.default_pose_positions.contains_key(element_select) { + asset_selection.default_pose_positions.get(element_select).unwrap().clone() + } else { + Transform::IDENTITY + } + }.clone(); + ui.label("Position"); + editable_vec3(ui, &mut trans.translation, &mut should_reshape); + ui.label("Scale"); + editable_vec3(ui, &mut trans.scale, &mut should_reshape); + ui.label("Rotation"); + editable_quat(ui, &mut trans.rotation, &mut should_reshape); + if should_reshape { + + println!("code reached 2."); + event_writer.send(StructureUpdateMessage { + update_type: StructureUpdateType::Reshape, + entity: structure.edit_entity, + }); + + asset_selection.default_pose_positions.insert(element_select.clone(), trans); + structure.has_changed_since_last_save = true; + } - selection.default_pose_positions.insert(selection_name, trans); - structure.has_changed_since_last_save = true; - } - - }); + }); + } + break; } - break; } } if ui.button("Edit Structure of Node").clicked() { - let selection = shared_ui_state.selected_structure_element.clone(); let mut should_close = false; if let PopupWindowMode::EditStructureElement(_, val, _) = - &shared_ui_state.popup + shared_ui_state.popup.clone() { - if val == &selection { - should_close = true; + if let Selection::Structure(select) = &shared_ui_state.selection { + let structure_name = select.clone(); + if let Entry::Occupied(element_select) = shared_ui_state.struct_element_selections.entry(structure_name.clone()) { + let element_select = element_select.get(); + + if val == *element_select { + should_close = true; + } + } } } if should_close { shared_ui_state.popup = PopupWindowMode::None; } else { - shared_ui_state.popup = PopupWindowMode::EditStructureElement( - shared_ui_state.selected_structure.clone(), - shared_ui_state.selected_structure_element.clone(), - shared_ui_state.selected_structure_element.clone(), - ) + + if let Selection::Structure(select) = &shared_ui_state.selection { + let structure_name = select.clone(); + if let Entry::Occupied(element_select) = shared_ui_state.struct_element_selections.clone().entry(structure_name.clone()) { + let element_select = element_select.get(); + shared_ui_state.popup = PopupWindowMode::EditStructureElement( + select.clone(), + element_select.clone(), + element_select.clone(), + ) + } + } } - ui.label( - "Tree Element Selection: ".to_owned() - + &shared_ui_state.selected_structure_element, - ); + if let Selection::Structure(select) = &shared_ui_state.selection { + let structure_name = select.clone(); + if let Entry::Occupied(element_select) = shared_ui_state.struct_element_selections.clone().entry(structure_name.clone()) { + let element_select = element_select.get(); + ui.label( + "Tree Element Selection: ".to_owned() + + &element_select, + ); + }} } if ui.button("deselect").clicked() { - shared_ui_state.selected_structure_element = "".into(); + shared_ui_state.selection = Selection::None; } ui.separator(); } - let mut string_selection = - shared_ui_state.selected_structure_element.clone(); - show_stringtree_selector(ui, &selection, &mut string_selection); - shared_ui_state.selected_structure_element = string_selection; + if let Selection::Structure(select) = &shared_ui_state.selection.clone() { + let structure_name = select.clone(); + let mut select_element = Option::::None; + if let Entry::Occupied(element_select) = shared_ui_state.struct_element_selections.clone().entry(structure_name.clone()) { + let element_select = element_select.get(); + select_element = Some(element_select.clone()); + } + + let mut string_selection = + if select_element.is_some() { + select_element.unwrap() + } else { + "".to_string() + }; + show_stringtree_selector(ui, &selection, &mut string_selection); + shared_ui_state.struct_element_selections.insert(select.to_string(), string_selection); + } }) }); } diff --git a/src/vvlib/mod.rs b/src/vvlib/mod.rs index 844a4d8..03bc1e3 100644 --- a/src/vvlib/mod.rs +++ b/src/vvlib/mod.rs @@ -1,6 +1,7 @@ #![allow(dead_code)] pub mod s_fps_display; +pub mod s_identifier_validation; pub mod s_inputs; pub mod s_intersections; pub mod s_obb; @@ -8,7 +9,6 @@ pub mod s_oct_asset; pub mod s_octtree; pub mod s_structure_asset; pub mod s_true_generic_octtree; -pub mod s_identifier_validation; pub const RANDOM_SPACE: f32 = 5.; // size of the random possibility space. pub const INTERVAL: f32 = 0.3; // how often to add ^ that many and remove ^ that many random locations