Box Instanced Grid
box-instanced-grid.js
Show Example Source
// enable shadow map
shadowMap();
// configure orthographic camera
ortho([3, 3, 3], 0, {controls: true});
const w = 0.02; // width
const h = 0.02; // height
const d = 0.02; // depth
const count = 50000; // how many instances
const drawLines = false; // toggle between lines and solid boxes
// create box geometry and material
let geometry = geom.box(w, h, d);
let material;
if (drawLines) {
// convert box to edges
geometry = geom.edges(geometry);
// black line basic material
material = mat.lineBasic({ color: color(0, 0, 0) });
}
else {
// grey solid color material with lambert shading cached as a texture
material = solid(0.5,0.5,0.5).lambert().texMat(o1);
}
// create scene with yellow background and default lighting setup
const sc = stage({background: color(1,1,0), name: "instanced-grid", key: "instanced-grid"})
.lights()
.render();
// add instanced box mesh to scene using public API
sc.mesh(
geometry,
material,
{instanced: count, key: "instanced-grid-mesh"}
);
const box = sc.at(0);
if (drawLines) {
// fix box if drawing lines
box.isMesh = false;
box.isLine = true;
box.isLineSegments = true;
}
const calcHeight = (x, z) => {
// get simplex noise between -2 and 5, using zoom 1
const simplexNoise = noiseUtil.get2(x, z, -2, 5, 1);
// get yellow fbm noise between 0 and 20, using zoom 0.5
const yellowNoise = noiseUtil.get2(x, z, 0, 20, 0.5, noiseUtil.YELLOW);
// this makes the high rises come from lower regions
return simplexNoise < 0 ? yellowNoise : simplexNoise;
}
// set matrix for each instance
const matrix = mat4(); // THREE.Matrix4
for ( let i = 0; i < count; i++ ) {
const position = vec3(); // THREE.Vector3
const quaternion = quat(); // THREE.Quaternion
const scale = vec3(1.0, 1.0, 1.0); // THREE.Vector3
const sqr = Math.sqrt(count);
const [x, z] = [(i % sqr), Math.floor(i / sqr)];
const y = calcHeight(x, z);
position.x = x * w - sqr * w / 2;
position.z = z * d - sqr * d / 2;
position.y = y * h / 2;
scale.y = y;
// compose THREE.Matrix4 from position, quaternion and scale
matrix.compose( position, quaternion, scale );
// set matrix for each instance
box.setMatrixAt( i, matrix );
}