Convert apply_mutations to use world directly
This commit is contained in:
parent
344f4983c3
commit
f668d43994
|
|
@ -1,7 +1,7 @@
|
||||||
use crate::events::is_supported_event;
|
use crate::events::is_supported_event;
|
||||||
use bevy::{
|
use bevy::{
|
||||||
ecs::{component::Component, entity::Entity, system::Commands, world::World},
|
ecs::{entity::Entity, world::World},
|
||||||
hierarchy::BuildChildren,
|
hierarchy::{BuildWorldChildren, Children, Parent},
|
||||||
prelude::default,
|
prelude::default,
|
||||||
render::color::Color,
|
render::color::Color,
|
||||||
text::{Text, TextStyle},
|
text::{Text, TextStyle},
|
||||||
|
|
@ -18,13 +18,11 @@ use dioxus::core::{
|
||||||
|
|
||||||
pub fn apply_mutations(
|
pub fn apply_mutations(
|
||||||
mutations: Mutations,
|
mutations: Mutations,
|
||||||
parent_to_children: &mut HashMap<(Entity, u8), Entity>,
|
|
||||||
children_to_parent: &mut EntityHashMap<Entity, Entity>,
|
|
||||||
element_id_to_bevy_ui_entity: &mut HashMap<ElementId, Entity>,
|
element_id_to_bevy_ui_entity: &mut HashMap<ElementId, Entity>,
|
||||||
bevy_ui_entity_to_element_id: &mut EntityHashMap<Entity, ElementId>,
|
bevy_ui_entity_to_element_id: &mut EntityHashMap<Entity, ElementId>,
|
||||||
templates: &mut HashMap<String, BevyTemplate>,
|
templates: &mut HashMap<String, BevyTemplate>,
|
||||||
root_entity: Entity,
|
root_entity: Entity,
|
||||||
commands: &mut Commands,
|
world: &mut World,
|
||||||
) {
|
) {
|
||||||
for new_template in mutations.templates {
|
for new_template in mutations.templates {
|
||||||
templates.insert(
|
templates.insert(
|
||||||
|
|
@ -40,22 +38,14 @@ pub fn apply_mutations(
|
||||||
for edit in mutations.edits {
|
for edit in mutations.edits {
|
||||||
match edit {
|
match edit {
|
||||||
Mutation::AppendChildren { id, m } => {
|
Mutation::AppendChildren { id, m } => {
|
||||||
let mut parent = commands.entity(element_id_to_bevy_ui_entity[&id]);
|
let mut parent = world.entity_mut(element_id_to_bevy_ui_entity[&id]);
|
||||||
let parent_existing_child_count = parent_to_children
|
for child in stack.drain((stack.len() - m)..) {
|
||||||
.keys()
|
|
||||||
.filter(|(p, _)| *p == parent.id())
|
|
||||||
.count();
|
|
||||||
for (i, child) in stack.drain((stack.len() - m)..).enumerate() {
|
|
||||||
parent.add_child(child);
|
parent.add_child(child);
|
||||||
parent_to_children.insert(
|
|
||||||
(parent.id(), (parent_existing_child_count + i + 1) as u8),
|
|
||||||
child,
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Mutation::AssignId { path, id } => todo!(),
|
Mutation::AssignId { path, id } => todo!(),
|
||||||
Mutation::CreatePlaceholder { id } => {
|
Mutation::CreatePlaceholder { id } => {
|
||||||
let entity = commands
|
let entity = world
|
||||||
.spawn((NodeBundle::default(), BackgroundColor::default()))
|
.spawn((NodeBundle::default(), BackgroundColor::default()))
|
||||||
.id();
|
.id();
|
||||||
element_id_to_bevy_ui_entity.insert(id, entity);
|
element_id_to_bevy_ui_entity.insert(id, entity);
|
||||||
|
|
@ -63,8 +53,8 @@ pub fn apply_mutations(
|
||||||
stack.push(entity);
|
stack.push(entity);
|
||||||
}
|
}
|
||||||
Mutation::CreateTextNode { value, id } => {
|
Mutation::CreateTextNode { value, id } => {
|
||||||
let entity = BevyTemplateNode::from_dioxus(&TemplateNode::Text { text: value })
|
let entity =
|
||||||
.spawn(commands, parent_to_children, children_to_parent);
|
BevyTemplateNode::from_dioxus(&TemplateNode::Text { text: value }).spawn(world);
|
||||||
element_id_to_bevy_ui_entity.insert(id, entity);
|
element_id_to_bevy_ui_entity.insert(id, entity);
|
||||||
bevy_ui_entity_to_element_id.insert(entity, id);
|
bevy_ui_entity_to_element_id.insert(entity, id);
|
||||||
stack.push(entity);
|
stack.push(entity);
|
||||||
|
|
@ -72,26 +62,38 @@ pub fn apply_mutations(
|
||||||
Mutation::HydrateText { path, value, id } => {
|
Mutation::HydrateText { path, value, id } => {
|
||||||
let mut entity = *stack.last().unwrap();
|
let mut entity = *stack.last().unwrap();
|
||||||
for index in path {
|
for index in path {
|
||||||
entity = parent_to_children[&(entity, *index)];
|
entity = world.entity(entity).get::<Children>().unwrap()[*index as usize];
|
||||||
}
|
}
|
||||||
commands
|
world
|
||||||
.entity(entity)
|
.entity_mut(entity)
|
||||||
.insert(Text::from_section(value, TextStyle::default()));
|
.insert(Text::from_section(value, TextStyle::default()));
|
||||||
element_id_to_bevy_ui_entity.insert(id, entity);
|
element_id_to_bevy_ui_entity.insert(id, entity);
|
||||||
bevy_ui_entity_to_element_id.insert(entity, id);
|
bevy_ui_entity_to_element_id.insert(entity, id);
|
||||||
}
|
}
|
||||||
Mutation::LoadTemplate { name, index, id } => {
|
Mutation::LoadTemplate { name, index, id } => {
|
||||||
let entity = templates[name].roots[index].spawn(
|
let entity = templates[name].roots[index].spawn(world);
|
||||||
commands,
|
|
||||||
parent_to_children,
|
|
||||||
children_to_parent,
|
|
||||||
);
|
|
||||||
element_id_to_bevy_ui_entity.insert(id, entity);
|
element_id_to_bevy_ui_entity.insert(id, entity);
|
||||||
bevy_ui_entity_to_element_id.insert(entity, id);
|
bevy_ui_entity_to_element_id.insert(entity, id);
|
||||||
stack.push(entity);
|
stack.push(entity);
|
||||||
}
|
}
|
||||||
Mutation::ReplaceWith { id, m } => todo!(),
|
Mutation::ReplaceWith { id, m } => todo!(),
|
||||||
Mutation::ReplacePlaceholder { path, m } => todo!(),
|
Mutation::ReplacePlaceholder { path, m } => {
|
||||||
|
let mut existing = stack[stack.len() - m - 1];
|
||||||
|
for index in path {
|
||||||
|
existing = world.entity(existing).get::<Children>().unwrap()[*index as usize];
|
||||||
|
}
|
||||||
|
let existing_parent = world.entity(existing).get::<Parent>().unwrap().get();
|
||||||
|
let mut existing_parent = world.entity_mut(existing_parent);
|
||||||
|
let existing_index = existing_parent
|
||||||
|
.get::<Children>()
|
||||||
|
.unwrap()
|
||||||
|
.iter()
|
||||||
|
.position(|child| *child == existing)
|
||||||
|
.unwrap();
|
||||||
|
let new = stack.drain((stack.len() - m)..).collect::<Vec<Entity>>();
|
||||||
|
existing_parent.insert_children(existing_index, &new);
|
||||||
|
world.despawn(existing);
|
||||||
|
}
|
||||||
Mutation::InsertAfter { id, m } => todo!(),
|
Mutation::InsertAfter { id, m } => todo!(),
|
||||||
Mutation::InsertBefore { id, m } => todo!(),
|
Mutation::InsertBefore { id, m } => todo!(),
|
||||||
Mutation::SetAttribute {
|
Mutation::SetAttribute {
|
||||||
|
|
@ -100,26 +102,21 @@ pub fn apply_mutations(
|
||||||
id,
|
id,
|
||||||
ns: _,
|
ns: _,
|
||||||
} => {
|
} => {
|
||||||
let entity = element_id_to_bevy_ui_entity[&id];
|
let value = match value {
|
||||||
// TODO: The rest of Style
|
BorrowedAttributeValue::Text(value) => value,
|
||||||
match (name, value) {
|
value => {
|
||||||
("background-color", BorrowedAttributeValue::Text(hex)) => {
|
|
||||||
let color = Color::hex(hex).expect(&format!(
|
|
||||||
"Encountered unsupported bevy_dioxus background-color `{hex}`."
|
|
||||||
));
|
|
||||||
commands.add(modify_component_command::<BackgroundColor, _>(
|
|
||||||
entity,
|
|
||||||
move |background_color| background_color.0 = color,
|
|
||||||
));
|
|
||||||
}
|
|
||||||
(name, value) => {
|
|
||||||
panic!("Encountered unsupported bevy_dioxus attribute `{name}: {value:?}`.")
|
panic!("Encountered unsupported bevy_dioxus attribute `{name}: {value:?}`.")
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
let (mut style, mut background_color) = world
|
||||||
|
.query::<(&mut Style, &mut BackgroundColor)>()
|
||||||
|
.get_mut(world, element_id_to_bevy_ui_entity[&id])
|
||||||
|
.unwrap();
|
||||||
|
set_style_attribute(name, value, &mut style, &mut background_color);
|
||||||
}
|
}
|
||||||
Mutation::SetText { value, id } => {
|
Mutation::SetText { value, id } => {
|
||||||
commands
|
world
|
||||||
.entity(element_id_to_bevy_ui_entity[&id])
|
.entity_mut(element_id_to_bevy_ui_entity[&id])
|
||||||
.insert(Text::from_section(value, TextStyle::default()));
|
.insert(Text::from_section(value, TextStyle::default()));
|
||||||
}
|
}
|
||||||
Mutation::NewEventListener { name, id: _ } => {
|
Mutation::NewEventListener { name, id: _ } => {
|
||||||
|
|
@ -190,39 +187,26 @@ impl BevyTemplateNode {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn spawn(
|
fn spawn(&self, world: &mut World) -> Entity {
|
||||||
&self,
|
|
||||||
commands: &mut Commands,
|
|
||||||
parent_to_children: &mut HashMap<(Entity, u8), Entity>,
|
|
||||||
children_to_parent: &mut EntityHashMap<Entity, Entity>,
|
|
||||||
) -> Entity {
|
|
||||||
match self {
|
match self {
|
||||||
BevyTemplateNode::Node {
|
BevyTemplateNode::Node {
|
||||||
style: (style, background_color),
|
style: (style, background_color),
|
||||||
children,
|
children,
|
||||||
} => {
|
} => {
|
||||||
// TODO: Can probably use with_children() instead
|
|
||||||
let children = children
|
let children = children
|
||||||
.iter()
|
.iter()
|
||||||
.map(|child| child.spawn(commands, parent_to_children, children_to_parent))
|
.map(|child| child.spawn(world))
|
||||||
.collect::<Box<[_]>>();
|
.collect::<Box<[_]>>();
|
||||||
let parent = commands
|
world
|
||||||
.spawn((
|
.spawn(NodeBundle {
|
||||||
NodeBundle {
|
|
||||||
style: style.clone(),
|
style: style.clone(),
|
||||||
|
background_color: background_color.clone(),
|
||||||
..default()
|
..default()
|
||||||
},
|
})
|
||||||
background_color.clone(),
|
|
||||||
))
|
|
||||||
.push_children(&children)
|
.push_children(&children)
|
||||||
.id();
|
.id()
|
||||||
for (i, child) in children.iter().enumerate() {
|
|
||||||
parent_to_children.insert((parent, i as u8), *child);
|
|
||||||
children_to_parent.insert(*child, parent);
|
|
||||||
}
|
}
|
||||||
parent
|
Self::TextNode(text) => world
|
||||||
}
|
|
||||||
Self::TextNode(text) => commands
|
|
||||||
.spawn(TextBundle {
|
.spawn(TextBundle {
|
||||||
text: text.clone(),
|
text: text.clone(),
|
||||||
..default()
|
..default()
|
||||||
|
|
@ -242,8 +226,20 @@ fn parse_style_attributes(attributes: &[TemplateAttribute]) -> (Style, Backgroun
|
||||||
namespace: _,
|
namespace: _,
|
||||||
} = attribute
|
} = attribute
|
||||||
{
|
{
|
||||||
|
set_style_attribute(name, value, &mut style, &mut background_color);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
(style, background_color)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn set_style_attribute(
|
||||||
|
name: &str,
|
||||||
|
value: &str,
|
||||||
|
style: &mut Style,
|
||||||
|
background_color: &mut BackgroundColor,
|
||||||
|
) {
|
||||||
// TODO: The rest of Style
|
// TODO: The rest of Style
|
||||||
match (*name, *value) {
|
match (name, value) {
|
||||||
("display", "flex") => style.display = Display::Flex,
|
("display", "flex") => style.display = Display::Flex,
|
||||||
("display", "grid") => style.display = Display::Grid,
|
("display", "grid") => style.display = Display::Grid,
|
||||||
("display", "none") => style.display = Display::None,
|
("display", "none") => style.display = Display::None,
|
||||||
|
|
@ -257,15 +253,4 @@ fn parse_style_attributes(attributes: &[TemplateAttribute]) -> (Style, Backgroun
|
||||||
}
|
}
|
||||||
_ => panic!("Encountered unsupported bevy_dioxus attribute `{name}: {value}`."),
|
_ => panic!("Encountered unsupported bevy_dioxus attribute `{name}: {value}`."),
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
(style, background_color)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn modify_component_command<C, F>(entity: Entity, f: F) -> impl FnOnce(&mut World) + Send + 'static
|
|
||||||
where
|
|
||||||
C: Component,
|
|
||||||
F: FnOnce(&mut C) + Send + 'static,
|
|
||||||
{
|
|
||||||
move |world: &mut World| (f)(&mut world.entity_mut(entity).get_mut::<C>().unwrap())
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue