buggy but working collapse button + title work

main
Elijah Voigt 2 years ago
parent b26517e721
commit fd1ee92d5f

@ -123,120 +123,155 @@ fn initialize_ui(mut commands: Commands) {
}; };
commands commands
.spawn((NodeBundle { .spawn(NodeBundle {
style: Style { style: Style {
border: UiRect::all(Val::Px(1.0)), border: UiRect::all(Val::Px(1.0)),
margin: UiRect::all(Val::Px(5.0)), margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)), padding: UiRect::all(Val::Px(5.0)),
flex_direction: FlexDirection::Row, flex_direction: FlexDirection::Column,
overflow: Overflow::clip(), overflow: Overflow::clip(),
..default() ..default()
}, },
background_color: Color::WHITE.into(), background_color: Color::WHITE.into(),
border_color: Color::BLACK.into(), border_color: Color::BLACK.into(),
..default() ..default()
},)) })
.with_children(|parent| { .with_children(|parent| {
// HACK: This is super janky but I think we need it like this for UI layout rules let container = parent
let mut content_containers: Vec<(String, Entity)> = Vec::new(); .spawn((NodeBundle {
style: Style {
// Containers with asset content border: UiRect::all(Val::Px(1.0)),
parent margin: UiRect::all(Val::Px(5.0)),
.spawn(( padding: UiRect::all(Val::Px(5.0)),
NodeBundle { flex_direction: FlexDirection::Row,
style: Style { overflow: Overflow::clip(),
border: UiRect::all(Val::Px(1.0)),
margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)),
flex_direction: FlexDirection::Column,
overflow: Overflow::clip(),
justify_content: JustifyContent::FlexStart,
..default()
},
background_color: Color::WHITE.into(),
border_color: Color::BLACK.into(),
..default() ..default()
}, },
ui::Sorting(2), background_color: Color::WHITE.into(),
)) border_color: Color::BLACK.into(),
..default()
},))
.with_children(|parent| { .with_children(|parent| {
content_containers.push(spawn_tab_container::<FontWidget>( // HACK: This is super janky but I think we need it like this for UI layout rules
"Font", let mut content_containers: Vec<(String, Entity)> = Vec::new();
parent,
&base_style, // Containers with asset content
ui::Select::Single, parent
)); .spawn((
content_containers.push(spawn_tab_container::<AudioWidget>( NodeBundle {
"Audio", style: Style {
parent, border: UiRect::all(Val::Px(1.0)),
&base_style, margin: UiRect::all(Val::Px(5.0)),
ui::Select::Multi, padding: UiRect::all(Val::Px(5.0)),
)); flex_direction: FlexDirection::Column,
content_containers.push(spawn_tab_container::<GltfWidget>( overflow: Overflow::clip(),
"Gltf", justify_content: JustifyContent::FlexStart,
parent, ..default()
&base_style, },
ui::Select::Single, background_color: Color::WHITE.into(),
)); border_color: Color::BLACK.into(),
content_containers.push(spawn_tab_container::<SceneWidget>( ..default()
"Scene", },
parent, ui::Sorting(2),
&base_style, ))
ui::Select::Single, .with_children(|parent| {
)); content_containers.push(spawn_tab_container::<FontWidget>(
content_containers.push(spawn_tab_container::<AnimationWidget>( "Font",
"Animation", parent,
parent, &base_style,
&base_style, ui::Select::Single,
ui::Select::Multi, ));
)); content_containers.push(spawn_tab_container::<AudioWidget>(
content_containers.push(spawn_tab_container::<CameraWidget>( "Audio",
"Camera", parent,
parent, &base_style,
&base_style, ui::Select::Multi,
ui::Select::Single, ));
)); content_containers.push(spawn_tab_container::<GltfWidget>(
}); "Gltf",
parent,
&base_style,
ui::Select::Single,
));
content_containers.push(spawn_tab_container::<SceneWidget>(
"Scene",
parent,
&base_style,
ui::Select::Single,
));
content_containers.push(spawn_tab_container::<AnimationWidget>(
"Animation",
parent,
&base_style,
ui::Select::Multi,
));
content_containers.push(spawn_tab_container::<CameraWidget>(
"Camera",
parent,
&base_style,
ui::Select::Single,
));
});
// Container for tabs that open/close containers // Container for tabs that open/close containers
parent parent
.spawn(( .spawn((
NodeBundle { NodeBundle {
style: Style { style: Style {
border: UiRect::all(Val::Px(1.0)), border: UiRect::all(Val::Px(1.0)),
margin: UiRect::all(Val::Px(5.0)), margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)), padding: UiRect::all(Val::Px(5.0)),
flex_direction: FlexDirection::Column, flex_direction: FlexDirection::Column,
overflow: Overflow::clip(), overflow: Overflow::clip(),
..default() ..default()
}, },
background_color: Color::WHITE.into(), background_color: Color::WHITE.into(),
border_color: Color::BLACK.into(), border_color: Color::BLACK.into(),
..default()
},
ui::Sorting(1),
ui::Select::Single,
))
.with_children(|parent| {
let b = ButtonBundle {
style: Style {
..base_style.clone()
},
background_color: Color::WHITE.into(),
border_color: Color::BLACK.into(),
..default()
};
content_containers.iter().for_each(|(name, target)| {
parent.spawn((
b.clone(),
ui::Title {
name: name.clone(),
..default() ..default()
}, },
ui::Collapse { target: *target }, ui::Sorting(1),
)); ui::Select::Single,
}); ))
}); .with_children(|parent| {
let b = ButtonBundle {
style: Style {
..base_style.clone()
},
background_color: Color::WHITE.into(),
border_color: Color::BLACK.into(),
..default()
};
content_containers.iter().for_each(|(name, target)| {
parent.spawn((
b.clone(),
ui::Title { text: name.clone() },
ui::Collapse { target: *target },
ui::Active,
));
});
});
})
.id();
parent.spawn((
NodeBundle {
style: Style {
border: UiRect::all(Val::Px(1.0)),
margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)),
flex_direction: FlexDirection::Row,
overflow: Overflow::clip(),
..default()
},
background_color: Color::ALICE_BLUE.into(),
border_color: Color::BLACK.into(),
..default()
},
ui::Title {
text: "Assets".into(),
},
ui::Minimize { target: container },
ui::Sorting(0),
));
}); });
} }
@ -261,10 +296,7 @@ fn spawn_tab_container<T: Default + Component>(
z_index: ZIndex::Local(100), z_index: ZIndex::Local(100),
..default() ..default()
}, },
ui::Title { ui::Title { text: title.into() },
name: title.into(),
..default()
},
T::default(), T::default(),
ui::Scroll, ui::Scroll,
Interaction::default(), Interaction::default(),
@ -436,7 +468,7 @@ mod assets {
border_color: Color::BLACK.into(), border_color: Color::BLACK.into(),
..default() ..default()
}, },
ui::Title { name, ..default() }, ui::Title { text: name },
)) ))
.set_parent(root.single()) .set_parent(root.single())
.id() .id()
@ -461,7 +493,7 @@ mod assets {
border_color: Color::BLACK.into(), border_color: Color::BLACK.into(),
..default() ..default()
}, },
ui::Title { name, ..default() }, ui::Title { text: name },
)) ))
.set_parent(root.single()) .set_parent(root.single())
.id() .id()

