-
-
Notifications
You must be signed in to change notification settings - Fork 1.1k
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
Accelerated env baking on the GPU #1165
Conversation
@riccardobl this looks really cool. Is there more info on this? |
You can see it working in The code is based on this https://learnopengl.com/PBR/IBL/Specular-IBL (and following articles). The PR works but as you can see in the two examples, it exposes two different apis, one that is similar to what is used now in the master branch (LightProbeFactory2) and one that use a control. I'm not sure which one should go in the final pr. Also it requires modifications to the framebuffer class, that i will have to extract to a dedicated PR. |
I've updated the PR and added a description. This is ready to be reviewed |
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/GenericEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/GenericEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLHybridEnvBakerLight.java
Show resolved
Hide resolved
Thank you for your review @danielperano |
…aking. Make them serializable by default if created with LightProbeFactory2. Accelerate Spherical Harmonics generator.
4d75d0d
to
0804ecd
Compare
Rebased to current master |
Are there any objections to merging this? It's worth noting that this PR doesn't break the current baking process. |
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
I would suggest adding to the
public abstract class AbstractControl implements Control, JmeCloneable {
...
} Edit: done, thanks @riccardobl |
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
* | ||
* @param assetManager | ||
*/ | ||
public void setAssetManager(AssetManager assetManager) { |
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.
The setAssetManager()
method is not necessary, since it is a mandatory parameter of the public constructor
public EnvironmentProbeControl(AssetManager assetManager, int size) {}
I would suggest removing it.
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.
i can be used to change the asset manager used internally by the control that might not be the same used to deserialize it in some circumstances i supppose
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.
Okay, but if you are not sure about this feature, you could change the visibility of the AssetManager
variable from private
to protected
by letting the developers decide whether to add a set
method or not. You also benefited from this trick by extending the LigthProbe
class. More freedom and less code to maintain ;)
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.
protected fields are evil. They become part of the public API and provide no recourse for changing.
Always always always better to provide protected methods because at least then you can change implementations, provide backwards compatibility, etc.. With protected fields you are stuck forever.
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.
JME technically supports multiple instances of AssetManager, so setAssetManager was there to allow to change the internal asset manager after the control is deserialized, but on second thought, maybe it only adds confusion.
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.
@riccardobl Ok, I suggest removing it.
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/GenericEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBakerLight.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLHybridEnvBakerLight.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/EnvironmentProbeControl.java
Outdated
Show resolved
Hide resolved
} | ||
|
||
/** | ||
* Create a new environment probe control. |
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.
The Javadoc summary fragment should not be a complete sentence.
I suggest "Create" -> "Creates"
} | ||
|
||
/** | ||
* Tag spatial as part of the environment for this EnvironmentProbeControl. |
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.
The Javadoc summary fragment should not be a complete sentence.
I suggest "Tag" -> "Tags the specified"
} | ||
|
||
/** | ||
* Untag spatial as part of the environment for this |
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.
The Javadoc summary fragment should not be a complete sentence.
I suggest "Untag" -> "Untags the specified"
} | ||
|
||
/** | ||
* Tag spatial as part of the environment for every EnvironmentProbeControl. |
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.
The Javadoc summary fragment should not be a complete sentence.
I suggest "Tag" -> "Tags the specified"
jme3-core/src/main/java/com/jme3/environment/baker/IBLGLEnvBaker.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLHybridEnvBakerLight.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLHybridEnvBakerLight.java
Outdated
Show resolved
Hide resolved
jme3-core/src/main/java/com/jme3/environment/baker/IBLHybridEnvBakerLight.java
Outdated
Show resolved
Hide resolved
jme3-examples/src/main/java/jme3test/light/pbr/TestPBRSimple.java
Outdated
Show resolved
Hide resolved
Apologies, but going through all the Javadoc to insert 's' and '.' seems a bit like nitpicking at this stage. If you check any file in the JME repo, you'll notice that these 'rules' were never enforced before. |
I kinda agree that with Javadoc, good enough is good enough. Enforcing strict rules on Javadoc doesn't serve much purpose to me at least. If it is understandable English and gives good enough information, that would be good enough. Good enough, did I mention this term? Difficult to measure, subjective, maybe you understand what I mean. And thanks @riccardobl for the feature and taking all the feedback maturely! |
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.
Thank you for your patience @riccardobl . I am curious to try this new feature! Just a couple of finishing touches and I think it's good enough for me ;)
tx.getImage().clearUpdateNeeded(); | ||
} | ||
|
||
protected int limitMips(int nbMipMaps, int baseW, int baseH, RenderManager rm) { |
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 are unused parameters in this method (int baseW, int baseH, RenderManager rm
). I would suggest to remove them ;)
* | ||
* @param assetManager | ||
*/ | ||
public void setAssetManager(AssetManager assetManager) { |
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.
Okay, but if you are not sure about this feature, you could change the visibility of the AssetManager
variable from private
to protected
by letting the developers decide whether to add a set
method or not. You also benefited from this trick by extending the LigthProbe
class. More freedom and less code to maintain ;)
* the asset manager | ||
* @return a debug node | ||
*/ | ||
public static Node getDebugGui(AssetManager manager, LightProbe probe) { |
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.
The default settings of this method may not satisfy users who want to decide the name to assign to the debug node
or its initial position in their tests. Since this is not typically a core, but a debugging feature, I would suggest moving this method to a test class (eg. TestPBRSimple
or TestPBRLighting
). That way you have more freedom to explain to users how to debug the data properly without raising exceptions ;) I too reading this method can't figure out when is the right time to test whether the LightProbe
is ready or not ;)
Solution: test class with example.
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 was copied from LightProbeFactory, so while i agree with you, the purpose of this class is to migrate the code using LightProbeFactory to the new baker, so it should expose the same api
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.
@riccardobl Ok, I don't particularly like it, but I can accept it.
* A control that automatically handles environment bake and rebake including | ||
* only tagged spatials. | ||
* | ||
* Simple usage example: <code> |
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.
I don't have a strong opinion on this, but I would suggest using this long explanation in a useful way by removing it from here and putting it in a test class. That way you simplify your life and don't have to worry about updating the javadoc in case of future changes or fixes ;)
@riccardobl I agree it's nitpicking, and I do appreciate the importance of your work. Are you implying you don't want me to review yourPRs? If so, just say so. In this instance, however, you specifically requested my review, so I felt obligated to do my best, poor though it is. Prior to PR #1655 (November 2021) this project had no official coding style. With nothing to enforce, there was of course no enforcement. Since then, I've tried to follow and enforce our preferred style, at least on new Java files. This involves plenty of nitpicking. I'm sure I sometimes make mistakes. If you don't like the "rules", you're in a good position to change them. |
Not at all. I appreciate your dedication to the project, and I value your input. However, I'd like to suggest that we focus more on the content during the reviews, rather than getting caught up in minor styling issues or comments. I think this adjustment also helps prevent contributors from feeling discouraged due to the strict rules. |
@stephengold , |
I'm not interested in re-reviewing this PR. |
You submitted changes request, therefore I asked |
This PR improves the performances and user friendliness of environment baking.
Accelerated Baking
This PR adds 3 accelerated bakers that can be used in place of the current CPU baker.
The enhancements brought by these bakers is very remarkable, as they allow the environment baking process to be completed in <1s, effectively rendering the need for prebaked environments obsolete.
IBLGLEnvBaker
This is the most high-performing baker. It run entirely on the GPU, and can generate prefiltered, irradiance, and BRDF maps.
This is the classic env baker implementation that is currently not used in jme.
IBLHybridEnvBakerLight and IBLGLEnvBakerLight
These bakers generate the prefiltered map and spherical harmonics currently used in the latest PBR shader in jme.
Although this method reduces the VRAM consumption, this approach doesn't allow for as much optimization as the IBLGLEnvBaker. Nonetheless, the following accelerated baking methods are available:
New APIs
The LightProbeFactory has now been deprecated in favor of the LightProbeFactory2, which seamlessly integrates the accelerated baking methods. This transition serves as a dedicated migration path for legacy code.
The new API
EnvironmentProbeControl
is designed to streamline and simplify the entire baking and rebaking process.Here's how it works:
Integration: Developers are only required to instantiate an EnvironmentProbeControl and attach it to the root node of their targeted scene (e.g., the rootNode).
Geometry Tagging: By employing the EnvironmentProbeControl.tag(Spatial) method, you can mark which geometries are part of the environment and should be baked (e.g., the skybox).
Profit: Once the tagging is in place, the control takes care of the rest. On the next frame, it automatically initiates baking for the tagged geometries within its node and completes it before the scene is rendered. No more waiting for the processes to conclude or resorting to convoluted culling tricks.
Update the baking: Every time the baking needs to be updated (eg. day-night cycles) the rebake() method of the control can be invoked.
This new system operates directly within the same scene. It uses RenderManager.setRenderFilter() (added by this PR) to filter out non tagged geometries, avoiding cloning, extra viewports, or other convoluted approaces.
Example
This is a fully functional remake of TestPBRLighting using the new API
As you can see, much simpler and cleaner.
Knowing issues
The difference in roughness levels in the prefiltered envmap generated by the accelerated baker is less prominent than the current one, i am not sure why, you can test it out by toggling USE_ACCELERATED_BAKING in the TestPBRLighting class included in this PR.
I am not sure if this is an issue or which one is the correct behavior.
Minimum requirements
OpenGL 3.1 or GL ES 3.0