mirror of
https://github.com/bevyengine/bevy
synced 2024-11-22 12:43:34 +00:00
add a SpatialBundle with visibility and transform components (#5344)
# Objective - Help user when they need to add both a `TransformBundle` and a `VisibilityBundle` ## Solution - Add a `SpatialBundle` adding all components
This commit is contained in:
parent
9c116d557d
commit
4affc8cd93
8 changed files with 92 additions and 12 deletions
|
@ -22,16 +22,17 @@ use bevy_render::{
|
|||
skinning::{SkinnedMesh, SkinnedMeshInverseBindposes},
|
||||
Indices, Mesh, VertexAttributeValues,
|
||||
},
|
||||
prelude::SpatialBundle,
|
||||
primitives::{Aabb, Frustum},
|
||||
render_resource::{AddressMode, Face, FilterMode, PrimitiveTopology, SamplerDescriptor},
|
||||
renderer::RenderDevice,
|
||||
texture::{CompressedImageFormats, Image, ImageSampler, ImageType, TextureError},
|
||||
view::{VisibilityBundle, VisibleEntities},
|
||||
view::VisibleEntities,
|
||||
};
|
||||
use bevy_scene::Scene;
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
use bevy_tasks::IoTaskPool;
|
||||
use bevy_transform::{components::Transform, TransformBundle};
|
||||
use bevy_transform::components::Transform;
|
||||
|
||||
use bevy_utils::{HashMap, HashSet};
|
||||
use gltf::{
|
||||
|
@ -465,8 +466,7 @@ async fn load_gltf<'a, 'b>(
|
|||
|
||||
world
|
||||
.spawn()
|
||||
.insert_bundle(TransformBundle::identity())
|
||||
.insert_bundle(VisibilityBundle::default())
|
||||
.insert_bundle(SpatialBundle::visible_identity())
|
||||
.with_children(|parent| {
|
||||
for node in scene.nodes() {
|
||||
let result = load_node(
|
||||
|
@ -705,10 +705,9 @@ fn load_node(
|
|||
) -> Result<(), GltfError> {
|
||||
let transform = gltf_node.transform();
|
||||
let mut gltf_error = None;
|
||||
let mut node = world_builder.spawn_bundle(TransformBundle::from(Transform::from_matrix(
|
||||
let mut node = world_builder.spawn_bundle(SpatialBundle::from(Transform::from_matrix(
|
||||
Mat4::from_cols_array_2d(&transform.matrix()),
|
||||
)));
|
||||
node.insert_bundle(VisibilityBundle::default());
|
||||
|
||||
node.insert(node_name(gltf_node));
|
||||
|
||||
|
|
|
@ -14,6 +14,7 @@ pub mod render_phase;
|
|||
pub mod render_resource;
|
||||
pub mod renderer;
|
||||
pub mod settings;
|
||||
mod spatial_bundle;
|
||||
pub mod texture;
|
||||
pub mod view;
|
||||
|
||||
|
@ -26,6 +27,7 @@ pub mod prelude {
|
|||
color::Color,
|
||||
mesh::{shape, Mesh},
|
||||
render_resource::Shader,
|
||||
spatial_bundle::SpatialBundle,
|
||||
texture::Image,
|
||||
view::{ComputedVisibility, Msaa, Visibility, VisibilityBundle},
|
||||
};
|
||||
|
|
59
crates/bevy_render/src/spatial_bundle.rs
Normal file
59
crates/bevy_render/src/spatial_bundle.rs
Normal file
|
@ -0,0 +1,59 @@
|
|||
use bevy_ecs::prelude::Bundle;
|
||||
use bevy_transform::prelude::{GlobalTransform, Transform};
|
||||
|
||||
use crate::view::{ComputedVisibility, Visibility};
|
||||
|
||||
/// A [`Bundle`] with the following [`Component`](bevy_ecs::component::Component)s:
|
||||
/// * [`Visibility`] and [`ComputedVisibility`], which describe the visibility of an entity
|
||||
/// * [`Transform`] and [`GlobalTransform`], which describe the position of an entity
|
||||
///
|
||||
/// * To show or hide an entity, you should set its [`Visibility`].
|
||||
/// * To get the computed visibility of an entity, you should get its [`ComputedVisibility`].
|
||||
/// * To place or move an entity, you should set its [`Transform`].
|
||||
/// * To get the global transform of an entity, you should get its [`GlobalTransform`].
|
||||
/// * For hierarchies to work correctly, you must have all four components.
|
||||
/// * You may use the [`SpatialBundle`] to guarantee this.
|
||||
#[derive(Bundle, Debug, Default)]
|
||||
pub struct SpatialBundle {
|
||||
/// The visibility of the entity.
|
||||
pub visibility: Visibility,
|
||||
/// The computed visibility of the entity.
|
||||
pub computed: ComputedVisibility,
|
||||
/// The transform of the entity.
|
||||
pub transform: Transform,
|
||||
/// The global transform of the entity.
|
||||
pub global_transform: GlobalTransform,
|
||||
}
|
||||
|
||||
impl SpatialBundle {
|
||||
/// Creates a new [`SpatialBundle`] from a [`Transform`].
|
||||
///
|
||||
/// This initializes [`GlobalTransform`] as identity, and visibility as visible
|
||||
#[inline]
|
||||
pub const fn from_transform(transform: Transform) -> Self {
|
||||
SpatialBundle {
|
||||
transform,
|
||||
// Note: `..Default::default()` cannot be used here, because it isn't const
|
||||
..Self::visible_identity()
|
||||
}
|
||||
}
|
||||
|
||||
/// Creates a new identity [`SpatialBundle`], with no translation, rotation, and a scale of 1
|
||||
/// on all axes.
|
||||
#[inline]
|
||||
pub const fn visible_identity() -> Self {
|
||||
SpatialBundle {
|
||||
transform: Transform::identity(),
|
||||
global_transform: GlobalTransform::identity(),
|
||||
visibility: Visibility::visible(),
|
||||
computed: ComputedVisibility::not_visible(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Transform> for SpatialBundle {
|
||||
#[inline]
|
||||
fn from(transform: Transform) -> Self {
|
||||
Self::from_transform(transform)
|
||||
}
|
||||
}
|
|
@ -34,19 +34,40 @@ pub struct Visibility {
|
|||
|
||||
impl Default for Visibility {
|
||||
fn default() -> Self {
|
||||
Self::visible()
|
||||
}
|
||||
}
|
||||
|
||||
impl Visibility {
|
||||
/// Creates a new [`Visibility`], set as visible
|
||||
pub const fn visible() -> Self {
|
||||
Self { is_visible: true }
|
||||
}
|
||||
}
|
||||
|
||||
/// Algorithmically-computed indication of whether an entity is visible and should be extracted for rendering
|
||||
#[derive(Component, Clone, Reflect, Debug, Eq, PartialEq, Default)]
|
||||
#[derive(Component, Clone, Reflect, Debug, Eq, PartialEq)]
|
||||
#[reflect(Component)]
|
||||
pub struct ComputedVisibility {
|
||||
is_visible_in_hierarchy: bool,
|
||||
is_visible_in_view: bool,
|
||||
}
|
||||
|
||||
impl Default for ComputedVisibility {
|
||||
fn default() -> Self {
|
||||
Self::not_visible()
|
||||
}
|
||||
}
|
||||
|
||||
impl ComputedVisibility {
|
||||
/// Creates a new [`ComputedVisibility`], set as not visible
|
||||
pub const fn not_visible() -> Self {
|
||||
Self {
|
||||
is_visible_in_hierarchy: false,
|
||||
is_visible_in_view: false,
|
||||
}
|
||||
}
|
||||
|
||||
/// Whether this entity is visible to something this frame. This is true if and only if [`Self::is_visible_in_hierarchy`] and [`Self::is_visible_in_view`]
|
||||
/// are true. This is the canonical method to call to determine if an entity should be drawn.
|
||||
/// This value is updated in [`CoreStage::PostUpdate`] during the [`VisibilitySystems::CheckVisibility`] system label. Reading it from the
|
||||
|
|
|
@ -8,7 +8,7 @@ use bevy_reflect::Reflect;
|
|||
/// Describe the position of an entity relative to the reference frame.
|
||||
///
|
||||
/// * To place or move an entity, you should set its [`Transform`].
|
||||
/// * To get the global position of an entity, you should get its [`GlobalTransform`].
|
||||
/// * To get the global transform of an entity, you should get its [`GlobalTransform`].
|
||||
/// * For transform hierarchies to work correctly, you must have both a [`Transform`] and a [`GlobalTransform`].
|
||||
/// * You may use the [`TransformBundle`](crate::TransformBundle) to guarantee this.
|
||||
///
|
||||
|
|
|
@ -9,7 +9,7 @@ use std::ops::Mul;
|
|||
/// to its parent position.
|
||||
///
|
||||
/// * To place or move an entity, you should set its [`Transform`].
|
||||
/// * To get the global position of an entity, you should get its [`GlobalTransform`].
|
||||
/// * To get the global transform of an entity, you should get its [`GlobalTransform`].
|
||||
/// * To be displayed, an entity must have both a [`Transform`] and a [`GlobalTransform`].
|
||||
/// * You may use the [`TransformBundle`](crate::TransformBundle) to guarantee this.
|
||||
///
|
||||
|
|
|
@ -20,7 +20,7 @@ use prelude::{GlobalTransform, Transform};
|
|||
/// [`Component`](bevy_ecs::component::Component)s, which describe the position of an entity.
|
||||
///
|
||||
/// * To place or move an entity, you should set its [`Transform`].
|
||||
/// * To get the global position of an entity, you should get its [`GlobalTransform`].
|
||||
/// * To get the global transform of an entity, you should get its [`GlobalTransform`].
|
||||
/// * For transform hierarchies to work correctly, you must have both a [`Transform`] and a [`GlobalTransform`].
|
||||
/// * You may use the [`TransformBundle`] to guarantee this.
|
||||
///
|
||||
|
|
|
@ -125,8 +125,7 @@ fn setup(
|
|||
.insert_bundle((planet, player))
|
||||
.with_children(|p| {
|
||||
// This entity is just used for animation, but doesn't display anything
|
||||
p.spawn_bundle(TransformBundle::default())
|
||||
.insert_bundle(VisibilityBundle::default())
|
||||
p.spawn_bundle(SpatialBundle::default())
|
||||
// Add the Name component
|
||||
.insert(orbit_controller)
|
||||
.with_children(|p| {
|
||||
|
|
Loading…
Reference in a new issue