Skip to content

Commit

Permalink
Create unique morph target manager ids when loading content from .bab…
Browse files Browse the repository at this point in the history
…ylon file (#15668) (#15669)
  • Loading branch information
HoferMarkus authored Oct 3, 2024
1 parent 0d6c440 commit 9f9c73c
Show file tree
Hide file tree
Showing 4 changed files with 40 additions and 21 deletions.
54 changes: 36 additions & 18 deletions packages/dev/core/src/Loading/Plugins/babylonFileLoader.ts
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ export class BabylonFileLoaderConfiguration {

let tempIndexContainer: { [key: string]: Node } = {};
let tempMaterialIndexContainer: { [key: string]: Material } = {};
let tempMorphTargetManagerIndexContainer: { [key: string]: MorphTargetManager } = {};

const parseMaterialByPredicate = (predicate: (parsedMaterial: any) => boolean, parsedData: any, scene: Scene, rootUrl: string) => {
if (!parsedData.materials) {
Expand Down Expand Up @@ -318,8 +319,9 @@ const loadAssetContainer = (scene: Scene, data: string, rootUrl: string, onError

// Morph targets
if (parsedData.morphTargetManagers !== undefined && parsedData.morphTargetManagers !== null) {
for (const managerData of parsedData.morphTargetManagers) {
const manager = MorphTargetManager.Parse(managerData, scene);
for (const parsedManager of parsedData.morphTargetManagers) {
const manager = MorphTargetManager.Parse(parsedManager, scene);
tempMorphTargetManagerIndexContainer[parsedManager.id] = manager;
container.morphTargetManagers.push(manager);
manager._parentContainer = container;
}
Expand Down Expand Up @@ -493,6 +495,14 @@ const loadAssetContainer = (scene: Scene, data: string, rootUrl: string, onError
}
});

// link meshes with morph target managers
scene.meshes.forEach((mesh) => {
if (mesh._waitingMorphTargetManagerId !== null) {
mesh.morphTargetManager = tempMorphTargetManagerIndexContainer[mesh._waitingMorphTargetManagerId];
mesh._waitingMorphTargetManagerId = null;
}
});

// link skeleton transform nodes
for (index = 0, cache = scene.skeletons.length; index < cache; index++) {
const skeleton = scene.skeletons[index];
Expand Down Expand Up @@ -582,6 +592,7 @@ const loadAssetContainer = (scene: Scene, data: string, rootUrl: string, onError
} finally {
tempIndexContainer = {};
tempMaterialIndexContainer = {};
tempMorphTargetManagerIndexContainer = {};

if (!addToScene) {
container.removeAllFromScene();
Expand Down Expand Up @@ -649,7 +660,7 @@ SceneLoader.RegisterPlugin({
const loadedSkeletonsIds = [];
const loadedMaterialsIds: string[] = [];
const loadedMaterialsUniqueIds: string[] = [];
const loadedMorphTargetsIds = [];
const loadedMorphTargetManagerIds: number[] = [];
for (let index = 0, cache = parsedData.meshes.length; index < cache; index++) {
const parsedMesh = parsedData.meshes[index];

Expand Down Expand Up @@ -773,14 +784,15 @@ SceneLoader.RegisterPlugin({

// Morph targets ?
if (parsedMesh.morphTargetManagerId > -1 && parsedData.morphTargetManagers !== undefined && parsedData.morphTargetManagers !== null) {
const morphTargetAlreadyLoaded = loadedMorphTargetsIds.indexOf(parsedMesh.morphTargetManagerId) > -1;
if (!morphTargetAlreadyLoaded) {
for (let morphTargetIndex = 0, morphTargetCache = parsedData.morphTargetManagers.length; morphTargetIndex < morphTargetCache; morphTargetIndex++) {
const parsedMorphTarget = parsedData.morphTargetManagers[morphTargetIndex];
if (parsedMorphTarget.id === parsedMesh.morphTargetManagerId) {
const morphTarget = MorphTargetManager.Parse(parsedMorphTarget, scene);
loadedMorphTargetsIds.push(morphTarget.uniqueId);
log += "\nMorph target " + morphTarget.toString();
const morphTargetManagerAlreadyLoaded = loadedMorphTargetManagerIds.indexOf(parsedMesh.morphTargetManagerId) > -1;
if (!morphTargetManagerAlreadyLoaded) {
for (let morphTargetManagerIndex = 0; morphTargetManagerIndex < parsedData.morphTargetManagers.length; morphTargetManagerIndex++) {
const parsedManager = parsedData.morphTargetManagers[morphTargetManagerIndex];
if (parsedManager.id === parsedMesh.morphTargetManagerId) {
const morphTargetManager = MorphTargetManager.Parse(parsedManager, scene);
tempMorphTargetManagerIndexContainer[parsedManager.id] = morphTargetManager;
loadedMorphTargetManagerIds.push(parsedManager.id);
log += "\nMorph target manager" + morphTargetManager.toString();
}
}
}
Expand Down Expand Up @@ -810,6 +822,14 @@ SceneLoader.RegisterPlugin({
}
});

// link meshes with morph target managers
scene.meshes.forEach((mesh) => {
if (mesh._waitingMorphTargetManagerId !== null) {
mesh.morphTargetManager = tempMorphTargetManagerIndexContainer[mesh._waitingMorphTargetManagerId];
mesh._waitingMorphTargetManagerId = null;
}
});

// Connecting parents and lods
for (let index = 0, cache = scene.transformNodes.length; index < cache; index++) {
const transformNode = scene.transformNodes[index];
Expand Down Expand Up @@ -841,12 +861,6 @@ SceneLoader.RegisterPlugin({
currentMesh._waitingParentInstanceIndex = null;
}
currentMesh.parent = parentNode;
if (currentMesh.parent?.getClassName() === "TransformNode") {
const loadedTransformNodeIndex = loadedTransformNodes.indexOf(currentMesh.parent as TransformNode);
if (loadedTransformNodeIndex > -1) {
loadedTransformNodes.splice(loadedTransformNodeIndex, 1);
}
}
currentMesh._waitingParentId = null;
}
if (currentMesh._waitingData.lods) {
Expand All @@ -856,7 +870,10 @@ SceneLoader.RegisterPlugin({

// Remove unused transform nodes
for (const transformNode of loadedTransformNodes) {
transformNode.dispose();
const childMeshes = transformNode.getChildMeshes(false);
if (!childMeshes.length) {
transformNode.dispose();
}
}

// link skeleton transform nodes
Expand Down Expand Up @@ -922,6 +939,7 @@ SceneLoader.RegisterPlugin({
Logger.Log(logOperation("importMesh", parsedData ? parsedData.producer : "Unknown") + (SceneLoader.loggingLevel !== SceneLoader.MINIMAL_LOGGING ? log : ""));
}
tempMaterialIndexContainer = {};
tempMorphTargetManagerIndexContainer = {};
}

return false;
Expand Down
3 changes: 3 additions & 0 deletions packages/dev/core/src/Meshes/abstractMesh.ts
Original file line number Diff line number Diff line change
Expand Up @@ -328,6 +328,9 @@ export abstract class AbstractMesh extends TransformNode implements IDisposable,
/** @internal */
public _waitingMaterialId: Nullable<string> = null;

/** @internal */
public _waitingMorphTargetManagerId: Nullable<number> = null;

/**
* The culling strategy to use to check whether the mesh must be rendered or not.
* This value can be changed at any time and will be used on the next render mesh selection.
Expand Down
2 changes: 1 addition & 1 deletion packages/dev/core/src/Meshes/mesh.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4276,7 +4276,7 @@ export class Mesh extends AbstractMesh implements IGetSetVerticesData {

// Morph targets
if (parsedMesh.morphTargetManagerId > -1) {
mesh.morphTargetManager = scene.getMorphTargetManagerById(parsedMesh.morphTargetManagerId);
mesh._waitingMorphTargetManagerId = parsedMesh.morphTargetManagerId;
}

// Skeleton
Expand Down
2 changes: 0 additions & 2 deletions packages/dev/core/src/Morph/morphTargetManager.ts
Original file line number Diff line number Diff line change
Expand Up @@ -559,8 +559,6 @@ export class MorphTargetManager implements IDisposable {
public static Parse(serializationObject: any, scene: Scene): MorphTargetManager {
const result = new MorphTargetManager(scene);

result._uniqueId = serializationObject.id;

for (const targetData of serializationObject.targets) {
result.addTarget(MorphTarget.Parse(targetData, scene));
}
Expand Down

0 comments on commit 9f9c73c

Please sign in to comment.