Skip to content

Commit

Permalink
Add support for hatching materials
Browse files Browse the repository at this point in the history
  • Loading branch information
ijlal99 committed Sep 10, 2024
1 parent 793532f commit 56dd443
Show file tree
Hide file tree
Showing 5 changed files with 73 additions and 15 deletions.
42 changes: 42 additions & 0 deletions examples/slicing/SectionCapsPlugin.html
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,14 @@ <h3>Components Used</h3>
id: "redLeg",
meshIds: ["redLegMesh"],
isObject: true,
capMaterial: new MetallicMaterial(viewer.scene, {
baseColor: [1, 0, 0],
backfaces: true,
baseColorMap: new Texture(viewer.scene, {
src: "../../assets/models/obj/fireHydrant/fire_hydrant_Base_Color.png",
encoding: "sRGB"
}),
})
});

sceneModel.createMesh({
Expand All @@ -106,6 +114,14 @@ <h3>Components Used</h3>
id: "greenLeg",
meshIds: ["greenLegMesh"],
isObject: true,
capMaterial: new MetallicMaterial(viewer.scene, {
baseColor: [0, 1, 0],
backfaces: true,
baseColorMap: new Texture(viewer.scene, {
src: "../../assets/models/obj/fireHydrant/fire_hydrant_Base_Color.png",
encoding: "sRGB"
}),
})
});

sceneModel.createMesh({
Expand All @@ -121,6 +137,14 @@ <h3>Components Used</h3>
id: "blueLeg",
meshIds: ["blueLegMesh"],
isObject: true,
capMaterial: new MetallicMaterial(viewer.scene, {
baseColor: [0, 0, 1],
backfaces: true,
baseColorMap: new Texture(viewer.scene, {
src: "../../assets/models/obj/fireHydrant/fire_hydrant_Base_Color.png",
encoding: "sRGB"
}),
})
});

sceneModel.createMesh({
Expand All @@ -136,6 +160,14 @@ <h3>Components Used</h3>
id: "yellowLeg",
meshIds: ["yellowLegMesh"],
isObject: true,
capMaterial: new MetallicMaterial(viewer.scene, {
baseColor: [1, 0, 1],
backfaces: true,
baseColorMap: new Texture(viewer.scene, {
src: "../../assets/models/obj/fireHydrant/fire_hydrant_Base_Color.png",
encoding: "sRGB"
}),
})
});

sceneModel.createMesh({
Expand All @@ -151,6 +183,16 @@ <h3>Components Used</h3>
id: "purpleTableTop",
meshIds: ["purpleTableTopMesh"],
isObject: true,
capMaterial: new MetallicMaterial(viewer.scene, {
baseColor: [1,1,1],
metallic: 1.0,
roughness: 1.0,
backfaces: true,
baseColorMap: new Texture(viewer.scene, {
src: "../../assets/models/obj/fireHydrant/fire_hydrant_Base_Color.png",
encoding: "sRGB"
}),
})
});

sceneModel.finalize();
Expand Down
26 changes: 14 additions & 12 deletions src/plugins/SectionCapsPlugin/SectionCapsPlugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ import { Plugin } from "../../viewer/Plugin.js";
import { math } from "../../viewer/scene/math/math.js";
import { Mesh } from "../../viewer/scene/mesh/Mesh.js";
import { ReadableGeometry } from "../../viewer/scene/geometry/ReadableGeometry.js";
import { PhongMaterial } from "../../viewer/scene/materials/PhongMaterial.js";
import CSG from "../lib/csg.js";

