# Cube RenderTargetTexture cameras, invertY, and rendering

**URL:** <https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999>\
**Category:** Questions\
**Tags:** texture\
**Created:** [November 24, 2022, 7:28pm UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999 "2022-11-24T19:28:10Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![heuristics7](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/heuristics7/32/27959_2.png) [@heuristics7](https://forum.babylonjs.com/u/heuristics7)\
**Post date:** [November 24, 2022, 7:28pm UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/1 "2022-11-24T19:28:10Z")

</div>

Hi all, I have a few questions about RTTs.

First, for a Cube RTT (actually, same for a normal RTT as well), I noticed the texture is created with `invertY` as true and there doesn’t appear to be a way to specify otherwise. In the below PG, I’ve addressed that by adding a parent xform node to the camera with y inversion and rotations as needed for the +y and -y faces. It works, but if I can create the texture without inversion, that would be simpler.

Second, regarding the way I’m adjusting the cameras for each face of the cube RTT render, it seems a bit hacky/inefficient. I think by changing the camera target each time, the matrices need to be recalculated many times and can’t be cached. Is there a better way to do this? I noticed a camera rig concept that looks like it’s used for VR which might be similar to this case but didn’t find much documenting how it works.

Last question, I’d like to be in full control over when the RTT renders. `refreshRate = 0` works well to render once after which I can choose when to render the RTT again, but not exactly what I want. I think using a separate scene might work, but I will have large meshes that I don’t want to duplicate in both scenes. Any thoughts here?

In the PG, I have a skybox in the main scene that samples from the RTT. The RTT renders another skybox with static texture and a rotating camera.

> **[Babylon.js Playground](https://playground.babylonjs.com/#V6U09N%234)**
>
> Babylon.js playground is a live editor for Babylon.js WebGL 3D scenes

---

<div class="post-metadata">

**Author:** ![sebavan](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/sebavan/32/57_2.png) [@sebavan](https://forum.babylonjs.com/u/sebavan)\
**Post date:** [November 25, 2022, 12:46am UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/2 "2022-11-25T00:46:48Z")

</div>

> [@heuristics7](#):
>
> I noticed the texture is created with `invertY` as true and there doesn’t appear to be a way to specify otherwise

This only impacts texture “upload” mainly when data are unpacked but not for rendering per se.

> [@heuristics7](#):
>
> Second, regarding the way I’m adjusting the cameras for each face of the cube RTT render, it seems a bit hacky/inefficient. I think by changing the camera target each time, the matrices need to be recalculated many times and can’t be cached. Is there a better way to do this? I noticed a camera rig concept that looks like it’s used for VR which might be similar to this case but didn’t find much documenting how it works.

It looks highly similar to what we do in [https://github.com/babylonjs/Babylon.js/blob/master/packages/dev/core/src/Probes/reflectionProbe.ts#L139](https://github.com/babylonjs/Babylon.js/blob/master/packages/dev/core/src/Probes/reflectionProbe.ts#L139) and yes I guess some info could be cached per index as long as the center does not move.

> [@heuristics7](#):
>
> Last question, I’d like to be in full control over when the RTT renders. `refreshRate = 0` works well to render once after which I can choose when to render the RTT again, but not exactly what I want. I think using a separate scene might work, but I will have large meshes that I don’t want to duplicate in both scenes. Any thoughts here?

Not sure what you want here ? (not rendering at all before using it will result in potentially broken data in the texture which is why the API enforces it I believe). If you are adventurous 🙂 you can set the private \_currentRefreshId to -2 which will never render automatically. If that works we could add smthg for this.

---

<div class="post-metadata">

**Author:** ![heuristics7](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/heuristics7/32/27959_2.png) [@heuristics7](https://forum.babylonjs.com/u/heuristics7)\
**Post date:** [November 25, 2022, 3:09am UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/3 "2022-11-25T03:09:49Z")

</div>

Thanks for your response!

> [@sebavan](#):
>
> This only impacts texture “upload” mainly when data are unpacked but not for rendering per se.

I thought this was the case, but I couldn’t come up with another explanation why all the faces of the texture were inverted in Y in this PG [https://playground.babylonjs.com/#V6U09N#5](https://playground.babylonjs.com/#V6U09N#5)  
I suppose it must have something to do with how cubemaps work internally in OpenGL. It does say the v coordinate goes “down” for X and Z.  
[Cubemap Texture - OpenGL Wiki](https://www.khronos.org/opengl/wiki/Cubemap_Texture#Upload_and_orientation)

> [@sebavan](#):
>
> It looks highly similar to what we do in [Babylon.js/reflectionProbe.ts at master · BabylonJS/Babylon.js · GitHub](https://github.com/babylonjs/Babylon.js/blob/master/packages/dev/core/src/Probes/reflectionProbe.ts#L139) and yes I guess some info could be cached per index as long as the center does not move.

Thanks for the reference! Looks like another option for getting the camera xforms set up correctly.

> [@sebavan](#):
>
> Not sure what you want here ? (not rendering at all before using it will result in potentially broken data in the texture which is why the API enforces it I believe). If you are adventurous 🙂 you can set the private \_currentRefreshId to -2 which will never render automatically. If that works we could add smthg for this.

I was finding it tricky to get the framework to actually only render once when setting `refreshRate = 0`. I think it might be detecting that something changed in the scene and needed a rerender? I’m not sure. Here’s a PG showing the behavior [https://playground.babylonjs.com/#V6U09N#6](https://playground.babylonjs.com/#V6U09N#6) - face 0 is rendered between 5-7 times each reload.

I tried your suggestion, `_currentRefreshId = -2`, but that didn’t work I think because of the above issue, `resetRefreshCounter()` is getting called overwriting it. So I tried creating a subclass where I just turn off `_shouldRender` and that works… mostly.

> **[Babylon.js Playground](https://playground.babylonjs.com/#V6U09N%238)**
>
> Babylon.js playground is a live editor for Babylon.js WebGL 3D scenes

Strangely, if I only render once, everything looks good except for the +X face, which is upside-down. If I render a second time (uncomment line 120) the +X face is corrected.

---

<div class="post-metadata">

**Author:** ![Evgeni\_Popov](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/evgeni_popov/32/4432_2.png) [@Evgeni\_Popov](https://forum.babylonjs.com/u/Evgeni_Popov)\
**Post date:** [November 25, 2022, 9:55am UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/4 "2022-11-25T09:55:56Z")

</div>

> [@heuristics7](#):
>
> I think it might be detecting that something changed in the scene and needed a rerender? I’m not sure. Here’s a PG showing the behavior [https://playground.babylonjs.com/#V6U09N#6](https://playground.babylonjs.com/#V6U09N#6) - face 0 is rendered between 5-7 times each reload.

Yes, it will render in the RTT until all ressources are ready. You can use `scene.executeWhenReady` to make sure everything is ready before returning from the create scene function:

> **[Babylon.js Playground](https://playground.babylonjs.com/#V6U09N%239)**
>
> Babylon.js playground is a live editor for Babylon.js WebGL 3D scenes

> [@heuristics7](#):
>
> Strangely, if I only render once, everything looks good except for the +X face, which is upside-down. If I render a second time (uncomment line 120) the +X face is corrected.

Using the `executeWhenReady` method as stated above + passing `true` as the second parameter will fix this problem.

---

<div class="post-metadata">

**Author:** ![heuristics7](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/heuristics7/32/27959_2.png) [@heuristics7](https://forum.babylonjs.com/u/heuristics7)\
**Post date:** [November 26, 2022, 6:25am UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/5 "2022-11-26T06:25:39Z")

</div>

I’ve been digging more into this today, and I was still finding it surprisingly difficult to get my RTT to render correctly with a single render call.

My understanding of the PG you linked, is that it is preventing the renders that happen while the materials are still loading by preventing the render loop from starting until the entire scene is ready. Makes sense, but won’t work when I need to RTTs on the fly while having a main interactive scene.

I tried to adapt your PG to use an explicit `render` call, but still running into the same strange +X upside-down issue. [https://playground.babylonjs.com/#V6U09N#13](https://playground.babylonjs.com/#V6U09N#13)

I even tried a totally different approach for waiting for the specific material, effect, and texture to finish loading and got the same issue. [https://playground.babylonjs.com/#V6U09N#12](https://playground.babylonjs.com/#V6U09N#12)

In both cases, uncommenting the second `render` line results in a correct render. I still trying to determine why the single face is upside-down when only rendering once.

---

<div class="post-metadata">

**Author:** ![heuristics7](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/heuristics7/32/27959_2.png) [@heuristics7](https://forum.babylonjs.com/u/heuristics7)\
**Post date:** [November 26, 2022, 7:07am UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/6 "2022-11-26T07:07:53Z")

</div>

Immediately after posting the above, it occurred to me to try fiddling with the transform node for the first face, and I found that no changes were being reflected in the render. So that meant that the matrix was not being calculated correctly for that face. Turns out this line was preventing the transform node’s world matrix from being calculated, only for the first face.

> <https://github.com/BabylonJS/Babylon.js/blob/master/packages/dev/core/src/node.ts#L449>

Not sure if the scene’s render ID is missed from being incremented somewhere or if it’s just a quirk of they way I’m using the camera, but here’s a now working PG, rendering only a single time to the RTT.

> **[Babylon.js Playground](https://playground.babylonjs.com/#V6U09N%2314)**
>
> Babylon.js playground is a live editor for Babylon.js WebGL 3D scenes

---

<div class="post-metadata">

**Author:** ![Evgeni\_Popov](https://sea2.discourse-cdn.com/flex024/user_avatar/forum.babylonjs.com/evgeni_popov/32/4432_2.png) [@Evgeni\_Popov](https://forum.babylonjs.com/u/Evgeni_Popov)\
**Post date:** [November 26, 2022, 1:09pm UTC](https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-rendering/35999/7 "2022-11-26T13:09:53Z")

</div>

> [@heuristics7](#):
>
> Turns out this line was preventing the transform node’s world matrix from being calculated, only for the first face.

Good find!

> [@heuristics7](#):
>
> Not sure if the scene’s render ID is missed from being incremented somewhere or if it’s just a quirk of they way I’m using the camera

I would say it behaves as expected because the world matrices are automatically calculated once for the frame, and you are modifying a node that has already had its world matrix calculated. Because you need the world matrix to be up to date for the current frame, you have to explicitly regenerate it.

Also, it works for faces \> 0 because `scene.renderId` is incremented after each face is rendered. But this is a bit of a “lucky” side effect because it turns out that the `Node.getWorldMatrix` uses `scene.renderId` as part of its dirty mechanism…

Thanks to your findings, I noticed that when checking for RTT availability, we don’t increment the `scene.frameId` counter when we should. This PR will fix that:

> <https://github.com/BabylonJS/Babylon.js/pull/13289>
>
> See https://forum.babylonjs.com/t/cube-rendertargettexture-cameras-inverty-and-r…endering/35999/6

With this PR, your PG will also be fixed and you will no longer need to call `invertYFixNode.computeWorldMatrix(true)`.

However, as mentioned above, this works more because of the way things are done internally and I would still call `computeWorldMatrix` even with the PR merged in (for example, if the texture was a regular 2D texture and not a cube, this would not work even with the PR applied because in this case we don’t increment `scene.frameId` after the RTT texture has been generated).
