Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct here to familiarize yourself with the rules and how to post constructively.

  2. Unity 2022.1 is now available as the latest Tech release.
    Dismiss Notice

[RELEASED] GPU Instancer

Discussion in 'Assets and Asset Store' started by LouskRad, May 3, 2018.

  1. Cover-Club-Media

    Cover-Club-Media

    Joined:
    Apr 30, 2015
    Posts:
    114
    Upgraded from 1.5.4 to 1.72 imported fine, but receiving this error. I've deleted SO and recompiled but the console spews hundreds of these out. Any suggestions?

    For now I just replaced the GPU folder with my old version and it's working fine again. Let me know.
    upload_2022-5-7_19-28-34.png
     
    Last edited: May 8, 2022
  2. Querke

    Querke

    Joined:
    Feb 21, 2013
    Posts:
    36
    Hello! I love your asset!
    But would it be possible to group all terrains into the same gameobject in the detail rendering component? I see that with the tree rendering component, the additional terrains is grouped under the same game object. This makes it much simpler to adjust settings. I got 16 terrain tiles and if I want to change a setting for my details, I have to do that change 16 times.
    Anyway, keep up the great work.
     
    marcell123455 likes this.
  3. Claytonious

    Claytonious

    Joined:
    Feb 16, 2009
    Posts:
    777
    Is there any way to use trees as Addressables with the GPUITreeManager? This would require somehow loading the tree prefabs as Addressable assets and then "setting" them on the tree manager.
     
  4. MonkeyPuzzle

    MonkeyPuzzle

    Joined:
    Jan 17, 2016
    Posts:
    101
    Trying to figure out GPU Instancer and Vegetation Engine. My scene has about 5 plant prefabs, which I have gotten set up in Vegetation Engine with the materials and animation that I want.

    I added the GPUI, prefab manager and added my prefabs. Most are in the 5000-10000 range, one in the 20+k.

    I have 9 standard Unity terrains, each with one type of non-billboard grass. I also added the detail manager. I was asked to "generate" prototypes.

    I have one camera "Main Camera" and camera auto detect on, which I have confirmed at runtime.

    It seems like everything is working in that it doesn't throw any errors, frustrum culling is working, but I don't see any performance increase. I have tried on my PC with a RTX 3050 TI and a 2020 Macbook Pro.

    Any thoughts on how I can best integrate GPUI is appreciated!
     
  5. GurhanH

    GurhanH

    Joined:
    Apr 24, 2017
    Posts:
    296
    Hi there,
    I am not sure what is causing this issue. We will need to debug to find out. If you can email us a sample project, we can investigate.

    Hi there,
    and thanks for your kind words.
    We are looking into improving the Detail Manager. I shared a simple script in this post which can help as a temporary solution to this problem.

    It should be possible, as long as you load the prefabs before the manager. But we do not currently have demos or documentations specific to Addressables.

    Hi there,
    Since you have high instance counts, there should be some benefit. However there are cases where the application is bound by another process or setting. Some examples:
    - Frame rate capped to monitor's refresh rate or limited max FPS
    - Very high vertex counts causing the application to be GPU bound by vertex processing
    - Some unoptimized visual effects multiplying the draw calls

    As for the Detail Manager, I recommend reading the Best Practices documentation, since it has features (such as shadows, cross-quads) that adversely affect performance.

    If these does not help, you can email us detailed information (including frame rate comparison, profiler data), we can investigate it.
     
  6. MonkeyPuzzle

    MonkeyPuzzle

    Joined:
    Jan 17, 2016
    Posts:
    101
    Thanks for the prompt reply. I will set up some simple tests with just my main character, a terrain and one prototype instanced multiple times and see if that helps. As far as the Vegetation Engine and the custom shaders that they create, is there a way to check that GPUI shaders are being added properly?
     
  7. Cover-Club-Media

    Cover-Club-Media

    Joined:
    Apr 30, 2015
    Posts:
    114
    That will take a long time to prepare. I've googled the issue and see others with the same error message. Can you at least offer a few suggestions before I spent an entire day compiling a mini project? I've reverted back to your older version and it's working fine again. Here is the same error as mine asked before. Perhaps they sent in the sample project as you asked them as well.
    upload_2022-5-10_9-35-55.png
     
  8. GurhanH

    GurhanH

    Joined:
    Apr 24, 2017
    Posts:
    296
    When there is an error on the shader usually the instances would not render correctly, so it would be obvious. But to make sure that they are rendered with GPUI, you can check the Registered Instances section of the manager at runtime, and see if you see the number of instances there.

    These are two completely different errors (one is IndexOutOfRangeException, other one is NullReferenceException). Also UpdateGPUBuffer is the main method which makes all the Compute Shader and Draw Call operations. So it does not give much information about what might be the problem. If you can not create a sample project, email us the full error log with the other information requested here and we will try to help.
     
  9. TanselAltinel

    TanselAltinel

    Joined:
    Jan 7, 2015
    Posts:
    177
    Hi,

    This is a little bit of an edge case but I was wondering if it's already supported with GPUI.

    There is Material Property Override component from Unity: https://github.com/Unity-Technologies/FPSSample/tree/master/Assets/Tools/MaterialPropertyOverride

    It basically creates a variant of the base shader with one or two difference.

    Is GPUI capable of getting prefab variants with this component into a single call?

    My use case would be like this:
    I have one mesh and 6 different base textures. I have one prefab and 5 prefab variants, each of them using a different material due to having different base texture (rest of the properties of this material is the same). If I am to use material variant, I can gather all 6 different object (same mesh, one base material, 5 material variants) into same GPU Instancing through material Enable Instancing checkbox.

    Color variant demo is not usable for me as all of my objects are manually placed in the scene, so I was wondering if a workflow like this would be better.
     
  10. ADAMN721

    ADAMN721

    Joined:
    Aug 7, 2015
    Posts:
    5
    Does this work with WebGL?
     
  11. GurhanH

    GurhanH

    Joined:
    Apr 24, 2017
    Posts:
    296
    Hi there,

    As described in Unity's documentation Material Variants can not be used for optimization. So the draw calls for material variants are not batched.
    You can however use GPUI's Material Variations in combination with Unity's Material Property Blocks to see them with their variant properties in edit mode. We will look into providing a demo with some helper scripts to make it easier to understand.

    For now you can check this partial code to get an idea:
    C# part which should run in a script with ExecuteInEditMode attribute:
    Code (CSharp):
    1. GPUInstancerPrefab gpuInstancerPrefab = GetComponent<GPUInstancerPrefab>();
    2. if (gpuInstancerPrefab.state == PrefabInstancingState.Instanced)
    3. {
    4.     GPUInstancerAPI.UpdateVariation(prefabManager, gpuInstancerPrefab, "textureUVBuffer", instanceUV);
    5. }
    6. else
    7. {
    8.     MeshRenderer[] meshRenderers = GetComponentsInChildren<MeshRenderer>();
    9.     foreach (MeshRenderer mr in meshRenderers)
    10.     {
    11.         MaterialPropertyBlock mpb = new MaterialPropertyBlock();
    12.         mpb.SetVector("textureUV", instanceUV);
    13.         mr.SetPropertyBlock(mpb);
    14.     }
    15. }
    Shader property definition:
    Code (CSharp):
    1. #ifdef UNITY_PROCEDURAL_INSTANCING_ENABLED
    2.         StructuredBuffer<float4> textureUVBuffer;
    3. #else
    4.         UNITY_INSTANCING_BUFFER_START(Props)
    5.             UNITY_DEFINE_INSTANCED_PROP(float4, textureUV)
    6.         UNITY_INSTANCING_BUFFER_END(Props)
    7. #endif
    Shader property access:
    Code (CSharp):
    1. #ifdef UNITY_PROCEDURAL_INSTANCING_ENABLED
    2.             float4 texUV = textureUVBuffer[gpui_InstanceID];
    3. #else
    4.             float4 texUV = UNITY_ACCESS_INSTANCED_PROP(Props, textureUV);
    5. #endif
    Hi there,

    Unfortunately GPUI does not support WebGL because of its dependence on Compute Shaders. You can see the list of supported graphics APIs and platforms from the Minimum Requirements.
     
    TanselAltinel likes this.
  12. diccon

    diccon

    Joined:
    Sep 13, 2013
    Posts:
    21
    Hello,
    we are finding that GPUInstancerDetailManager uses an excessive amount of memory as we try to scale our project and I wonder if you have any advice. We are using it to put 4 vegetation prototypes onto a island with Terrain approximately 3000x3000 and our full game has 22 of these, so when we create the world the memory profiler shows an increase of around 1Gb, including 700mb of arrays of ints and floats.
    I have tried a naive approach of disabling the detail manager on each island and turning it on when the player is close enough, this is successful in reducing the memory but causes a frame rate spike when the manager initializes (even with the threaded option).
    I am thinking that the best approach would be a custom solution would be to serialize the instance transforms in the editor and stream them in from an asset at runtime. Since our detail instances are fairly sparse this might only be a few hundred or low thousands. Can you tell me if the API would allow me to do something like this, and maybe point me in the right direction?

    Thanks for your help.
     
  13. madhh

    madhh

    Joined:
    Jan 1, 2014
    Posts:
    2
    Hey guys

    I noticed there are shadows on the GPUI generated billboards. Can someone tell me how they work? No matter what I do, the shadow direction is always wrong. When I move the sun around, the shadows change direction, but their direction is never the one the sun position implies.
     
  14. marcell123455

    marcell123455

    Joined:
    Jun 18, 2014
    Posts:
    224
    Hi,

    I run into a problem with my tree manager. I simply switched from open GL 3.1 to direct x 11 as graphics engine, and the GPU instancer tree manager stopped working. It shows me these errors when pressing play:

    Kernel 'CSInstancedRenderingVisibilityKernelLOD0' not found
    0x00007ff60d5df46c (Unity) StackWalker::GetCurrentCallstack
    0x00007ff60d5e6a69 (Unity) StackWalker::ShowCallstack
    0x00007ff60e378d4c (Unity) GetStacktrace
    0x00007ff60eddb497 (Unity) DebugStringToFile
    0x00007ff60d30b5ce (Unity) ComputeShader::FindKernel
    0x00007ff60d0a506c (Unity) ComputeShaderScripting::FindKernel
    0x00007ff60d615261 (Unity) ComputeShader_CUSTOM_FindKernel
    0x000001ac60f2fac6 (Mono JIT Code) (wrapper managed-to-native) UnityEngine.ComputeShader:FindKernel (UnityEngine.ComputeShader,string)
    0x000001ac60f2ebbb (Mono JIT Code) [GPUInstancerManager.cs:148] GPUInstancer.GPUInstancerManager:Awake ()
    0x000001ac60f2e763 (Mono JIT Code) [GPUInstancerPrefabManager.cs:34] GPUInstancer.GPUInstancerPrefabManager:Awake ()
    0x000001ac60791490 (Mono JIT Code) (wrapper runtime-invoke) object:runtime_invoke_void__this__ (object,intptr,intptr,intptr)
    0x00007ffd5175f1e0 (mono-2.0-bdwgc) [mini-runtime.c:2849] mono_jit_runtime_invoke
    0x00007ffd516e2ac2 (mono-2.0-bdwgc) [object.c:2921] do_runtime_invoke
    0x00007ffd516ebb1f (mono-2.0-bdwgc) [object.c:2968] mono_runtime_invoke
    0x00007ff60d5239c4 (Unity) scripting_method_invoke
    0x00007ff60d51eb81 (Unity) ScriptingInvocation::Invoke
    0x00007ff60d51ecde (Unity) ScriptingInvocation::InvokeChecked
    0x00007ff60d5777d6 (Unity) SerializableManagedRef::CallMethod
    0x00007ff60d4ebfa4 (Unity) MonoBehaviour::CallAwake
    0x00007ff60d4eafb0 (Unity) MonoBehaviour::AwakeFromLoad
    0x00007ff60d5b803f (Unity) AwakeFromLoadQueue::InvokePersistentManagerAwake
    0x00007ff60d5b89d2 (Unity) AwakeFromLoadQueue::persistentManagerAwakeFromLoad
    0x00007ff60d5b8b43 (Unity) AwakeFromLoadQueue::persistentManagerAwakeFromLoad
    0x00007ff60d27b21e (Unity) LoadSceneOperation::CompleteAwakeSequence
    0x00007ff60d27e9ab (Unity) LoadSceneOperation::playerLoadSceneFromThread
    0x00007ff60d27cb03 (Unity) LoadSceneOperation::IntegrateMainThread
    0x00007ff60d280376 (Unity) PreloadManager::UpdatePreloadingSingleStep
    0x00007ff60d27ffbd (Unity) PreloadManager::UpdatePreloading
    0x00007ff60d2563e3 (Unity) `InitPlayerLoopCallbacks'::`2'::EarlyUpdateUpdatePreloadingRegistrator::Forward
    0x00007ff60d23e4ac (Unity) ExecutePlayerLoop
    0x00007ff60d23e583 (Unity) ExecutePlayerLoop
    0x00007ff60d245259 (Unity) PlayerLoop
    0x00007ff60df11e81 (Unity) PlayerLoopController::UpdateScene
    0x00007ff60df100a9 (Unity) Application::TickTimer
    0x00007ff60e37f201 (Unity) MainMessageLoop
    0x00007ff60e3833a1 (Unity) WinMain
    0x00007ff60fa25f3e (Unity) __scrt_common_main_seh
    0x00007ffdb73f54e0 (KERNEL32) BaseThreadInitThunk
    0x00007ffdb76a485b (ntdll) RtlUserThreadStart
    ArgumentException: Kernel 'CSInstancedRenderingVisibilityKernelLOD0' not found.
    GPUInstancer.GPUInstancerManager.Awake () (at Assets/GPUInstancer/Scripts/Core/Contract/GPUInstancerManager.cs:148)
    GPUInstancer.GPUInstancerPrefabManager.Awake () (at Assets/GPUInstancer/Scripts/GPUInstancerPrefabManager.cs:32)

    When I switch back to open GL it works again. Any idea how to fix this or what it could be caused by?

    Thanks ;)
     
  15. marcell123455

    marcell123455

    Joined:
    Jun 18, 2014
    Posts:
    224
    Forget it, fixed it by switching build plattform from android to windows pc.
     
    GurhanH likes this.
  16. GurhanH

    GurhanH

    Joined:
    Apr 24, 2017
    Posts:
    296
    Hi there,
    The memory cost and initial spikes mainly come from the data structure of the detail layers of the Unity Terrain API. It is only provided as a 2D int array.
    There are multiple options you can choose from especially if you have sparse vegetation:
    - Use the Tree Manager instead of Detail Manager. Unlike details, trees are stored in an instance based data structure. So the loaded data size will be equal to the instance count, instead of being based on terrain detail resolution.
    - Use the No-GameObject workflow with Prefab Manager. With this approach you can have full control over when the instances are loaded and how they are stored.

    Hi there,
    Normally billboards do not cast shadows, so I am not sure what happened here. If you can send us a sample project (e.g. a scene with minimum amount of content to show the problem), we can investigate.
     
  17. Marco-Playable

    Marco-Playable

    Joined:
    Nov 12, 2020
    Posts:
    45
    I am trying to write a detail spawner similar to what you have in CSInstancedRenderingGrassInstantiationKernel, but without a terrain - just placing grass instances on a mesh after querying GetTransformDataBuffer(). My code is working , but the performance I am getting is underwhelming.

    To see if I messed anything up I looked at your Boids demo instead. If I crank the spawn count up to 100k, the stats window in Unity tells me that the CPU thread takes 150ms per frame (on an RTX 2060 Super). This is where it gets interesting: when I disable the GPUI Instancer Prefab Manager at runtime- the CPU thread usage goes down to 2ms. Likewise, if I disable the BoidsController at runtime then the CPU thread usage goes down to 3ms.

    So I am guessing the Boids kernel is dispatched and writing to the transformationMatrixVisibilityBuffer. Then it's time for GPUI's Update call and it tries to dispatch a kernel that uses the transformationMatrixVisibilityBuffer so the system becomes blocked until that compute buffer is no longer used by Boids?

    Given the 2ms from spawning and 3ms from culling I was hoping to see a total frame time of around 5ms and instead it's 30 times as much.

    Do you have any recommendations on how to achieve better performance?
     
  18. madhh

    madhh

    Joined:
    Jan 1, 2014
    Posts:
    2
    Hi, sorry, I try to explain it better.
    I did not mean the shadows cast by the billboard, but the shadows on the billboard.
    https://www.dropbox.com/s/7g6d8zh19atybse/tree-billboard-shadow.jpg?dl=0
    On this picture you can see the actual tree models in the foreground, and the generated billboards a bit further away and also in the background. As you can see they both have a lit side, and the other side is in shadow, but they don't match, it looks like it's completly the opposite. I just don't know how to set it up, so the lit sides match up, and i don't find anything about this in the documentation.
    I can see that these shadows get baked into the billboard, because when I'm rotating a tree, the shadow rotates with it. I can actually rotate the trees by hand so the shadows match, I just can't seem to be able to instantiate them that way.
    https://www.dropbox.com/s/b0ydrdtoji7f685/tree-bilboard-shadows-all-over.jpg?dl=0
    On the picture all the trees have the same rotation. If i place the trees with random rotations, the billboard shadows are all over the place, like on this second picture.
    In this scene I'm using the prefab manager. I'm instancing the prefabs in runtime, then registering them with the prefab manager. Is there a way to regenerate the billboards in runtime? What sun direction is used, when the billboards are generated?
    I also tried using the tree manager, but I still can't seem to be able to make the billboards shadow match the shadow on the actual model.
     
    Last edited: May 16, 2022 at 11:07 PM
  19. Grigler_f

    Grigler_f

    Joined:
    May 14, 2020
    Posts:
    8
    Hello, are there any plans for adding API support for using NativeArrays in PrefabVariationData rather than managed arrays? We use the no GameObject pipeline with large numbers of instances and make heavy usage of the JobSystem, being able to populate a NativeArray for the data in an IJob rather than a manage array would be largely benficial for us
     
  20. roundyyy

    roundyyy

    Joined:
    Dec 23, 2019
    Posts:
    83
    Hi, Was there any change how cross fade on trees is handled on recent update? It's not fading correctly now after update, before it was less noticeable, so transition was very smooth, now there is moment where you can badly see dithering . Thanks

    Edit : just reverted from backup to previous version and transition is correct again

    Please also add SceneName to billboard prototype data name or some additional folders for each scene, so billboard of the same trees from other scenes are not overwritten (this is very annoying)
     
    Last edited: May 18, 2022 at 7:49 AM
unityunity