Oswald

Second camera viewport fail to resize on engine.resize()

Recommended Posts

Hi,

I have 2 scenes overlaying one another (the first is a UI using AdvancedDynamicTexture, the second is a 3D content).

Both have their own camera (one each), and are rendered like so :

this.UIScene = new BABYLON.Scene(this.engine);
this.UIContainer = new BABYLON.GUI.AdvancedDynamicTexture.CreateFullscreenUI("UI");

var UICamera = new BABYLON.ArcRotateCamera("UICamera", 0, 0.8, 100, BABYLON.Vector3.Zero(), this.UIScene);
UICamera.layerMask = 0x40000000;
this.UIContainer.layer.layerMask = 0x40000000;

this.UIScene.autoClear = false;
// Register a render loop to repeatedly render the scene
this.engine.runRenderLoop(() => {
    this.currentScene.scene.render();
    this.UIScene.render();
});

The ("this.currentScene" is a wrapper class meant to easily change the second scene. It properly points to a valid instance of that class, which contains a valid scene.

All elements of the second scene are on the default layer mask, at 0x0FFFFFFF.

My issue is that, while the content of the first scene is rendered properly, the content of the second scene is rendered as if its camera viewport was a perfect square, then stretched to match the canvas real aspect ratio (which is about 16:9, so the content looks flattened).

I attached 2 pictures of my scene (the white icons on top are from the "UIscene", and the main content is from the "currentScene"). As you can see, when I make the canvas square, the second scene content is properly rendered, but when I let it take any other aspect ratio, (in this case 16:9), the image is clearly stretched).

 

Before anyone ask, I have set a resize event listener on the window to react to canva resize events (it works as expected) :

// Watch for browser/canvas resize events
window.addEventListener("resize", () => {
    this.engine.resize();
});

 

I tried something similar on this PG, but there it works properly (you need to add the snippet above in the code to test the resize feature).

 

Thanks for you help !

Babylon_16_9.PNG

Babylon_square.PNG

Share this post


Link to post
Share on other sites

By the way, I also use a glow effect on certain meshes : those are rendered with the correct aspect ratio (see attached picture).

The glow effects are supposed to activate "OnPointerOverTrigger" on target meshes, and do so when the cursor is in the blue zone, yet out of the rendered texture, which makes me think that the mesh has a correct position and aspect ratio, but the texture has not...

 

Babylon_glow.PNG

Share this post


Link to post
Share on other sites

I stripped my code of everything except :

  • a "hello world" text block in my AdvancedTextureLayout in the UIScene (first scene, overlay the second)
  • a square box in my second scene

The issue is still present.

Here is the code and a JSFiddle that reproduce the issue :

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">

<head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    <title>Test</title>

    <style>
        html,
        body {
            overflow: hidden;
            width: 100%;
            height: 100%;
            margin: 0;
            padding: 0;
        }

        #renderCanvas {
            width: 100%;
            height: 100%;
            touch-action: none;
        }
    </style>

    <script src="https://preview.babylonjs.com/babylon.js"></script>
    <script src="https://preview.babylonjs.com/inspector/babylon.inspector.bundle.js"></script>
    <script src="https://preview.babylonjs.com/loaders/babylonjs.loaders.min.js"></script>
    <script src="https://preview.babylonjs.com/materialsLibrary/babylonjs.materials.min.js"></script>
    <script src="https://preview.babylonjs.com/postProcessesLibrary/babylonjs.postProcess.min.js"></script>
    <script src="https://preview.babylonjs.com/gui/babylon.gui.min.js"></script>
    <script src="https://preview.babylonjs.com/proceduralTexturesLibrary/babylonjs.proceduralTextures.min.js"></script>
    <script src="https://preview.babylonjs.com/serializers/babylonjs.serializers.min.js"></script>
    <script src="https://preview.babylonjs.com/nodeEditor/babylon.nodeEditor.js"></script>
    <script src="https://code.jquery.com/pep/0.4.3/pep.js"></script>

</head>

<body>
    <canvas id="renderCanvas" touch-action="none"></canvas> <!--touch-action="none" for best results from PEP-->
    <script>
        // Global variables
        var babylonStage;

        // Stage to contain and manipulate the scene
        class BabylonStage {
            constructor() {
                // Engine and properties
                this.engine = new BABYLON.Engine(document.getElementById("renderCanvas"), true, {stencil: true}); // Generate the BABYLON 3D engine

                // GUI 2D layer (control overlay)
                this.UIScene = new BABYLON.Scene(this.engine);
                this.UIContainer = new BABYLON.GUI.AdvancedDynamicTexture.CreateFullscreenUI("UI");

                // Initialize scenes
                this.currentScene = new SceneTest(this.engine);
                
                // Initialize GUI elements
                var UICamera = new BABYLON.ArcRotateCamera("UICamera", 0, 0.8, 100, BABYLON.Vector3.Zero(), this.UIScene);
                UICamera.layerMask = 0x40000000;
                this.UIContainer.layer.layerMask = 0x40000000;
                // Add GUI elements
                var text1 = new BABYLON.GUI.TextBlock();
                text1.text = "Hello world";
                text1.color = "white";
                text1.fontSize = 24;
                this.UIContainer.addControl(text1); 
                
                this.UIScene.autoClear = false;
                // Register a render loop to repeatedly render the scene
                this.engine.runRenderLoop(() => {
                    this.currentScene.scene.render();
                    this.UIScene.render();
                });
            
                // Watch for browser/canvas resize events
                window.addEventListener("resize", () => {
                    this.engine.resize();
                });   
            }
        }

        class SceneTest {
            constructor(engine) {
                // Create the scene
                this.scene = new BABYLON.Scene(engine);

                // Definitions
                this.camera_Base_pos = new BABYLON.Vector3(2900, 1500, 3100);
                this.camera_Base_target = new BABYLON.Vector3(-1300, 600, -2500);
                // Camera
                this.camera = new BABYLON.ArcRotateCamera("Camera", 0, 0, 1000, this.camera_Base_target, this.scene);
                this.camera.fovMode = BABYLON.Camera.FOVMODE_HORIZONTAL_FIXED;
                this.camera.fov = 1.5;
                this.camera.maxZ = 15000;
                this.camera.position = this.camera_Base_pos;
                this.camera.target = this.camera_Base_target;
                // Highlighter
                this.highlighter = new BABYLON.HighlightLayer("Highlighter", this.scene);
                this.highlighter.innerGlow = false;

                new BABYLON.HemisphericLight("ambiantLight", new BABYLON.Vector3(0, 1, 0), this.scene);

                this.myBox = BABYLON.MeshBuilder.CreateBox("myBox", {height: 1000, width: 1000, depth: 1000}, this.scene);
                var highlightColor = new BABYLON.Color3(0.1, 0.1, 0.8);
                this.highlighter.addMesh(this.myBox, highlightColor);
                
                /* Create glow effects */
                var glow = new BABYLON.GlowLayer("glow", this.scene, { 
                    mainTextureFixedSize: 1024,
                    blurKernelSize: 64
                });
                glow.intensity = 0.5;
            }
        }

        window.onload=function() {
            // Build the 3D stage
            babylonStage = new BabylonStage();
        }

    </script>
</body>

</html>

 

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...

  • Recently Browsing   0 members

    No registered users viewing this page.