@ -33,12 +33,13 @@ impl Plugin for GameUiPlugin {
Update, Update,
( (
init_titles, init_titles,
manage_titles,
manage_button_interaction, manage_button_interaction,
manage_select_active, manage_select_active,
manage_cursor, manage_cursor,
manage_scroll, manage_scroll,
manage_collapse_active,
manage_collapse_hiding, manage_collapse_hiding,
manage_collapse_active,
show_child_number, show_child_number,
manage_sort, manage_sort,
), ),
@ -50,66 +51,123 @@ pub use title::*;
mod title { mod title {
use super::*; use super::*;
#[derive(Debug, Component, Default)] #[derive(Debug, Component)]
pub struct Title { pub struct Title {
pub name: String, pub text: String,
pub note: Option<String>, }
#[derive(Debug, Component)]
pub struct Note {
pub text: String,
}
#[derive(Debug, Component)]
pub struct TitleText;
#[derive(Debug, Component)]
pub struct Minimize {
pub target: Entity,
} }
pub fn init_titles( pub fn init_titles(
events: Query<(Entity, &Title), Or<(Changed<Title>, Added<Title>)>>, events: Query<(Entity, &Title, Option<&Note>, Option<&Minimize>), Added<Title>>,
mut commands: Commands, mut commands: Commands,
) { ) {
events.for_each(|(entity, Title { name, note })| { events.for_each(|(entity, title, note, minimize)| {
commands commands.entity(entity).with_children(|parent| {
.entity(entity) parent.spawn((
.despawn_descendants() TextBundle {
.with_children(|parent| { text: Text {
parent sections: vec![
.spawn(( TextSection {
NodeBundle { value: title.text.clone(),
style: Style { style: TextStyle {
padding: UiRect::all(Val::Px(5.0)), color: Color::BLACK,
margin: UiRect::all(Val::Px(5.0)), ..default()
border: UiRect::all(Val::Px(1.0)), },
flex_direction: FlexDirection::Row, },
..default() TextSection {
value: note
.unwrap_or(&Note {
text: String::new(),
})
.text
.clone(),
style: TextStyle {
color: Color::BLACK,
..default()
},
}, },
],
..default()
},
style: Style {
margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)),
..default()
},
..default()
},
Sorting(0),
TitleText,
));
if let Some(target) = minimize {
parent.spawn((
ButtonBundle {
style: Style {
border: UiRect::all(Val::Px(1.0)),
margin: UiRect::all(Val::Px(5.0)),
padding: UiRect::all(Val::Px(5.0)),
right: Val::Px(0.0),
..default() ..default()
}, },
Sorting(0), background_color: Color::WHITE.into(),
)) border_color: Color::BLACK.into(),
.with_children(|parent| { ..default()
parent.spawn(TextBundle { },
text: Text { Collapse {
sections: vec![ target: target.target,
TextSection { },
value: name.clone(), ));
style: TextStyle { }
color: Color::BLACK, });
..default() });
}, }
},
TextSection { pub fn manage_titles(
value: note.clone().unwrap_or(String::new()), events: Query<(&Title, Option<&Note>, &Children), Changed<Title>>,
style: TextStyle { mut texts: Query<&mut Text, With<TitleText>>,
color: Color::BLACK, ) {
..default() events.iter().for_each(|(title, note, children)| {
}, children.iter().for_each(|child| {
}, if let Ok(mut text) = texts.get_mut(*child) {
], *text = Text {
sections: vec![
TextSection {
value: title.text.clone(),
style: TextStyle {
color: Color::BLACK,
..default() ..default()
}, },
style: Style { },
margin: UiRect::all(Val::Px(5.0)), TextSection {
padding: UiRect::all(Val::Px(5.0)), value: note
.unwrap_or(&Note {
text: String::new(),
})
.text
.clone(),
style: TextStyle {
color: Color::BLACK,
..default() ..default()
}, },
..default() },
}); ],
}); ..default()
}); }
}); }
})
})
} }
} }
@ -171,22 +229,26 @@ mod collapse {
pub fn show_child_number( pub fn show_child_number(
events: Query<(Entity, &Children), (Changed<Children>, With<Node>)>, events: Query<(Entity, &Children), (Changed<Children>, With<Node>)>,
mut tabs: Query<(&Collapse, &mut Title)>, mut tabs: Query<(Entity, &Collapse)>,
mut commands: Commands,
) { ) {
// Any time a widget changes // Any time a widget changes
events.iter().for_each(|(entity, children)| { events.iter().for_each(|(entity, children)| {
// Find any tabs which have this as a target // Find any tabs which have this as a target
tabs.iter_mut() tabs.iter_mut()
.find_map(|(collapse, title)| { .find_map(|(button, collapse)| {
if entity == collapse.target { if entity == collapse.target {
Some(title) Some(button)
} else { } else {
None None
} }
}) })
.iter_mut() .iter()
.for_each(|title| { .for_each(|button| {
title.note = Some(format!("({})", children.len().saturating_sub(1))) let num_children = children.len();
commands.entity(*button).insert(Note {
text: format!("({})", num_children),
});
}); });
}); });
} }

Loading…
Cancel
Save