Add cone generator.
This commit is contained in:
parent
a68902f33b
commit
603d7c8699
@ -6,7 +6,7 @@ import { ArrayToQuaternion, Quaternion } from '../geometry/quaternion.js';
|
||||
import { Transformation } from '../geometry/transformation.js';
|
||||
import { ArrayBufferToUtf8String } from '../io/bufferutils.js';
|
||||
import { ArrayToColor } from '../model/color.js';
|
||||
import { GenerateCuboid, GenerateCylinder, GeneratePlatonicSolid, GenerateSphere, GeneratorParams } from '../model/generator.js';
|
||||
import { GenerateCone, GenerateCuboid, GenerateCylinder, GeneratePlatonicSolid, GenerateSphere, GeneratorParams } from '../model/generator.js';
|
||||
import { PhysicalMaterial } from '../model/material.js';
|
||||
import { Node, NodeType } from '../model/node.js';
|
||||
import { Property, PropertyGroup, PropertyType } from '../model/property.js';
|
||||
@ -111,6 +111,13 @@ export class ImporterO3dv extends ImporterBase
|
||||
let segments = ValueOrDefault (parameters.segments, 25);
|
||||
let smooth = ValueOrDefault (parameters.smooth, true);
|
||||
mesh = GenerateCylinder (genParams, parameters.radius, parameters.height, segments, smooth);
|
||||
} else if (meshContent.type === 'cone') {
|
||||
if (parameters.top_radius === undefined || parameters.bottom_radius === undefined || parameters.height === undefined) {
|
||||
return;
|
||||
}
|
||||
let segments = ValueOrDefault (parameters.segments, 25);
|
||||
let smooth = ValueOrDefault (parameters.smooth, true);
|
||||
mesh = GenerateCone (genParams, parameters.top_radius, parameters.bottom_radius, parameters.height, segments, smooth);
|
||||
} else if (meshContent.type === 'sphere') {
|
||||
if (parameters.radius === undefined) {
|
||||
return;
|
||||
|
||||
@ -41,7 +41,7 @@ import { SetExternalLibLocation, LoadExternalLibrary } from './io/externallibs.j
|
||||
import { GetFileName, GetFileExtension, RequestUrl, ReadFile, TransformFileHostUrls, FileSource, FileFormat } from './io/fileutils.js';
|
||||
import { TextWriter } from './io/textwriter.js';
|
||||
import { Color, ColorComponentFromFloat, ColorFromFloatComponents, SRGBToLinear, LinearToSRGB, IntegerToHexString, ColorToHexString, HexStringToColor, ArrayToColor, ColorIsEqual } from './model/color.js';
|
||||
import { GeneratorParams, Generator, GeneratorHelper, GenerateCuboid, GenerateCylinder, GenerateSphere, GeneratePlatonicSolid } from './model/generator.js';
|
||||
import { GeneratorParams, Generator, GeneratorHelper, GenerateCuboid, GenerateCone, GenerateCylinder, GenerateSphere, GeneratePlatonicSolid } from './model/generator.js';
|
||||
import { TextureMap, MaterialBase, FaceMaterial, PhongMaterial, PhysicalMaterial, TextureMapIsEqual, TextureIsEqual, MaterialType } from './model/material.js';
|
||||
import { Mesh } from './model/mesh.js';
|
||||
import { MeshPrimitiveBuffer, MeshBuffer, ConvertMeshToMeshBuffer } from './model/meshbuffer.js';
|
||||
@ -200,6 +200,7 @@ export {
|
||||
Generator,
|
||||
GeneratorHelper,
|
||||
GenerateCuboid,
|
||||
GenerateCone,
|
||||
GenerateCylinder,
|
||||
GenerateSphere,
|
||||
GeneratePlatonicSolid,
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import { Coord2D } from '../geometry/coord2d.js';
|
||||
import { Coord3D } from '../geometry/coord3d.js';
|
||||
import { IsZero } from '../geometry/geometry.js';
|
||||
import { IsPositive, IsNegative, IsZero } from '../geometry/geometry.js';
|
||||
import { Mesh } from './mesh.js';
|
||||
import { Triangle } from './triangle.js';
|
||||
|
||||
@ -164,8 +164,20 @@ export class GeneratorHelper
|
||||
}
|
||||
}
|
||||
|
||||
function GetCylindricalCoord (radius, angle)
|
||||
{
|
||||
return new Coord2D (
|
||||
radius * Math.cos (angle),
|
||||
radius * Math.sin (angle)
|
||||
);
|
||||
}
|
||||
|
||||
export function GenerateCuboid (genParams, xSize, ySize, zSize)
|
||||
{
|
||||
if (!IsPositive (xSize) || !IsPositive (ySize) || !IsPositive (zSize)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let generator = new Generator (genParams);
|
||||
let vertices = [
|
||||
new Coord2D (0.0, 0.0),
|
||||
@ -178,32 +190,73 @@ export function GenerateCuboid (genParams, xSize, ySize, zSize)
|
||||
return generator.GetMesh ();
|
||||
}
|
||||
|
||||
export function GenerateCylinder (genParams, radius, height, segments, smooth)
|
||||
export function GenerateCone (genParams, topRadius, bottomRadius, height, segments, smooth)
|
||||
{
|
||||
function GetCylindricalCoord (radius, angle)
|
||||
{
|
||||
return new Coord2D (
|
||||
radius * Math.cos (angle),
|
||||
radius * Math.sin (angle)
|
||||
);
|
||||
if (IsNegative (topRadius) || IsNegative (bottomRadius)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (segments < 3) {
|
||||
if (!IsPositive (height) || segments < 3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let isZeroTop = IsZero (topRadius);
|
||||
let isZeroBottom = IsZero (bottomRadius);
|
||||
if (isZeroTop && isZeroBottom) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let generator = new Generator (genParams);
|
||||
let baseVertices = [];
|
||||
const step = 2.0 * Math.PI / segments;
|
||||
for (let i = 0; i < segments; i++) {
|
||||
let cylindrical = GetCylindricalCoord (radius, i * step);
|
||||
baseVertices.push (cylindrical);
|
||||
}
|
||||
let helper = new GeneratorHelper (generator);
|
||||
helper.GenerateExtrude (baseVertices, height, smooth ? 1 : null);
|
||||
const step = 2.0 * Math.PI / segments;
|
||||
const curve = (smooth ? 1 : null);
|
||||
|
||||
let topPolygon = [];
|
||||
if (isZeroTop) {
|
||||
topPolygon.push (generator.AddVertex (0.0, 0.0, height));
|
||||
} else {
|
||||
for (let i = 0; i < segments; i++) {
|
||||
let topVertex = GetCylindricalCoord (topRadius, i * step);
|
||||
topPolygon.push (generator.AddVertex (topVertex.x, topVertex.y, height));
|
||||
}
|
||||
}
|
||||
|
||||
let bottomPolygon = [];
|
||||
if (isZeroBottom) {
|
||||
bottomPolygon.push (generator.AddVertex (0.0, 0.0, 0.0));
|
||||
} else {
|
||||
for (let i = 0; i < segments; i++) {
|
||||
let bottomVertex = GetCylindricalCoord (bottomRadius, i * step);
|
||||
bottomPolygon.push (generator.AddVertex (bottomVertex.x, bottomVertex.y, 0.0));
|
||||
}
|
||||
}
|
||||
|
||||
if (isZeroTop) {
|
||||
generator.SetCurve (curve);
|
||||
helper.GenerateTriangleFan (bottomPolygon, topPolygon[0]);
|
||||
generator.ResetCurve ();
|
||||
generator.AddConvexPolygonInverted (bottomPolygon);
|
||||
} else if (isZeroBottom) {
|
||||
generator.SetCurve (curve);
|
||||
helper.GenerateTriangleFan (topPolygon.slice ().reverse (), bottomPolygon[0]);
|
||||
generator.ResetCurve ();
|
||||
generator.AddConvexPolygon (topPolygon);
|
||||
} else {
|
||||
generator.SetCurve (curve);
|
||||
helper.GenerateSurfaceBetweenPolygons (bottomPolygon, topPolygon);
|
||||
generator.ResetCurve ();
|
||||
generator.AddConvexPolygonInverted (bottomPolygon);
|
||||
generator.AddConvexPolygon (topPolygon);
|
||||
}
|
||||
|
||||
return generator.GetMesh ();
|
||||
}
|
||||
|
||||
export function GenerateCylinder (genParams, radius, height, segments, smooth)
|
||||
{
|
||||
return GenerateCone (genParams, radius, radius, height, segments, smooth);
|
||||
}
|
||||
|
||||
export function GenerateSphere (genParams, radius, segments, smooth)
|
||||
{
|
||||
function GetSphericalCoord (radius, theta, phi)
|
||||
@ -215,7 +268,7 @@ export function GenerateSphere (genParams, radius, segments, smooth)
|
||||
);
|
||||
}
|
||||
|
||||
if (segments < 3) {
|
||||
if (!IsPositive (radius) || segments < 3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@ -261,7 +314,7 @@ export function GeneratePlatonicSolid (genParams, type, radius)
|
||||
generator.AddVertex (vertex.x, vertex.y, vertex.z);
|
||||
}
|
||||
|
||||
if (IsZero (radius)) {
|
||||
if (!IsPositive (radius)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
83
test/testfiles/o3dv/all_shapes.o3dv
Normal file
83
test/testfiles/o3dv/all_shapes.o3dv
Normal file
@ -0,0 +1,83 @@
|
||||
{
|
||||
"root" : 0,
|
||||
"nodes" : [
|
||||
{
|
||||
"children" : [1, 2, 3, 4]
|
||||
},
|
||||
{
|
||||
"transformation" : {
|
||||
"translation" : [0.0, 0.0, 0.0]
|
||||
},
|
||||
"mesh" : 0
|
||||
},
|
||||
{
|
||||
"transformation" : {
|
||||
"translation" : [2.0, 0.0, 0.0]
|
||||
},
|
||||
"mesh" : 1
|
||||
},
|
||||
{
|
||||
"transformation" : {
|
||||
"translation" : [4.0, 0.0, 0.0]
|
||||
},
|
||||
"mesh" : 2
|
||||
},
|
||||
{
|
||||
"transformation" : {
|
||||
"translation" : [6.0, 0.0, 0.0]
|
||||
},
|
||||
"mesh" : 3
|
||||
}
|
||||
],
|
||||
"materials" : [
|
||||
{
|
||||
"name" : "Blue",
|
||||
"color" : [0, 0, 200]
|
||||
}
|
||||
],
|
||||
"meshes" : [
|
||||
{
|
||||
"name" : "Cube",
|
||||
"type" : "cuboid",
|
||||
"material" : 0,
|
||||
"parameters" : {
|
||||
"size_x" : 1.0,
|
||||
"size_y" : 1.0,
|
||||
"size_z" : 1.0
|
||||
}
|
||||
},
|
||||
{
|
||||
"name" : "Cylinder",
|
||||
"type" : "cylinder",
|
||||
"material" : 0,
|
||||
"parameters" : {
|
||||
"radius" : 0.5,
|
||||
"height" : 1.0,
|
||||
"segments" : 25,
|
||||
"smooth" : true
|
||||
}
|
||||
},
|
||||
{
|
||||
"name" : "Sphere",
|
||||
"type" : "sphere",
|
||||
"material" : 0,
|
||||
"parameters" : {
|
||||
"radius" : 0.5,
|
||||
"segments" : 25,
|
||||
"smooth" : true
|
||||
}
|
||||
},
|
||||
{
|
||||
"name" : "Cone",
|
||||
"type" : "cone",
|
||||
"material" : 0,
|
||||
"parameters" : {
|
||||
"top_radius" : 0.2,
|
||||
"bottom_radius" : 0.5,
|
||||
"height" : 1.0,
|
||||
"segments" : 25,
|
||||
"smooth" : true
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
@ -26,6 +26,24 @@ describe ('Generator', function () {
|
||||
assert.ok (OV.IsEqualEps (OV.CalculateVolume (cylinder), Math.PI * 0.5 * 0.5 * 1.0, 0.1));
|
||||
});
|
||||
|
||||
it ('Cone with Default Parameters', function () {
|
||||
const cone = OV.GenerateCone (null, 0.2, 0.5, 1.0, 20, false);
|
||||
assert.ok (OV.IsSolid (cone));
|
||||
assert.ok (OV.IsEqualEps (OV.CalculateVolume (cone), Math.PI / 3.0 * 1.0 * (0.2 * 0.2 + 0.2 * 0.5 + 0.5 * 0.5), 0.1));
|
||||
});
|
||||
|
||||
it ('Cone Zero Top', function () {
|
||||
const cone = OV.GenerateCone (null, 0.0, 0.5, 1.0, 20, false);
|
||||
assert.ok (OV.IsSolid (cone));
|
||||
assert.ok (OV.IsEqualEps (OV.CalculateVolume (cone), 0.5 * 0.5 * Math.PI * 1.0 / 3.0, 1.0));
|
||||
});
|
||||
|
||||
it ('Cone Zero Bottom', function () {
|
||||
const cone = OV.GenerateCone (null, 0.5, 0.0, 1.0, 20, false);
|
||||
assert.ok (OV.IsSolid (cone));
|
||||
assert.ok (OV.IsEqualEps (OV.CalculateVolume (cone), 0.5 * 0.5 * Math.PI * 1.0 / 3.0, 1.0));
|
||||
});
|
||||
|
||||
it ('Sphere with Default Parameters', function () {
|
||||
const cylinder = OV.GenerateSphere (null, 0.5, 20, false);
|
||||
assert.ok (OV.IsSolid (cylinder));
|
||||
|
||||
Loading…
Reference in New Issue
Block a user