From dc5daec640ae304e242f6a20e3fd92ab257c0baa Mon Sep 17 00:00:00 2001 From: Brian Zinn Date: Fri, 23 Oct 2020 12:27:28 -0700 Subject: [PATCH] allow 'assignTo' to be assigned to multiple properties. --- src/CreatedInstance.ts | 2 +- src/customHosts/MaterialsLifecycleListener.ts | 17 +----- src/helper/property.ts | 59 ++++++++++--------- 3 files changed, 34 insertions(+), 44 deletions(-) diff --git a/src/CreatedInstance.ts b/src/CreatedInstance.ts index fd89c09c..ce464881 100644 --- a/src/CreatedInstance.ts +++ b/src/CreatedInstance.ts @@ -62,7 +62,7 @@ export type CustomProps = { /** * Assign to this property on the parent. Parent property is cleared on umnount. */ - assignTo?: string + assignTo?: string | string[] /** * for VRExperienceHelper */ diff --git a/src/customHosts/MaterialsLifecycleListener.ts b/src/customHosts/MaterialsLifecycleListener.ts index 24d1ed64..5c6c725c 100644 --- a/src/customHosts/MaterialsLifecycleListener.ts +++ b/src/customHosts/MaterialsLifecycleListener.ts @@ -2,6 +2,7 @@ import { CreatedInstance } from "../CreatedInstance" import { LifecycleListener } from "../LifecycleListener" import { Scene, AbstractMesh } from "@babylonjs/core" import { Material } from '@babylonjs/core/Materials' +import { assignProperty } from "../helper/property" export default class MaterialsLifecycleListener implements LifecycleListener { onCreated(instance: CreatedInstance, scene: Scene) { @@ -49,21 +50,7 @@ export default class MaterialsLifecycleListener implements LifecycleListener { - if (propToAssign[prop] === undefined) { - // create property if it doesn't exist. - console.warn('Assign to created property', prop, 'on', propToAssign) - propToAssign[prop] = {} - } - - if (index === propsList.length - 1) { - propToAssign[prop] = material; - } else { - propToAssign = propToAssign[prop] - } - }) + assignProperty(material, tmp.hostInstance, instance.customProps.assignTo); } else { tmp.hostInstance.material = material } diff --git a/src/helper/property.ts b/src/helper/property.ts index be799249..af2b5662 100644 --- a/src/helper/property.ts +++ b/src/helper/property.ts @@ -6,40 +6,43 @@ * @param propertyPath Where to assign value to on target (path to assign. ie: "baseTexture" or "mesh.material") * */ -export function assignProperty(value: any, target: any, propertyPath: string) { - const propsList: string[] = propertyPath.split('.'); +export function assignProperty(value: any, target: any, propertyPath: string | string[]) { + const propertyPaths: string[] = Array.isArray(propertyPath) ? propertyPath : [propertyPath]; + propertyPaths.forEach(propPath => { + const propsList: string[] = propPath.split('.'); - propsList.forEach((prop: string, index: number) => { - // for assigning to arrays (ie: Texture to model -> meshes[1].material.albedoTexture) - const arrayRegex = /(?.*)\[(?\d+)\]$/; - const match = prop.match(arrayRegex); + propsList.forEach((prop: string, index: number) => { + // for assigning to arrays (ie: Texture to model -> meshes[1].material.albedoTexture) + const arrayRegex = /(?.*)\[(?\d+)\]$/; + const match = prop.match(arrayRegex); - if (match && (match as any).groups) { - const { arrayName, arrayIndexString} = (match as any).groups; - const arrayIndex = parseInt(arrayIndexString); - const arrayProp = target[arrayName]; - if (arrayProp === undefined || !Array.isArray(arrayProp) || arrayIndex >= arrayProp.length ) { - console.error(`Array not found or missing index (skipping) for property assignment: '${arrayName}[${arrayIndex}]'`, target); + if (match && (match as any).groups) { + const { arrayName, arrayIndexString} = (match as any).groups; + const arrayIndex = parseInt(arrayIndexString); + const arrayProp = target[arrayName]; + if (arrayProp === undefined || !Array.isArray(arrayProp) || arrayIndex >= arrayProp.length ) { + console.error(`Array not found or missing index (skipping) for property assignment: '${arrayName}[${arrayIndex}]'`, target); + } else { + if (index === propsList.length - 1) { + arrayProp[arrayIndex] = value; + } else { + target = arrayProp[arrayIndex]; + } + } } else { + if (target[prop] === undefined) { + // create property if it doesn't exist. + console.warn(`Created property ${prop} on: (from ${propsList})`, target) + target[prop] = {} + } + if (index === propsList.length - 1) { - arrayProp[arrayIndex] = value; + target[prop] = value; } else { - target = arrayProp[arrayIndex]; + target = target[prop] } } - } else { - if (target[prop] === undefined) { - // create property if it doesn't exist. - console.warn(`Created property ${prop} on: (from ${propsList})`, target) - target[prop] = {} - } - - if (index === propsList.length - 1) { - target[prop] = value; - } else { - target = target[prop] - } - } - }) + }) + }); }