Skip to content

Instantly share code, notes, and snippets.

@zz85
Last active August 29, 2015 13:56
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save zz85/9087239 to your computer and use it in GitHub Desktop.
Save zz85/9087239 to your computer and use it in GitHub Desktop.
Exploring ParametricGeometry2
/**
* @author zz85 / https://github.com/zz85
* Parametric Surfaces Geometry
* based on the brilliant article by @prideout http://prideout.net/blog/?p=44
*
* new THREE.ParametricGeometry( parametricFunction, uSegments, ySegements );
*
*/
THREE.ParametricGeometry2 = function ( func, slices, stacks ) {
THREE.Geometry2.call( this, slices * stacks * 2 * 3 );
// Buffer needed is slices * stacks * 2 triangles * 3 vertices
var vertices = this.vertices;
var normals = this.normals;
var uvs = this.uvs;
var i, il, j, p;
var u, v;
var offset = 0;
var stackCount = stacks + 1;
var sliceCount = slices + 1;
var verts = [];
for ( i = 0; i <= stacks; i ++ ) {
v = i / stacks;
for ( j = 0; j <= slices; j ++ ) {
u = j / slices;
p = func( u, v );
verts.push( p );
}
}
var a, b, c, d;
var uva, uvb, uvc, uvd;
var uvOffset = 0;
function verts_push() {
for (var i=0; i < arguments.length; i++) {
vertices[ offset++ ] = arguments[i];
}
}
function uvs_push() {
for (var i=0; i < arguments.length; i++) {
uvs[ uvOffset++ ] = arguments[i];
}
}
uva = new THREE.Vector2();
uvb = new THREE.Vector2();
uvc = new THREE.Vector2();
uvd = new THREE.Vector2();
for ( i = 0; i < stacks; i ++ ) {
for ( j = 0; j < slices; j ++ ) {
a = i * sliceCount + j;
b = i * sliceCount + j + 1;
c = (i + 1) * sliceCount + j + 1;
d = (i + 1) * sliceCount + j;
var va = verts[ a ],
vb = verts[ b ],
vc = verts[ c ],
vd = verts[ d ];
verts_push( va.x, va.y, va.z,
vb.x, vb.y, vb.z,
vd.x, vd.y, vd.z );
verts_push( vb.x, vb.y, vb.z,
vc.x, vc.y, vc.z,
vd.x, vd.y, vd.z );
// Equivalent of
// faces.push( new THREE.Face3( a, b, d ) );
// faces.push( new THREE.Face3( b, c, d ) );
uva.set( j / slices, i / stacks );
uvb.set( (j + 1 ) / slices, i / stacks );
uvc.set( ( j + 1 ) / slices, ( i + 1 ) / stacks );
uvd.set( j / slices, ( i + 1 ) / stacks );
uvs_push( uva.x, uva.y, uvb.x, uvb.y, uvd.x, uvd.y );
uvs_push( uvb.x, uvb.y, uvc.x, uvc.y, uvd.x, uvd.y );
// uvs.push( [ uva, uvb, uvd ] );
// uvs.push( [ uvb.clone(), uvc, uvd.clone() ] );
}
}
var normal = new THREE.Vector3();
var cb = new THREE.Vector3(), ab = new THREE.Vector3();
var vA = new THREE.Vector3(), vB = new THREE.Vector3(), vC = new THREE.Vector3();
/* Yeah compute all face normals given all vertices are triangles */
function computeFaceNormals() {
var l = vertices.length / 3 / 3;
var j;
var m = 0;
for (var i = 0; i < l; i++ ) {
j = i * 3 * 3;
vA.set( vertices[ j++ ], vertices[ j++ ], vertices[ j++ ] );
vB.set( vertices[ j++ ], vertices[ j++ ], vertices[ j++ ] );
vC.set( vertices[ j++ ], vertices[ j++ ], vertices[ j++ ] );
cb.subVectors( vC, vB );
ab.subVectors( vA, vB );
cb.cross( ab ).normalize();
normal.copy( cb );
normals[ m++ ] = normal.x;
normals[ m++ ] = normal.y;
normals[ m++ ] = normal.z;
}
}
// this.computeCentroids();
computeFaceNormals();
// this.computeVertexNormals();
};
THREE.ParametricGeometry2.prototype = Object.create( THREE.Geometry2.prototype );
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment