From a96fb086294d0a55a3dcece114e095d46fca620b Mon Sep 17 00:00:00 2001
From: Patrick Cozzi
* This filter is commonly used to create a wireframe mesh for visual debugging.
*
- * @param {Object} mesh The mesh to filter, which is modified in place.
+ * @param {Geometry} mesh The mesh to filter, which is modified in place.
*
* @returns The modified mesh
argument, with its triangle indices converted to lines.
*
@@ -186,7 +192,7 @@ define([
* The mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
*
- * @param {Object} mesh The mesh to filter, which is modified in place.
+ * @param {Geometry} mesh The mesh to filter, which is modified in place.
*
* @exception {DeveloperError} All mesh attribute lists must have the same number of attributes.
*
@@ -271,7 +277,7 @@ define([
* The mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
*
- * @param {Object} mesh The mesh to filter, which is modified in place.
+ * @param {Geometry} mesh The mesh to filter, which is modified in place.
* @param {Number} [cacheCapacity=24] The number of vertices that can be held in the GPU's vertex cache.
*
* @exception {DeveloperError} Mesh's index list must be defined.
@@ -305,9 +311,11 @@ define([
maximumIndex = indices[j];
}
}
- indexLists[i].values = Tipsify.tipsify({indices : indices,
- maximumIndex : maximumIndex,
- cacheSize : cacheCapacity});
+ indexLists[i].values = Tipsify.tipsify({
+ indices : indices,
+ maximumIndex : maximumIndex,
+ cacheSize : cacheCapacity
+ });
}
}
}
@@ -329,11 +337,11 @@ define([
for ( var attribute in attributes) {
if (attributes.hasOwnProperty(attribute) && attributes[attribute].values) {
var attr = attributes[attribute];
- newAttributes[attribute] = {
+ newAttributes[attribute] = new GeometryAttribute({
componentDatatype : attr.componentDatatype,
componentsPerAttribute : attr.componentsPerAttribute,
values : []
- };
+ });
}
}
@@ -360,13 +368,13 @@ define([
*/
MeshFilters.fitToUnsignedShortIndices = function(mesh) {
function createMesh(attributes, primitiveType, indices) {
- return {
+ return new Geometry({
attributes : attributes,
- indexLists : [{
+ indexLists : [new GeometryIndices({
primitiveType : primitiveType,
values : indices
- }]
- };
+ })]
+ });
}
var meshes = [];
@@ -498,7 +506,7 @@ define([
* This is commonly used to create high-precision position vertex attributes.
*
indexList
with
@@ -51,9 +51,9 @@ define([
*
* @example
* var mesh = BoxTessellator.compute();
- * mesh = MeshFilters.toWireframeInPlace(mesh);
+ * mesh = GeometryFilters.toWireframe(mesh);
*/
- MeshFilters.toWireframeInPlace = function(mesh) {
+ GeometryFilters.toWireframe = function(mesh) {
function addTriangle(lines, i0, i1, i2) {
lines.push(i0);
lines.push(i1);
@@ -135,7 +135,7 @@ define([
/**
* DOC_TBA
*/
- MeshFilters.createAttributeIndices = function(mesh) {
+ GeometryFilters.createAttributeIndices = function(mesh) {
var indices = {};
if (typeof mesh !== 'undefined') {
@@ -155,7 +155,7 @@ define([
/**
* DOC_TBA
*/
- MeshFilters.mapAttributeIndices = function(indices, map) {
+ GeometryFilters.mapAttributeIndices = function(indices, map) {
var mappedIndices = {};
if (typeof indices !== 'undefined' && typeof map !== 'undefined') {
@@ -169,7 +169,7 @@ define([
return mappedIndices;
};
- MeshFilters._computeNumberOfAttributes = function(mesh) {
+ GeometryFilters._computeNumberOfAttributes = function(mesh) {
var numberOfVertices = -1;
for ( var property in mesh.attributes) {
if (mesh.attributes.hasOwnProperty(property) && mesh.attributes[property].values) {
@@ -198,15 +198,15 @@ define([
*
* @returns The modified mesh
argument, with its vertices and indices reordered for the GPU's pre-vertex-shader cache.
*
- * @see MeshFilters.reorderForPostVertexCache
+ * @see GeometryFilters.reorderForPostVertexCache
*
* @example
* var mesh = new EllipsoidGeometry(...);
- * mesh = MeshFilters.reorderForPreVertexCache(mesh);
+ * mesh = GeometryFilters.reorderForPreVertexCache(mesh);
*/
- MeshFilters.reorderForPreVertexCache = function(mesh) {
+ GeometryFilters.reorderForPreVertexCache = function(mesh) {
if (typeof mesh !== 'undefined') {
- var numVertices = MeshFilters._computeNumberOfAttributes(mesh);
+ var numVertices = GeometryFilters._computeNumberOfAttributes(mesh);
var indexCrossReferenceOldToNew = [];
for ( var i = 0; i < numVertices; i++) {
@@ -287,7 +287,7 @@ define([
*
* @returns The modified mesh
argument, with its indices optimally reordered for the post-vertex-shader cache.
*
- * @see MeshFilters.reorderForPreVertexCache
+ * @see GeometryFilters.reorderForPreVertexCache
* @see Tipsify
* @see
* Fast Triangle Reordering for Vertex Locality and Reduced Overdraw
@@ -295,9 +295,9 @@ define([
*
* @example
* var mesh = new EllipsoidGeometry(...);
- * mesh = MeshFilters.reorderForPostVertexCache(mesh);
+ * mesh = GeometryFilters.reorderForPostVertexCache(mesh);
*/
- MeshFilters.reorderForPostVertexCache = function(mesh, cacheCapacity) {
+ GeometryFilters.reorderForPostVertexCache = function(mesh, cacheCapacity) {
if (typeof mesh !== 'undefined') {
var indexLists = mesh.indexLists;
if (typeof indexLists !== 'undefined') {
@@ -322,7 +322,7 @@ define([
return mesh;
};
- MeshFilters._verifyTrianglesPrimitiveType = function(indexLists) {
+ GeometryFilters._verifyTrianglesPrimitiveType = function(indexLists) {
var length = indexLists.length;
for ( var i = 0; i < length; ++i) {
if (indexLists[i].primitiveType !== PrimitiveType.TRIANGLES) {
@@ -331,7 +331,7 @@ define([
}
};
- MeshFilters._copyAttributesDescriptions = function(attributes) {
+ GeometryFilters._copyAttributesDescriptions = function(attributes) {
var newAttributes = {};
for ( var attribute in attributes) {
@@ -366,7 +366,7 @@ define([
* @exception {DeveloperError} The mesh's index-lists must have PrimitiveType equal to PrimitiveType.TRIANGLES.
* @exception {DeveloperError} All mesh attribute lists must have the same number of attributes.
*/
- MeshFilters.fitToUnsignedShortIndices = function(mesh) {
+ GeometryFilters.fitToUnsignedShortIndices = function(mesh) {
function createMesh(attributes, primitiveType, indices) {
return new Geometry({
attributes : attributes,
@@ -380,9 +380,9 @@ define([
var meshes = [];
if (typeof mesh !== 'undefined') {
- MeshFilters._verifyTrianglesPrimitiveType(mesh.indexLists);
+ GeometryFilters._verifyTrianglesPrimitiveType(mesh.indexLists);
- var numberOfVertices = MeshFilters._computeNumberOfAttributes(mesh);
+ var numberOfVertices = GeometryFilters._computeNumberOfAttributes(mesh);
// If there's an index list and more than 64K attributes, it is possible that
// some indices are outside the range of unsigned short [0, 64K - 1]
@@ -397,7 +397,7 @@ define([
var oldToNewIndex = [];
var newIndices = [];
var currentIndex = 0;
- var newAttributes = MeshFilters._copyAttributesDescriptions(mesh.attributes);
+ var newAttributes = GeometryFilters._copyAttributesDescriptions(mesh.attributes);
var originalIndices = indexLists[i].values;
var numberOfIndices = originalIndices.length;
@@ -444,7 +444,7 @@ define([
oldToNewIndex = [];
newIndices = [];
currentIndex = 0;
- newAttributes = MeshFilters._copyAttributesDescriptions(mesh.attributes);
+ newAttributes = GeometryFilters._copyAttributesDescriptions(mesh.attributes);
}
}
@@ -464,7 +464,7 @@ define([
/**
* DOC_TBA
*/
- MeshFilters.projectTo2D = function(mesh, projection) {
+ GeometryFilters.projectTo2D = function(mesh, projection) {
if (typeof mesh !== 'undefined' && typeof mesh.attributes !== 'undefined' && typeof mesh.attributes.position !== 'undefined') {
projection = typeof projection !== 'undefined' ? projection : new GeographicProjection();
var ellipsoid = projection.getEllipsoid();
@@ -519,11 +519,11 @@ define([
* @exception {DeveloperError} The attribute componentDatatype must be ComponentDatatype.FLOAT.
*
* @example
- * mesh = MeshFilters.encodeAttribute(mesh, 'position3D', 'position3DHigh', 'position3DLow');
+ * mesh = GeometryFilters.encodeAttribute(mesh, 'position3D', 'position3DHigh', 'position3DLow');
*
* @see EncodedCartesian3
*/
- MeshFilters.encodeAttribute = function(mesh, attributeName, attributeHighName, attributeLowName) {
+ GeometryFilters.encodeAttribute = function(mesh, attributeName, attributeHighName, attributeLowName) {
attributeName = defaultValue(attributeName, 'position');
attributeHighName = defaultValue(attributeHighName, 'positionHigh');
attributeLowName = defaultValue(attributeLowName, 'positionLow');
@@ -621,7 +621,7 @@ define([
*
* @exception {DeveloperError} meshes is required and must have length greater than zero.
*/
- MeshFilters.combine = function(meshes) {
+ GeometryFilters.combine = function(meshes) {
if ((typeof meshes === 'undefined') || (meshes.length < 1)) {
throw new DeveloperError('meshes is required.');
}
@@ -744,5 +744,5 @@ define([
});
};
- return MeshFilters;
+ return GeometryFilters;
});
diff --git a/Source/Renderer/Context.js b/Source/Renderer/Context.js
index 676852d394b9..0468a4d9be2a 100644
--- a/Source/Renderer/Context.js
+++ b/Source/Renderer/Context.js
@@ -2349,7 +2349,7 @@ define([
* @see Context#createVertexArray
* @see Context#createVertexBuffer
* @see Context#createIndexBuffer
- * @see MeshFilters.createAttributeIndices
+ * @see GeometryFilters.createAttributeIndices
* @see ShaderProgram
* @see BoxTessellator
*
@@ -2360,7 +2360,7 @@ define([
* var mesh = BoxTessellator.compute();
* var va = context.createVertexArrayFromMesh({
* mesh : mesh,
- * attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ * attributeIndices : GeometryFilters.createAttributeIndices(mesh),
* });
*
* ////////////////////////////////////////////////////////////////////////////////
@@ -2369,7 +2369,7 @@ define([
* // single vertex buffer. The vertex and index buffer have static draw usage.
* var va = context.createVertexArrayFromMesh({
* mesh : mesh,
- * attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ * attributeIndices : GeometryFilters.createAttributeIndices(mesh),
* bufferUsage : BufferUsage.STATIC_DRAW,
* vertexLayout : VertexLayout.INTERLEAVED
* });
diff --git a/Source/Scene/CentralBodySurface.js b/Source/Scene/CentralBodySurface.js
index f33636e89c09..5dbdd70b5a51 100644
--- a/Source/Scene/CentralBodySurface.js
+++ b/Source/Scene/CentralBodySurface.js
@@ -48,7 +48,7 @@ define([
EllipsoidalOccluder,
Intersect,
Matrix4,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
Queue,
TaskProcessor,
@@ -723,10 +723,10 @@ define([
if (!surface._debug.boundingSphereVA) {
var radius = surface._debug.boundingSphereTile.boundingSphere3D.radius;
var sphere = new EllipsoidGeometry(new Ellipsoid(radius, radius, radius), 10);
- MeshFilters.toWireframeInPlace(sphere);
+ GeometryFilters.toWireframe(sphere);
surface._debug.boundingSphereVA = context.createVertexArrayFromMesh({
mesh : sphere,
- attributeIndices : MeshFilters.createAttributeIndices(sphere)
+ attributeIndices : GeometryFilters.createAttributeIndices(sphere)
});
}
diff --git a/Source/Scene/Polygon.js b/Source/Scene/Polygon.js
index 6f9969f3c7be..71b3f5dd8635 100644
--- a/Source/Scene/Polygon.js
+++ b/Source/Scene/Polygon.js
@@ -50,7 +50,7 @@ define([
Cartesian4,
Cartographic,
ComponentDatatype,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
EllipsoidTangentPlane,
PolygonPipeline,
@@ -596,10 +596,10 @@ define([
return undefined;
}
- mesh = MeshFilters.combine(meshes);
+ mesh = GeometryFilters.combine(meshes);
mesh = PolygonPipeline.scaleToGeodeticHeight(mesh, polygon.height, polygon.ellipsoid);
- mesh = MeshFilters.reorderForPostVertexCache(mesh);
- mesh = MeshFilters.reorderForPreVertexCache(mesh);
+ mesh = GeometryFilters.reorderForPostVertexCache(mesh);
+ mesh = GeometryFilters.reorderForPreVertexCache(mesh);
if (polygon._mode === SceneMode.SCENE3D) {
mesh.attributes.position2DHigh = { // Not actually used in shader
@@ -608,9 +608,9 @@ define([
mesh.attributes.position2DLow = { // Not actually used in shader
value : [0.0, 0.0]
};
- mesh = MeshFilters.encodeAttribute(mesh, 'position', 'position3DHigh', 'position3DLow');
+ mesh = GeometryFilters.encodeAttribute(mesh, 'position', 'position3DHigh', 'position3DLow');
} else {
- mesh = MeshFilters.projectTo2D(mesh, polygon._projection);
+ mesh = GeometryFilters.projectTo2D(mesh, polygon._projection);
if (polygon._mode !== SceneMode.SCENE3D) {
var projectedPositions = mesh.attributes.position2D.values;
@@ -625,11 +625,11 @@ define([
polygon._boundingVolume2D.center = new Cartesian3(0.0, center2DPositions.x, center2DPositions.y);
}
- mesh = MeshFilters.encodeAttribute(mesh, 'position3D', 'position3DHigh', 'position3DLow');
- mesh = MeshFilters.encodeAttribute(mesh, 'position2D', 'position2DHigh', 'position2DLow');
+ mesh = GeometryFilters.encodeAttribute(mesh, 'position3D', 'position3DHigh', 'position3DLow');
+ mesh = GeometryFilters.encodeAttribute(mesh, 'position2D', 'position2DHigh', 'position2DLow');
}
- return MeshFilters.fitToUnsignedShortIndices(mesh);
+ return GeometryFilters.fitToUnsignedShortIndices(mesh);
}
function getGranularity(polygon, mode) {
diff --git a/Source/Scene/Primitive.js b/Source/Scene/Primitive.js
index c6b2db0cbf99..d65c4ca7bb65 100644
--- a/Source/Scene/Primitive.js
+++ b/Source/Scene/Primitive.js
@@ -13,7 +13,7 @@ define([
], function(
destroyObject,
Matrix4,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
BoundingSphere,
BufferUsage,
@@ -67,7 +67,7 @@ define([
// TODO: throw if mesh and appearance are not defined
if (typeof this._va === 'undefined') {
- var attributeIndices = MeshFilters.createAttributeIndices(this.mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(this.mesh);
var appearance = this.appearance;
this._va = context.createVertexArrayFromMesh({
diff --git a/Source/Scene/SkyAtmosphere.js b/Source/Scene/SkyAtmosphere.js
index b85fb352be38..7a6d5dca448f 100644
--- a/Source/Scene/SkyAtmosphere.js
+++ b/Source/Scene/SkyAtmosphere.js
@@ -17,7 +17,7 @@ define([
defaultValue,
EllipsoidGeometry,
destroyObject,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
Ellipsoid,
BufferUsage,
@@ -136,7 +136,7 @@ define([
var mesh = new EllipsoidGeometry(Ellipsoid.fromCartesian3(this._ellipsoid.getRadii().multiplyByScalar(1.025)), 60);
command.vertexArray = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh),
bufferUsage : BufferUsage.STATIC_DRAW
});
command.primitiveType = PrimitiveType.TRIANGLES;
diff --git a/Source/Scene/SkyBox.js b/Source/Scene/SkyBox.js
index 0990f0afd9ef..5c73a3a04a72 100644
--- a/Source/Scene/SkyBox.js
+++ b/Source/Scene/SkyBox.js
@@ -20,7 +20,7 @@ define([
destroyObject,
DeveloperError,
Matrix4,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
loadCubeMap,
BufferUsage,
@@ -151,7 +151,7 @@ define([
var mesh = BoxTessellator.compute({
dimensions : new Cartesian3(2.0, 2.0, 2.0)
});
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
command.primitiveType = PrimitiveType.TRIANGLES;
command.modelMatrix = Matrix4.IDENTITY.clone();
diff --git a/Specs/Core/GeometryFiltersSpec.js b/Specs/Core/GeometryFiltersSpec.js
index 3aa53a2f9ec4..fd632d01a3b4 100644
--- a/Specs/Core/GeometryFiltersSpec.js
+++ b/Specs/Core/GeometryFiltersSpec.js
@@ -1,6 +1,6 @@
/*global defineSuite*/
defineSuite([
- 'Core/MeshFilters',
+ 'Core/GeometryFilters',
'Core/PrimitiveType',
'Core/ComponentDatatype',
'Core/EllipsoidGeometry',
@@ -13,7 +13,7 @@ defineSuite([
'Core/GeometryAttribute',
'Core/GeometryIndices'
], function(
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
ComponentDatatype,
EllipsoidGeometry,
@@ -29,7 +29,7 @@ defineSuite([
/*global jasmine,describe,xdescribe,it,xit,expect,beforeEach,afterEach,beforeAll,afterAll,spyOn,runs,waits,waitsFor*/
it('converts triangles to wireframe in place', function() {
- var mesh = MeshFilters.toWireframeInPlace({
+ var mesh = GeometryFilters.toWireframe({
indexLists : [{
primitiveType : PrimitiveType.TRIANGLES,
values : [0, 1, 2, 3, 4, 5]
@@ -57,7 +57,7 @@ defineSuite([
});
it('converts a triangle fan to wireframe in place', function() {
- var mesh = MeshFilters.toWireframeInPlace({
+ var mesh = GeometryFilters.toWireframe({
indexLists : [{
primitiveType : PrimitiveType.TRIANGLE_FAN,
values : [0, 1, 2, 3]
@@ -85,7 +85,7 @@ defineSuite([
});
it('converts a triangle strip to wireframe in place', function() {
- var mesh = MeshFilters.toWireframeInPlace({
+ var mesh = GeometryFilters.toWireframe({
indexLists : [{
primitiveType : PrimitiveType.TRIANGLE_STRIP,
values : [0, 1, 2, 3]
@@ -121,7 +121,7 @@ defineSuite([
}
};
- var indices = MeshFilters.createAttributeIndices(mesh);
+ var indices = GeometryFilters.createAttributeIndices(mesh);
var validIndices = [0, 1, 2];
expect(validIndices).toContain(indices.position);
@@ -138,7 +138,7 @@ defineSuite([
colors : 2
};
- var mappedIndices = MeshFilters.mapAttributeIndices(indices, {
+ var mappedIndices = GeometryFilters.mapAttributeIndices(indices, {
positions : 'position',
normals : 'normal',
colors : 'color'
@@ -165,7 +165,7 @@ defineSuite([
componentsPerAttribute : 3,
values : [0, 1, 2, 3, 4, 5]
};
- mesh = MeshFilters.reorderForPreVertexCache(mesh);
+ mesh = GeometryFilters.reorderForPreVertexCache(mesh);
}).toThrow();
});
@@ -195,7 +195,7 @@ defineSuite([
componentsPerAttribute : 3,
values : [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]
};
- MeshFilters.reorderForPreVertexCache(mesh);
+ GeometryFilters.reorderForPreVertexCache(mesh);
expect(mesh.indexLists[0].values[0]).toEqual(0);
expect(mesh.indexLists[0].values[1]).toEqual(1);
@@ -252,7 +252,7 @@ defineSuite([
maximumIndex : maximumIndex,
cacheSize : 24});
expect(ACMRbefore).toBeGreaterThan(1.00);
- mesh = MeshFilters.reorderForPostVertexCache(mesh);
+ mesh = GeometryFilters.reorderForPostVertexCache(mesh);
indices = mesh.indexLists[0].values;
var ACMRafter = Tipsify.calculateACMR({indices : indices,
maximumIndex : maximumIndex,
@@ -280,7 +280,7 @@ defineSuite([
}]
};
- var meshes = MeshFilters.fitToUnsignedShortIndices(mesh);
+ var meshes = GeometryFilters.fitToUnsignedShortIndices(mesh);
expect(meshes.length).toEqual(1);
expect(meshes[0]).toBe(mesh);
@@ -307,7 +307,7 @@ defineSuite([
}]
};
- var meshes = MeshFilters.fitToUnsignedShortIndices(mesh);
+ var meshes = GeometryFilters.fitToUnsignedShortIndices(mesh);
expect(meshes.length).toEqual(1);
expect(meshes[0].attributes.time.componentDatatype).toEqual(ComponentDatatype.FLOAT);
@@ -346,7 +346,7 @@ defineSuite([
}]
};
- var meshes = MeshFilters.fitToUnsignedShortIndices(mesh);
+ var meshes = GeometryFilters.fitToUnsignedShortIndices(mesh);
expect(meshes.length).toEqual(2);
@@ -374,7 +374,7 @@ defineSuite([
};
expect(function() {
- return MeshFilters.fitToUnsignedShortIndices(mesh);
+ return GeometryFilters.fitToUnsignedShortIndices(mesh);
}).toThrow();
});
@@ -401,7 +401,7 @@ defineSuite([
};
expect(function() {
- return MeshFilters.fitToUnsignedShortIndices(mesh);
+ return GeometryFilters.fitToUnsignedShortIndices(mesh);
}).toThrow();
});
@@ -417,7 +417,7 @@ defineSuite([
values : [p1.x, p1.y, p1.z, p2.x, p2.y, p2.z]
};
- mesh = MeshFilters.projectTo2D(mesh);
+ mesh = GeometryFilters.projectTo2D(mesh);
var ellipsoid = Ellipsoid.WGS84;
var projection = new GeographicProjection();
@@ -437,7 +437,7 @@ defineSuite([
expect(mesh.attributes.position3D.values[5]).toEqual(p2.z);
});
- it('MeshFilters.encodeAttribute encodes positions', function() {
+ it('GeometryFilters.encodeAttribute encodes positions', function() {
var c = new Cartesian3(-10000000.0, 0.0, 10000000.0);
var encoded = EncodedCartesian3.fromCartesian(c);
@@ -450,7 +450,7 @@ defineSuite([
}
}
};
- mesh = MeshFilters.encodeAttribute(mesh);
+ mesh = GeometryFilters.encodeAttribute(mesh);
expect(mesh.attributes.positionHigh).toBeDefined();
expect(mesh.attributes.positionHigh.values[0]).toEqual(encoded.high.x);
@@ -463,29 +463,29 @@ defineSuite([
expect(mesh.attributes.position).not.toBeDefined();
});
- it('MeshFilters.encodeAttribute throws without a mesh', function() {
+ it('GeometryFilters.encodeAttribute throws without a mesh', function() {
expect(function() {
- MeshFilters.encodeAttribute(undefined);
+ GeometryFilters.encodeAttribute(undefined);
}).toThrow();
});
- it('MeshFilters.encodeAttribute throws with mesh without attributes property', function() {
+ it('GeometryFilters.encodeAttribute throws with mesh without attributes property', function() {
expect(function() {
- MeshFilters.encodeAttribute({});
+ GeometryFilters.encodeAttribute({});
}).toThrow();
});
- it('MeshFilters.encodeAttribute throws without attribute', function() {
+ it('GeometryFilters.encodeAttribute throws without attribute', function() {
expect(function() {
var mesh = {
attributes : {
}
};
- MeshFilters.encodeAttribute(mesh);
+ GeometryFilters.encodeAttribute(mesh);
}).toThrow();
});
- it('MeshFilters.encodeAttribute throws without ComponentDatatype.FLOAT', function() {
+ it('GeometryFilters.encodeAttribute throws without ComponentDatatype.FLOAT', function() {
expect(function() {
var mesh = {
attributes : {
@@ -494,11 +494,11 @@ defineSuite([
values : [0.0]
}
};
- MeshFilters.encodeAttribute(mesh);
+ GeometryFilters.encodeAttribute(mesh);
}).toThrow();
});
- it('MeshFilters.combine combines one mesh', function() {
+ it('GeometryFilters.combine combines one mesh', function() {
var mesh = new Geometry({
attributes : new GeometryAttribute({
position : {
@@ -509,11 +509,11 @@ defineSuite([
})
});
- var combinedMesh = MeshFilters.combine([mesh]);
+ var combinedMesh = GeometryFilters.combine([mesh]);
expect(combinedMesh).toBe(mesh);
});
- it('MeshFilters.combine combines several meshes', function() {
+ it('GeometryFilters.combine combines several meshes', function() {
var mesh = new Geometry({
attributes : {
position : new GeometryAttribute({
@@ -564,7 +564,7 @@ defineSuite([
})]
});
- var combinedMesh = MeshFilters.combine([mesh, anotherMesh]);
+ var combinedMesh = GeometryFilters.combine([mesh, anotherMesh]);
expect(combinedMesh).toEqual(new Geometry({
attributes : {
position : new GeometryAttribute({
@@ -593,15 +593,15 @@ defineSuite([
}));
});
- it('MeshFilters.combine throws with meshes', function() {
+ it('GeometryFilters.combine throws with meshes', function() {
expect(function() {
- MeshFilters.combine();
+ GeometryFilters.combine();
}).toThrow();
});
- it('MeshFilters.combine throws when meshes.length is zero', function() {
+ it('GeometryFilters.combine throws when meshes.length is zero', function() {
expect(function() {
- MeshFilters.combine([]);
+ GeometryFilters.combine([]);
}).toThrow();
});
diff --git a/Specs/Renderer/VertexArrayFactorySpec.js b/Specs/Renderer/VertexArrayFactorySpec.js
index e73147244fe2..3dd14d9f3186 100644
--- a/Specs/Renderer/VertexArrayFactorySpec.js
+++ b/Specs/Renderer/VertexArrayFactorySpec.js
@@ -13,7 +13,7 @@ defineSuite([
createContext,
destroyContext,
ComponentDatatype,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
IndexDatatype,
BufferUsage,
@@ -66,7 +66,7 @@ defineSuite([
var va = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh)
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh)
});
expect(va.getNumberOfAttributes()).toEqual(1);
@@ -95,7 +95,7 @@ defineSuite([
var va = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh),
vertexLayout : VertexLayout.INTERLEAVED,
bufferUsage : BufferUsage.STATIC_DRAW
});
@@ -131,7 +131,7 @@ defineSuite([
var va = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh)
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh)
});
expect(va.getNumberOfAttributes()).toEqual(2);
@@ -172,7 +172,7 @@ defineSuite([
var va = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh),
vertexLayout : VertexLayout.INTERLEAVED
});
@@ -216,7 +216,7 @@ defineSuite([
var va = context.createVertexArrayFromMesh({
mesh : mesh,
- attributeIndices : MeshFilters.createAttributeIndices(mesh),
+ attributeIndices : GeometryFilters.createAttributeIndices(mesh),
vertexLayout : VertexLayout.INTERLEAVED
});
@@ -263,7 +263,7 @@ defineSuite([
}
};
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
var va = context.createVertexArrayFromMesh({
mesh : mesh,
attributeIndices : attributeIndices,
@@ -323,7 +323,7 @@ defineSuite([
}
};
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
var va = context.createVertexArrayFromMesh({
mesh : mesh,
attributeIndices : attributeIndices,
@@ -397,7 +397,7 @@ defineSuite([
}
};
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
var va = context.createVertexArrayFromMesh({
mesh : mesh,
attributeIndices : attributeIndices,
@@ -465,7 +465,7 @@ defineSuite([
}
};
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
var va = context.createVertexArrayFromMesh({
mesh : mesh,
attributeIndices : attributeIndices,
diff --git a/Specs/Scene/MultifrustumSpec.js b/Specs/Scene/MultifrustumSpec.js
index bb4a343ab080..f4b3c48b246a 100644
--- a/Specs/Scene/MultifrustumSpec.js
+++ b/Specs/Scene/MultifrustumSpec.js
@@ -33,7 +33,7 @@ defineSuite([
defaultValue,
CesiumMath,
Matrix4,
- MeshFilters,
+ GeometryFilters,
PrimitiveType,
BlendingState,
BufferUsage,
@@ -216,7 +216,7 @@ defineSuite([
minimumCorner: minimumCorner,
maximumCorner: maximumCorner
});
- var attributeIndices = MeshFilters.createAttributeIndices(mesh);
+ var attributeIndices = GeometryFilters.createAttributeIndices(mesh);
this._va = context.createVertexArrayFromMesh({
mesh: mesh,
attributeIndices: attributeIndices,
From eee2853bc3e510d03322716b65250b4561000d29 Mon Sep 17 00:00:00 2001
From: Patrick Cozzi triangles
, triangleStrip
, or trangleFan
is converted to a
* list of indices with a primitive type of lines
. Lists of indices with other primitive types remain unchanged.
* mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
+ * The mesh
argument should use the standard layout like the mesh returned by {@link BoxGeometry}.
* mesh
argument, with its triangle indices converted to lines.
*
- * @see BoxTessellator
- *
* @example
- * var mesh = BoxTessellator.compute();
+ * var mesh = new BoxGeometry();
* mesh = GeometryFilters.toWireframe(mesh);
*/
GeometryFilters.toWireframe = function(mesh) {
@@ -189,7 +187,7 @@ define([
* Reorders a mesh's indices to achieve better performance from the GPU's pre-vertex-shader cache.
* Each list of indices in the mesh's indexList
is reordered to keep the same index-vertex correspondence.
* mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
+ * The mesh
argument should use the standard layout like the mesh returned by {@link BoxGeometry}.
* indexList
is optimally reordered.
* mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
+ * The mesh
argument should use the standard layout like the mesh returned by {@link BoxGeometry}.
* mesh
argument should use the standard layout like the mesh returned by {@link BoxTessellator}.
+ * The mesh
argument should use the standard layout like the mesh returned by {@link BoxGeometry}.
* creationArguments
can have four properties:
* indexList
is reordered to keep the same index-vertex correspondence.
@@ -210,7 +194,7 @@ define([
*/
GeometryFilters.reorderForPreVertexCache = function(mesh) {
if (typeof mesh !== 'undefined') {
- var numVertices = GeometryFilters._computeNumberOfAttributes(mesh);
+ var numVertices = Geometry.computeNumberOfVertices(mesh);
var indexCrossReferenceOldToNew = [];
for ( var i = 0; i < numVertices; i++) {
@@ -390,7 +374,7 @@ define([
if (typeof mesh !== 'undefined') {
GeometryFilters._verifyTrianglesPrimitiveType(mesh.indexLists);
- var numberOfVertices = GeometryFilters._computeNumberOfAttributes(mesh);
+ var numberOfVertices = Geometry.computeNumberOfVertices(mesh);
// If there's an index list and more than 64K attributes, it is possible that
// some indices are outside the range of unsigned short [0, 64K - 1]
diff --git a/Source/Core/IndexDatatype.js b/Source/Core/IndexDatatype.js
index b30e5432751b..a3c0aa5fe801 100644
--- a/Source/Core/IndexDatatype.js
+++ b/Source/Core/IndexDatatype.js
@@ -15,13 +15,34 @@ define(['./Enumeration'], function(Enumeration) {
* @type {Enumeration}
*/
UNSIGNED_BYTE : new Enumeration(0x1401, 'UNSIGNED_BYTE'),
+
+ /**
+ * DOC_TBA
+ *
+ * @constant
+ * @type {Enumeration}
+ */
+ UNSIGNED_SHORT : new Enumeration(0x1403, 'UNSIGNED_SHORT'),
/**
* DOC_TBA
*
* @constant
* @type {Enumeration}
*/
- UNSIGNED_SHORT : new Enumeration(0x1403, 'UNSIGNED_SHORT')
+ UNSIGNED_INT : new Enumeration(0x1405, 'UNSIGNED_INT')
+ };
+
+ IndexDatatype.UNSIGNED_BYTE.sizeInBytes = Uint8Array.BYTES_PER_ELEMENT;
+ IndexDatatype.UNSIGNED_SHORT.sizeInBytes = Uint16Array.BYTES_PER_ELEMENT;
+ IndexDatatype.UNSIGNED_INT.sizeInBytes = Uint32Array.BYTES_PER_ELEMENT;
+
+ /**
+ * DOC_TBA
+ */
+ IndexDatatype.validate = function(indexDatatype) {
+ return ((indexDatatype === IndexDatatype.UNSIGNED_BYTE) ||
+ (indexDatatype === IndexDatatype.UNSIGNED_SHORT) ||
+ (indexDatatype === IndexDatatype.UNSIGNED_INT));
};
return IndexDatatype;
diff --git a/Source/Renderer/Context.js b/Source/Renderer/Context.js
index d6ba144dfb3d..f38165efd2b0 100644
--- a/Source/Renderer/Context.js
+++ b/Source/Renderer/Context.js
@@ -7,6 +7,7 @@ define([
'../Core/IndexDatatype',
'../Core/RuntimeError',
'../Core/PrimitiveType',
+ '../Core/Geometry',
'../Core/createGuid',
'../Core/Matrix4',
'./Buffer',
@@ -40,6 +41,7 @@ define([
IndexDatatype,
RuntimeError,
PrimitiveType,
+ Geometry,
createGuid,
Matrix4,
Buffer,
@@ -222,6 +224,7 @@ define([
// Query and initialize extensions
this._standardDerivatives = gl.getExtension('OES_standard_derivatives');
+ this._elementIndexUint = gl.getExtension('OES_element_index_uint');
this._depthTexture = gl.getExtension('WEBKIT_WEBGL_depth_texture') || gl.getExtension('MOZ_WEBGL_depth_texture');
this._textureFloat = gl.getExtension('OES_texture_float');
var textureFilterAnisotropic = gl.getExtension('EXT_texture_filter_anisotropic') || gl.getExtension('WEBKIT_EXT_texture_filter_anisotropic') || gl.getExtension('MOZ_EXT_texture_filter_anisotropic');
@@ -687,6 +690,21 @@ define([
return !!this._standardDerivatives;
};
+ /**
+ * Returns true
if the OES_element_index_uint extension is supported. This
+ * extension allows the use of unsigned int indices, which can improve performance by
+ * eliminating batch breaking caused by unsigned short indices.
+ *
+ * @memberof Context
+ *
+ * @returns {Boolean} true
if OES_element_index_uint is supported; otherwise, false
.
+ *
+ * @see OES_element_index_uint
+ */
+ Context.prototype.getElementIndexUint = function() {
+ return !!this._elementIndexUint;
+ };
+
/**
* Returns true
if WEBGL_depth_texture is supported. This extension provides
* access to depth textures that, for example, can be attached to framebuffers for shadow mapping.
@@ -1037,6 +1055,7 @@ define([
*
* @return {IndexBuffer} The index buffer, ready to be attached to a vertex array.
*
+ * @exception {RuntimeError} IndexDatatype.UNSIGNED_INT requires OES_element_index_uint, which is not supported on this system.
* @exception {DeveloperError} The size in bytes must be greater than zero.
* @exception {DeveloperError} Invalid usage
.
* @exception {DeveloperError} Invalid indexDatatype
.
@@ -1062,16 +1081,16 @@ define([
* BufferUsage.STATIC_DRAW, IndexDatatype.UNSIGNED_SHORT)
*/
Context.prototype.createIndexBuffer = function(typedArrayOrSizeInBytes, usage, indexDatatype) {
- var bytesPerIndex;
-
- if (indexDatatype === IndexDatatype.UNSIGNED_BYTE) {
- bytesPerIndex = Uint8Array.BYTES_PER_ELEMENT;
- } else if (indexDatatype === IndexDatatype.UNSIGNED_SHORT) {
- bytesPerIndex = Uint16Array.BYTES_PER_ELEMENT;
- } else {
+ if (!IndexDatatype.validate(indexDatatype)) {
throw new DeveloperError('Invalid indexDatatype.');
}
+ if ((indexDatatype === IndexDatatype.UNSIGNED_INT) && !this.getElementIndexUint()) {
+ throw new RuntimeError('IndexDatatype.UNSIGNED_INT requires OES_element_index_uint, which is not supported on this system.');
+ }
+
+ var bytesPerIndex = indexDatatype.sizeInBytes;
+
var gl = this._gl;
var buffer = createBuffer(gl, gl.ELEMENT_ARRAY_BUFFER, typedArrayOrSizeInBytes, usage);
var numberOfIndices = buffer.getSizeInBytes() / bytesPerIndex;
@@ -2395,7 +2414,11 @@ define([
var va = createVertexArrayAttributes(this, creationArguments);
if (indexLists) {
- va.setIndexBuffer(this.createIndexBuffer(new Uint16Array(indexLists[0].values), bufferUsage, IndexDatatype.UNSIGNED_SHORT));
+ if ((Geometry.computeNumberOfVertices(mesh) > 64 * 1024) && this.getElementIndexUint()) {
+ va.setIndexBuffer(this.createIndexBuffer(new Uint32Array(indexLists[0].values), bufferUsage, IndexDatatype.UNSIGNED_INT));
+ } else{
+ va.setIndexBuffer(this.createIndexBuffer(new Uint16Array(indexLists[0].values), bufferUsage, IndexDatatype.UNSIGNED_SHORT));
+ }
}
return va;
diff --git a/Source/Scene/Primitive.js b/Source/Scene/Primitive.js
index 69928fc4837b..d06adb05176f 100644
--- a/Source/Scene/Primitive.js
+++ b/Source/Scene/Primitive.js
@@ -161,8 +161,13 @@ define([
// Split position for GPU RTE
GeometryFilters.encodeAttribute(geometry, 'position', 'positionHigh', 'positionLow');
- // Break into multiple geometries to fit within unsigned short indices if needed
- return GeometryFilters.fitToUnsignedShortIndices(geometry);
+ if (!context.getElementIndexUint()) {
+ // Break into multiple geometries to fit within unsigned short indices if needed
+ return GeometryFilters.fitToUnsignedShortIndices(geometry);
+ }
+
+ // Unsigned int indices are supported. No need to break into multiple geometries.
+ return [geometry];
}
/**
diff --git a/Specs/Renderer/ContextSpec.js b/Specs/Renderer/ContextSpec.js
index 85fd869ac081..21792d351e2a 100644
--- a/Specs/Renderer/ContextSpec.js
+++ b/Specs/Renderer/ContextSpec.js
@@ -2,12 +2,16 @@
defineSuite([
'Renderer/Context',
'Core/Color',
+ 'Core/IndexDatatype',
+ 'Renderer/BufferUsage',
'Specs/createContext',
'Specs/destroyContext',
'Specs/renderFragment'
], function(
Context,
Color,
+ IndexDatatype,
+ BufferUsage,
createContext,
destroyContext,
renderFragment) {
@@ -162,6 +166,18 @@ defineSuite([
}
});
+ it('gets the element index uint extension', function() {
+ if (context.getElementIndexUint()) {
+ var buffer = context.createIndexBuffer(6, BufferUsage.STREAM_DRAW, IndexDatatype.UNSIGNED_INT);
+ expect(buffer).toBeDefined();
+ buffer.destroy();
+ } else {
+ expect(function() {
+ context.createIndexBuffer(6, BufferUsage.STREAM_DRAW, IndexDatatype.UNSIGNED_INT);
+ }).toThrow();
+ }
+ });
+
it('gets the depth texture extension', function() {
expect(context.getDepthTexture()).toBeDefined();
});
From 5bd91a782cc8957526990d5ad83a29085dc0bd6e Mon Sep 17 00:00:00 2001
From: hpinkos Cartesian3
, respectively.
+ * @param {VertexFormat} [options.vertexFormat=VertexFormat.DEFAULT] The vertex attributes to be computed.
+ * @param {Matrix4} [options.modelMatrix] The model matrix for this box. See {@link czm_model}.
+ * @param {DOC_TBA} [options.pickData] DOC_TBA
+ *
* @exception {DeveloperError} All dimensions components must be greater than or equal to zero.
*/
var BoxGeometry = function(options) {
@@ -352,22 +359,38 @@ define([
}
/**
- * DOC_TBA
+ * An object containing {@link GeometryAttribute} properties named after each of the
+ * true
values of the {@link VertexFormat} option.
+ *
+ * @type Object
*/
this.attributes = attributes;
/**
- * DOC_TBA
+ * An array of {@link GeometryIndices} defining primitives.
+ *
+ * @type Array
*/
this.indexLists = indexLists;
/**
- * DOC_TBA
+ * A tight-fitting bounding sphere that encloses the vertices of the box
+ *
+ * @type BoundingSphere
*/
this.boundingSphere = new BoundingSphere(new Cartesian3(), max.subtract(min).magnitude() * 0.5);
/**
- * DOC_TBA
+ * The 4x4 transformation matrix that transforms the box from model to world coordinates.
+ * When this is the identity matrix, the box is drawn in world coordinates, i.e., Earth's WGS84 coordinates.
+ * Local reference frames can be used by providing a different transformation matrix, like that returned
+ * by {@link Transforms.eastNorthUpToFixedFrame}. This matrix is available to GLSL vertex and fragment
+ * shaders via {@link czm_model} and derived uniforms.
+ *
+ * @type Matrix4
+ *
+ * @see Transforms.eastNorthUpToFixedFrame
+ * @see czm_model
*/
this.modelMatrix = defaultValue(options.modelMatrix, Matrix4.IDENTITY.clone());
From 14e5f2ef75a37672fa5ab15b142e47c0c8679984 Mon Sep 17 00:00:00 2001
From: Dan Bagnell mesh
argument.
+ *
+ * @exception {DeveloperError} mesh.attributes.position.values is required
+ *
+ * @example
+ * mesh = GeometryFilters.computeNormals(mesh);
+ *
+ */
+ var pScratch = new Cartesian3();
+ var qScratch = new Cartesian3();
var normal = new Cartesian3();
- GeometryFilters.computeNormals = function(vertices, indices, result) {
- if (typeof vertices === 'undefined' || vertices.length < 0) {
- throw new DeveloperError('vertices is required to have a length greater than zero');
- }
- if (typeof indices === 'undefined' || indices.length < 2) {
- throw new DeveloperError('indices is requred to have a length greater than two');
- }
- if (indices.length % 3 !== 0) {
- throw new DeveloperError('length of indices must be a multiple of three');
+ GeometryFilters.computeNormals = function(mesh) {
+ if (typeof mesh === 'undefined') {
+ throw new DeveloperError('mesh is required.');
}
-
- var normalsPerVertex = [];
- var normalsPerTriangle = [];
- var normalIndices = [];
- var numVertices = vertices.length;
- var numIndices = indices.length;
-
- if (typeof result === 'undefined') {
- result = [];
+ var attributes = mesh.attributes;
+ if (typeof mesh === 'undefined' || typeof attributes.position === 'undefined' ||
+ typeof attributes.position.values === 'undefined' || typeof mesh.attributes.position.values === 'undefined') {
+ throw new DeveloperError('mesh.attributes.position.values is required');
}
-
- for (var i = 0; i < numVertices; i++) {
- normalsPerVertex[i] = {
- indexOffset: 0,
- count: 0,
- currentCount: 0
- };
+ var vertices = mesh.attributes.position.values;
+ var indexLists = mesh.indexLists;
+ if (typeof indexLists === 'undefined') {
+ return mesh;
}
- var j = 0;
- for (i = 0; i < numIndices; i+=3) {
- var i0 = indices[i];
- var i1 = indices[i+1];
- var i2 = indices[i+2];
-
- var v0 = vertices[i0];
- var v1 = vertices[i1];
- var v2 = vertices[i2];
-
- normalsPerVertex[i0].count++;
- normalsPerVertex[i1].count++;
- normalsPerVertex[i2].count++;
-
- v1.subtract(v0, p);
- v2.subtract(v1, q);
- normalsPerTriangle[j] = p.cross(q);
- j++;
- }
+ var length = indexLists.length;
+ for (var k = 0; k < length; k++) {
+ var indices = indexLists[k].values;
+ if (indexLists[k].primitiveType !== PrimitiveType.TRIANGLES || typeof indices === 'undefined' ||
+ indices.length < 2 || indices.length % 3 !== 0) {
+ continue;
+ }
- var indexOffset = 0;
- for (i = 0; i < numVertices; i++) {
- normalsPerVertex[i].indexOffset += indexOffset;
- indexOffset += normalsPerVertex[i].count;
- }
+ var normalsPerVertex = [];
+ var normalsPerTriangle = [];
+ var normalIndices = [];
+ var numVertices = vertices.length;
+ var numIndices = indices.length;
+
+ for (var i = 0; i < numVertices; i++) {
+ normalsPerVertex[i] = {
+ indexOffset: 0,
+ count: 0,
+ currentCount: 0
+ };
+ }
- j = 0;
- var vertexNormalData;
- for (i = 0; i < numIndices; i+=3) {
- vertexNormalData = normalsPerVertex[indices[i]];
- var index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
- normalIndices[index] = j;
- vertexNormalData.currentCount++;
+ var j = 0;
+ for (i = 0; i < numIndices; i+=3) {
+ var i0 = indices[i];
+ var i1 = indices[i+1];
+ var i2 = indices[i+2];
+
+ var v0 = vertices[i0];
+ var v1 = vertices[i1];
+ var v2 = vertices[i2];
+
+ normalsPerVertex[i0].count++;
+ normalsPerVertex[i1].count++;
+ normalsPerVertex[i2].count++;
+
+ v1.subtract(v0, pScratch);
+ v2.subtract(v1, qScratch);
+ normalsPerTriangle[j] = pScratch.cross(qScratch);
+ j++;
+ }
- vertexNormalData = normalsPerVertex[indices[i+1]];
- index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
- normalIndices[index] = j;
- vertexNormalData.currentCount++;
+ var indexOffset = 0;
+ for (i = 0; i < numVertices; i++) {
+ normalsPerVertex[i].indexOffset += indexOffset;
+ indexOffset += normalsPerVertex[i].count;
+ }
- vertexNormalData = normalsPerVertex[indices[i+2]];
- index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
- normalIndices[index] = j;
- vertexNormalData.currentCount++;
+ j = 0;
+ var vertexNormalData;
+ for (i = 0; i < numIndices; i+=3) {
+ vertexNormalData = normalsPerVertex[indices[i]];
+ var index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
+ normalIndices[index] = j;
+ vertexNormalData.currentCount++;
+
+ vertexNormalData = normalsPerVertex[indices[i+1]];
+ index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
+ normalIndices[index] = j;
+ vertexNormalData.currentCount++;
+
+ vertexNormalData = normalsPerVertex[indices[i+2]];
+ index = vertexNormalData.indexOffset + vertexNormalData.currentCount;
+ normalIndices[index] = j;
+ vertexNormalData.currentCount++;
+
+ j++;
+ }
- j++;
- }
+ for (i = 0; i < numVertices; i++) {
+ vertexNormalData = normalsPerVertex[i];
+ if (typeof mesh.attributes.normal === 'undefined') {
+ mesh.attributes.normal = {
+ values: []
+ };
+ }
- for (i = 0; i < numVertices; i++) {
- vertexNormalData = normalsPerVertex[i];
- if (vertexNormalData.count > 0) {
- Cartesian3.ZERO.clone(normal);
- for (j = 0; j < vertexNormalData.count; j++) {
- normal.add(normalsPerTriangle[normalIndices[vertexNormalData.indexOffset + j]], normal);
+ if (vertexNormalData.count > 0) {
+ Cartesian3.ZERO.clone(normal);
+ for (j = 0; j < vertexNormalData.count; j++) {
+ normal.add(normalsPerTriangle[normalIndices[vertexNormalData.indexOffset + j]], normal);
+ }
+ mesh.attributes.normal.values[i] = normal.normalize();
+ } else {
+ mesh.attributes.normal.values[i] = Cartesian3.UNIT_Z.clone();
}
- result[i] = normal.normalize();
- } else {
- result[i] = Cartesian3.UNIT_Z;
}
}
- return result;
+ return mesh;
};
return GeometryFilters;
diff --git a/Specs/Core/GeometryFiltersSpec.js b/Specs/Core/GeometryFiltersSpec.js
index ffda01ce6553..2c2308ec43a3 100644
--- a/Specs/Core/GeometryFiltersSpec.js
+++ b/Specs/Core/GeometryFiltersSpec.js
@@ -608,63 +608,149 @@ defineSuite([
}).toThrow();
});
+ it('GeometryFilters.computeNormals throws when mesh is undefined', function() {
+ expect(function() {
+ GeometryFilters.computeNormals();
+ }).toThrow();
+ });
- it('GeometryFilters.computeNormals computes normal for one triangle', function() {
- var vertices = [];
- var indices = [0, 1, 2];
+ it('GeometryFilters.computeNormals throws when mesh.attributes is undefined', function() {
+ expect(function() {
+ GeometryFilters.computeNormals(new Geometry());
+ }).toThrow();
+ });
- vertices.push(Cartesian3.ZERO);
- vertices.push(Cartesian3.UNIT_X);
- vertices.push(Cartesian3.UNIT_Y);
+ it('GeometryFilters.computeNormals throws when mesh.attributes.position is undefined', function() {
+ expect(function() {
+ GeometryFilters.computeNormals(new Geometry( {
+ attributes: {}
+ }));
+ }).toThrow();
+ });
- var results = GeometryFilters.computeNormals(vertices, indices);
+ it('GeometryFilters.computeNormals throws when mesh.attributes.position.values is undefined', function() {
+ expect(function() {
+ GeometryFilters.computeNormals(new Geometry( {
+ attributes: {
+ position: {}
+ }
+ }));
+ }).toThrow();
+ });
- expect(results.length).toEqual(3);
- expect(results[0]).toEqual(Cartesian3.UNIT_Z);
- expect(results[1]).toEqual(Cartesian3.UNIT_Z);
- expect(results[2]).toEqual(Cartesian3.UNIT_Z);
+ it('GeometryFilters.computeNormals does not compute normals when mesh.indexLists is undefined', function() {
+ var mesh = new Geometry({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, Cartesian3.UNIT_X, Cartesian3.UNIT_Y]
+ }
+ }
+ });
+
+ mesh = GeometryFilters.computeNormals(mesh);
+
+ expect(typeof mesh.attributes.normal === 'undefined').toEqual(true);
});
- it('GeometryFilters.computeNormals computes normal for two triangles', function() {
- var vertices = [];
- var indices = [0, 1, 2, 1, 3, 2];
+ it('GeometryFilters.computeNormals does not compute normals when mesh.indexLists is undefined', function() {
+ var mesh = new Geometry({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, Cartesian3.UNIT_X, Cartesian3.UNIT_Y]
+ }
+ }
+ });
+
+ mesh = GeometryFilters.computeNormals(mesh);
- vertices.push(Cartesian3.ZERO);
- vertices.push(new Cartesian3(1,0,1));
- vertices.push(new Cartesian3(1,1,1));
- vertices.push(new Cartesian3(2,0,0));
+ expect(typeof mesh.attributes.normal === 'undefined').toEqual(true);
+ });
+
+ it('GeometryFilters.computeNormals does not compute normals when primitive type is not triangle', function() {
+ var mesh = new Geometry({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, Cartesian3.UNIT_X, Cartesian3.UNIT_Y]
+ }
+ },
+ indexLists: [{
+ primitiveType: PrimitiveType.TRIANGLE_STRIP,
+ values: [0, 1, 2]
+ }]
+ });
- var results = GeometryFilters.computeNormals(vertices, indices);
+ mesh = GeometryFilters.computeNormals(mesh);
- expect(results.length).toEqual(4);
- expect(results[0]).toEqual(new Cartesian3(-1, 0, 1).normalize());
- expect(results[1]).toEqual(Cartesian3.UNIT_Z);
- expect(results[2]).toEqual(Cartesian3.UNIT_Z);
- expect(results[3]).toEqual(new Cartesian3(1, 0, 1).normalize());
+ expect(typeof mesh.attributes.normal === 'undefined').toEqual(true);
});
- it('GeometryFilters.computeNormals computes normal for six triangles', function() {
- var vertices = [];
- var indices = [0, 1, 2, 3, 0, 2, 4, 0, 3, 4, 5, 0, 5, 6, 0, 6, 1, 0];
- vertices.push(Cartesian3.ZERO);
- vertices.push(new Cartesian3(1,0,0));
- vertices.push(new Cartesian3(1,0,1));
- vertices.push(new Cartesian3(0,0,1));
- vertices.push(new Cartesian3(0,1,1));
- vertices.push(new Cartesian3(0,1,0));
- vertices.push(new Cartesian3(1,1,0));
+ it('GeometryFilters.computeNormals computes normal for one triangle', function() {
+ var mesh = new Geometry({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, Cartesian3.UNIT_X, Cartesian3.UNIT_Y]
+ }
+ },
+ indexLists: [{
+ primitiveType: PrimitiveType.TRIANGLES,
+ values: [0, 1, 2]
+ }]
+ });
- var results = GeometryFilters.computeNormals(vertices, indices);
+ mesh = GeometryFilters.computeNormals(mesh);
- expect(results.length).toEqual(7);
- expect(results[0]).toEqual(new Cartesian3(-1, -1, -1).normalize());
- expect(results[1]).toEqual(new Cartesian3(0, -1, -1).normalize());
- expect(results[2]).toEqual(new Cartesian3(0, -1, 0).normalize());
- expect(results[3]).toEqual(new Cartesian3(-1, -1, 0).normalize());
- expect(results[4]).toEqual(new Cartesian3(-1, 0, 0).normalize());
- expect(results[5]).toEqual(new Cartesian3(-1, 0, -1).normalize());
- expect(results[6]).toEqual(new Cartesian3(0, 0, -1).normalize());
+ expect(mesh.attributes.normal.values.length).toEqual(3);
+ expect(mesh.attributes.normal.values[0]).toEqual(Cartesian3.UNIT_Z);
+ expect(mesh.attributes.normal.values[1]).toEqual(Cartesian3.UNIT_Z);
+ expect(mesh.attributes.normal.values[2]).toEqual(Cartesian3.UNIT_Z);
});
+ it('GeometryFilters.computeNormals computes normal for two triangles', function() {
+ var mesh = new Geometry({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, new Cartesian3(1,0,1), new Cartesian3(1,1,1), new Cartesian3(2,0,0)]
+ }
+ },
+ indexLists: [{
+ primitiveType: PrimitiveType.TRIANGLES,
+ values: [0, 1, 2, 1, 3, 2]
+ }]
+ });
+
+ mesh = GeometryFilters.computeNormals(mesh);
+
+ expect(mesh.attributes.normal.values.length).toEqual(4);
+ expect(mesh.attributes.normal.values[0]).toEqual(new Cartesian3(-1, 0, 1).normalize());
+ expect(mesh.attributes.normal.values[1]).toEqual(Cartesian3.UNIT_Z);
+ expect(mesh.attributes.normal.values[2]).toEqual(Cartesian3.UNIT_Z);
+ expect(mesh.attributes.normal.values[3]).toEqual(new Cartesian3(1, 0, 1).normalize());
+ });
+
+ it('GeometryFilters.computeNormals computes normal for six triangles', function() {
+ var mesh = new Geometry ({
+ attributes: {
+ position: {
+ values: [Cartesian3.ZERO, new Cartesian3(1,0,0), new Cartesian3(1,0,1), new Cartesian3(0,0,1),
+ new Cartesian3(0,1,1), new Cartesian3(0,1,0), new Cartesian3(1,1,0)]
+ }
+ },
+ indexLists: [{
+ primitiveType: PrimitiveType.TRIANGLES,
+ values: [0, 1, 2, 3, 0, 2, 4, 0, 3, 4, 5, 0, 5, 6, 0, 6, 1, 0]
+ }]
+ });
+
+ mesh = GeometryFilters.computeNormals(mesh);
+
+ expect(mesh.attributes.normal.values.length).toEqual(7);
+ expect(mesh.attributes.normal.values[0]).toEqual(new Cartesian3(-1, -1, -1).normalize());
+ expect(mesh.attributes.normal.values[1]).toEqual(new Cartesian3(0, -1, -1).normalize());
+ expect(mesh.attributes.normal.values[2]).toEqual(new Cartesian3(0, -1, 0).normalize());
+ expect(mesh.attributes.normal.values[3]).toEqual(new Cartesian3(-1, -1, 0).normalize());
+ expect(mesh.attributes.normal.values[4]).toEqual(new Cartesian3(-1, 0, 0).normalize());
+ expect(mesh.attributes.normal.values[5]).toEqual(new Cartesian3(-1, 0, -1).normalize());
+ expect(mesh.attributes.normal.values[6]).toEqual(new Cartesian3(0, 0, -1).normalize());
+ });
});
\ No newline at end of file
From 9615e3c32bb024fcdbcfad0773547cf9974b0e59 Mon Sep 17 00:00:00 2001
From: Dan Bagnell Cartesian3
, respectively.
* @param {VertexFormat} [options.vertexFormat=VertexFormat.DEFAULT] The vertex attributes to be computed.
- * @param {Matrix4} [options.modelMatrix] The model matrix for this box. See {@link czm_model}.
+ * @param {Matrix4} [options.modelMatrix] The model matrix for this box.
* @param {DOC_TBA} [options.pickData] DOC_TBA
*
* @exception {DeveloperError} All dimensions components must be greater than or equal to zero.
@@ -381,7 +381,7 @@ define([
this.indexLists = indexLists;
/**
- * A tight-fitting bounding sphere that encloses the vertices of the box
+ * A tight-fitting bounding sphere that encloses the vertices of the geometry.
*
* @type BoundingSphere
*/
diff --git a/Source/Core/EllipsoidGeometry.js b/Source/Core/EllipsoidGeometry.js
index 5d627b5b8952..443ead6eaf66 100644
--- a/Source/Core/EllipsoidGeometry.js
+++ b/Source/Core/EllipsoidGeometry.js
@@ -27,13 +27,31 @@ define([
VertexFormat) {
"use strict";
+ var sphericalNormal = new Cartesian3();
+ var normal = new Cartesian3();
+ var tangent = new Cartesian3();
+ var binormal = new Cartesian3();
+
/**
- * DOC_TBA
+ * Creates vertices and indices for an ellipsoid centered at the origin.
*
* @alias EllipsoidGeometry
* @constructor
*
+ * @param {Ellipsoid} [options.ellipsoi=Ellipsoid.UNIT_SPHERE] The ellipsoid used to create vertex attributes.
+ * @param {Number} [options.numberOfPartitions=32] The number of times to partition the ellipsoid in a plane formed by two radii in a single quadrant.
+ * @param {VertexFormat} [options.vertexFormat=VertexFormat.DEFAULT] The vertex attributes to be computed.
+ * @param {Matrix4} [options.modelMatrix] The model matrix for this ellipsoid.
+ * @param {DOC_TBA} [options.pickData] DOC_TBA
+ *
* @exception {DeveloperError} options.numberOfPartitions must be greater than zero.
+ *
+ * @example
+ * var ellipsoid = new EllipsoidGeometry({
+ * vertexFormat : VertexFormat.POSITION_ONLY,
+ * ellipsoid : new Ellipsoid(1000000.0, 500000.0, 500000.0),
+ * modelMatrix : Transforms.eastNorthUpToFixedFrame(center)
+ * });
*/
var EllipsoidGeometry = function(options) {
options = defaultValue(options, defaultValue.EMPTY_OBJECT);
@@ -139,7 +157,6 @@ define([
if (vertexFormat.st) {
var texCoords = new Array(length * 2);
var oneOverRadii = ellipsoid.getOneOverRadii();
- var sphericalNormal = new Cartesian3();
for (i = j = 0; i < length; ++i) {
Cartesian3.multiplyComponents(positions[i], oneOverRadii, sphericalNormal);
@@ -161,10 +178,6 @@ define([
var tangents = new Array(length * 3);
var binormals = new Array(length * 3);
- var normal = new Cartesian3();
- var tangent = new Cartesian3();
- var binormal = new Cartesian3();
-
for (i = j = 0; i < length; ++i, j += 3) {
ellipsoid.geodeticSurfaceNormal(positions[i], normal);
Cartesian3.cross(Cartesian3.UNIT_Z, normal, tangent);
@@ -209,12 +222,17 @@ define([
}
/**
- * DOC_TBA
+ * An object containing {@link GeometryAttribute} properties named after each of the
+ * true
values of the {@link VertexFormat} option.
+ *
+ * @type Object
*/
this.attributes = attributes;
/**
- * DOC_TBA
+ * An array of {@link GeometryIndices} defining primitives.
+ *
+ * @type Array
*/
this.indexLists = [
new GeometryIndices({
@@ -224,12 +242,21 @@ define([
];
/**
- * DOC_TBA
+ * A tight-fitting bounding sphere that encloses the vertices of the geometry.
+ *
+ * @type BoundingSphere
*/
this.boundingSphere = BoundingSphere.fromEllipsoid(ellipsoid);
/**
- * DOC_TBA
+ * The 4x4 transformation matrix that transforms the geometry from model to world coordinates.
+ * When this is the identity matrix, the geometry is drawn in world coordinates, i.e., Earth's WGS84 coordinates.
+ * Local reference frames can be used by providing a different transformation matrix, like that returned
+ * by {@link Transforms.eastNorthUpToFixedFrame}.
+ *
+ * @type Matrix4
+ *
+ * @see Transforms.eastNorthUpToFixedFrame
*/
this.modelMatrix = defaultValue(options.modelMatrix, Matrix4.IDENTITY.clone());
@@ -239,28 +266,37 @@ define([
this.pickData = options.pickData;
};
+ var scratchDirection = new Cartesian3();
+
function addEdgePositions(i0, i1, numberOfPartitions, positions) {
var indices = [];
indices[0] = i0;
indices[2 + (numberOfPartitions - 1) - 1] = i1;
var origin = positions[i0];
- var direction = positions[i1].subtract(positions[i0]);
+ var direction = Cartesian3.subtract(positions[i1], positions[i0], scratchDirection);
for ( var i = 1; i < numberOfPartitions; ++i) {
var delta = i / numberOfPartitions;
+ var position = Cartesian3.multiplyByScalar(direction, delta);
+ Cartesian3.add(origin, position, position);
indices[i] = positions.length;
- positions.push(origin.add(direction.multiplyByScalar(delta)));
+ positions.push(position);
}
return indices;
}
+ var scratchX = new Cartesian3();
+ var scratchY = new Cartesian3();
+ var scratchOffsetX = new Cartesian3();
+ var scratchOffsetY = new Cartesian3();
+
function addFaceTriangles(leftBottomToTop, bottomLeftToRight, rightBottomToTop, topLeftToRight, numberOfPartitions, positions, indices) {
var origin = positions[bottomLeftToRight[0]];
- var x = positions[bottomLeftToRight[bottomLeftToRight.length - 1]].subtract(origin);
- var y = positions[topLeftToRight[0]].subtract(origin);
+ var x = Cartesian3.subtract(positions[bottomLeftToRight[bottomLeftToRight.length - 1]], origin, scratchX);
+ var y = Cartesian3.subtract(positions[topLeftToRight[0]], origin, scratchY);
var bottomIndicesBuffer = [];
var topIndicesBuffer = [];
@@ -282,14 +318,16 @@ define([
topIndicesBuffer[numberOfPartitions] = rightBottomToTop[j];
var deltaY = j / numberOfPartitions;
- var offsetY = y.multiplyByScalar(deltaY);
+ var offsetY = Cartesian3.multiplyByScalar(y, deltaY, scratchOffsetY);
for ( var i = 1; i < numberOfPartitions; ++i) {
var deltaX = i / numberOfPartitions;
- var offsetX = x.multiplyByScalar(deltaX);
+ var offsetX = Cartesian3.multiplyByScalar(x, deltaX, scratchOffsetX);
+ var position = Cartesian3.add(origin, offsetX);
+ Cartesian3.add(position, offsetY, position);
topIndicesBuffer[i] = positions.length;
- positions.push(origin.add(offsetX).add(offsetY));
+ positions.push(position);
}
} else {
if (j !== 1) {
From 4a6cc957043b859642297038fdc76ae9ecae99e2 Mon Sep 17 00:00:00 2001
From: Dan Bagnell 5KF8H5J{Q+zHf0m_A95rju
zW=#DrA&Jv?!`x&!XN>ma+vC;FG0x1XKe(DPvnPYb243Y~uC)aAAI&}gj1{TfV$J)^
z+iyKq(W%ka8y9?Oe*U>ld-gjm;subj`c)dUwHD&AVL83!g5)b~z<&&h=^{*}hV&;}vs)8MOXVE~XIjFg7Nl!zgeIwiy&
z2**JsF3bR`-vkiQY+I%-u>hiD1gxT1iwiLjpbn%-H}Cwb-~fOy
#G#Rkq|*6$b3C9R-CS!h5o8t?6QX2Hb+|
z
mesh
argument.
*
* @exception {DeveloperError} mesh.attributes.position.values is required
+ * @exception {DeveloperError} mesh.attributes.position.values.length must be a multiple of 3
*
* @example
* mesh = GeometryFilters.computeNormals(mesh);
@@ -887,7 +888,7 @@ define([
var numIndices = indices.length;
var normalsPerVertex = new Array(numVertices);
var normalsPerTriangle = new Array(numIndices/3);
- var normalIndices = new Array(numVertices);
+ var normalIndices = new Array(numIndices);
for (var i = 0; i < numVertices; i++) {
normalsPerVertex[i] = {
@@ -902,16 +903,19 @@ define([
var i0 = indices[i];
var i1 = indices[i+1];
var i2 = indices[i+2];
-
- v0.x = vertices[i0*3];
- v0.y = vertices[i0*3+1];
- v0.z = vertices[i0*3+2];
- v1.x = vertices[i1*3];
- v1.y = vertices[i1*3+1];
- v1.z = vertices[i1*3+2];
- v2.x = vertices[i2*3];
- v2.y = vertices[i2*3+1];
- v2.z = vertices[i2*3+2];
+ var i03 = i0*3;
+ var i13 = i1*3;
+ var i23 = i2*3;
+
+ v0.x = vertices[i03];
+ v0.y = vertices[i03+1];
+ v0.z = vertices[i03+2];
+ v1.x = vertices[i13];
+ v1.y = vertices[i13+1];
+ v1.z = vertices[i13+2];
+ v2.x = vertices[i23];
+ v2.y = vertices[i23+1];
+ v2.z = vertices[i23+2];
normalsPerVertex[i0].count++;
normalsPerVertex[i1].count++;
@@ -957,7 +961,9 @@ define([
values: new Array(numVertices * 3)
});
}
+ var normalValues = mesh.attributes.normal.values;
for (i = 0; i < numVertices; i++) {
+ var i3 = i * 3;
vertexNormalData = normalsPerVertex[i];
if (vertexNormalData.count > 0) {
Cartesian3.ZERO.clone(normal);
@@ -965,13 +971,13 @@ define([
normal.add(normalsPerTriangle[normalIndices[vertexNormalData.indexOffset + j]], normal);
}
normal.normalize(normal);
- mesh.attributes.normal.values[3*i] = normal.x;
- mesh.attributes.normal.values[3*i+1] = normal.y;
- mesh.attributes.normal.values[3*i+2] = normal.z;
+ normalValues[i3] = normal.x;
+ normalValues[i3+1] = normal.y;
+ normalValues[i3+2] = normal.z;
} else {
- mesh.attributes.normal.values[3*i] = 0;
- mesh.attributes.normal.values[3*i+1] = 0;
- mesh.attributes.normal.values[3*i+2] = 1;
+ normalValues[i3] = 0;
+ normalValues[i3+1] = 0;
+ normalValues[i3+2] = 1;
}
}
}
From 260d6cf23c61467aaeedb677f8c3ba32d23c4f7e Mon Sep 17 00:00:00 2001
From: Patrick Cozzi