// =========================================================================== // Copyright 2018 Autodesk, Inc. All rights reserved. // // Use of this software is subject to the terms of the Autodesk license // agreement provided at the time of installation or download, or which // otherwise accompanies this software in either electronic or hard copy form. // =========================================================================== // setupAnimatedDisplacement // This mel command allows one to convert to poly a displacement map that has animation. // It sets up an expression that calls displacement to poly each frame. This expression // preserves a persistent mesh, using the result of the displacement to poly command as history // to this persistent mesh, allowing it to be used for things like collisions. // TODO?? a corresponding delete routine to restore the original setup and displacement (could be a scriptnode+callback on delete) // TODO?? allow creation of lower resolution displacement mesh for things like collision? (rendered displacement would then be left with intermediate object off) // TODO?? allow for global disable of update of all animated displacement meshes? global proc setupAnimatedDisplacement() { if(`about -batch`){ // not sure this is needed, but it could be that "hypershade -assign" below has problems in batch warning( (uiRes("m_setupAnimatedDisplacement.kNoBatchWarn"))); } string $sl[] = `ls -sl -dag -ni -type mesh -type nurbsSurface`; int $numSel =size($sl); if( $numSel < 1 ){ warning( (uiRes("m_setupAnimatedDisplacement.kSelectObjWarn")) ); return; } string $obj; string $newObjs[]; int $numNewObjs = 0; for( $obj in $sl ){ // find shading group for object string $shadCons[] = `listConnections -d 1 -sh 1 -type "shadingEngine" ($obj + ".instObjGroups[0]")`; if( size( $shadCons ) < 1 ){ continue; } // find input connection to displacement material on shader group string $shadOutDisp = ($shadCons[0] + ".displacementShader"); string $displacementConnection = `connectionInfo -sfd $shadOutDisp`; if( size( $displacementConnection ) < 1 ){ // check for ocean shader? // warning obj x has no displacement map? continue; } // for now force feature based displacement off for stability setAttr ( $obj + ".featureDisplacement") false; // convert original to displacement select -r $obj; displacementToPoly; string $disp[] = `ls -sl -dag -type mesh`; if( size( $disp ) < 1 ){ // warning? continue; } string $baseName= ($obj+"Displacement#"); // create a new mesh string $newMesh = `createNode "mesh" -name $baseName`; $newObjs[$numNewObjs] = $newMesh; $numNewObjs++; // Parent??? Only if convert to poly is in local space // duplicate shader assignments from original object hyperShade -assign $shadCons[0]; // newMesh should be currently selected // add attribute on new mesh to allow disabling of updates for faster playback addAttr -ln "disableDisplacementUpdates" -sn "ddup" -at bool $newMesh; setAttr -e-keyable true ($newMesh+".disableDisplacementUpdates"); // make original an intermediate object setAttr ( $obj + ".intermediateObject") true; // make the displaced surface input history to new mesh connectAttr -f ($disp[0] + ".outMesh") ($newMesh + ".inMesh"); setAttr ($disp[0] + ".intermediateObject") true; // break connection to displacement material so the new mesh does not get a double displacement // HOW to handle break for Ocean Shader????? disconnectAttr $displacementConnection $shadOutDisp; string $newMeshTform[] =`listTransforms $newMesh`; // setup expression to manage calling displacementToPoly and replacing input history to the persistent output mesh // Do a dummy reference of the displacement connection to cause expression to update when displacement changes string $exp = ("if(!"+$newMesh+".disableDisplacementUpdates){\n" +" updateAnimatedDisplacement( \""+$obj+"\",\""+$newMesh+"\",\""+$displacementConnection+"\");\n" +"}\n" +"\/\/Setting the following attribute here dirties the mesh so Mental Ray updates properly\n" +$newMesh+".featureDisplacement = 0;\n" +"\/\/The next two lines cause the expression to trigger when editing attributes that affect the displacement\n" +"float $dummy = "+$displacementConnection+";\n" +($newMeshTform[0])+".inheritsTransform = true;\n" ); /* string $exp = ("float $dummy = "+$displacementConnection+";\n" +"if(!"+$newMesh+".disableDisplacementUpdates){\n" +" string $obj = \""+$obj+"\";\n" +" string $mesh = \""+$newMesh+"\";\n" +" string $oldSel[] = `ls -sl`;\n" +" connectAttr "+$displacementConnection+" "+$shadOutDisp+";\n" +" setAttr ($obj + \".intermediateObject\") false;\n" +" select -r $obj;\n" +" displacementToPoly;\n" +" string $newDisp[] = `ls -sl -dag -type mesh`;\n" +" setAttr ($obj + \".intermediateObject\") true;\n" +" string $oldDisp[] = `listConnections ($mesh + \".inMesh\")`;\n" +" disconnectAttr "+$displacementConnection+" "+$shadOutDisp+";\n" +" connectAttr -f ($newDisp[0] + \".outMesh\") ($mesh + \".inMesh\");\n" +" setAttr ($newDisp[0] + \".intermediateObject\") true;\n" +" delete $oldDisp[0];\n" +" select -r $oldSel;\n" +"}\n" ); */ expression -s $exp; // We could potentially disable frame change updates of the expression so that it doesn't rebuild when the texture doesn't change. } // replace current selection with all new output meshes if( $numNewObjs > 0 ){ select -r $newObjs; } }