Add mesh instance object that represents a mesh with transformation.

This commit is contained in:
kovacsv 2021-10-24 16:46:49 +02:00
parent f045d214c7
commit 4250ab3b58
20 changed files with 147 additions and 68 deletions

View File

@ -30,7 +30,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -30,7 +30,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -29,7 +29,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -30,7 +30,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -30,7 +30,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -29,7 +29,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -29,7 +29,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -1,4 +1,4 @@
OV.Mesh = class extends OV.Element
OV.Mesh = class extends OV.ModelObject3D
{
constructor ()
{

View File

@ -0,0 +1,52 @@
OV.MeshInstance = class extends OV.Object3D
{
constructor (mesh, transformation)
{
super ();
this.mesh = mesh;
this.transformation = transformation;
}
VertexCount ()
{
return this.mesh.VertexCount ();
}
NormalCount ()
{
return this.mesh.NormalCount ();
}
TextureUVCount ()
{
return this.mesh.TextureUVCount ();
}
TriangleCount ()
{
return this.mesh.TriangleCount ();
}
EnumerateVertices (onVertex)
{
this.mesh.EnumerateVertices ((vertex) => {
const transformed = this.transformation.TransformCoord3D (vertex);
onVertex (transformed);
});
}
EnumerateTriangles (onTriangle)
{
this.mesh.EnumerateTriangles (onTriangle);
}
EnumerateTriangleVertices (onTriangleVertices)
{
this.mesh.EnumerateTriangleVertices ((v0, v1, v2) => {
const v0Transformed = this.transformation.TransformCoord3D (v0);
const v1Transformed = this.transformation.TransformCoord3D (v1);
const v2Transformed = this.transformation.TransformCoord3D (v2);
onTriangleVertices (v0Transformed, v1Transformed, v2Transformed);
});
}
};

View File

@ -12,7 +12,7 @@ OV.MeshInstanceId = class
}
};
OV.Model = class extends OV.Element
OV.Model = class extends OV.ModelObject3D
{
constructor ()
{

View File

@ -165,24 +165,24 @@ OV.EnumerateModelVerticesAndTriangles = function (model, callbacks)
});
};
OV.EnumerateTrianglesWithNormals = function (element, onTriangle)
OV.EnumerateTrianglesWithNormals = function (object3D, onTriangle)
{
element.EnumerateTriangleVertices ((v0, v1, v2) => {
object3D.EnumerateTriangleVertices ((v0, v1, v2) => {
let normal = OV.CalculateTriangleNormal (v0, v1, v2);
onTriangle (v0, v1, v2, normal);
});
};
OV.GetBoundingBox = function (element)
OV.GetBoundingBox = function (object3D)
{
let calculator = new OV.BoundingBoxCalculator3D ();
element.EnumerateVertices ((vertex) => {
object3D.EnumerateVertices ((vertex) => {
calculator.AddPoint (vertex);
});
return calculator.GetBox ();
};
OV.GetTopology = function (element)
OV.GetTopology = function (object3D)
{
function GetVertexIndex (vertex, octree, topology)
{
@ -194,11 +194,11 @@ OV.GetTopology = function (element)
return index;
}
let boundingBox = OV.GetBoundingBox (element);
let boundingBox = OV.GetBoundingBox (object3D);
let octree = new OV.Octree (boundingBox);
let topology = new OV.Topology ();
element.EnumerateTriangleVertices ((v0, v1, v2) => {
object3D.EnumerateTriangleVertices ((v0, v1, v2) => {
let v0Index = GetVertexIndex (v0, octree, topology);
let v1Index = GetVertexIndex (v1, octree, topology);
let v2Index = GetVertexIndex (v2, octree, topology);
@ -207,7 +207,7 @@ OV.GetTopology = function (element)
return topology;
};
OV.IsSolid = function (element)
OV.IsSolid = function (object3D)
{
function GetEdgeOrientationInTriangle (topology, triangleIndex, edgeIndex)
{
@ -227,7 +227,7 @@ OV.IsSolid = function (element)
return null;
}
const topology = OV.GetTopology (element);
const topology = OV.GetTopology (object3D);
for (let edgeIndex = 0; edgeIndex < topology.edges.length; edgeIndex++) {
const edge = topology.edges[edgeIndex];
let triCount = edge.triangles.length;

View File

@ -1,21 +1,10 @@
OV.Element = class
OV.Object3D = class
{
constructor ()
{
this.name = '';
this.propertyGroups = [];
}
GetName ()
{
return this.name;
}
SetName (name)
{
this.name = name;
}
VertexCount ()
{
return 0;
@ -36,22 +25,6 @@ OV.Element = class
return 0;
}
PropertyGroupCount ()
{
return this.propertyGroups.length;
}
AddPropertyGroup (propertyGroup)
{
this.propertyGroups.push (propertyGroup);
return this.propertyGroups.length - 1;
}
GetPropertyGroup (index)
{
return this.propertyGroups[index];
}
EnumerateVertices (onVertex)
{
@ -67,3 +40,39 @@ OV.Element = class
}
};
OV.ModelObject3D = class extends OV.Object3D
{
constructor ()
{
super ();
this.name = '';
this.propertyGroups = [];
}
GetName ()
{
return this.name;
}
SetName (name)
{
this.name = name;
}
PropertyGroupCount ()
{
return this.propertyGroups.length;
}
AddPropertyGroup (propertyGroup)
{
this.propertyGroups.push (propertyGroup);
return this.propertyGroups.length - 1;
}
GetPropertyGroup (index)
{
return this.propertyGroups[index];
}
};

View File

@ -16,22 +16,22 @@ OV.GetTetrahedronSignedVolume = function (v0, v1, v2)
return OV.DotVector3D (v0, OV.CrossVector3D (v1, v2)) / 6.0;
};
OV.CalculateVolume = function (element)
OV.CalculateVolume = function (object3D)
{
if (!OV.IsSolid (element)) {
if (!OV.IsSolid (object3D)) {
return null;
}
let volume = 0.0;
element.EnumerateTriangleVertices ((v0, v1, v2) => {
object3D.EnumerateTriangleVertices ((v0, v1, v2) => {
volume += OV.GetTetrahedronSignedVolume (v0, v1, v2);
});
return volume;
};
OV.CalculateSurfaceArea = function (element)
OV.CalculateSurfaceArea = function (object3D)
{
let surface = 0.0;
element.EnumerateTriangleVertices ((v0, v1, v2) => {
object3D.EnumerateTriangleVertices ((v0, v1, v2) => {
surface += OV.GetTriangleArea (v0, v1, v2);
});
return surface;

View File

@ -86,6 +86,15 @@ describe ('Model Utils', function () {
assert (OV.CoordIsEqual3D (cubeBounds.max, new OV.Coord3D (1.0, 1.0, 1.0)));
});
it ('Mesh Instance Bounding Box', function () {
let cube = OV.GenerateCuboid (null, 1.0, 1.0, 1.0);
let transformation = new OV.Transformation (new OV.Matrix ().CreateTranslation (2.0, 0.0, 0.0));
let cubeInstance = new OV.MeshInstance (cube, transformation);
let cubeInstanceBounds = OV.GetBoundingBox (cubeInstance);
assert (OV.CoordIsEqual3D (cubeInstanceBounds.min, new OV.Coord3D (2.0, 0.0, 0.0)));
assert (OV.CoordIsEqual3D (cubeInstanceBounds.max, new OV.Coord3D (3.0, 1.0, 1.0)));
});
it ('Model Bounding Box', function () {
var model = new OV.Model ();

View File

@ -72,7 +72,7 @@ describe ('Quantities', function () {
});
it ('Tetrahedron Volume Calculation', function () {
let edgeLength = OV.CoordDistance3D (new OV.Coord3D (1.0, 1.0, 1.0), new OV.Coord3D (-1.0, -1.0, 1.0));
const edgeLength = OV.CoordDistance3D (new OV.Coord3D (1.0, 1.0, 1.0), new OV.Coord3D (-1.0, -1.0, 1.0));
const mesh = testUtils.GetTetrahedronMesh ();
const model = testUtils.GetModelWithOneMesh (mesh);
assert (OV.IsEqual (OV.CalculateVolume (mesh), Math.pow (edgeLength, 3.0) / (6.0 * Math.sqrt (2))));
@ -80,10 +80,18 @@ describe ('Quantities', function () {
});
it ('Tetrahedron Surface Area Calculation', function () {
let edgeLength = OV.CoordDistance3D (new OV.Coord3D (1.0, 1.0, 1.0), new OV.Coord3D (-1.0, -1.0, 1.0));
const edgeLength = OV.CoordDistance3D (new OV.Coord3D (1.0, 1.0, 1.0), new OV.Coord3D (-1.0, -1.0, 1.0));
const mesh = testUtils.GetTetrahedronMesh ();
const model = testUtils.GetModelWithOneMesh (mesh);
assert (OV.IsEqual (OV.CalculateSurfaceArea (mesh), Math.sqrt (3) * Math.pow (edgeLength, 2.0)));
assert (OV.IsEqual (OV.CalculateSurfaceArea (model), Math.sqrt (3) * Math.pow (edgeLength, 2.0)));
});
it ('Cube Scaled Volume and Area Calculation', function () {
const mesh = OV.GenerateCuboid (null, 1.0, 1.0, 1.0);
const transformation = new OV.Transformation (new OV.Matrix ().CreateScale (2.0, 2.0, 2.0));
const meshInstance = new OV.MeshInstance (mesh, transformation);
assert (OV.IsEqual (OV.CalculateVolume (meshInstance), 8.0));
assert (OV.IsEqual (OV.CalculateSurfaceArea (meshInstance), 24.0));
});
});

View File

@ -26,8 +26,9 @@
"source/model/material.js",
"source/model/triangle.js",
"source/model/property.js",
"source/model/element.js",
"source/model/object.js",
"source/model/mesh.js",
"source/model/meshinstance.js",
"source/model/meshbuffer.js",
"source/model/node.js",
"source/model/model.js",

View File

@ -39,7 +39,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -39,7 +39,7 @@
<script type="text/javascript" src="../source/model/material.js"></script>
<script type="text/javascript" src="../source/model/triangle.js"></script>
<script type="text/javascript" src="../source/model/property.js"></script>
<script type="text/javascript" src="../source/model/element.js"></script>
<script type="text/javascript" src="../source/model/object.js"></script>
<script type="text/javascript" src="../source/model/mesh.js"></script>
<script type="text/javascript" src="../source/model/meshbuffer.js"></script>
<script type="text/javascript" src="../source/model/node.js"></script>

View File

@ -10,35 +10,35 @@ OV.DetailsSidebarPanel = class extends OV.SidebarPanel
return 'Details';
}
AddElementProperties (element)
AddObject3DProperties (object3D)
{
this.Clear ();
let table = $('<div>').addClass ('ov_property_table').appendTo (this.contentDiv);
let boundingBox = OV.GetBoundingBox (element);
let boundingBox = OV.GetBoundingBox (object3D);
let size = OV.SubCoord3D (boundingBox.max, boundingBox.min);
this.AddProperty (table, new OV.Property (OV.PropertyType.Integer, 'Vertex Count', element.VertexCount ()));
this.AddProperty (table, new OV.Property (OV.PropertyType.Integer, 'Triangle Count', element.TriangleCount ()));
this.AddProperty (table, new OV.Property (OV.PropertyType.Integer, 'Vertex Count', object3D.VertexCount ()));
this.AddProperty (table, new OV.Property (OV.PropertyType.Integer, 'Triangle Count', object3D.TriangleCount ()));
this.AddProperty (table, new OV.Property (OV.PropertyType.Number, 'Size X', size.x));
this.AddProperty (table, new OV.Property (OV.PropertyType.Number, 'Size Y', size.y));
this.AddProperty (table, new OV.Property (OV.PropertyType.Number, 'Size Z', size.z));
this.AddCalculatedProperty (table, 'Volume', () => {
const volume = OV.CalculateVolume (element);
const volume = OV.CalculateVolume (object3D);
if (volume === null) {
return null;
}
return new OV.Property (OV.PropertyType.Number, null, volume);
});
this.AddCalculatedProperty (table, 'Surface Area', () => {
const volume = OV.CalculateSurfaceArea (element);
const volume = OV.CalculateSurfaceArea (object3D);
if (volume === null) {
return null;
}
return new OV.Property (OV.PropertyType.Number, null, volume);
});
if (element.PropertyGroupCount () > 0) {
if (object3D.PropertyGroupCount () > 0) {
let customTable = $('<div>').addClass ('ov_property_table ov_property_table_custom').appendTo (this.contentDiv);
for (let i = 0; i < element.PropertyGroupCount (); i++) {
const propertyGroup = element.GetPropertyGroup (i);
for (let i = 0; i < object3D.PropertyGroupCount (); i++) {
const propertyGroup = object3D.GetPropertyGroup (i);
this.AddPropertyGroup (customTable, propertyGroup);
for (let j = 0; j < propertyGroup.PropertyCount (); j++) {
const property = propertyGroup.GetProperty (j);

View File

@ -695,10 +695,10 @@ OV.Website = class
return GetMaterialsForModel (this.model);
},
onModelSelected : () => {
this.detailsPanel.AddElementProperties (this.model);
this.detailsPanel.AddObject3DProperties (this.model);
},
onMeshSelected : (meshIndex) => {
this.detailsPanel.AddElementProperties (this.model.GetMesh (meshIndex));
this.detailsPanel.AddObject3DProperties (this.model.GetMesh (meshIndex));
},
onMaterialSelected : (materialIndex) => {
this.detailsPanel.AddMaterialProperties (this.model.GetMaterial (materialIndex));