Skip to content
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

Replace Ambient Lights with Environment Map Lights #17482

Open
wants to merge 6 commits into
base: main
Choose a base branch
from

Conversation

SparkyPotato
Copy link

@SparkyPotato SparkyPotato commented Jan 21, 2025

Objective

Transparently uses simple EnvironmentMapLights to mimic AmbientLights. Implements the first part of #17468, but I can implement hemispherical lights in this PR too if needed.

Solution

  • A function EnvironmentMapLight::solid_color(&mut Assets<Image>, Color) is provided to make an environment light with a solid color.
  • A new system is added to SimulationLightSystems that maps AmbientLights on views or the world to a corresponding EnvironmentMapLight.

I have never worked with (or on) Bevy before, so nitpicky comments on how I did things are appreciated :).

Testing

Testing was done on a modified version of the 3d/lighting example, where I removed all lights except the ambient light. I have not included the example, but can if required.

Migration

bevy_pbr::AmbientLight has been deprecated, so all usages of it should be replaced by a bevy_pbr::EnvironmentMapLight created with EnvironmentMapLight::solid_color placed on the camera. There is no alternative to ambient lights as resources.

Copy link
Contributor

Welcome, new contributor!

Please make sure you've read our contributing guide and we look forward to reviewing your pull request shortly ✨

@@ -522,6 +523,26 @@ pub enum SimulationLightSystems {
CheckLightVisibility,
}

