一、挖空原理说明

subtract 用墙面减去与门重叠的部分,产生一个新的对象,导入材质安装门即可

//参与减去几何体
//平行于x轴门
var meshH4Door = new ThreeBSP( meshHDoor );
//平行x轴横墙面
var meshWall4 = new ThreeBSP( meshH4 ); //平行x轴横墙面meshWall4对象 减去与meshH4Door门重叠部分
var subtract_bsp = meshWall4.subtract( meshH4Door );
var result = subtract_bsp.toMesh( new THREE.MeshLambertMaterial({
shading: THREE.SmoothShading,
map: THREE.ImageUtils.loadTexture('./img/floor-1.jpg'),
color: 0xff0000}) );
result.geometry.computeVertexNormals();
//添加至场景中
scene.add( result );  

效果图

源代码如下

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>threejs中挖空解决闪烁bug</title>
<style>
#canvas-frame {
width: 100%;
height: 450px;
}
</style>
</head>
<body onload="threeStart()">
<div id="canvas-frame" ></div>
</body>
<script type="text/javascript" src="./lib/three.js" ></script>
<!-- 运算挖门 解决闪烁bug -->
<script type="text/javascript" src="lib/ThreeCSG.js"></script>
<script type="text/javascript">
var renderer, //渲染器
width = document.getElementById('canvas-frame').clientWidth, //画布宽
height = document.getElementById('canvas-frame').clientHeight; //画布高
//照相机配置
var fov = 45,//拍摄距离 视野角值越大,场景中的物体越小
near = 1,//最小范围
far = 1000;//最大范围
//DOM对象
var canvas = null;
//初始化DOM对象
function initDOM(){
canvas = document.getElementById("canvas-frame");
}
//初始化渲染器
function initThree(){
renderer = new THREE.WebGLRenderer({
antialias : true
//canvas: document.getElementById('canvas-frame')
});
renderer.setSize(width, height);
renderer.setClearColor(0xFFFFFF, 1.0);
document.getElementById('canvas-frame').appendChild(renderer.domElement);
renderer.setClearColor(0xFFFFFF, 1.0);
}
//初始化场景
var scene;
function initScene(){
scene = new THREE.Scene();
}
var camera;
function initCamera() { //透视相机
camera = new THREE.PerspectiveCamera(fov, width/height , near, far);
camera.position.x = 150;
camera.position.y = 150;
camera.position.z =450;
camera.up.x = 0;
camera.up.y = 1; //相机朝向--相机上方为y轴
camera.up.z = 0;
camera.lookAt({ //相机的中心点
x : 0,
y : 0,
z : 0
});
}
function initLight(){
// light--这里使用环境光
//var light = new THREE.DirectionalLight(0xffffff); /*方向性光源*/
//light.position.set(600, 1000, 800);
var light = new THREE.AmbientLight(0xffffff); //模拟漫反射光源
light.position.set(600, 1000, 800); //使用Ambient Light时可以忽略方向和角度,只考虑光源的位置
scene.add(light);
}
function initObject(){ //初始化对象
//初始化地板
initFloor();
initWall();
}
function initGrid(){ //辅助网格
var helper = new THREE.GridHelper( 1000, 50 );
helper.setColors( 0x0000ff, 0x808080 );
scene.add( helper );
}
function initFloor(){ //导入材质
var texture = THREE.ImageUtils.loadTexture('img/floor-1.jpg', {}, function() {
renderer.render(scene, camera);
});
/**
* 关于material材料注意点说明
* MeshBasicMaterial:对光照无感,给几何体一种简单的颜色或显示线框。
* MeshLambertMaterial:这种材质对光照有反应,用于创建暗淡的不发光的物体。
* MeshPhongMaterial:这种材质对光照也有反应,用于创建金属类明亮的物体。
*/
var material = new THREE.MeshLambertMaterial({
map: texture
}); //创建一个立方体
var geometry = new THREE.BoxGeometry(400, 20, 400);
for ( var i = 0; i < geometry.faces.length; i += 2 ) {
var hex = Math.random() * 0xffffff;
geometry.faces[ i ].color.setHex( hex );
geometry.faces[ i + 1 ].color.setHex( hex );
}
//var material = new THREE.MeshBasicMaterial( { vertexColors: THREE.FaceColors} );
//将material材料添加到几何体geometry
var mesh = new THREE.Mesh(geometry, material);
mesh.position = new THREE.Vector3(0,0,0);
scene.add(mesh);
}
//墙面
function initWall(){ //导入墙面材质(后面墙面共用)
var texture = THREE.ImageUtils.loadTexture('img/floor-1.jpg', {}, function() {
renderer.render(scene, camera);
});
/**
* 关于material材料注意点说明
* MeshBasicMaterial:对光照无感,给几何体一种简单的颜色或显示线框。
* MeshLambertMaterial:这种材质对光照有反应,用于创建暗淡的不发光的物体。
* MeshPhongMaterial:这种材质对光照也有反应,用于创建金属类明亮的物体。
*/
var material = new THREE.MeshLambertMaterial({
map: texture
}); /*--------平行z轴横墙面3、x轴为墙面的厚度、 z轴为墙面长度、y轴为墙面高度--------------------*/
//平行z轴横墙面1 x轴为墙面厚度
var geometryH1 = new THREE.BoxGeometry(10, 65, 360);
/*var materialH1 = new THREE.MeshBasicMaterial( { color:0xFF0000 } );*/
//将material材料添加到几何体geometry
var meshH1 = new THREE.Mesh(geometryH1, material);
meshH1.position.x = 180;
meshH1.position.y = 45;
//scene.add(meshH1);
var meshWall1 = new ThreeBSP( meshH1 ); var geometryHDoor1 = new THREE.BoxGeometry(10, 56, 35);
var materialHDoor1 = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor1 = new THREE.Mesh(geometryHDoor1, materialHDoor1);
meshHDoor1.position.x = 180;
meshHDoor1.position.y = 45;
meshHDoor1.position.z = 0;
//scene.add(meshHDoor2);
var meshHDoor1 = new ThreeBSP( meshHDoor1 );
//墙面减去重叠的门
subtractMesh(meshHDoor1, meshWall1); //为墙面1安装门
var geometryHDoor1 = new THREE.BoxGeometry(10, 56, 35);
//加载材质
var textureDoor1 = THREE.ImageUtils.loadTexture('img/door.png', {}, function() {
renderer.render(scene, camera);
});
var materialDoor1 = new THREE.MeshBasicMaterial({
map: textureDoor1
});
//var materialHDoor2 = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor1 = new THREE.Mesh(geometryHDoor1, materialDoor1);
meshHDoor1.position.x = 180;
meshHDoor1.position.y = 45;
meshHDoor1.position.z = 0;
scene.add(meshHDoor1); //平行z轴横墙面2 x轴为墙面厚度
var geometryH2 = new THREE.BoxGeometry(10, 65, 360);
var materialH2 = new THREE.MeshBasicMaterial( { color:0xFF00FF } );
//将material材料添加到几何体geometry
var meshH2 = new THREE.Mesh(geometryH2, materialH2);
meshH2.position.x = -180;
meshH2.position.y = 45;
var meshWall2 = new ThreeBSP( meshH2 );
//scene.add(meshH2); var geometryHDoor2 = new THREE.BoxGeometry(10, 56, 35);
var materialHDoor2 = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor2 = new THREE.Mesh(geometryHDoor2, materialHDoor2);
meshHDoor2.position.x = -180;
meshHDoor2.position.y = 45;
meshHDoor2.position.z = 0;
var meshHDoor2 = new ThreeBSP( meshHDoor2 );
//scene.add(meshHDoor2);
//墙面减去重叠的门
subtractMesh(meshHDoor2, meshWall2); //为墙面2安装门
var geometryHDoor2 = new THREE.BoxGeometry(10, 56, 35);
//加载材质
var textureDoor2 = THREE.ImageUtils.loadTexture('img/door.png', {}, function() {
renderer.render(scene, camera);
});
var materialDoor2 = new THREE.MeshBasicMaterial({
map: textureDoor2
});
//var materialHDoor2 = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor2 = new THREE.Mesh(geometryHDoor2, materialDoor2);
meshHDoor2.position.x = -180;
meshHDoor2.position.y = 45;
meshHDoor2.position.z = 0;
scene.add(meshHDoor2);
/*--------平行z轴横墙面3、x轴为墙面的厚度、 z轴为墙面长度、y轴为墙面高度--------------------*/ /*--------平行x轴横墙面3、x轴为墙面长度、 z轴为墙面厚度、y轴为墙面高度--------------------*/
//平行x轴横墙面3 z轴为墙面厚度
var geometryH3 = new THREE.BoxGeometry(365, 65, 10);
var materialH3 = new THREE.MeshBasicMaterial( { color:0x808080 } );
//将material材料添加到几何体geometry
var meshH3 = new THREE.Mesh(geometryH3, material);
meshH3.position.x = 0;
meshH3.position.y = 45;
meshH3.position.z = -180;
var meshWall3 = new ThreeBSP( meshH3 );
//scene.add(meshH3); //平行x轴横重叠门3 z轴为墙面厚度
var geometryHDoor = new THREE.BoxGeometry(35, 50, 10);
var materialHDoor = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor = new THREE.Mesh(geometryHDoor, materialHDoor);
meshHDoor.position.x = 0;
meshHDoor.position.y = 45;
meshHDoor.position.z = -180;
var meshHDoor3 = new ThreeBSP( meshHDoor );
//scene.add(meshHDoor);
//墙面减去重叠的门
subtractMesh(meshHDoor3, meshWall3); //平行x轴横墙面3安装门
var geometryDoor3 = new THREE.BoxGeometry(35, 50, 10);
//加载材质
var textureDoor3 = THREE.ImageUtils.loadTexture('img/door.png', {}, function() {
renderer.render(scene, camera);
});
var materialDoor3 = new THREE.MeshBasicMaterial({
map: textureDoor3
});
door3 = new THREE.Mesh( geometryDoor3,materialDoor3);
door3.position.x = 0;
door3.position.y = 45;
door3.position.z = -180;
scene.add(door3);
/*--------平行x轴横墙面3、 z轴为墙面厚度、y轴为墙面高度--------------------*/ /*--------平行x轴横墙面4、 z轴为墙面厚度、y轴为墙面高度--------------------*/
//平行x轴横墙面4 z轴为墙面厚度
var geometryH4 = new THREE.BoxGeometry(365, 65, 10);
var materialH4 = new THREE.MeshBasicMaterial( { color:0x00AABB, wireframe: true} );
//将material材料添加到几何体geometry
var meshH4 = new THREE.Mesh(geometryH4, materialH4);
meshH4.position.x = 0;
meshH4.position.y = 45;
meshH4.position.z = 180;
//平行x轴横墙面4 挖出一道门
var meshWall4 = new ThreeBSP( meshH4 );
//scene.add(meshH4); //平行x轴横重叠门4 z轴为墙面厚度
var geometryHDoor = new THREE.BoxGeometry(35, 50, 10);
var materialHDoor = new THREE.MeshBasicMaterial( { color:0x00BBAA} );
//将material材料添加到几何体geometry
var meshHDoor = new THREE.Mesh(geometryHDoor, materialHDoor);
meshHDoor.position.x = 0;
meshHDoor.position.y = 45;
meshHDoor.position.z = 180;
//scene.add(meshHDoor);
//重叠门
var meshHDoor4 = new ThreeBSP( meshHDoor );
//墙面减去重叠的门
subtractMesh(meshHDoor4, meshWall4); //平行x轴横墙面4安装门
var geometryDoor4 = new THREE.BoxGeometry(35, 50, 10);
//加载材质
var textureDoor4 = THREE.ImageUtils.loadTexture('img/door.png', {}, function() {
renderer.render(scene, camera);
});
var materialDoor4 = new THREE.MeshBasicMaterial({
map: textureDoor4
});
door4 = new THREE.Mesh( geometryDoor4,materialDoor4);
door4.position.x = 0;
door4.position.y = 45;
door4.position.z = 180;
scene.add(door4);
/*--------平行x轴横墙面3、x轴为墙面长度、 z轴为墙面厚度、y轴为墙面高度-------------------*/ } //运算减去
/*
* meshDoor 门面
* meshWall 墙面
*/
function subtractMesh(meshDoor,meshWall){
//平行x轴横墙面4减去与meshHDoor门重叠部分
var subtract_bsp = meshWall.subtract( meshDoor );
var result = subtract_bsp.toMesh( new THREE.MeshLambertMaterial({
shading: THREE.SmoothShading,
map: THREE.ImageUtils.loadTexture('./img/floor-1.jpg')
}));
result.geometry.computeVertexNormals();
scene.add( result );
}
//初始化页面加载
function threeStart(){
//初始化DOM对象
initDOM();
//初始化渲染器
initThree();
//初始化场景
initScene();
//初始透视化相机
initCamera();
//初始化光源
initLight();
//模型对象
initObject();
//初始化网格辅助线
initGrid();
//渲染
//renderer.render(scene, camera);
//实时动画
animation();
//监听鼠标滚动事件
canvas.addEventListener('mousewheel', mousewheel, false);
}
function animation(){
//相机围绕y轴旋转,并且保持场景中的物体一直再相机的视野中
//实时渲染成像
var timer = Date.now()*0.0001;
camera.position.x = Math.cos(timer)*400;
camera.position.z = Math.sin(timer)*400;
camera.lookAt(scene.position);
renderer.render(scene, camera);
requestAnimationFrame(animation);
}
//鼠标滑轮-鼠标上下滑轮实现放大缩小效果
function mousewheel(e) {
e.preventDefault();
//e.stopPropagation();
if (e.wheelDelta) { //判断浏览器IE,谷歌滑轮事件
if (e.wheelDelta > 0) { //当滑轮向上滚动时
fov -= (near < fov ? 1 : 0);
}
if (e.wheelDelta < 0) { //当滑轮向下滚动时
fov += (fov < far ? 1 : 0);
}
} else if (e.detail) { //Firefox滑轮事件
if (e.detail > 0) { //当滑轮向上滚动时
fov -= 1;
}
if (e.detail < 0) { //当滑轮向下滚动时
fov += 1;
}
}
//改变fov值,并更新场景的渲染
camera.fov = fov;
camera.updateProjectionMatrix();
renderer.render(scene, camera);
//updateinfo();
}
</script>
</html>

使用Three.js挖空安装门来解决重叠闪烁的问题的更多相关文章

  1. windows下node.js+sublime中安装coffeescript

    node.js中安装Coffeescript 1.我的node.js安装目录 2.node.js 全局模块所在目录   3.node.js安装coffeescript npm install -g c ...

  2. node.js的npm安装

    我不打算引进node.js的npm安装,但发现node.js通过管理一些包npm实现,或给一个简短的npm. 1.npm什么        npm是一个node包管理和分发工具,已经成为了非官方的公布 ...

  3. Node.js 多版本安装

    Node.js 多版本安装 Node.js® is a JavaScript runtime built on Chrome's V8 JavaScript engine(Node.js 是一个基于 ...

  4. <亲测>CentOS 7.3下Node.js 8.6安装配置(含NPM以及PM2)

    CentOS 7.3下Node.js 8.6安装配置 2017年09月30日 14:12:02 阅读数:2245更多 个人分类: Nodejs   版权声明:本文为博主原创文章,未经博主允许不得转载. ...

  5. ArcGIS案例学习笔记-批处理擦除挖空挖除相减

    ArcGIS案例学习笔记-批处理擦除挖空挖除相减 联系方式:谢老师,135-4855-4328,xiexiaokui#qq.com 目的:批处理擦除.挖空.挖除.相减 数据源:chp13/ex5/pa ...

  6. ArcGIS案例学习笔记-手动编辑擦除挖空挖除相减

    ArcGIS案例学习笔记-手动编辑擦除挖空挖除相减 联系方式:谢老师,135-4855-4328,xiexiaokui#qq.com 目的:手动编辑擦除.挖空.挖除.相减 1. 选中内部要素 2. c ...

  7. js判断是否安装flash player及当前版本 和 检查flash版本是否需要升级

    一.js检查flash版本升级 for (var i = 0, len = navigator.plugins.length; i < len; i++) { var plugin = navi ...

  8. light,node.js,webStorm 安装项目搭建

    light,是一个移动应用开发平台,旨在降低H5.APP的开发门槛.运维成本.提升移动应用产品的持续交付能力. 用light可以做什么 快速组织移动H5应用的协作开发.调试.应用发布,发布的应用可直接 ...

  9. vue.js 2.0 --- 安装node环境,webpack和脚手架(入门篇)

    1.环境搭建 1.1.安装node.js 1.2 安装过程很简单,一路“下一步”就可以了.安装完成之后,打开命令行工具(win+r,然后输入cmd),输入 node -v,如下图,如果出现相应的版本号 ...

随机推荐

  1. final关键字。

    final关键之代表最终,不可变的. 用法: 1.修饰类 2.修饰方法 3.修饰局部变量. 4.修饰成员变量. 修饰类: 不能有任何子类.(太监类) public final class MyClas ...

  2. ___简单的MVC单个图片上传预览

    js: $("#btnImg").click(function () { $("#form0").ajaxSubmit({ url: "/Studen ...

  3. IIS (安装SSL证书后) 实现 HTTP 自动跳转到 HTTPS

    IIS 里 安装好 SSL 证书后,如何实现 在浏览器里录入 http://www.xxx.com,会自动跳转到 https://www.xxx.com 呢. 首先,下载并安装 IIS 扩展: URL ...

  4. ASP.NET MVC3 在_ViewStart设置Layout使用RenderAction的注意事項

    来源:https://dotblogs.com.tw/lastsecret/archive/2012/03/26/71052.aspx ASP.NET MVC3 在_ViewStart設定Layout ...

  5. quartz定时任务实例

    一.spring注解方式 <!--<!–配置文件添加允许Spring注解–>--> <!--<task:annotation-driven scheduler=&q ...

  6. 【Spring】22、Spring缓存注解@Cache使用

    缓存注解有以下三个: @Cacheable      @CacheEvict     @CachePut @Cacheable(value=”accountCache”),这个注释的意思是,当调用这个 ...

  7. js 面向对象 ES5 AND ES6

    1. ES5实现 父类: // 职员类 function Employees(id,name,salary) { // 属性 this.id = id; this.name = name; this. ...

  8. 用webpack2.0构建vue2.0超详细精简版

    初始化环境 npm init -y 初始化项目 安装各种依赖项 npm install --save vue 安装vue2.0 npm install --save-dev webpack@^2.1. ...

  9. JavaScript之Object对象常用属性与方法手册

    MDN Object参考地址:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Obje ...

  10. 简析服务端通过geotools导入SHP至PG的方法

    文章版权由作者李晓晖和博客园共有,若转载请于明显处标明出处:http://www.cnblogs.com/naaoveGIS/ 1.背景 项目中需要在浏览器端直接上传SHP后服务端进行数据的自动入PG ...