Skip to content

Commit

Permalink
sync
Browse files Browse the repository at this point in the history
  • Loading branch information
IDEDARY committed Jun 6, 2024
1 parent 00903e0 commit 408029e
Show file tree
Hide file tree
Showing 2 changed files with 110 additions and 2 deletions.
2 changes: 1 addition & 1 deletion docs/src/SUMMARY.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@
- [Cursor](advanced/cursor.md)
- [Text](advanced/text.md)
- [Abstraction](advanced/abstraction.md)
- [Routes](advanced/abstraction/routes.md)
- [Components](advanced/abstraction/components.md)
- [Routes](advanced/abstraction/routes.md)
- [Interactivity](advanced/interactivity.md)
- [Animation](advanced/animation.md)
- [2D & 3D](advanced/2d_and_3d.md)
Expand Down
110 changes: 109 additions & 1 deletion docs/src/advanced/abstraction/components.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,111 @@
# Components

*Coming soon...*
Components (Not Bevy ECS componets, but UI components) bundle certain UI behavior under a single entity. Example can be **Button**, **Text input**, **Calendar**, **Minimap**, etc.

## Creating a Component

Begin by creating a new `.rs` file in the `components` folder. First, define a public component that will serve as the abstraction.

```rust
// components/custom_button.rs

/// When this component is added, a UI system is built
#[derive(Component)]
pub struct CustomButtom {
// Any fields we want to interact with should be here.
text: String,
}
```

Best practice is that all components should be sandboxed. For that reason we need to define a new marker component, that will be used ONLY for UI inside this button component.

```rust
// components/custom_button.rs

/// Marker struct for the sandboxed UI
#[derive(Component)]
struct CustomButtonUi;
```


Next, create a system that builds the component UI when the component is added. This system will insert the `UiTree` component into the same entity and spawn the UI elements as children.

```rust
// components/custom_button.rs

/// System that builds the route when the component is added
fn build_route(mut commands: Commands, assets: Res<AssetServer>, query: Query<Entity, Added<MyRoute>>) {
for entity in &query {
commands.entity(entity).insert((
// Insert this bundle into the entity that just got the MyRoute component
// Note that CustomButtonUi is used here instead of MainUi
UiTreeBundle::<CustomButtonUi>::from(UiTree::new("MyRoute")),
// Now spawn the UI as children
)).with_children(|ui| {
// Spawn some UI nodes
ui.spawn((
// Link this widget
// Note that CustomButtonUi is used here instead of MainUi
UiLink::<CustomButtonUi>::path("Control/Image"),

// Add layout
UiLayout::window_full().pack(),

// Give it a background image
UiImage2dBundle {
texture: assets.load("images/button.png"),
sprite: Sprite { color: Color::RED, ..default() },
..default()
},

// Give the texture 9-slice tilling
ImageScaleMode::Sliced(TextureSlicer { border: BorderRect::square(32.0), ..default() }),
))
});
}
}
```

Finally, add the system to a plugin.

```rust
// components/custom_button.rs

pub struct CustomButtonPlugin;
impl Plugin for CustomButtonPlugin {
fn build(&self, app: &mut App) {
app
// Add Lunex plugins for our sandboxed UI
.add_plugins(UiPlugin::<CustomButtonUi>::new())

// NOTE! Systems changing the UI need to run before UiSystems::Compute
// or they will not get picked up by change detection.
.add_systems(Update, build_route.before(UiSystems::Compute));
}
}
```

Don't forget to add this plugin in `component/mod.rs`.

## Spawning a component

To spawn the component, you have to spawn it as UI node of another UI system, either a route or another component.

```rust
// Spawning the component
ui.spawn((
UiLink::<MainUi>::path("Button"),
UiLayout::window().size(Rl(50.0)).pack(),

CustomButton {
text: "PRESS ME!".to_string(),
},
));
```

To despawn the component, call `.despawn_recursive` on the spawned entity.

```rust
// Despawning the component
commands.entity(component_entity).despawn_recursive();
```

0 comments on commit 408029e

Please sign in to comment.