use original vertexes when creating faces from edges

This commit is contained in:
Stewart Allen 2024-08-10 15:19:52 -04:00
commit 3226b7d2d7
3 changed files with 28 additions and 11 deletions

View file

@ -30,6 +30,19 @@ let geo, mat, obj = new Line2(
); );
// true if values differ by less than 10e-3
function cmp(v1, v2) {
return Math.abs(v1 - v2) < 0.001;
}
// points equal if all axis values are within tolerance of each other
function eq(p1, p2) {
return
cmp(p1.x, p2.x) &&
cmp(p1.y, p2.y) &&
cmp(p1.z, p2.z);
}
// split functions // split functions
let edges = { let edges = {
active() { active() {
@ -93,11 +106,11 @@ let edges = {
let model = selected[0].object.model; let model = selected[0].object.model;
let pos = new Vector3().fromArray(model.meta.pos); let pos = new Vector3().fromArray(model.meta.pos);
let verts = selected.map(s => [ s.side.p0, s.side.p1 ]).flat(); let verts = selected.map(s => [ s.side.p0, s.side.p1 ]).flat();
// clean up floating point cruft for comparison // translate into mesh space
for (let v of verts) { for (let v of verts) {
v.x = (v.x - pos.x).round(3); v.x = (v.x - pos.x);
v.y = (v.y - pos.z).round(3); v.y = (v.y - pos.z);
v.z = (v.z + pos.y).round(3); v.z = (v.z + pos.y);
} }
// sort points so dups show up next to each other // sort points so dups show up next to each other
let sort = verts.sort((a,b) => { let sort = verts.sort((a,b) => {
@ -109,10 +122,8 @@ let edges = {
return a.z - b.z; return a.z - b.z;
} }
}).filter((point, index, arr) => { }).filter((point, index, arr) => {
return index === 0 || // allow first point then compare others to one before
point.x !== arr[index - 1].x || return index === 0 || !eq(point, arr[index - 1]);
point.y !== arr[index - 1].y ||
point.z !== arr[index - 1].z;
}); });
if (sort.length === 3) { if (sort.length === 3) {
await model.duplicate({ append: [ await model.duplicate({ append: [

View file

@ -194,22 +194,22 @@ mesh.model = class MeshModel extends mesh.object {
} }
scale(x = 1, y = 1, z = 1) { scale(x = 1, y = 1, z = 1) {
this.log('model-scale', ...arguments, this.bounds);
if (x === 1 && y === 1 && z === 1) return; if (x === 1 && y === 1 && z === 1) return;
this.log('model-scale', ...arguments, this.bounds);
this.geometry.scale(x, y, z); this.geometry.scale(x, y, z);
this.updateBounds(); this.updateBounds();
} }
translate(x = 0, y = 0, z = 0) { translate(x = 0, y = 0, z = 0) {
this.log('model-translate', ...arguments);
if (!(x || y || z)) return; if (!(x || y || z)) return;
this.log('model-translate', ...arguments);
this.geometry.translate(x, y, z); this.geometry.translate(x, y, z);
this.updateBounds(); this.updateBounds();
} }
move(x = 0, y = 0, z = 0) { move(x = 0, y = 0, z = 0) {
this.log('model-move', ...arguments);
if (!(x || y || z)) return; if (!(x || y || z)) return;
this.log('model-move', ...arguments);
let pos = this.position(); let pos = this.position();
return this.position(pos.x + x, pos.y + y, pos.z + z); return this.position(pos.x + x, pos.y + y, pos.z + z);
} }
@ -253,6 +253,8 @@ mesh.model = class MeshModel extends mesh.object {
return this; return this;
} }
// when geometry updates, recompute bounds for ray intersections
// and sync data to worker and indexed db
updateBounds() { updateBounds() {
if (this._wire) if (this._wire)
this._wire.geometry.attributes.position.needsUpdate = true; this._wire.geometry.attributes.position.needsUpdate = true;
@ -398,6 +400,7 @@ mesh.model = class MeshModel extends mesh.object {
return this.select(); return this.select();
} }
// toggle whether this is a boolean subtraction tool or not
tool(bool) { tool(bool) {
if (bool === undefined) { if (bool === undefined) {
return this.mesh.material[0] === this.mats.tool; return this.mesh.material[0] === this.mats.tool;

View file

@ -77,6 +77,9 @@ let split = {
select() { select() {
let { log } = mesh.api; let { log } = mesh.api;
let { models, plane } = split.state; let { models, plane } = split.state;
if (!(models && plane)) {
return split.end();
}
log.emit(`splitting ${models.length} model(s) at ${plane.z.round(3)}`).pin(); log.emit(`splitting ${models.length} model(s) at ${plane.z.round(3)}`).pin();
Promise.all(models.map(m => m.split(plane))).then(models => { Promise.all(models.map(m => m.split(plane))).then(models => {
mesh.api.selection.set(models.filter(m => m)); mesh.api.selection.set(models.filter(m => m));