How to make hexagons instead of cubes?
I’m trying to make a map of hexagons following the example three.js manual .
When I did the first option in the manual, it turned out to make a hexagonal mesh and position it.
The second one turned out to make the hexagon itself , but the class does not work with it.
I don’t have much experience in programming just 4-months.
Code: HEX/client.ts at 1259451da2b210b1cec3960cdcee00ec965cb67a · drPapus/HEX · GitHub
Maybe this will help you?
From the Collection of examples from discourse.threejs.org
BeginnerExample step 13
line 696:
const honeyComb = createHoneyComb( radius, rings, thick, depth ); // see function below
// ======= to step 13 ============
function createCaps( radius, rings, thick, depth ) {
radius = radius || 0.5; // radius of corner points, size of a single outer hexagon, see createHoneyComb( )
rings = rings || 6; // rings of hexagons around the central hexagon
thick = thick || 0.1; // wall thick ( per cell, to calculate interior hexagon, caps )
depth = depth || 1; // depth ( of cell, to calculate z of position )
const rt = radius - thick / Math.cos( Math.PI / 3); // radius of corner points of interior hexagon
const hexagonCount = 3 * rings * rings + 3 * rings + 1;
const capGeometry = new THREE.CircleGeometry( rt, 6, Math.PI / 6 );
const capMaterial = new THREE.MeshLambertMaterial( { color: 0xffff33, side: THREE.DoubleSide, wireframe: false } );
const caps = new THREE.InstancedMesh( capGeometry , capMaterial, hexagonCount );
positionHexagonInstance( caps, radius, rings, -depth / 2 );
return caps;
}
function createHoneyComb( radius, rings, thick, depth ) {
radius = radius || 0.5; // radius of corner points, size of a single outer hexagon
rings = rings || 6; // rings of hexagons around the central hexagon
thick = thick || 0.1; // wall thick ( per cell, to calculate interior hexagon, caps )
depth = depth || 1; // depth ( of cell, to calculate z of position )
const hexagonCount = 3 * rings * rings + 3 * rings + 1;
const hexagonGeometry = new THREE.BufferGeometry( );
const indices = new Uint32Array( 108 );
const positions = new Float32Array( 84 );
hexagonGeometry.setIndex( new THREE.BufferAttribute( indices, 1 ) );
hexagonGeometry.setAttribute( 'position', new THREE.BufferAttribute( positions, 3 ) );
let x, y;
const z = depth / 2;
makeHexagonPositions( );
makeHexagonIndices( );
hexagonGeometry.computeVertexNormals( );
const hexagonMaterial = new THREE.MeshLambertMaterial( {color: 'yellow', side: THREE.DoubleSide, wireframe: false } );
//const hexagonMesh = new THREE.Mesh( hexagonGeometry, hexagonMaterial ); // a single only
const honeyComb = new THREE.InstancedMesh( hexagonGeometry, hexagonMaterial, hexagonCount );
positionHexagonInstance( honeyComb, radius, rings, 0 );
return honeyComb;
function makeHexagonPositions( ) {
const rt = radius - thick / Math.cos( Math.PI / 3); // radius of corner points of interior hexagon
let cv, sv;
for( let i = 0; i < 7; i ++ ) {
cv = Math.cos( ( 2 * i + 1 ) * Math.PI / 6 );
sv = Math.sin( ( 2 * i + 1 ) * Math.PI / 6 );
x = rt * cv;
y = rt * sv;
positions[ i * 12 ] = x;
positions[ i * 12 + 1 ] = y;
positions[ i * 12 + 2 ] = -z;
positions[ i * 12 + 3 ] = x;
positions[ i * 12 + 4 ] = y;
positions[ i * 12 + 5 ] = z;
x = radius * cv;
y = radius * sv;
positions[ i * 12 + 6 ] = x;
positions[ i * 12 + 7 ] = y;
positions[ i * 12 + 8 ] = -z;
positions[ i * 12 + 9 ] = x;
positions[ i * 12 + 10 ] = y;
positions[ i * 12 + 11 ] = z;
}
}
function makeHexagonIndices( ) {
for( let i = 0; i < 6; i ++ ) {
indices[ i * 18 ] = 4 * i + 1; // interior
indices[ i * 18 + 1 ] = 4 * i + 4;
indices[ i * 18 + 2 ] = 4 * i;
indices[ i * 18 + 3 ] = 4 * i + 1;
indices[ i * 18 + 4 ] = 4 * i + 5;
indices[ i * 18 + 5 ] = 4 * i + 4;
indices[ i * 18 + 6 ] = 4 * i; // back
indices[ i * 18 + 7 ] = 4 * i + 6;
indices[ i * 18 + 8 ] = 4 * i + 2;
indices[ i * 18 + 9 ] = 4 * i;
indices[ i * 18 + 10 ] = 4 * i + 4;
indices[ i * 18 + 11 ] = 4 * i + 6;
indices[ i * 18 + 12 ] = 4 * i + 3; // front
indices[ i * 18 + 13 ] = 4 * i + 5;
indices[ i * 18 + 14 ] = 4 * i + 1;
indices[ i * 18 + 15 ] = 4 * i + 3;
indices[ i * 18 + 16 ] = 4 * i + 7;
indices[ i * 18 + 17 ] = 4 * i + 5;
}
}
}
function positionHexagonInstance( iMesh, radius, rings, z ) {
const M4 = new THREE.Matrix4( );
const ri = radius * Math.sqrt( 3 ) / 2; // inner radius of a single outer hexagon
let x, y;
let h = 0; // hexagon instances
for ( let sg = -1; sg < 2; sg ++ ) {
const rg0 = sg === 0 ? rings : 0;
for( let i = 1, k = 2 * rings + 1 - Math.abs( sg ); k > rings + rg0; i ++, k -- ) {
x = ri * ( 1 - k );
y = sg * 1.5 * radius * i;
for( let j = 0 ; j < k; j ++ ) {
x += ri * 2;
iMesh.setMatrixAt( h, M4.setPosition( x, y, z ) );
h ++;
}
}
}
}
function showHideCapsFront( ) {
const showCapsFront = depth / 2;
const hideCapsFront = -Infinity;
let sh;
let M4 = new THREE.Matrix4( );
const position = new THREE.Vector3( );
const quaternion = new THREE.Quaternion( ); // not used
const scale = new THREE.Vector3( ); // not used
for ( let i = 0; i < capsFront.count; i ++ ) {
sh = Math.random( ) < 0.3 ? showCapsFront : hideCapsFront;
capsFront.getMatrixAt( i, M4 );
M4.decompose( position, quaternion, scale );
capsFront.setMatrixAt( i, M4.setPosition( position.x, position.y, sh ) );
capsFront.instanceMatrix.needsUpdate = true;
}
}
→ see also grids
Thanks a lot i will try it!