stub in ungrouping, add analysis step

This commit is contained in:
Stewart Allen 2022-01-11 14:41:49 -05:00
commit 9f73e6e3c3
5 changed files with 83 additions and 30 deletions

View file

@ -79,7 +79,7 @@ function restore_space() {
let count = 0;
let space = moto.Space;
let parray = [];
let mcache;
let mcache = {};
mesh.db.admin.get("camera")
.then(saved => {
if (saved) {
@ -158,7 +158,7 @@ function space_init(data) {
case 'KeyD':
if (shiftKey) {
for (let m of selection.models()) {
m.debug();
m.duplicate();
}
}
break;
@ -182,6 +182,8 @@ function space_init(data) {
return selection.boundsBox({toggle:true});
case 'KeyH':
return space.view.home();
case 'KeyA':
return api.tool.analyze();
case 'KeyR':
return api.tool.repair();
case 'KeyT':

View file

@ -258,7 +258,13 @@ let file = {
let tool = {
analyze() {
console.log('...analyze todo');
api.log.emit('analyzing mesh(es)...').pin();
for (let m of selection.models()) {
worker.model_analyze(m.id).then(data => {
console.log({data});
api.log.emit('analysis complete').unpin();
});
}
},
repair() {

View file

@ -79,14 +79,14 @@ mesh.model = class MeshModel extends mesh.object {
return this.mesh.matrixWorld.elements;
}
debug() {
worker.model_debug({
// return new group containing just this model in world coordinates
duplicate() {
worker.model_duplicate({
matrix: this.matrix,
id: this.id
}).then(data => {
// for debugging matrix ops
return mesh.api.group.new([new mesh.model({
file: `synth-${this.name}`,
file: `${this.file}-dup`,
mesh: data
})]);
});
@ -101,12 +101,6 @@ mesh.model = class MeshModel extends mesh.object {
meh.receiveShadow = true;
meh.castShadow = true;
meh.renderOrder = 1;
// center vertices then restore mesh object position
// still this doesn't work. scale broken for bounding boxes
let { mid } = meh.getBoundingBox();
geo.moveMesh(-mid.x, -mid.y, -mid.z);
geo.computeBoundingBox();
this.move(mid.x, mid.y, mid.z);
// sets fallback opacity for wireframe toggle
this.opacity(1);
// this ref allows clicks to be traced to models and groups
@ -116,7 +110,7 @@ mesh.model = class MeshModel extends mesh.object {
}
reload(vertices, indices, normals) {
this.wireframe(false);
let was = this.wireframe(false);
let geo = this.mesh.geometry;
geo.setAttribute('position', new THREE.BufferAttribute(vertices, 3));
geo.setAttribute('normal', undefined);
@ -125,6 +119,8 @@ mesh.model = class MeshModel extends mesh.object {
if (!normals) geo.computeVertexNormals();
// sync data to worker
worker.model_load({id: this.id, name: this.name, vertices, indices});
// restore wireframe state
this.wireframe(was);
}
get group() {
@ -150,6 +146,19 @@ mesh.model = class MeshModel extends mesh.object {
return this.vertices / 3;
}
// todo -- put model into its own group
ungroup() {
// get current world coordinates
let { mid } = meh.getBoundingBox();
// transform mesh into world coordinates
// move mesh to origin
// create and add to group
// move group center back to original center
geo.moveMesh(-mid.x, -mid.y, -mid.z);
geo.computeBoundingBox();
this.move(mid.x, mid.y, mid.z);
}
visible(bool) {
if (bool === undefined) {
return this.mesh.visible;
@ -204,6 +213,7 @@ mesh.model = class MeshModel extends mesh.object {
if (bool.toggle) {
return this.wireframe(this._wire ? false : true, opt);
}
let was = this._wire ? true : false;
if (this._wire) {
this.mesh.remove(this._wire);
this._wire = undefined;
@ -215,6 +225,7 @@ mesh.model = class MeshModel extends mesh.object {
this.opacity({temp: opt.opacity || 0});
}
space.update();
return was;
}
remove() {

View file

@ -113,7 +113,7 @@ mesh.tool = class MeshTool {
* construct ordered line maps with array of connected edges.
* connect lines into polys. earcut polys into new faces.
*/
heal() {
heal(opt = { merge: true }) {
let vertices = this.vertices;
let faces = this.faces;
let hash = {}; // key to line map
@ -314,6 +314,7 @@ mesh.tool = class MeshTool {
// rotate/flatten to Z plane and use earcut to generate faces
// because earcut emits point indexes, no need to un-rotate
function emitLoop(loop) {
let faces = [];
let lastPoint;
let pindex = [];
let points = [];
@ -371,17 +372,33 @@ mesh.tool = class MeshTool {
for (let point of ec) {
faces.push(pindex[point]);
}
// newly generated faces
return faces;
}
// emit loops
let faceCount = this.faces.length;
// create area faces covering loops
let areas = this.areas = [];
for (let loop of loops) {
emitLoop(loop);
this.areas.push(emitLoop(loop));
}
// track newly created faces when loop areas are merged
let faceCount = this.faces.length;
if (opt.merge) {
this.merge();
}
this.newFaces = this.faces.length - faceCount;
return this;
}
// merge poly areas into faces
merge() {
for (let area of this.areas || []) {
this.faces.appendAll(area);
}
}
};
})();

View file

@ -38,6 +38,20 @@ function translate_encode(id, matrix) {
return geo.attributes.position.array;
}
function analyze(id) {
log(`${id} | indexing...`);
let geo = cache[id].geo;
let tool = new mesh.tool({
vertices: geo.attributes.position.array,
faces: geo.index ? geo.index.array : undefined,
debug: false
});
log(`${id} | analyzing...`);
tool.heal();
dbug.log(tool);
return tool;
}
let model = {
load(data) {
let { vertices, indices, name, id } = data;
@ -47,7 +61,8 @@ let model = {
cacheUpdate(id, { name, geo, matrix: core_matrix.clone() });
},
debug(data) {
// return new vertices in world coordinates
duplicate(data) {
let { id, matrix } = data;
return translate_encode(id, matrix);
throw "should not here";
@ -55,21 +70,23 @@ let model = {
let geo = rec.geo.clone();
let m4 = core_matrix.clone().multiply( new THREE.Matrix4().fromArray(matrix) );
geo.applyMatrix4(m4);
// for debugging state / matrix ops
return geo.attributes.position.array;
},
analyze(id) {
let tool = analyze(id);
let { stats, newFaces } = tool;
let { cull, dups, faces } = stats;
log(`${id} | face count=${faces} bad=${cull} dup=${dups}`);
log(`${id} | open loops=${tool.loops.length} edges=${tool.edges.length}`);
return {
new: newFaces
};
},
heal(id) {
log(`${id} | indexing...`);
let geo = cache[id].geo;
let tool = new mesh.tool({
vertices: geo.attributes.position.array,
faces: geo.index ? geo.index.array : undefined,
debug: false
});
log(`${id} | healing...`);
tool.heal();
dbug.log(tool);
let tool = analyze(id);
log(`${id} | unrolling...`);
return true || tool.newFaces ? {
vertices: tool.unrolled().toFloat32(),
} : 0;