// =========================================================================== // 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. // =========================================================================== // // // Creation Date: 2004 // // // // // // bakeFluidShading resolutionFactor // // // None. // // // This mel procedure bakes the density and shading of selected fluid nodes. // For each node a new fluid is created that does not have textures or // self shadowing, yet which has the effect of textures and self shadowing // defined into its density and color arrays. In some respects it is like // rendering the fluid into a 3D volume, rather than into a 2d image. // The resolution factor determines the resolution of the resulting baked // fluids. For example a value of 2 will double the resolution of the original // fluid. In order to resolve textural details one may need fairly high resolutions // on the baked fluids. The original fluids are hidden after the operation. // // // None. // // // // bakeFluidShading 2.0; // // global proc bakeFluidToFluid( string $source, string $destination ) { // float $res[3] = getAttr($source + ".resolution"); float $res[3] = getAttr($destination + ".resolution"); int $is2d = getAttr($source + ".is2d"); int $destIs2d = getAttr($destination + ".is2d"); if( $is2d != $destIs2d ){ warning((uiRes("m_bakeFluidShading.kInvalidBakeTarget"))); return; } int $realLights = getAttr($source + ".realLights"); if( $realLights ){ setAttr ($source + ".realLights" ) false; } int $sourceVis = `getAttr ($source + ".visibility")`; int $destinationVis = `getAttr ($destination + ".visibility")`; setAttr ($source + ".visibility") false; setAttr ($destination + ".visibility") false; int $i,$j,$k; string $near = ($source + ".pointObj"); string $far = ($source + ".farPointObj"); string $outCol = ($source + ".outColor"); string $outTransp = ($source + ".outTransparency"); if( $is2d ){ float $voxelDepth = 1.0/$res[0]; if( $res[1] > $res[0] ){ $voxelDepth = 1.0/$res[1]; } setAttr ($source + ".filterSizeZ") $voxelDepth; float $pz = -0.95; // float $pz = 0; float $pzFar = 0.95; // float $pzFar = $voxelDepth * 0.05; for( $i = 0; $i < $res[0]; $i++ ){ float $px = ((float)$i + 0.5)/$res[0]; $px = $px * 2 - 1.0; for( $j = 0; $j < $res[1]; $j++ ){ float $py = ((float)$j + 0.5)/$res[1]; $py = $py * 2 - 1.0; setAttr $near $px $py $pz; setAttr $far $px $py $pzFar; float $color[3] = `getAttr $outCol`; float $transp[3] = `getAttr $outTransp`; float $opacity = 1.0 - $transp[0]; if( $opacity > 0.000001 ){ $color[0] /= $opacity; $color[1] /= $opacity; $color[2] /= $opacity; } setFluidAttr -at "density" -fv ($opacity) -xi $i -yi $j $destination; setFluidAttr -at "color" -vv ($color[0]) ($color[1]) ($color[2]) -xi $i -yi $j $destination; } } } else { float $voxelDepth = 1.0/$res[2]; setAttr ($source + ".filterSizeZ") $voxelDepth; for( $i = 0; $i < $res[0]; $i++ ){ float $px = ((float)$i + 0.5)/$res[0]; $px = $px * 2 - 1.0; for( $j = 0; $j < $res[1]; $j++ ){ float $py = ((float)$j + 0.5)/$res[1]; $py = $py * 2 - 1.0; for( $k = 0; $k < $res[2]; $k++ ){ float $pz = (float)$k /$res[2]; $pz = $pz * 2 - 1.0; float $pzFar = $pz + $voxelDepth; setAttr $near $px $py $pz; setAttr $far $px $py $pzFar; float $color[3] = `getAttr $outCol`; float $transp[3] = `getAttr $outTransp`; float $opacity = 1.0 - $transp[0]; if( $opacity > 0.000001 ){ $color[0] /= $opacity; $color[1] /= $opacity; $color[2] /= $opacity; } setFluidAttr -at "density" -fv ($opacity) -xi $i -yi $j -zi $k $destination; setFluidAttr -at "color" -vv ($color[0]) ($color[1]) ($color[2]) -xi $i -yi $j -zi $k $destination; } } } } setAttr ($destination + ".visibility") $destinationVis; setAttr ($source + ".visibility") $sourceVis; if( $realLights ){ setAttr ($source + ".realLights" ) true; } } global proc bakeFluidShading(float $resolutionFactor) { string $fluids[] = `ls -sl -dag -shapes -type fluid`; if( size( $fluids ) < 1 ){ warning((uiRes("m_bakeFluidShading.kNoFluidsSelected"))); return; } string $fluid; for( $fluid in $fluids ){ float $res[3] = getAttr($fluid + ".resolution"); float $dim[3] = getAttr($fluid + ".dimensions"); int $is2d = getAttr($fluid + ".is2d"); int $newX = $res[0] * $resolutionFactor; int $newY = $res[1] * $resolutionFactor; int $newZ = $res[2] * $resolutionFactor; if( $is2d ){ $newZ = 1; } int $numVoxels = $newX * $newY * $newZ; if( $numVoxels > 8000000 ){ warning((uiRes("m_bakeFluidShading.kResolutionTooHigh"))); return; } string $newFluid; if( $is2d ){ $newFluid = `create2DFluid $newX $newY $dim[0] $dim[1] $dim[2]`; } else { $newFluid = `create3DFluid $newX $newY $newZ $dim[0] $dim[1] $dim[2]`; } setAttr ($newFluid + ".velocityMethod") 0 ; setAttr ($newFluid + ".colorMethod") 1 ; setAttr ($newFluid + ".densityMethod") 1 ; setAttr ($newFluid + ".densityScale") 1.0 ; setAttr ($newFluid + ".realLights") false ; setAttr ($newFluid + ".renderInterpolator") 3; setAttr ($newFluid + ".dropoffShape") 0; string $tforms[] = `listTransforms $fluid`; string $newTforms[] = `listTransforms $newFluid`; if( size($tforms) < 1 || size( $newTforms ) < 1 ){ // should never happen but we are being cautious warning( (uiRes("m_bakeFluidShading.kMissingTransformErr"))); return; } parent -r $newTforms[0] $tforms[0]; if( $numVoxels > 10000 ){ string $fmt = (uiRes("m_bakeFluidShading.kBakeMsg")); warning(`format -s $fluid $fmt`); } waitCursor -state on; setAttr ($fluid + ".visibility") false; bakeFluidToFluid( $fluid, $newFluid ); waitCursor -state off; } print( "\n"); }