I’m not sure how to upload font.json
and model.glb
to the PG, so I haven’t been able to test it there…
stair_apply.zip (2.6 MB)
Below is the code I’m using in my project, and although I don’t fully understand how the stencil works, I’ve left it as is because it produces the desired results.
I’ve organized the code to make it easier to understand and removed unnecessary properties to simplify it further.
const engine = new BABYLON.Engine(canvas, true, { preserveDrawingBuffer: true, stencil: true, antialias: true, depth: true});
const scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color4(1, 1, 1, 1);
const camera = new BABYLON.ArcRotateCamera('camera', -Math.PI / 2, Math.PI / 2, 40, BABYLON.Vector3.Zero(), scene);
camera.attachControl(canvas, true);
const light = new BABYLON.HemisphericLight("light1", new BABYLON.Vector3(1, 1, 0), scene);
light.intensity = 2;
// sphere
const sphere = BABYLON.MeshBuilder.CreateSphere('sphere', { segments: 36, diameter: 100 }, scene);
sphere.position = new BABYLON.Vector3(0, 0, 0);
sphere.enableEdgesRendering(0.9999);
sphere.edgesWidth = 10;
sphere.edgesColor = BABYLON.Color4.FromColor3(BABYLON.Color3.Black());
// text
const fontData = await (await fetch('/fonts/Pretendard_Variable_Regular.json')).json(); // Providing you have a font data file at that location
const myText = BABYLON.MeshBuilder.CreateText("myText", " WE DESIGN \n AND DEVELOP \n DIGITAL SPACES", fontData, {
size: 8,
resolution: 64,
depth: 0,
faceUV: [
new BABYLON.Vector4(0, 0, 1, 1),
new BABYLON.Vector4(0, 0, 1, 1),
new BABYLON.Vector4(0, 0, 1, 1),
]
});
myText.position = new BABYLON.Vector3(0, -20, 150);
myText.parent = camera;
myText.material = new BABYLON.PBRMaterial("material", scene);
myText.renderingGroupId = 1;
var previousStencilMask = engine.getStencilMask();
var previousStencilFunction = engine.getStencilFunction();
myText.onBeforeRenderObservable.add(function(){
engine.setStencilMask(0x00);
engine.setStencilBuffer(true);
engine.setStencilFunctionReference(1);
engine.setStencilFunction(BABYLON.Engine.NOTEQUAL);
});
myText.onAfterRenderObservable.add(function(){
engine.setStencilBuffer(false);
engine.setStencilMask(previousStencilMask);
engine.setStencilFunction(previousStencilFunction);
});
scene.setRenderingAutoClearDepthStencil(1, false);
/// logo
const logoMaterial = new BABYLON.PBRMaterial("glass", scene);
logoMaterial.metallic = .5;
logoMaterial.roughness = .5;
logoMaterial.backFaceCulling = false;
const renderTargetTexture = new BABYLON.RenderTargetTexture("opaqueRTT", 2048);
renderTargetTexture.clearColor = BABYLON.Color4.FromHexString("#6615E9");
logoMaterial.refractionTexture = renderTargetTexture;
const horizontalBlur = new BABYLON.BlurPostProcess("horizontalBlur", new BABYLON.Vector2(2.0, 0), 12.0, 1.0, null, BABYLON.Texture.BILINEAR_SAMPLINGMODE, engine, false);
const verticalBlur = new BABYLON.BlurPostProcess("verticalBlur", new BABYLON.Vector2(0, 2.0), 12.0, 1.0, null,BABYLON. Texture.BILINEAR_SAMPLINGMODE, engine, false);
renderTargetTexture.addPostProcess(horizontalBlur);
renderTargetTexture.addPostProcess(verticalBlur);
logoMaterial.stencil.enabled = true;
logoMaterial.stencil.func = BABYLON.Engine.ALWAYS;
logoMaterial.stencil.funcRef = 1;
logoMaterial.stencil.funcMask = 0xFF;
logoMaterial.stencil.mask = 0xFF;
logoMaterial.stencil.opDepthFail = BABYLON.Engine.KEEP;
logoMaterial.stencil.opStencilDepthPass = BABYLON.Engine.REPLACE;
logoMaterial.stencil.opStencilFail = BABYLON.Engine.KEEP;
let logo;
BABYLON.SceneLoader.ImportMesh("", "/stair_apply.glb", "", scene, function (newMeshes) {
logo = newMeshes[1];
logo.material = logoMaterial;
logo.position = new BABYLON.Vector3(0, 0, 0);
logo.rotation = new BABYLON.Vector3(-Math.PI / 9, -Math.PI / 9, 0);
logo.scaling = new BABYLON.Vector3(5, 5, 5);
});
let backPlateLogo;
BABYLON.SceneLoader.ImportMesh("", "/stair_apply.glb", "", scene, function (newMeshes) {
backPlateLogo = newMeshes[1];
const backPlateMaterial = new BABYLON.PBRMaterial("glass", scene);
backPlateMaterial.alpha = .5;
backPlateMaterial.metallic = .5;
backPlateMaterial.roughness = .5;
backPlateMaterial.backFaceCulling = false;
backPlateLogo.material = backPlateMaterial;
backPlateLogo.position = new BABYLON.Vector3(0, 0, 0);
backPlateLogo.rotation = new BABYLON.Vector3(-Math.PI / 9, -Math.PI / 9, 0);
backPlateLogo.scaling = new BABYLON.Vector3(5, 5, 5);
backPlateLogo.layerMask = 0x10000000;
});
camera.layerMask = 0x0FFFFFFF;
engine.runRenderLoop(() => {
renderTargetTexture.renderList = [myText, backPlateLogo];
scene.render();
});