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

Add a level of detail system for GPUParticles3D and CPUParticles3D #2743

Closed
Calinou opened this issue May 19, 2021 · 7 comments
Closed

Add a level of detail system for GPUParticles3D and CPUParticles3D #2743

Calinou opened this issue May 19, 2021 · 7 comments

Comments

@Calinou
Copy link
Member

Calinou commented May 19, 2021

See also #2744 which is for light nodes and #2784 for reflection probes.

Describe the project you are working on

The Godot editor 🙂

Describe the problem or limitation you are having in your project

Particles currently don't feature a built-in LOD system.

When you use many particles nodes (e.g. for torches in a room), you don't want those to emit particles if the player is too far away to see the torches. This is especially true with small particles like sparks.

For the record, the Decal node (new in 4.0) features a built-in LOD system with configurable distance and fade distance.

Describe the feature / enhancement and how it helps to overcome the problem or limitation

Add emission range and fade distance properties to GPUParticles3D and CPUParticles3D.

Describe how your proposal will work, with code, pseudo-code, mock-ups, and/or diagrams

If we find out a way to allow changing the number of particles emitted without resetting emission, this would likely be the ideal way to do LOD for particles as it will likely look the most seamless in action.

Alterntively, we can:

  • Reduce the opacity of distant particles progressively. This can be more suited for particle systems that only emit a few large particles, but it's arguably less suited for particle systems that emit hundreds of particles or more.
  • Disable emission for distant particles entirely (without affecting the public emitting property, so that it doesn't interfere with toggling it from a script). This is better than toggling the visibility (which causes visible pop-ins), but due to the "all or nothing" nature of toggling emission, it's still worse than the proposed alternatives.

If this enhancement will not be used often, can it be worked around with a few lines of script?

Kind of. It's possible to toggle particle emission in a script. The Godot LOD add-on I wrote provides such a feature.

Is there a reason why this should be core and not an add-on in the asset library?

Implementing this LOD system in C++ would lead to better performance when using large amounts of particle nodes (hundreds or more).

@QbieShay
Copy link

I like this idea!

It could be done by LOD'ing both the particle number and the material for the particles (switch from alpha to cutout?)

@Calinou
Copy link
Member Author

Calinou commented May 19, 2021

It could be done by LOD'ing both the particle number and the material for the particles (switch from alpha to cutout?)

The issue with switching materials is that you need to introduce a second material for each type of particle that needs LOD. Not only this would require more work from the user, but it'd also kind of negate the performance benefit.
Also, won't alpha testing going look bad in the distance due to aliasing? (We have alpha antialiasing options in master, but these have a cost too.)

This is why I proposed solutions that don't require creating a new material, such as reducing the particle number or reducing the particle opacity. (Particles' color can already be adjusted with the color ramp in each material, so it should be possible to multiply this color by an opacity set by the LOD system.)

@Zireael07
Copy link

Would it be possible to use scale for LOD? I have a rain particle that could benefit from being bigger in the back and smaller closer to the camera, so that it's almost uniform (but not quite) in size.

@clayjohn
Copy link
Member

I'm concerned that this proposal is too limited. I echo Qbie's and Zireael's concerns, proper LODs will need to tweak more than just emission rate. Good particle LODs will need to change emission rate and process material (or even mesh and mesh material as well.

I think the only solution is to have something like HLODs for particles. Where one node fades out and another fades in based on distance with a specified hysteresis.

@Calinou
Copy link
Member Author

Calinou commented Feb 24, 2022

With the implementation of visibility ranges and distance fade in master, it's possible to use this (H)LOD system for both GPUParticles3D and CPUParticles3D 🎉

Testing project: test_particle_lod.zip

How to set up visibility ranges for particles:

  • Add a GPUParticles3D node or CPUParticles3D node.
  • Configure the ParticlesMaterial and the mesh resource to use in the particle.
  • Duplicate the node and move it to be a child of the first particle node. Perform one or more changes that make the child particle node less demanding to render:
    • Use a less demanding mesh/material.
    • Use a lower amount of particles.
    • Use a different ParticlesMaterial.
  • In the inspector's GeometryInstance3D section, configure Visibility Range so that the End distance of the parent node is equal to the Begin distance of the child node. (The distance should be set to whichever cutoff distance you desire; try 25.0 for instance.)
  • If you want hysteresis or fading, set the fade mode accordingly in the Visibility Range section, then configure End Margin and Begin Margin on the parent and child nodes respectively.
particles.mp4

I'll close this proposal as visibility ranges cover the original need in the proposal well enough. (In fact, it's more powerful than the solution proposed here, since it lets you adjust materials, meshes and process materials as well.

For Godot 3.x, you can use the Level of Detail add-on as always.

@Calinou Calinou closed this as completed Feb 24, 2022
@Calinou Calinou added this to the 4.0 milestone Feb 24, 2022
@Zireael07
Copy link

@Calinou: This is an excellent explanation worth documenting somewhere more accessible than Godot proposals... godot documentation itself...?

@Calinou
Copy link
Member Author

Calinou commented Feb 25, 2022

@Calinou: This is an excellent explanation worth documenting somewhere more accessible than Godot proposals... godot documentation itself...?

Documentation on visibility ranges and particles hasn't been updated yet, so I'd wait until that part is done.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants