我见过voxel js,但似乎已经过时了,它使用了我不想使用的节点js。我想使用for循环生成简单的地形,并使用我的函数创建一个块。
这是我的功能:
function createBlock(block, x, y, z, top, bottom, front, back, left, right) {
var geometry;
var meshFaceMaterial;
var mesh;
var material;
var blockObj = {};
if (top == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].top)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z;
mesh.position.x = x;
mesh.position.y = y+5;
mesh.rotation.x = (-90 * Math.PI)/180;
blockObj.top = mesh;
}
if (bottom == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].bottom)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z;
mesh.position.x = x;
mesh.position.y = y-5;
mesh.rotation.x = (90 * Math.PI)/180;
blockObj.bottom = mesh;
}
if (back == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].side)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z-5;
mesh.position.x = x;
mesh.position.y = y;
mesh.rotation.y = (180 * Math.PI)/180;
blockObj.back = mesh;
}
if (right == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].side)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z;
mesh.position.x = x+5;
mesh.position.y = y;
mesh.rotation.y = (90 * Math.PI)/180;
blockObj.right = mesh;
}
if (left == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].side)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z;
mesh.position.x = x-5;
mesh.position.y = y;
mesh.rotation.y = (-90 * Math.PI)/180;
blockObj.left = mesh;
}
if (front == true) {
geometry = new THREE.PlaneGeometry(1, 1);
material = new THREE.MeshPhongMaterial({map: THREE.ImageUtils.loadTexture(blocks[block].side)});
meshFaceMaterial = new THREE.MeshFaceMaterial(material);
mesh = new THREE.Mesh(geometry, meshFaceMaterial);
mesh.position.z = z+5;
mesh.position.x = x;
mesh.position.y = y;
blockObj.front = mesh;
}
blockObjects.push(blockObj);
return blockObj;
}
任何帮助都将不胜感激。
答案 0 :(得分:1)
如果我理解你的问题,你就会要求循环来调用你在3轴x,y,z上的功能。
你可以这样做:
for (var i = 0; i < SIZEX; i++) {
for (var j = 0; j < SIZEY; j++) {
for (var k = 0; k < SIZEZ; k++) {
createBlock(block, i, j, k, (k == SIZEZ-1), (k == 0), (j == SIZEY-1), (j == 0), (i == SIZEX-1), (i == 0));
}
}
}
此代码将以3维方式导航。
如果(k == SIZEZ-1)
为真,则top
将在您的函数中为true
。所有其他人都一样。
我不知道block
是什么。
我希望你正在寻找的东西。
答案 1 :(得分:1)
这是一种创建立方体并使用它们构建随机地形的算法。在这种情况下,我已将地形高度变化固定为最多比相邻立方体高一个立方体高度。我为每个立方体随机生成了一种绿色,但你可以明显地应用你想到的任何纹理。
var camera, scene, renderer;
var mesh;
var cubesize = 30;
var landscape_width = 30;
var landscape_length = 30;
var heights = [];
var camera_offset = cubesize * landscape_width *0.7;
var camera_height = cubesize * landscape_width / 2;
function init() {
camera = new THREE.PerspectiveCamera( 70, window.innerWidth / window.innerHeight, 1, 10000 );
camera.position.set(0,camera_offset,camera_height);
camera.up = new THREE.Vector3(0,0,1);
camera.lookAt(new THREE.Vector3(0,0,0));
scene = new THREE.Scene();
geom = new THREE.CubeGeometry( cubesize, cubesize, cubesize );
cubes = new THREE.Object3D();
scene.add( cubes );
var xoff = landscape_width * cubesize / 2;
var yoff = landscape_length * cubesize / 2;
for(var i=0; i<landscape_width; i++) heights[i,0] = 0;
for(var j=0; j<landscape_length; j++) heights[0,j] = 0;
for(var i=1; i<landscape_width; i++) {
var h = heights[i-1,0];
for(var j=1; j< landscape_length; j++ ) {
var rand = Math.random();
if(heights[i-1,j] == heights[i,j-1]) { // level ground, go up dn or stay
if(rand < 0.33)
heights[i,j] = heights[i-1,j] - cubesize;
else if (rand > 0.66)
heights[i,j] = heights[i-1,j] + cubesize;
else
heights[i,j] = heights[i-1,j];
}
else if(Math.abs(heights[i-1,j] - heights[i,j-1]) > cubesize) { // two edges are wide apart, split the difference
heights[i,j] = (heights[i-1,j] +heights[i,j-1])/2;
}
else {
if(rand > 0.5)
heights[i,j] = heights[i-1,j];
else
heights[i,j] = heights[i,j-1];
}
var grayness = Math.random() * 0.5 + 0.25,
mat = new THREE.MeshBasicMaterial(),
cube = new THREE.Mesh( geom, mat );
mat.color.setRGB( 0, grayness, 0 );
cube.position.set( i*cubesize - xoff, j*cubesize - yoff, heights[i,j] );
cubes.add( cube );
}
}
renderer = new THREE.WebGLRenderer();
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
document.body.appendChild( renderer.domElement );
//
window.addEventListener( 'resize', onWindowResize, false );
}
function onWindowResize() {
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize( window.innerWidth, window.innerHeight );
}
var angle = 0;
function animate() {
angle += 0.5;
var rads = angle * Math.PI /180;
camera.position.set(Math.cos(rads)*camera_offset,Math.sin(rads)*camera_offset,camera_height);
camera.lookAt(scene.position);
requestAnimationFrame( animate );
renderer.render( scene, camera );
}
init();
animate();
body {
margin: 0px;
background-color: #000000;
overflow: hidden;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/85/three.js"></script>