You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Three.js实现可穿透图层的‘窗口’效果?

Three.js 可穿透图层的“窗口”元素实现求助

需求描述

我正在做课程实验项目,用Three.js开发一款小型游戏,想要实现一个能“穿透”图层的“窗口”元素。相关效果截图:

当前代码实现

相机配置

// 创建相机
const ratio = 130;
const camera = new THREE.OrthographicCamera(window.innerWidth / -ratio, window.innerWidth / ratio, window.innerHeight / ratio, window.innerHeight / -ratio, 0.1, 1000);
// const camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.set(0, 0, 10);

// 旋转相机
const angleY = THREE.MathUtils.degToRad(-30);
const rotationMatrixY = new THREE.Matrix4().makeRotationY(-angleY); // 负角度实现顺时针旋转
camera.applyMatrix4(rotationMatrixY); // 将旋转应用到相机
const angleZ = THREE.MathUtils.degToRad(-45);
const rotationMatrixZ = new THREE.Matrix4().makeRotationZ(-angleZ);
camera.applyMatrix4(rotationMatrixZ);
camera.lookAt(0, 0, 0); // 让相机看向原点

// 平移相机
const translationMatrix = new THREE.Matrix4().makeTranslation(0, 1.5, 0);
camera.applyMatrix4(translationMatrix);

物体与材质配置

const blockMaterialYellow = new THREE.MeshBasicMaterial({color: 0xffcc00});
const blockMaterialRed = new THREE.MeshBasicMaterial({color: 0xff3300});
const blockMaterialBlue = new THREE.MeshBasicMaterial({color: 0x0000ff});

// 黄色方块
const yellowBlockGeometry = new THREE.BoxGeometry(1, 1, 4);
yellowBlockGeometry.applyMatrix4(new THREE.Matrix4().makeTranslation(0, 0, 0.5));
const yellowBlock = new THREE.Mesh(yellowBlockGeometry, blockMaterialYellow);
yellowBlock.position.set(-5, 0, -3);
scene.add(yellowBlock);

// 红色方块
const redBlockGeometry = new THREE.BoxGeometry(4, 1, 1);
redBlockGeometry.applyMatrix4(new THREE.Matrix4().makeTranslation(1.5, 0, 0));
const redBlock = new THREE.Mesh(redBlockGeometry, blockMaterialRed);
redBlock.position.set(-1, 0, -2);
scene.add(redBlock);

// 蓝色方块
const blueBlockGeometry = new THREE.BoxGeometry(4, 1, 1);
blueBlockGeometry.applyMatrix4(new THREE.Matrix4().makeTranslation(1.5, 0, 0));
const blueBlock = new THREE.Mesh(blueBlockGeometry, blockMaterialBlue);
blueBlock.position.set(-1, 0, -8);
scene.add(blueBlock);

// 创建镜子(窗口元素)
const mirrorWidth = 3;
const mirrorHeight = 5;
const mirrorGeometry = new THREE.PlaneGeometry(mirrorWidth, mirrorHeight);
const mirrorMaterial = new THREE.MeshBasicMaterial({color: 0x000000, side: THREE.DoubleSide});
const mirror = new THREE.Mesh(mirrorGeometry, mirrorMaterial);
mirror.position.set(0, 0, -6);
scene.add(mirror);

图层配置

// 图层配置
const MAIN_LAYER = 0;
const REFLECTION_LAYER = 1;

yellowBlock.layers.set(MAIN_LAYER);
redBlock.layers.set(MAIN_LAYER);
mirror.layers.set(MAIN_LAYER);
blueBlock.layers.set(REFLECTION_LAYER);
mirrorCamera.layers.set(REFLECTION_LAYER);

求助

我是Three.js新手,希望各位能给出实现目标效果的建议,谢谢!

内容的提问来源于stack exchange,提问作者Ender Xie

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.17 19:47:05