-
-
Notifications
You must be signed in to change notification settings - Fork 3.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Move AmbientLight to a component, instead of a resource. #7209
Move AmbientLight to a component, instead of a resource. #7209
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Concerning migration: You'll need to update some examples:
examples/tools/scene_viewer/main.rs
examples/stress_tests/many_foxes.rs
examples/animation/animated_transform.rs
examples/animation/gltf_skinned_mesh.rs
examples/animation/animated_fox.rs
examples/animation/custom_skinned_mesh.rs
examples/ecs/iter_combinations.rs
examples/3d/load_gltf.rs
examples/3d/spotlight.rs
examples/3d/skybox.rs
examples/3d/lighting.rs
It should be as simple as removing the .insert_resouce(AmbientLight…)
and adding a ambient_light: AmbientLight {…},
field to the Camera3dBundle
the example spawns.
pub fn add_ambient_lights(mut commands: Commands, cameras: Query<Entity, With<Camera>>) { | ||
for entity in &cameras { | ||
commands.entity(entity).insert(AmbientLight::default()); | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This would add the component every frame to every cameras, overwriting the previous value. This would prevent users from setting their own ambient light. You shouldn't need such system. Instead, it's likely the best solution is to add the AmbientLight
component to Camera3dBundle
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for taking the time to give feedback!
Yeah I kind of arrived at the same conclusion but I am now facing a different issue. Currently AmbientLight
is part of the pbr crate/feature and is only ever used there. Does this mean it should be behind a #[cfg(feature = "bevy_pbr")]
directive?:
#[derive(Bundle)]
pub struct Camera3dBundle {
pub camera: Camera,
pub camera_render_graph: CameraRenderGraph,
pub projection: Projection,
pub visible_entities: VisibleEntities,
pub frustum: Frustum,
pub transform: Transform,
pub global_transform: GlobalTransform,
pub camera_3d: Camera3d,
pub tonemapping: Tonemapping,
#[cfg(feature = "bevy_pbr")]
pub ambient_light: AmbientLight,
}
Or do we just move the whole struct into the bevy_core_pipeline
crate? Are there other options I'm overlooking?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah, this is a tough decision, because ambient light relates to pbr while core_pipeline is just the generic bevy rendering infra (no expert actually, might be wrong).
An alternative would be to not add AmbientLight
to Camera3dBundle
and assume default when the component is not present on the camera entity. (that is, in the prepare_lights
system, you'd accept a Option<&ExtractedAmbientLight>
instead of &ExtractedAmbientLight
, and go with the default value when None
) It's easy for the user to do:
commands.spawn((
Camera3dBundle {
//...
}),
AmbientLight { … },
))
If they want a custom ambient light.
The cfg feature would require bevy_core_pipeline
to depend on bevy_pbr
which is not OK IMO because of circular dependency (even on feature gate). I would really prefer if this was a field of Camera3dBundle, but it seems not possible. Moving the struct to bevy_core_pipeline
seems fine, but it would be misleading (ie: it does nothing when not using bevy_pbr). Moving the struct to bevy_core_pipeline and toggling it on feature flag seems overly complex.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
An alternative would be to not add AmbientLight to Camera3dBundle and assume default when the component is not present on the camera entity. (that is, in the prepare_lights system, you'd accept a Option<&ExtractedAmbientLight> instead of &ExtractedAmbientLight, and go with the default value when None)
This is the approach I'm currently taking, but it's definitely harder to discover as a user. I will finish the implementation with this direction and maybe then a SME (have to look up who) can chime in. This seems relevant because #7194 will probably deal with a similar issue. So will any another (future) per-camera feature.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we want to go forward with this, I think it should behave like UiCameraConfig
. Default behaviour if not present, custom if present
Does bors rebase and squash this or do I need to do that? |
bors rebases and squashes. yeah |
adding Controversial label, neither the original issue or this PR has a good justification on why to split ambient light per camera |
For the case where you only have one camera and a custom A feature where this might be interesting: |
Even if we want multiple ambient light, I don't think it should be a component of the camera. Ambient light should then be its own entity, and respect render layers. |
Backlog cleanup: closing in favour of tracking issue #7193 due to inactivity, lack of consensus. |
Objective
Fixes #7193
Solution
AmbientLight
from aResource
to aComponent
.PbrPlugin
adds a defaultAmbientLight
to each camera inPostUpdate
. I suspect this doesn't make much sense and should be configurable somewhere else? Not sure. If this would live somewhere else, that would also get rid ofSimulationLightSystems::AddAmbientLights
which seems misplaced.ReanderStage::Extract
. Currently the data is put into a dedicatedExtractedAmbientLights
struct. This should probably be a more generalExtractedCameraConfig
struct or similar, thoughts?Changelog
Migration Guide
Previously setting up an
AmbientLight
looked something like this:With
AmbientLight
as a per camera component the code needs to be transformed into:AmbientLight
can be directly added to the camera entity as a component