pub fn map_ambient_lights(
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we may want to add a deprecation notice to the AmbientLight component and remove it after 0.16. For this PR I think this is fine as is though.

Copy link
Contributor

@JMS55 JMS55 Jan 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to adding a deprecated attribute to ambient light, and then removing this system in 0.17.

EDIT: I mean adding the attribute in this PR, and then opening an issue to remind us to delete this system, and have put it in the 0.17 milestone.

Copy link
Contributor

@IceSentry IceSentry left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is great, thank you!

@IceSentry IceSentry added A-Rendering Drawing game state to the screen C-Code-Quality A section of code that is hard to understand or change C-Usability A targeted quality-of-life change that makes Bevy easier to use S-Needs-Review Needs reviewer attention (from anyone!) to move forward labels Jan 21, 2025
@IceSentry
Copy link
Contributor

I can implement hemispherical lights in this PR too if needed

The PR is simple enough that you could add this in too I think. Up to you, but I would approve it either way.

@SparkyPotato
Copy link
Author

I can implement hemispherical lights in this PR too if needed

The PR is simple enough that you could add this in too I think. Up to you, but I would approve it either way.

Might as well add it in then.

@robtfm
Copy link
Contributor

robtfm commented Jan 21, 2025

code looks good.

simplifying the shaders is nice, but is the cost of binding an extra texture per view and looking up for every pixel really worth the saving of 7-8 lines of shader code?

@SparkyPotato
Copy link
Author

Found a bug with user-provided environment maps being overridden by the default ambient light, so I had to complicate the sync system a bit. Not sure if what I did was the most optimal.

code looks good.

simplifying the shaders is nice, but is the cost of binding an extra texture per view and looking up for every pixel really worth the saving of 7-8 lines of shader code?

The lighting example does go from about 0.51 ms to 0.55 ms on my machine (and enabling deferred makes that 0.46 ms to 0.49 ms), but I do doubt the usage of ambient light will be widespread enough that this matters, especially after the new procedural sky rolls around.

@alice-i-cecile alice-i-cecile added the M-Needs-Release-Note Work that should be called out in the blog due to impact label Jan 22, 2025
@IceSentry
Copy link
Contributor

simplifying the shaders is nice, but is the cost of binding an extra texture per view and looking up for every pixel really worth the saving of 7-8 lines of shader code?

I guess what we could do is keep the constructor thing in this PR and do the ambient light thing separately? I can see why that part could be a bit more controversial and that people might still want that around.

@pcwalton
Copy link
Contributor

It's not just about simplifying the shader code: it's that the interaction between ambient and environment map light never made any sense. They should be considered basically mutually exclusive (strictly speaking, ambient should be considered a type of light probe, which this PR moves us toward).

@BenjaminBrienen BenjaminBrienen added D-Straightforward Simple bug fixes and API improvements, docs, test and examples D-Shaders This code uses GPU shader languages labels Jan 22, 2025
.into_iter()
.flat_map(Srgba::to_u8_array)
.collect(),
TextureFormat::Rgba8UnormSrgb,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This does not need to be a HDR texture right, since the user is defining the color in sRGB and an intensity?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, it's an 8-bit sRGB texture.

@robtfm
Copy link
Contributor

robtfm commented Jan 22, 2025

The lighting example does go from about 0.51 ms to 0.55 ms on my machine (and enabling deferred makes that 0.46 ms to 0.49 ms)

is that in release? if so then i'd argue a ~10% fps reduction is not justified, but it's surprising how large the impact is.

They should be considered basically mutually exclusive (strictly speaking, ambient should be considered a type of light probe, which this PR moves us toward).

makes sense. if the impact is really this big then perhaps we need some investigation into env map perf before going further though?

@SparkyPotato
Copy link
Author

SparkyPotato commented Jan 22, 2025

The lighting example does go from about 0.51 ms to 0.55 ms on my machine (and enabling deferred makes that 0.46 ms to 0.49 ms)

is that in release? if so then i'd argue a ~10% fps reduction is not justified, but it's surprising how large the impact is.

In release, the difference is 0.49 ms vs 0.53 ms, but the deferred timings don't change.

They should be considered basically mutually exclusive (strictly speaking, ambient should be considered a type of light probe, which this PR moves us toward).

makes sense. if the impact is really this big then perhaps we need some investigation into env map perf before going further though?

I'd think ambient lights are usually used only in simple scenes where we'd be CPU bound anyways. For anything more complex, users would probably switch to an environment map or one baked by the procedural sky.

@SparkyPotato
Copy link
Author

I decided to profile the case without an ambient light or envmap, which takes 0.47 ms on this branch.

This means we'll actually be slightly faster in scenes with an envmap after this PR. For example:

  • the deferred rendering example goes from 1.16 to 1.12 ms
  • SSR goes from 0.92 to 0.89 ms
  • post processing goes from 1.02 to 0.96 ms
  • meshlet goes from 1.68 to 1.67 ms
  • color grading goes from 0.88 to 0.87 ms

Note that these are all overall frametimes and not individual pass timings like that of the lighting example (for lighting, the overall frame went from 0.98 to 0.96 ms without any ambient or env light).

Copy link
Contributor

@JMS55 JMS55 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code looks fine. Needs some docs, as well as a changelog and migration guide in the PR description. Ask on discord how to do that, I think we changed our process recently and I forget what the new system is.

@@ -114,6 +116,80 @@ pub struct EnvironmentMapLight {
pub affects_lightmapped_mesh_diffuse: bool,
}

impl EnvironmentMapLight {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Needs docs for the new functions. Esp since EnviornmentMapLight is supposed to have diffuse/specular components that get run through a bunch of sampling and multiscattering stuff, having a single "color" is a bit confusing. Please add some docs and I guess note that it's a bit of a hack? Something along these lines.

@@ -522,6 +523,26 @@ pub enum SimulationLightSystems {
CheckLightVisibility,
}

pub fn map_ambient_lights(
Copy link
Contributor

@JMS55 JMS55 Jan 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to adding a deprecated attribute to ambient light, and then removing this system in 0.17.

EDIT: I mean adding the attribute in this PR, and then opening an issue to remind us to delete this system, and have put it in the 0.17 milestone.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-Rendering Drawing game state to the screen C-Code-Quality A section of code that is hard to understand or change C-Usability A targeted quality-of-life change that makes Bevy easier to use D-Shaders This code uses GPU shader languages D-Straightforward Simple bug fixes and API improvements, docs, test and examples M-Needs-Release-Note Work that should be called out in the blog due to impact S-Needs-Review Needs reviewer attention (from anyone!) to move forward
Projects
Status: No status
Development

Successfully merging this pull request may close these issues.

8 participants