class SectionCapsPlugin extends Plugin {
Expand Down Expand Up @@ -113,11 +112,14 @@ class SectionCapsPlugin extends Plugin {

this._deletePreviousModels();

const csgGeometries = this._convertWebglGeometriesToCsgGeometries(sceneModel);
const { csgGeometries, materials } = this._convertWebglGeometriesToCsgGeometries(sceneModel);

if (Object.keys(materials).length <= 0) return;


const csgPlane = this._createCSGPlane(plane);
let caps = this._getCapGeometries(csgGeometries, csgPlane);
this._addIntersectedGeometries(caps);
this._addIntersectedGeometries(caps, materials);
}

//#region main callers
Expand All @@ -133,14 +135,17 @@ class SectionCapsPlugin extends Plugin {

_convertWebglGeometriesToCsgGeometries(sceneModels) {
let csgGeometries = {};
let materials = {};
sceneModels.forEach((sceneModel) => {
const objects = {};
for (const key in sceneModel.objects) {

const object = sceneModel.objects[key];
const isSolid = object.meshes[0].layer.solid !== false;
if (isSolid && object.opacity >= this._opacityThreshold)
if (isSolid && object.opacity >= this._opacityThreshold && object.capMaterial) {
objects[key] = sceneModel.objects[key];
materials[key] = sceneModel.objects[key].capMaterial;
}
}

let cloneModel = {
Expand All @@ -156,7 +161,7 @@ class SectionCapsPlugin extends Plugin {
}
})

return csgGeometries;
return { csgGeometries, materials };
}

_getVerticesAndIndices(sceneModel) {
Expand Down Expand Up @@ -288,10 +293,10 @@ class SectionCapsPlugin extends Plugin {
return cappedGeometries;
}

_addIntersectedGeometries(csgGometries) {
_addIntersectedGeometries(csgGometries, materials) {
for (const key in csgGometries) {
const webglGeometry = this._csgToWebGLGeometry(csgGometries[key]);
const model = this._addGeometryToScene(webglGeometry.vertices, webglGeometry.indices, key);
const model = this._addGeometryToScene(webglGeometry.vertices, webglGeometry.indices, key, materials[key]);
if (model)
this._prevIntersectionModels[key] = model;
}
Expand Down Expand Up @@ -399,7 +404,7 @@ class SectionCapsPlugin extends Plugin {
return { vertices: new Float32Array(vertices), indices: new Uint16Array(indices) };
}

_addGeometryToScene(vertices, indices, id) {
_addGeometryToScene(vertices, indices, id, material) {
if (vertices.length <= 0 && indices.length <= 0) return;
const intersectedModel = new Mesh(this.viewer.scene, {
id,
Expand All @@ -410,10 +415,7 @@ class SectionCapsPlugin extends Plugin {
}),
position: [0, 0, 0],
rotation: [0, 0, 0],
material: new PhongMaterial(this.viewer.scene, {
diffuse: [1, 0, 0],
backfaces: true,
}),
material,
})

return intersectedModel;
Expand Down
2 changes: 1 addition & 1 deletion src/plugins/SectionCapsPlugin/index.js
Original file line number Diff line number Diff line change
@@ -1 +1 @@
export * from "./SectionCapsPlugin";
export * from "./SectionCapsPlugin.js";
5 changes: 4 additions & 1 deletion src/viewer/scene/model/SceneModel.js
Original file line number Diff line number Diff line change
Expand Up @@ -3450,6 +3450,7 @@ export class SceneModel extends Component {
* @param {Boolean} [cfg.highlighted=false] Indicates if the SceneModelEntity is initially highlighted. Highlighted appearance is configured by {@link SceneModel#highlightMaterial}.
* @param {Boolean} [cfg.selected=false] Indicates if the SceneModelEntity is initially selected. Selected appearance is configured by {@link SceneModel#selectedMaterial}.
* @param {Boolean} [cfg.edges=false] Indicates if the SceneModelEntity's edges are initially emphasized. Edges appearance is configured by {@link SceneModel#edgeMaterial}.
* @param {Material} [cfg.capMaterial=null] Material that will be used if user slices and caps this entity
* @returns {SceneModelEntity} The new SceneModelEntity.
*/
createEntity(cfg) {
Expand Down Expand Up @@ -3518,7 +3519,9 @@ export class SceneModel extends Component {
cfg.id,
meshes,
cfg.flags,
lodCullable); // Internally sets SceneModelEntity#parent to this SceneModel
lodCullable,
cfg.capMaterial
); // Internally sets SceneModelEntity#parent to this SceneModel
this._entityList.push(entity);
this._entities[cfg.id] = entity;
this._entitiesToFinalize.push(entity);
Expand Down
13 changes: 12 additions & 1 deletion src/viewer/scene/model/SceneModelEntity.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ export class SceneModelEntity {
/**
* @private
*/
constructor(model, isObject, id, meshes, flags, lodCullable) {
constructor(model, isObject, id, meshes, flags, lodCullable, capMaterial) {

this._isObject = isObject;

Expand All @@ -43,6 +43,7 @@ export class SceneModelEntity {
this.meshes = meshes;

this._numPrimitives = 0;
this._capMaterial = null;

for (let i = 0, len = this.meshes.length; i < len; i++) { // TODO: tidier way? Refactor?
const mesh = this.meshes[i];
Expand Down Expand Up @@ -73,6 +74,7 @@ export class SceneModelEntity {
this._culled = false;
this._culledVFC = false;
this._culledLOD = false;
this.capMaterial = capMaterial;

if (this._isObject) {
model.scene._registerObject(this);
Expand Down Expand Up @@ -644,6 +646,15 @@ export class SceneModelEntity {
return this.model.saoEnabled;
}

set capMaterial(value) {
if (((value instanceof Material) || value === null) && value !== this._capMaterial)
this._capMaterial = value;
}

get capMaterial() {
return this._capMaterial;
}

getEachVertex(callback) {
for (let i = 0, len = this.meshes.length; i < len; i++) {
this.meshes[i].getEachVertex(callback)
Expand Down

0 comments on commit 56dd443

Please sign in to comment.