mirror of
https://github.com/xibyte/jsketcher
synced 2025-12-21 16:05:44 +01:00
purdge old modeling commands.
This commit is contained in:
parent
dbceeaea99
commit
de8268abb5
40 changed files with 1 additions and 963 deletions
|
|
@ -58,7 +58,7 @@ export const ModelerWorkspace: WorkbenchConfig = {
|
|||
"SHELL_TOOL", "FILLET_TOOL", "SCALE_BODY","-",
|
||||
"MIRROR_BODY", "PATTERN_LINEAR", "PATTERN_RADIAL", "-",
|
||||
"CYLINDER", "BOX", "CONE", "SPHERE", "TORUS", "-",
|
||||
"HOLE_TOOL", "-", 'GET_VOLUME', "IMPORT_MODEL","DELETE_BODY"
|
||||
"HOLE_TOOL", "-", 'GET_VOLUME', "IMPORT_MODEL","DELETE_BODY",
|
||||
]
|
||||
},
|
||||
icon: GiCubes
|
||||
|
|
|
|||
|
|
@ -1,11 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../wizard/components/form/Form';
|
||||
import EntityList from '../wizard/components/form/EntityList';
|
||||
import Entity from '../wizard/components/form/Entity';
|
||||
|
||||
export default function BooleanWizard() {
|
||||
return <Group>
|
||||
<Entity name='operandA' label='operand A' />
|
||||
<Entity name='operandB' label='operand B' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
export default {
|
||||
operandA: {
|
||||
type: 'shell',
|
||||
markColor: 0xC9FFBC,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
operandB: {
|
||||
type: 'shell',
|
||||
markColor: 0xFFBEB4,
|
||||
initializeBySelection: 1
|
||||
}
|
||||
};
|
||||
|
|
@ -1,45 +0,0 @@
|
|||
import schema from './booleanOpSchema';
|
||||
import BooleanWizard from './BooleanWizard';
|
||||
|
||||
const run = type => (params, services) => {
|
||||
return services.craftEngine.boolean({
|
||||
type,
|
||||
operandsA: [services.cadRegistry.findShell(params.operandA)],
|
||||
operandsB: [services.cadRegistry.findShell(params.operandB)]
|
||||
});
|
||||
};
|
||||
|
||||
const paramsInfo = ({operandA, operandB}) => `(${operandA}, ${operandB})`;
|
||||
|
||||
export const intersectionOperation = {
|
||||
id: 'INTERSECTION',
|
||||
label: 'intersection',
|
||||
icon: 'img/cad/intersection',
|
||||
info: 'intersection operation on two shells',
|
||||
paramsInfo,
|
||||
form: BooleanWizard,
|
||||
schema,
|
||||
run: run('INTERSECTION'),
|
||||
};
|
||||
|
||||
export const subtractOperation = {
|
||||
id: 'SUBTRACT',
|
||||
label: 'subtract',
|
||||
icon: 'img/cad/subtract',
|
||||
info: 'subtract operation on two shells',
|
||||
paramsInfo,
|
||||
form: BooleanWizard,
|
||||
schema,
|
||||
run: run('SUBTRACT'),
|
||||
};
|
||||
|
||||
export const unionOperation = {
|
||||
id: 'UNION',
|
||||
label: 'union',
|
||||
icon: 'img/cad/union',
|
||||
info: 'union operation on two shells',
|
||||
paramsInfo,
|
||||
form: BooleanWizard,
|
||||
schema,
|
||||
run: run('UNION'),
|
||||
};
|
||||
|
|
@ -1,23 +0,0 @@
|
|||
import {roundValueForPresentation as r} from '../operationHelper';
|
||||
import form from './form';
|
||||
import {createPreviewGeomProvider} from './previewer';
|
||||
import {Cut} from './cutExtrude';
|
||||
import {requiresFaceSelection} from '../../actions/actionHelpers';
|
||||
import schema from './schema';
|
||||
import {onParamsUpdate} from './extrudeOperation';
|
||||
|
||||
export default {
|
||||
id: 'CUT',
|
||||
label: 'Cut',
|
||||
icon: 'img/cad/cut',
|
||||
info: 'makes a cut based on 2D sketch',
|
||||
paramsInfo: ({value}) => `(${r(value)})`,
|
||||
onParamsUpdate,
|
||||
previewGeomProvider: createPreviewGeomProvider(true),
|
||||
run: Cut,
|
||||
actionParams: {
|
||||
...requiresFaceSelection(1)
|
||||
},
|
||||
form: form('depth'),
|
||||
schema
|
||||
};
|
||||
|
|
@ -1,34 +0,0 @@
|
|||
import {roundValueForPresentation as r} from '../operationHelper';
|
||||
import {createPreviewGeomProvider} from './previewer';
|
||||
import {Extrude} from './cutExtrude';
|
||||
import {requiresFaceSelection} from '../../actions/actionHelpers';
|
||||
import form from './form';
|
||||
import schema from './schema';
|
||||
|
||||
export default {
|
||||
id: 'EXTRUDE',
|
||||
label: 'Extrude',
|
||||
icon: 'img/cad/extrude',
|
||||
info: 'extrudes 2D sketch',
|
||||
paramsInfo: ({value}) => `(${r(value)})`,
|
||||
onParamsUpdate,
|
||||
previewGeomProvider: createPreviewGeomProvider(false),
|
||||
run: Extrude,
|
||||
actionParams: {
|
||||
...requiresFaceSelection(1)
|
||||
},
|
||||
form: form('height'),
|
||||
schema
|
||||
};
|
||||
|
||||
const INVARIANT = ['datumAxisVector', 'edgeVector', 'sketchSegmentVector'];
|
||||
|
||||
export function onParamsUpdate(params, name, value) {
|
||||
if (INVARIANT.includes(name)) {
|
||||
INVARIANT.forEach(param => {
|
||||
if (param !== name) {
|
||||
delete params[param];
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
|
@ -1,21 +0,0 @@
|
|||
import React from 'react';
|
||||
import {CheckboxField, NumberField} from '../wizard/components/form/Fields';
|
||||
import {Group} from '../wizard/components/form/Form';
|
||||
import Entity from '../wizard/components/form/Entity';
|
||||
import {StackSection} from 'ui/components/controls/FormSection';
|
||||
|
||||
export default function (valueLabel) {
|
||||
return function PrismForm() {
|
||||
return <Group>
|
||||
<NumberField name='value' defaultValue={50} label={valueLabel}/>
|
||||
<NumberField name='prism' defaultValue={1} min={0} step={0.1} round={1}/>
|
||||
<Entity name='face'/>
|
||||
<StackSection title='vector'>
|
||||
<Entity label='datum axis' name='datumAxisVector' />
|
||||
<Entity label='edge' name='edgeVector' />
|
||||
<Entity label='sketch segment' name='sketchSegmentVector' />
|
||||
<CheckboxField name='flip'/>
|
||||
</StackSection>
|
||||
</Group>;
|
||||
};
|
||||
}
|
||||
|
|
@ -1,55 +0,0 @@
|
|||
|
||||
import {getEncloseDetails, resolveExtrudeVector} from './cutExtrude';
|
||||
import {curveTessParams} from "geom/impl/curve/curve-tess";
|
||||
import Vector from "math/vector";
|
||||
import {TriangulatePolygons} from "../../tess/triangulation";
|
||||
import {createMeshGeometry} from "scene/geoms";
|
||||
|
||||
|
||||
export function createPreviewGeomProvider(inversed) {
|
||||
|
||||
return function previewGeomProvider(params, services) {
|
||||
|
||||
const face = services.cadRegistry.findFace(params.face);
|
||||
if (!face || !face.sketch) return null;
|
||||
let sketch = face.sketch.fetchContours();
|
||||
let vector = resolveExtrudeVector(services.cadRegistry, face, params, !inversed);
|
||||
const encloseDetails = getEncloseDetails(params, sketch, vector, face.csys, face.surface, !inversed);
|
||||
const triangles = [];
|
||||
|
||||
for (let {basePath, lidPath, baseSurface, lidSurface} of encloseDetails) {
|
||||
const basePoints = [];
|
||||
const lidPoints = [];
|
||||
for (let i = 0; i < basePath.length; ++i) {
|
||||
let baseNurbs = basePath[i];
|
||||
let lidNurbs = lidPath[i];
|
||||
|
||||
let tessCurve = params.prism > 1 ? lidNurbs : baseNurbs;
|
||||
|
||||
const us = curveTessParams(tessCurve.impl, tessCurve.uMin, tessCurve.uMax);
|
||||
const base = us.map(u => baseNurbs.point(u));
|
||||
const lid = us.map(u => lidNurbs.point(u));
|
||||
const n = base.length;
|
||||
for (let p = n - 1, q = 0; q < n; p = q++) {
|
||||
triangles.push([base[p], base[q], lid[q]]);
|
||||
triangles.push([lid[q], lid[p], base[p]]);
|
||||
}
|
||||
for (let j = 0; j < base.length - 1; j++) {
|
||||
basePoints.push(base[j]);
|
||||
lidPoints.push(base[j]);
|
||||
}
|
||||
}
|
||||
|
||||
function collectOnSurface(points, normal) {
|
||||
TriangulatePolygons([points], normal, (v) => v.toArray(), (arr) => new Vector().set3(arr))
|
||||
.forEach(tr => triangles.push(tr));
|
||||
}
|
||||
|
||||
collectOnSurface(basePoints, baseSurface.normal);
|
||||
collectOnSurface(lidPoints, lidSurface.normal);
|
||||
}
|
||||
|
||||
return createMeshGeometry(triangles);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1,41 +0,0 @@
|
|||
export default {
|
||||
value: {
|
||||
type: 'number',
|
||||
defaultValue: 50
|
||||
},
|
||||
prism: {
|
||||
type: 'number',
|
||||
min: 0,
|
||||
defaultValue: 1
|
||||
},
|
||||
angle: {
|
||||
type: 'number',
|
||||
defaultValue: 0
|
||||
},
|
||||
rotation: {
|
||||
type: 'number',
|
||||
defaultValue: 0
|
||||
},
|
||||
face: {
|
||||
type: 'face',
|
||||
initializeBySelection: 0
|
||||
},
|
||||
datumAxisVector: {
|
||||
type: 'datumAxis',
|
||||
optional: true
|
||||
},
|
||||
edgeVector: {
|
||||
type: 'edge',
|
||||
optional: true,
|
||||
accept: edge => edge.brepEdge.curve.degree === 1
|
||||
},
|
||||
sketchSegmentVector: {
|
||||
type: 'sketchObject',
|
||||
optional: true,
|
||||
accept: obj => obj.isSegment
|
||||
},
|
||||
flip: {
|
||||
type: 'boolean',
|
||||
defaultValue: false,
|
||||
}
|
||||
}
|
||||
|
|
@ -1,11 +0,0 @@
|
|||
import React from 'react';
|
||||
import {NumberField} from '../wizard/components/form/Fields';
|
||||
import EntityList from '../wizard/components/form/EntityList';
|
||||
import {Group} from '../wizard/components/form/Form';
|
||||
|
||||
export default function FilletWizard() {
|
||||
return <Group>
|
||||
<EntityList name='edges' entity='edge' />
|
||||
<NumberField name='thickness' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
import FilletForm from './FilletForm';
|
||||
import schema from './schema';
|
||||
|
||||
export default {
|
||||
id: 'FILLET',
|
||||
label: 'Fillet',
|
||||
icon: 'img/cad/fillet',
|
||||
info: 'creates a fillet on selected edges',
|
||||
paramsInfo: ({edges}) => edges.map(o => o.thikness).join(' ,'),
|
||||
previewGeomProvider: () => new THREE.Geometry(),
|
||||
run: (request, ctx) => ctx.craftEngine.fillet(request),
|
||||
form: FilletForm,
|
||||
schema
|
||||
};
|
||||
|
||||
|
|
@ -1,21 +0,0 @@
|
|||
export default {
|
||||
edges: {
|
||||
type: 'array',
|
||||
itemType: ['edge', 'face'],
|
||||
|
||||
max: 1,
|
||||
initializeBySelection: true,
|
||||
ui: {
|
||||
|
||||
}
|
||||
},
|
||||
thickness: {
|
||||
type: 'number',
|
||||
defaultValue: 20,
|
||||
min: 10,
|
||||
max: 30,
|
||||
ui: {
|
||||
widget: 'slider'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../wizard/components/form/Form';
|
||||
import Entity from '../wizard/components/form/Entity';
|
||||
import BooleanChoice from '../wizard/components/form/BooleanChioce';
|
||||
|
||||
export default function LoftForm() {
|
||||
|
||||
return <Group>
|
||||
<Entity name='sections' entity='loop' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,24 +0,0 @@
|
|||
import schema from './schema';
|
||||
import {loftPreviewGeomProvider} from './loftPreviewer';
|
||||
import {assignBooleanParams} from '../primitives/booleanOptionHelper';
|
||||
import LoftForm from './LoftForm';
|
||||
|
||||
export default {
|
||||
id: 'LOFT',
|
||||
label: 'Loft',
|
||||
icon: 'img/cad/loft',
|
||||
info: 'creates a loft cross selected sections shape',
|
||||
paramsInfo: () => '',
|
||||
previewGeomProvider: loftPreviewGeomProvider,
|
||||
run: runLoft,
|
||||
form: LoftForm,
|
||||
schema
|
||||
};
|
||||
|
||||
|
||||
function runLoft(params, services) {
|
||||
return services.craftEngine.loft({
|
||||
sections: params.sections.map(services.cadRegistry.findLoop)
|
||||
});
|
||||
}
|
||||
|
||||
|
|
@ -1,10 +0,0 @@
|
|||
import {createSmoothMeshGeometryFromData} from 'scene/geoms';
|
||||
|
||||
export function loftPreviewGeomProvider(params, services) {
|
||||
|
||||
const tessInfo = services.craftEngine.loftPreview({
|
||||
sections: params.sections.map(services.cadRegistry.findLoop)
|
||||
});
|
||||
|
||||
return createSmoothMeshGeometryFromData(tessInfo);
|
||||
}
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
export default {
|
||||
sections: {
|
||||
type: 'array',
|
||||
itemType: 'loop',
|
||||
initializeBySelection: true,
|
||||
min: 2
|
||||
},
|
||||
boolean: {
|
||||
type: 'enum',
|
||||
values: ['INTERSECT', 'SUBTRACT', 'UNION'],
|
||||
defaultValue: 'UNION',
|
||||
optional: true
|
||||
}
|
||||
}
|
||||
|
|
@ -1,10 +0,0 @@
|
|||
|
||||
export function assignBooleanParams(execParams, rawParams, getAllShells) {
|
||||
if (rawParams.boolean) {
|
||||
execParams.boolean = {
|
||||
type: rawParams.boolean,
|
||||
operands: getAllShells()
|
||||
}
|
||||
}
|
||||
return execParams;
|
||||
}
|
||||
|
|
@ -1,5 +0,0 @@
|
|||
export default {
|
||||
type: 'enum',
|
||||
optional: true,
|
||||
values: ['INTERSECT', 'SUBTRACT', 'UNION']
|
||||
};
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../../wizard/components/form/Form';
|
||||
import {NumberField} from '../../wizard/components/form/Fields';
|
||||
import BooleanChoice from '../../wizard/components/form/BooleanChioce';
|
||||
import Entity from '../../wizard/components/form/Entity';
|
||||
|
||||
export default function BoxWizard() {
|
||||
return <Group>
|
||||
<Entity name='datum' placeholder='origin'/>
|
||||
<NumberField name='width' />
|
||||
<NumberField name='height' />
|
||||
<NumberField name='depth' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,25 +0,0 @@
|
|||
import booleanOptionSchema from '../booleanOptionSchema';
|
||||
|
||||
export default {
|
||||
datum: {
|
||||
type: 'datum',
|
||||
optional: true,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
width: {
|
||||
type: 'number',
|
||||
defaultValue: 500,
|
||||
min: 0
|
||||
},
|
||||
height: {
|
||||
type: 'number',
|
||||
defaultValue: 500,
|
||||
min: 0
|
||||
},
|
||||
depth: {
|
||||
type: 'number',
|
||||
defaultValue: 500,
|
||||
min: 0
|
||||
},
|
||||
boolean: booleanOptionSchema
|
||||
}
|
||||
|
|
@ -1,31 +0,0 @@
|
|||
import BoxWizard from './BoxWizard';
|
||||
import {BoxGeometry} from 'three';
|
||||
import schema from './boxOpSchema';
|
||||
import primitivePreviewer from '../primitivePreviewer';
|
||||
import datumConsumingOperation from '../datumConsumingOperation';
|
||||
import {assignBooleanParams} from '../booleanOptionHelper';
|
||||
|
||||
function run(params, services) {
|
||||
return datumConsumingOperation(params, services, csys => services.craftEngine.createBox(
|
||||
assignBooleanParams({
|
||||
csys,
|
||||
width: params.width,
|
||||
height: params.height,
|
||||
depth: params.depth
|
||||
}, params, services.cadRegistry.getAllShells)
|
||||
));
|
||||
}
|
||||
|
||||
export default {
|
||||
id: 'BOX',
|
||||
label: 'Box',
|
||||
icon: 'img/cad/cube',
|
||||
info: 'creates new object box',
|
||||
paramsInfo: ({width, height, depth}) => `(${width}, ${height}, ${depth})`,
|
||||
previewer: primitivePreviewer(() => new BoxGeometry(),
|
||||
({width: dx, height: dy, depth: dz}) => ({dx, dy, dz}), [0.5, 0.5, 0.5]),
|
||||
form: BoxWizard,
|
||||
schema,
|
||||
run
|
||||
};
|
||||
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../../wizard/components/form/Form';
|
||||
import {NumberField} from '../../wizard/components/form/Fields';
|
||||
import BooleanChoice from '../../wizard/components/form/BooleanChioce';
|
||||
import Entity from '../../wizard/components/form/Entity';
|
||||
|
||||
export default function TorusWizard() {
|
||||
return <Group>
|
||||
<Entity name='datum' placeholder='origin'/>
|
||||
<NumberField name='radius' />
|
||||
<NumberField name='frustum' />
|
||||
<NumberField name='height' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,25 +0,0 @@
|
|||
import booleanOptionSchema from '../booleanOptionSchema';
|
||||
|
||||
export default {
|
||||
datum: {
|
||||
type: 'datum',
|
||||
optional: true,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
radius: {
|
||||
type: 'number',
|
||||
defaultValue: 100,
|
||||
min: 0
|
||||
},
|
||||
frustum: {
|
||||
type: 'number',
|
||||
defaultValue: 0,
|
||||
min: 0
|
||||
},
|
||||
height: {
|
||||
type: 'number',
|
||||
defaultValue: 250,
|
||||
min: 0
|
||||
},
|
||||
boolean: booleanOptionSchema
|
||||
}
|
||||
|
|
@ -1,87 +0,0 @@
|
|||
import {Mesh, ConeGeometry, Matrix4, CylinderGeometry} from 'three';
|
||||
import schema from './coneOpSchema';
|
||||
import ConeWizard from './ConeWizard';
|
||||
import {IMAGINARY_SURFACE_MATERIAL} from '../../../preview/scenePreviewer';
|
||||
import CSys from 'math/csys';
|
||||
import * as SceneGraph from 'scene/sceneGraph';
|
||||
import datumConsumingOperation from '../datumConsumingOperation';
|
||||
import {assignBooleanParams} from '../booleanOptionHelper';
|
||||
|
||||
function run(params, services) {
|
||||
return datumConsumingOperation(params, services, csys => services.craftEngine.createCone(
|
||||
assignBooleanParams({
|
||||
csys,
|
||||
radius: params.radius,
|
||||
frustum: params.frustum,
|
||||
height: params.height
|
||||
}, params, services.cadRegistry.getAllShells)
|
||||
));
|
||||
}
|
||||
|
||||
function previewer(ctx, initialParams) {
|
||||
let mDatum = initialParams.datum && ctx.services.cadRegistry.findDatum(initialParams.datum);
|
||||
let cs = mDatum ? mDatum.csys : CSys.ORIGIN;
|
||||
let o = cs.origin;
|
||||
|
||||
let mesh = null;
|
||||
let auxMatrix = new Matrix4();
|
||||
|
||||
function update(params) {
|
||||
|
||||
dispose();
|
||||
|
||||
let geometry;
|
||||
if (params.frustum) {
|
||||
geometry = new CylinderGeometry(params.frustum, params.radius, params.height, 50, 1);
|
||||
} else {
|
||||
geometry = new ConeGeometry(params.radius, params.height, 50, 1)
|
||||
}
|
||||
|
||||
mesh = new Mesh(geometry, IMAGINARY_SURFACE_MATERIAL);
|
||||
mesh.matrixAutoUpdate = false;
|
||||
|
||||
mesh.matrix.set(
|
||||
cs.x.x, cs.y.x, cs.z.x, o.x,
|
||||
cs.x.y, cs.y.y, cs.z.y, o.y,
|
||||
cs.x.z, cs.y.z, cs.z.z, o.z,
|
||||
0, 0, 0, 1
|
||||
);
|
||||
auxMatrix.set(
|
||||
1, 0, 0, 0,
|
||||
0, 1, 0, params.height * 0.5,
|
||||
0, 0, 1, 0,
|
||||
0, 0, 0, 1
|
||||
);
|
||||
mesh.matrix.multiplyMatrices(mesh.matrix, auxMatrix);
|
||||
mesh.matrixWorldNeedsUpdate = true;
|
||||
|
||||
SceneGraph.addToGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
}
|
||||
|
||||
function dispose() {
|
||||
if (mesh !== null ) {
|
||||
SceneGraph.removeFromGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
mesh.geometry.dispose();
|
||||
mesh = null;
|
||||
}
|
||||
}
|
||||
|
||||
update(initialParams);
|
||||
|
||||
return {
|
||||
update, dispose
|
||||
}
|
||||
}
|
||||
|
||||
export default {
|
||||
id: 'CONE',
|
||||
label: 'Cone',
|
||||
icon: 'img/cad/cone',
|
||||
info: 'creates new cone',
|
||||
paramsInfo: ({radius, frustum, height}) => `(${radius}, ${frustum}, ${height})`,
|
||||
previewer,
|
||||
form: ConeWizard,
|
||||
schema,
|
||||
run
|
||||
};
|
||||
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../../wizard/components/form/Form';
|
||||
import {NumberField} from '../../wizard/components/form/Fields';
|
||||
import BooleanChoice from '../../wizard/components/form/BooleanChioce';
|
||||
import Entity from '../../wizard/components/form/Entity';
|
||||
|
||||
export default function CylinderWizard() {
|
||||
return <Group>
|
||||
<Entity name='datum' placeholder='origin'/>
|
||||
<NumberField name='radius' />
|
||||
<NumberField name='height' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
import booleanOptionSchema from '../booleanOptionSchema';
|
||||
|
||||
export default {
|
||||
datum: {
|
||||
type: 'datum',
|
||||
optional: true,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
radius: {
|
||||
type: 'number',
|
||||
defaultValue: 100,
|
||||
min: 0
|
||||
},
|
||||
height: {
|
||||
type: 'number',
|
||||
defaultValue: 250,
|
||||
min: 0
|
||||
},
|
||||
boolean: booleanOptionSchema
|
||||
}
|
||||
|
|
@ -1,30 +0,0 @@
|
|||
import {CylinderGeometry} from 'three';
|
||||
import schema from './cylinderOpSchema';
|
||||
import primitivePreviewer from '../primitivePreviewer';
|
||||
import CylinderWizard from './CylinderWizard';
|
||||
import datumConsumingOperation from '../datumConsumingOperation';
|
||||
import {assignBooleanParams} from '../booleanOptionHelper';
|
||||
|
||||
function run(params, services) {
|
||||
return datumConsumingOperation(params, services, csys => services.craftEngine.createCylinder(
|
||||
assignBooleanParams({
|
||||
csys,
|
||||
radius: params.radius,
|
||||
height: params.height
|
||||
}, params, services.cadRegistry.getAllShells)
|
||||
));
|
||||
}
|
||||
|
||||
export default {
|
||||
id: 'CYLINDER',
|
||||
label: 'Cylinder',
|
||||
icon: 'img/cad/cylinder',
|
||||
info: 'creates new cylinder',
|
||||
paramsInfo: ({radius, height}) => `(${radius}, ${height})`,
|
||||
previewer: primitivePreviewer(() => new CylinderGeometry(1, 1, 1, 50, 1),
|
||||
({radius: dx, height: dy, radius:dz}) => ({dx, dy, dz}), [0, 0.5, 0]),
|
||||
form: CylinderWizard,
|
||||
schema,
|
||||
run
|
||||
};
|
||||
|
||||
|
|
@ -1,10 +0,0 @@
|
|||
import CSys from 'math/csys';
|
||||
|
||||
export default function datumConsumingOperation(params, services, run) {
|
||||
let mDatum = params.datum && services.cadRegistry.findDatum(params.datum);
|
||||
let res = run(mDatum ? mDatum.csys : CSys.ORIGIN);
|
||||
if (mDatum) {
|
||||
res.consumed.push(mDatum);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
|
@ -1,53 +0,0 @@
|
|||
import {BoxGeometry, Matrix4, Mesh} from 'three';
|
||||
import {IMAGINARY_SURFACE_MATERIAL} from '../../preview/scenePreviewer';
|
||||
import CSys from 'math/csys';
|
||||
import * as SceneGraph from 'scene/sceneGraph';
|
||||
|
||||
export default function primitivePreviewer(createThreePrimitiveGeometry, paramsToScales, shift) {
|
||||
return function previewer(ctx, initialParams) {
|
||||
|
||||
let geometry = createThreePrimitiveGeometry();
|
||||
let mesh = new Mesh(geometry, IMAGINARY_SURFACE_MATERIAL);
|
||||
mesh.matrixAutoUpdate = false;
|
||||
SceneGraph.addToGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
|
||||
let auxMatrix = new Matrix4();
|
||||
|
||||
function update(params) {
|
||||
let mDatum = params.datum && ctx.services.cadRegistry.findDatum(params.datum);
|
||||
let cs = mDatum ? mDatum.csys : CSys.ORIGIN;
|
||||
let o = cs.origin;
|
||||
|
||||
let {dx, dy, dz} = paramsToScales(params);
|
||||
mesh.matrix.set(
|
||||
dx*cs.x.x, dy*cs.y.x, dz*cs.z.x, o.x,
|
||||
dx*cs.x.y, dy*cs.y.y, dz*cs.z.y, o.y,
|
||||
dx*cs.x.z, dy*cs.y.z, dz*cs.z.z, o.z,
|
||||
0, 0, 0, 1
|
||||
);
|
||||
|
||||
if (shift) {
|
||||
auxMatrix.set(
|
||||
1, 0, 0, shift[0],
|
||||
0, 1, 0, shift[1],
|
||||
0, 0, 1, shift[2],
|
||||
0, 0, 0, 1
|
||||
);
|
||||
mesh.matrix.multiplyMatrices(mesh.matrix, auxMatrix);
|
||||
}
|
||||
|
||||
mesh.matrixWorldNeedsUpdate = true
|
||||
}
|
||||
|
||||
function dispose() {
|
||||
SceneGraph.removeFromGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
geometry.dispose();
|
||||
}
|
||||
|
||||
update(initialParams);
|
||||
|
||||
return {
|
||||
update, dispose
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../../wizard/components/form/Form';
|
||||
import {NumberField} from '../../wizard/components/form/Fields';
|
||||
import BooleanChoice from '../../wizard/components/form/BooleanChioce';
|
||||
import Entity from '../../wizard/components/form/Entity';
|
||||
|
||||
export default function SphereWizard() {
|
||||
return <Group>
|
||||
<Entity name='datum' placeholder='origin'/>
|
||||
<NumberField name='radius' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
import booleanOptionSchema from '../booleanOptionSchema';
|
||||
|
||||
export default {
|
||||
datum: {
|
||||
type: 'datum',
|
||||
optional: true,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
radius: {
|
||||
type: 'number',
|
||||
defaultValue: 250,
|
||||
min: 0
|
||||
},
|
||||
boolean: booleanOptionSchema
|
||||
}
|
||||
|
|
@ -1,28 +0,0 @@
|
|||
import {SphereGeometry} from 'three';
|
||||
import schema from './sphereOpSchema';
|
||||
import primitivePreviewer from '../primitivePreviewer';
|
||||
import SphereWizard from './SphereWizard';
|
||||
import datumConsumingOperation from '../datumConsumingOperation';
|
||||
import {assignBooleanParams} from '../booleanOptionHelper';
|
||||
|
||||
function run(params, services) {
|
||||
return datumConsumingOperation(params, services, csys => services.craftEngine.createSphere(
|
||||
assignBooleanParams({
|
||||
csys,
|
||||
radius: params.radius,
|
||||
}, params, services.cadRegistry.getAllShells)
|
||||
));
|
||||
}
|
||||
|
||||
export default {
|
||||
id: 'SPHERE',
|
||||
label: 'Sphere',
|
||||
icon: 'img/cad/sphere',
|
||||
info: 'creates new sphere',
|
||||
paramsInfo: ({radius}) => `(${radius})`,
|
||||
previewer: primitivePreviewer(() => new SphereGeometry(1, 50, 50), ({radius: dx, radius: dy, radius: dz}) => ({dx, dy, dz})),
|
||||
form: SphereWizard,
|
||||
schema,
|
||||
run
|
||||
};
|
||||
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
import React from 'react';
|
||||
import {Group} from '../../wizard/components/form/Form';
|
||||
import {NumberField} from '../../wizard/components/form/Fields';
|
||||
import BooleanChoice from '../../wizard/components/form/BooleanChioce';
|
||||
import Entity from '../../wizard/components/form/Entity';
|
||||
|
||||
export default function TorusWizard() {
|
||||
return <Group>
|
||||
<Entity name='datum' placeholder='origin'/>
|
||||
<NumberField name='radius' />
|
||||
<NumberField name='tube' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
import booleanOptionSchema from '../booleanOptionSchema';
|
||||
|
||||
export default {
|
||||
datum: {
|
||||
type: 'datum',
|
||||
optional: true,
|
||||
initializeBySelection: 0
|
||||
},
|
||||
radius: {
|
||||
type: 'number',
|
||||
defaultValue: 250,
|
||||
min: 0
|
||||
},
|
||||
tube: {
|
||||
type: 'number',
|
||||
defaultValue: 50,
|
||||
min: 0
|
||||
},
|
||||
boolean: booleanOptionSchema
|
||||
}
|
||||
|
|
@ -1,72 +0,0 @@
|
|||
import {Mesh, TorusGeometry} from 'three';
|
||||
import schema from './torusOpSchema';
|
||||
import TorusWizard from './TorusWizard';
|
||||
import {IMAGINARY_SURFACE_MATERIAL} from '../../../preview/scenePreviewer';
|
||||
import CSys from 'math/csys';
|
||||
import * as SceneGraph from 'scene/sceneGraph';
|
||||
import datumConsumingOperation from '../datumConsumingOperation';
|
||||
import {assignBooleanParams} from '../booleanOptionHelper';
|
||||
|
||||
function run(params, services) {
|
||||
return datumConsumingOperation(params, services, csys => services.craftEngine.createTorus(
|
||||
assignBooleanParams({
|
||||
csys,
|
||||
radius: params.radius,
|
||||
tube: params.tube
|
||||
}, params, services.cadRegistry.getAllShells)
|
||||
));
|
||||
}
|
||||
|
||||
function previewer(ctx, initialParams) {
|
||||
let mDatum = initialParams.datum && ctx.services.cadRegistry.findDatum(initialParams.datum);
|
||||
let cs = mDatum ? mDatum.csys : CSys.ORIGIN;
|
||||
let o = cs.origin;
|
||||
|
||||
let mesh = null;
|
||||
|
||||
function update(params) {
|
||||
|
||||
dispose();
|
||||
|
||||
mesh = new Mesh(new TorusGeometry(params.radius, params.tube, 50, 50), IMAGINARY_SURFACE_MATERIAL);
|
||||
mesh.matrixAutoUpdate = false;
|
||||
|
||||
mesh.matrix.set(
|
||||
cs.x.x, cs.y.x, cs.z.x, o.x,
|
||||
cs.x.y, cs.y.y, cs.z.y, o.y,
|
||||
cs.x.z, cs.y.z, cs.z.z, o.z,
|
||||
0, 0, 0, 1
|
||||
);
|
||||
|
||||
mesh.matrixWorldNeedsUpdate = true;
|
||||
|
||||
SceneGraph.addToGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
}
|
||||
|
||||
function dispose() {
|
||||
if (mesh !== null ) {
|
||||
SceneGraph.removeFromGroup(ctx.services.cadScene.workGroup, mesh);
|
||||
mesh.geometry.dispose();
|
||||
mesh = null;
|
||||
}
|
||||
}
|
||||
|
||||
update(initialParams);
|
||||
|
||||
return {
|
||||
update, dispose
|
||||
}
|
||||
}
|
||||
|
||||
export default {
|
||||
id: 'TORUS',
|
||||
label: 'Torus',
|
||||
icon: 'img/cad/torus',
|
||||
info: 'creates new torus',
|
||||
paramsInfo: ({radius, tube}) => `(${radius} - ${tube})`,
|
||||
previewer,
|
||||
form: TorusWizard,
|
||||
schema,
|
||||
run
|
||||
};
|
||||
|
||||
|
|
@ -1,15 +0,0 @@
|
|||
import React from 'react';
|
||||
import {CheckboxField, NumberField} from '../wizard/components/form/Fields';
|
||||
import {Group} from '../wizard/components/form/Form';
|
||||
import Entity from '../wizard/components/form/Entity';
|
||||
import BooleanChoice from '../wizard/components/form/BooleanChioce';
|
||||
|
||||
export default function RevolveForm() {
|
||||
|
||||
return <Group>
|
||||
<NumberField name='angle' />
|
||||
<Entity name='face' entity='face' />
|
||||
<Entity name='axis' entity='sketchObject' />
|
||||
<BooleanChoice name='boolean' />
|
||||
</Group>;
|
||||
}
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
import RevolveForm from './RevolveForm';
|
||||
import schema from './schema';
|
||||
import {revolvePreviewGeomProvider} from './revolvePreviewer';
|
||||
|
||||
export default {
|
||||
id: 'REVOLVE',
|
||||
label: 'Revolve',
|
||||
icon: 'img/cad/revolve',
|
||||
info: 'creates a solid based on revolve surfaces',
|
||||
paramsInfo: ({angle}) => angle,
|
||||
previewGeomProvider: revolvePreviewGeomProvider,
|
||||
run: (request, ctx) => ctx.craftEngine.revolve(request),
|
||||
form: RevolveForm,
|
||||
schema
|
||||
};
|
||||
|
||||
|
||||
|
|
@ -1,36 +0,0 @@
|
|||
import {createMeshGeometry} from 'scene/geoms';
|
||||
import {DEG_RAD} from 'math/commons';
|
||||
import {revolveToTriangles} from '../../legacy/mesh/revolve';
|
||||
|
||||
let cache = {};
|
||||
|
||||
export function revolvePreviewGeomProvider(params, services) {
|
||||
|
||||
const face = services.cadRegistry.findFace(params.face);
|
||||
const axisModel = services.cadRegistry.findSketchObject(params.axis);
|
||||
const axis = axisModel.sketchPrimitive;
|
||||
if (!face || !face.sketch || !axis) return null;
|
||||
let contours = face.sketch.fetchContours();
|
||||
|
||||
let polygons = [];
|
||||
for (let contour of contours) {
|
||||
const curves = contour.transferInCoordinateSystem(face.csys);
|
||||
let polygon = [];
|
||||
for (let curve of curves) {
|
||||
let points = curve.tessellate();
|
||||
for (let i = 0; i < points.length - 1; i++) {
|
||||
polygon.push(points[i]);
|
||||
}
|
||||
}
|
||||
polygons.push(polygon);
|
||||
}
|
||||
|
||||
let angle = params.angle * DEG_RAD;
|
||||
let tr = face.csys.outTransformation.apply;
|
||||
const triangles = revolveToTriangles(polygons, [tr(axis.a), tr(axis.b)], angle, defaultResolution(params.angle), true);
|
||||
return createMeshGeometry(triangles);
|
||||
}
|
||||
|
||||
function defaultResolution(angle) {
|
||||
return Math.max(2, Math.round(Math.abs(angle) / 4.0));
|
||||
}
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
export default {
|
||||
angle: {
|
||||
type: 'number',
|
||||
defaultValue: 45
|
||||
},
|
||||
face: {
|
||||
type: 'face',
|
||||
initializeBySelection: 0
|
||||
},
|
||||
axis: {
|
||||
type: 'sketchObject',
|
||||
initializeBySelection: 0
|
||||
},
|
||||
boolean: {
|
||||
type: 'enum',
|
||||
values: ['INTERSECT', 'SUBTRACT', 'UNION'],
|
||||
defaultValue: 'UNION',
|
||||
optional: true
|
||||
}
|
||||
}
|
||||
|
|
@ -1,20 +1,10 @@
|
|||
import {WorkbenchRegistry} from "workbenches/registry";
|
||||
import planeOperation from "cad/craft/primitives/simplePlane/simplePlaneOperation";
|
||||
import boxOperation from "cad/craft/primitives/box/boxOperation";
|
||||
import cutOperation from "cad/craft/cutExtrude/cutOperation";
|
||||
import revolveOperation from "cad/craft/revolve/revolveOperation";
|
||||
import filletOperation from "cad/craft/fillet/filletOperation";
|
||||
import createDatumOperation from "cad/craft/datum/create/createDatumOperation";
|
||||
import moveDatumOperation from "cad/craft/datum/move/moveDatumOperation";
|
||||
import rotateDatumOperation from "cad/craft/datum/rotate/rotateDatumOperation";
|
||||
import datumOperation from "cad/craft/primitives/plane/planeOperation";
|
||||
import sphereOperation from "cad/craft/primitives/sphere/sphereOperation";
|
||||
import cylinderOperation from "cad/craft/primitives/cylinder/cylinderOperation";
|
||||
import torusOperation from "cad/craft/primitives/torus/torusOperation";
|
||||
import coneOperation from "cad/craft/primitives/cone/coneOperation";
|
||||
import spatialCurveOperation from "cad/craft/spatialCurve/spatialCurveOperation";
|
||||
import loftOperation from "cad/craft/loft/loftOperation";
|
||||
import {intersectionOperation, subtractOperation, unionOperation} from "cad/craft/boolean/booleanOperation";
|
||||
import {Plugin} from "plugable/pluginSystem";
|
||||
import {WorkbenchService} from "cad/workbench/workbenchService";
|
||||
import {OperationService} from "cad/craft/operationPlugin";
|
||||
|
|
@ -45,23 +35,10 @@ function registerCoreOperations(ctx: WorkbenchesLoaderInputContext) {
|
|||
|
||||
ctx.operationService.registerOperations([
|
||||
planeOperation,
|
||||
// boxOperation,
|
||||
// extrudeOperation,
|
||||
// cutOperation,
|
||||
revolveOperation,
|
||||
filletOperation,
|
||||
createDatumOperation,
|
||||
moveDatumOperation,
|
||||
rotateDatumOperation,
|
||||
datumOperation,
|
||||
// sphereOperation,
|
||||
// cylinderOperation,
|
||||
// torusOperation,
|
||||
// coneOperation,
|
||||
spatialCurveOperation,
|
||||
loftOperation,
|
||||
intersectionOperation,
|
||||
subtractOperation,
|
||||
unionOperation,
|
||||
] as any);
|
||||
}
|
||||
Loading…
Reference in a new issue