HTML Content in BabylonJS Scenes

I have use this util in my project, it’s powerful and easy to use. Just one question, is it possible to make HTMLmesh “backFaceCulling = true”? The back face is transparent.

Thanks for the feedback. HtmlMesh doesn’t explicitly disable backface culling. I wonder if backface culling doesn’t apply to depth masks somehow. @sebavan How would you expect a material to behave that writes to the depth buffer but not the color buffer when viewed from the back? If backface culling is enabled, I would expect that it would not render at all and you would see nothing, but it appears that is not the case. You can see this in https://www.babylonjs-playground.com/#Y2LIXI#44 as you rotate the camera to view the backside of the mesh with the Babylon site, it cuts out the background.

Yes, i had test serval times. I hope that it can be improved and the contents could be seeing on backside and frontside, just like THREEJS CSS3D
Threejs Css3d

Well if you want to be able to see the backside of the html content, that is easy. You could do something like

htmlMeshSite._element.style.backfaceVisibility = "visible"

I turned off backface visibility by default because it can contribute to text clarity issues. I’ll add an option to enable it on my next push, but you can use this workaround for now.

1 Like

Thanks, it works :smile:

Thanks for the contribution !
I’m having trouble displaying html on a plane mesh.
my project is a 360° stage.
My html element (in my case the form shown in the example) is not displayed but is replaced by a grey rectangle


But you can interact with
image
Knowing that I’m coding in typescript, that my scene is actually an Angular component and that I instantiate my scene like this :

and add I use the htmlmesh library like this :

image
I hope someone will have a solution to my problem, which has been blocking me for a while now.
Thanks in advance for your feedback!

Did you check that your scene clear color is transparent? I suspect that the gray is your clear color. HtmlMesh requires that the scene clear color is transparent so the DOM content can be seen through the canvas.

Not sure what the issue is there. I would recommend creating a separate post about it as I believe it is unrelated to HtmlMesh.

Is it possible to specify canvas in the html construct on which I can render a separate scene with a second engine?

Are you asking if you could use a canvas as your HTML element that gets rendered in the HtmlMesh? I don’t see why not, but then why wouldn’t you just use DynamicTexture? Becasue the HtmlMesh would update in real time versus the texture you would have to call update in a render observable?

I would like to create a scene within a scene that has independent objects.

If this really works, it would be a quantum leap in the possibilities offered by Babylon.js! :heart_eyes:

1 Like

Gotcha. If the objects in one canvas were always on top, you could just overlay the canvases and do something like this as described in the docs. On the other hand if you want the objects in one scene to be able to be occluded by the objects in another scene and vice versa, then yeah, I don’t see why HTML mesh wouldn’t work. Be advised, though, that what you will get is a flat rectangular viewport into the second scene. If you were hoping to just get an object (versus a view of the canvas) from the second scene displayed in the first scene, this wouldn’t work.

First of all: thank you very much for this great extension! :slight_smile:

Unfortunately, I failed in my attempt to call up a scene within a scene at the position BABYLON.Scene(engine2)

HtmlMesh inner Canvas Problem

image

Maybe instead of creating a second engine just use multiview?

let view = engine.registerView(document.getElementById("renderCanvas1"));

let myRenderLoop = () => {
  if (engine.activeView.camera === undefined) {
    mainScene.render();
  } else if (engine.activeView.target === view1) {
    scene1.render();
  }
};
1 Like

Thanks, I will get it a try. Meanwhile, I found a portal implementation which seems promising for my purposes: portals | Babylon.js Playground (babylonjs-playground.com)

1 Like

Excellent work!

One caveat you might want to add is that this will not work correctly with WebXR immersive sessions.

Perhaps WebXRDOMOverlay can help with this?

I think DOM overlays are promising. But as is typically the case, Apple is dragging their feet on supporting it, so we end up with yet another thing we can do in webXR as long as we are willing to exclude all the iphone and now vision pro users.

So I have a small change that I was wondering if you would be willing to PR!

In Frame with how we have multiple cameras that can be toggled at any given time which leads to the observeCamera not truly working as intended.

When in third person everything is fine.

When switching to first person the matrix refs go stale and do not update.

There were a couple fixes for this that I was able to work out but the best one so far has been update the init function to do something like this:

    const boundCameraMatrixChanged = this.onCameraMatrixChanged.bind(this);

    let projectionObs, matrixObs;

    const observeCamera = () => {
      const camera = scene.activeCamera;
      if (camera) {
        projectionObs = camera.onProjectionMatrixChangedObservable.add(
          boundCameraMatrixChanged,
        );
        matrixObs = camera.onViewMatrixChangedObservable.add(
          boundCameraMatrixChanged,
        );
      }
    };

    observeCamera();

    scene.onActiveCameraChanged.add(() => {
      if (projectionObs) {
        scene.activeCamera?.onProjectionMatrixChangedObservable.remove(
          projectionObs,
        );
      }
      if (matrixObs) {
        scene.activeCamera?.onViewMatrixChangedObservable.remove(matrixObs);
      }
      observeCamera();
    });
2 Likes

This looks like a great addition. Would love to get a PR for it.

It needs linting I bet, just did this in the github browser editor.

2 Likes