aboutsummaryrefslogtreecommitdiff
path: root/scripts/shaveRenderman.mel
diff options
context:
space:
mode:
authorBen Marsh <[email protected]>2019-10-22 09:07:59 -0400
committerBen Marsh <[email protected]>2019-10-22 09:07:59 -0400
commitbd0027e737c6512397f841c22786274ed74b927f (patch)
treef7ffbdb8f3741bb7f24635616cc189cba5cb865c /scripts/shaveRenderman.mel
downloadshave-and-a-haircut-bd0027e737c6512397f841c22786274ed74b927f.tar.xz
shave-and-a-haircut-bd0027e737c6512397f841c22786274ed74b927f.zip
Adding Shave-and-a-Haircut 9.6
Diffstat (limited to 'scripts/shaveRenderman.mel')
-rw-r--r--scripts/shaveRenderman.mel528
1 files changed, 528 insertions, 0 deletions
diff --git a/scripts/shaveRenderman.mel b/scripts/shaveRenderman.mel
new file mode 100644
index 0000000..192ea29
--- /dev/null
+++ b/scripts/shaveRenderman.mel
@@ -0,0 +1,528 @@
+// Shave and a Haircut
+// (c) 2019 Epic Games
+// US Patent 6720962
+
+global string $shaveRenderman_fileVersion = "$Revision$";
+
+
+// WARNING: The rman plugin may not be loaded when this script gets
+// sourced so all references to commands from that plugin
+// (e.g. 'rman', 'rmanGetGlobals', 'RiReadArchive') must be
+// executed within an 'eval' otherwise the results will be
+// unpredictable.
+
+global int $gShave_rmanPluginIsLoaded = false;
+global int $gShave_rmanWaitingForPlugin = false;
+global string $gShave_rmanArchiveFiles[];
+
+
+// Local Procedures
+
+// We need this because all of Maya's native string search commands take
+// some kind of pattern and we don't want any "special chars" in our
+// search.
+proc int strIndex(string $needle, string $haystack)
+{
+ int $needleLen = size($needle);
+ int $haystackLen = size($haystack);
+ int $i;
+
+ for ($i = 1; $i <= ($haystackLen - $needleLen) + 1; $i++)
+ {
+ if (substring($haystack, $i, $i + $needleLen - 1) == $needle)
+ return $i;
+ }
+
+ return 0;
+}
+
+
+proc string getRManGlobals()
+{
+ string $globals = "";
+
+ if (exists("rmanGetGlobals")) {
+ $globals = rmanGetGlobals();
+ }
+
+ return $globals;
+}
+
+
+// Returns the version of RenderMan for Maya as a float.
+//
+proc float getRfMVersion()
+{
+ float $version = 0.0;
+
+ if (`pluginInfo -q -loaded RenderMan_for_Maya`) {
+ string $versionStr = eval("rman getversion");
+
+ // The version string will be of the form "5.5 (@1457856 Mar 16 2015)".
+ // We want just the version number part.
+ //
+ $version = float(match("^[0-9.]+", $versionStr));
+ }
+
+ return $version;
+}
+
+
+// Returns the version of Renderman as a float.
+//
+// NOTE: As of RenderMan Studio 18 the RMS version is the same as the
+// Renderman version.
+//
+proc float getRManVersion()
+{
+ float $version = 0.0;
+
+ if (`pluginInfo -q -loaded RenderMan_for_Maya`) {
+ string $versionStr = eval("rman getversion prman");
+
+ // The version string will be of the form "prman 19.0 @1457856".
+ // We want just the version number part.
+ //
+ $version = float(match("[0-9.]+", $versionStr));
+ }
+
+ return $version;
+}
+
+
+proc addShaderPath()
+{
+ // Our SLIM shader sits in the 'prman/shaders' directory beneath the
+ // same directory as our plugin was loaded from. Update RenderMan's shader
+ // path to include this directory.
+ //
+ string $pluginDir = dirname(`pluginInfo -q -path shaveNode`);
+ RiOption("searchpath", "string shader", $pluginDir + "/prman/shaders:&");
+
+ // Our Bxdf lies in the 'prman/RMSnn' directory beneath the same
+ // directory as our plugin was loaded from, where 'nn' is the
+ // version of the RMS plugin currently loaded into Maya. Update
+ // RenderMan's rixplugin path to include this directory.
+ //
+ int $rmsVersion = int(getRManVersion());
+
+ if ($rmsVersion >= 19) {
+ RiOption("searchpath", "string rixplugin", $pluginDir + "/prman/RMS" + $rmsVersion + ":&:@");
+ }
+}
+
+
+proc removeCallback(string $node, string $attr, string $callback)
+{
+ if (objExists($node) && `attributeExists $attr $node`)
+ {
+ string $val = getAttr($node + "." + $attr);
+
+ // The callback might be one command buried in a string of
+ // semi-colon separate commands. So let's strip out all the
+ // possible permutations.
+ $val = substitute((";[ \t]*" + $callback + "[ \t]*"), $val, "");
+ $val = substitute(("[ \t]*" + $callback + "[ \t]*;"), $val, "");
+ $val = substitute(("[ \t]*" + $callback + "[ \t]*"), $val, "");
+
+ setAttr -type "string" ($node + "." + $attr) $val;
+ }
+}
+
+
+proc addCallback(string $node, string $attr, string $callback)
+{
+ if (objExists($node) && `attributeExists $attr $node`)
+ {
+ // Make sure that we're not creating multiple entries for the same
+ // callback by first removing any existing ones.
+ removeCallback($node, $attr, $callback);
+
+ string $val = getAttr($node + "." + $attr);
+
+ if (($val == "") || (size(`match "^[ \t]*$" $val`) > 0))
+ $val = $callback;
+ else
+ $val += "; " + $callback;
+
+ setAttr -type "string" ($node + "." + $attr) $val;
+ }
+ else
+ warning("Shave: can not add callback, attribute not found.");
+}
+
+
+proc waitForPlugin()
+{
+ global int $gShave_rmanWaitingForPlugin;
+
+ if (!$gShave_rmanWaitingForPlugin)
+ {
+ pluginInfo -cc shave_rmanCheckNewPlugin;
+ $gShave_rmanWaitingForPlugin = true;
+ }
+}
+
+
+// Global procedures
+global proc shave_rmanInit()
+{
+ // we do not want to set callbacks in defaultRenderGlobals when loading renderman plugin - dub|22Jun2012
+ // not clear why its handled diffent way then for other renderers
+ //shave_rmanSetupCallbacks();
+}
+
+global proc shave_rmanCleanup()
+{
+ //aslo we want to let these get saved with the scene - dub|22Jun2012
+ // not clear why its handled diffent way then for other renderers
+ //shave_rmanRemoveCallbacks();
+}
+
+
+global proc shave_rmanSetupCallbacks()
+{
+ //print "tryint to set renderMan callbacks\n";
+
+ // If there's no shaveGlobals node yet then there can't be any hair in
+ // the scene so there's no reason to set up callbacks yet.
+
+ //no we can not do this cut off because render will fail with this steps:
+ //set renderer to prman, create hair, render
+ //if (!objExists("shaveGlobals"))
+ //{
+ // //warning("Shave: shaveGlobals not found ");
+ // return;
+ //}
+
+ // If the rman plugin isn't loaded yet, we'll need to wait for it.
+ if (!shave_rmanPluginIsLoaded())
+ {
+ waitForPlugin();
+ //warning("Shave: renderMan is not loaded.");
+ return;
+ }
+
+ string $globals = getRManGlobals();
+
+ if ($globals == "")
+ {
+ warning("Shave: renderMan globals not found. Giving up.");
+ return;
+ }
+
+ addCallback(
+ $globals,
+ "rman__torattr___renderBeginScript",
+ "shave_rmanRenderStart"
+ );
+
+ addCallback(
+// $globals,
+ "defaultRenderGlobals",
+// "rman__torattr___preRenderScript",
+ "preRenderMel",
+ "shave_rmanFrameStart"
+ );
+
+ // RMS 19 and onward use an external prman instance which runs as a
+ // separate process. As a result all of the 'Post * MEL' scripts fire
+ // before the render has completed, making them basically useless.
+ //
+ // At the moment all that we do post render is to delete temp files
+ // generated for that render. We can instead do that using system
+ // commands injected into the rman stream.
+ //
+ if (getRManVersion() >= 19) {
+ addCallback(
+ $globals,
+ "rman__torattr___preRenderScript",
+ "shave_rmanSetOptions"
+ );
+
+ addCallback(
+ $globals,
+ "rman__torattr___postRenderScript",
+ "shave_rmanInjectCleanup"
+ );
+ } else {
+ addCallback(
+ "defaultRenderGlobals",
+ "postRenderMel",
+ "shave_rmanFrameEnd"
+ );
+ }
+
+ addCallback(
+ $globals,
+ "rman__torattr___postTransformScript",
+ "shave_rmanInsertArchive"
+ );
+
+ //print "done.\n";
+}
+
+
+global proc shave_rmanRemoveCallbacks()
+{
+ //print "renderMan callbacks removed\n";
+
+ string $globals = getRManGlobals();
+
+ removeCallback(
+ $globals,
+ "rman__torattr___renderBeginScript",
+ "shave_rmanRenderStart"
+ );
+
+ removeCallback(
+// $globals,
+ "defaultRenderGlobals",
+// "rman__torattr___preRenderScript",
+ "preRenderMel",
+ "shave_rmanFrameStart"
+ );
+
+ if (getRManVersion() >= 19) {
+ addCallback(
+ $globals,
+ "rman__torattr___preRenderScript",
+ "shave_rmanSetOptions"
+ );
+
+ removeCallback(
+ $globals,
+ "rman__torattr___postRenderScript",
+ "shave_rmanInjectCleanup"
+ );
+ } else {
+ removeCallback(
+ "defaultRenderGlobals",
+ "postRenderMel",
+ "shave_rmanFrameEnd"
+ );
+ }
+
+ removeCallback(
+ $globals,
+ "rman__torattr___postTransformScript",
+ "shave_rmanInsertArchive"
+ );
+}
+
+
+global proc shave_rmanRenderStart()
+{
+ global int $gShave_rmanArchiveInserted;
+ $gShave_rmanArchiveInserted = false;
+}
+
+
+global proc shave_rmanSetOptions()
+{
+ addShaderPath();
+}
+
+
+global proc string shave_rmanFrameStart()
+{
+ ///////////////// dumps //////////////
+ /*
+ string $globals = getRManGlobals();
+
+ $mob =`getAttr ($globals + ".rman__torattr___motionBlur")`;
+ print "prman: Motion Blur:"; print $mob; print "\n";
+
+ $cab =`getAttr ($globals + ".rman__torattr___cameraBlur")`;
+ print "prman: Motion Blur:"; print $cab; print "\n";
+
+
+ $a =`getAttr ($globals + ".rman__toropt___shutterAngle")`;
+ print "prman: Sutter Angle:"; print $a; print "\n";
+
+ $o =`getAttr ($globals + ".rman__riopt__Camera_shutteropening0")`;
+ print "prman: Sutter Open:"; print $o; print "\n";
+
+
+ $c =`getAttr ($globals + ".rman__riopt__Camera_shutteropening1")`;
+ print "prman: Sutter Close:"; print $c; print "\n";
+
+
+ $t =`getAttr ($globals + ".rman__toropt___shutterTiming")`;
+ print "prman: Sutter Timing:"; print $t; print "\n";
+
+
+ $k =`getAttr ($globals + ".rman__toropt___motionBlurType")`;
+ print "prman: Blur Type:"; print $k; print "\n";
+ */
+ //////////////////////////////////////
+
+ global string $gShave_rmanArchiveFiles[];
+
+ float $frame = `currentTime -q`;
+ string $dir = shaveGetTempDir();
+ string $ribFile = `shaveUtil -makeTempFileName $dir "shave" ("." + $frame + ".rib")`;
+
+ $gShave_rmanArchiveFiles = `shaveWriteRib -fullPaths $ribFile`;
+
+ if (size($gShave_rmanArchiveFiles) == 0) return "";
+
+ return $gShave_rmanArchiveFiles[0];
+}
+
+
+global proc shave_rmanFrameEnd()
+{
+ global string $gShave_rmanArchiveFiles[];
+
+ if (objExists("shaveGlobals") && !getAttr("shaveGlobals.ribKeepRibFiles"))
+ {
+ string $file;
+
+ for ($file in $gShave_rmanArchiveFiles)
+ sysFile -del $file;
+ }
+
+ clear $gShave_rmanArchiveFiles;
+}
+
+
+// We no longer need this but some people have it embedded in their
+// renderManGlobals now so we keep it around to prevent errors.
+global proc shave_rmanRenderEnd()
+{
+}
+
+
+global proc string shave_rmanGetReadArchiveCmd()
+{
+ global string $gShave_rmanArchiveFiles[];
+
+ if (size($gShave_rmanArchiveFiles) > 0)
+ return ("ReadArchive \"" + $gShave_rmanArchiveFiles[0] + "\"");
+
+ return "";
+}
+
+
+global proc shave_rmanInsertArchive()
+{
+ global int $gShave_rmanArchiveInserted;
+
+ if (!$gShave_rmanArchiveInserted) {
+ global string $gShave_rmanArchiveFiles[];
+
+ // We need to insert our archive under a suitable transform node.
+ // Shave's group node would be fine for that, however we cannot
+ // guarantee that it will be named 'shaveDisplayGroup': the user may
+ // have renamed it or it may be prefaced by a namespace if loaded from
+ // a reference.
+ //
+ // Instead we'll use the group of the first hairnode to get rendered.
+ //
+ string $groups[] = shave_getDisplayGroups();
+ string $group;
+ string $curObj = eval("rman ctxGetObject");
+
+ for ($group in $groups) {
+ if ($curObj == $group) {
+ // If there are multiple files the first one is the base file
+ // which includes all the others. So we always just want to
+ // emit the first one into the RIB stream.
+ //
+ if (size($gShave_rmanArchiveFiles) > 0)
+ {
+ eval("RiReadArchive(\"" + $gShave_rmanArchiveFiles[0] + "\")");
+ }
+
+ $gShave_rmanArchiveInserted = true;
+ break;
+ }
+ }
+ }
+}
+
+
+global proc shave_rmanInjectCleanup()
+{
+ global string $gShave_rmanArchiveFiles[];
+
+ if (objExists("shaveGlobals") && !getAttr("shaveGlobals.ribKeepRibFiles"))
+ {
+ string $file;
+
+ for ($file in $gShave_rmanArchiveFiles) {
+ if (`about -win`) {
+ // Convert the file path to a Windows-friendly form.
+ //
+ $file = toNativePath($file);
+
+ // All backslashes in the path must be escaped so that they
+ // don't get misinterpreted by rman's 'System' command.
+ //
+ $file = substituteAllString($file, "\\", "\\\\");
+
+ string $cmd = "System \"cmd.exe /x /a /c del \\\"" + $file + "\\\"\"";
+ RiArchiveRecord("verbatim", $cmd);
+ } else {
+ string $cmd = "System \"rm \\\"" + $file + "\\\"\"";
+ RiArchiveRecord("verbatim", $cmd);
+ }
+ }
+ }
+
+ clear $gShave_rmanArchiveFiles;
+}
+
+
+global proc int shave_rmanPluginIsLoaded()
+{
+ if (`pluginInfo -q -loaded RenderMan_for_Maya`)
+ {
+ // Only the 'Pro' version supports RIB insertion so make sure that
+ // this is Pro.
+// string $version = `pluginInfo -q -version RenderMan_for_Maya`;
+
+// return endsWith($version, "Pro");
+ string $isProVersion = eval("exists(\"RiAttribute\")");
+
+ return $isProVersion;
+ }
+
+ return false;
+}
+
+
+global proc shave_rmanCheckNewPlugin()
+{
+ print "shave_rmanCheckNewPlugin\n";
+
+ // There's no way to remove a pluginInfo callback if Shave is unloaded
+ // so let's first make sure that Shave is still loaded.
+ if (`pluginInfo -q -loaded shaveNode`)
+ {
+ //print "plugInfo - OK\n";
+
+ global int $gShave_rmanPluginIsLoaded;
+
+ // Is the rman plugin loaded?
+ if (shave_rmanPluginIsLoaded())
+ {
+ //print "rmanPluginIsLoaded - OK\n";
+
+ // If it wasn't loaded before then do our rman initialization.
+ if (!$gShave_rmanPluginIsLoaded)
+ {
+ //print "gShave_rmanPluginIsLoaded - OK\n";
+
+ $gShave_rmanPluginIsLoaded = true;
+ shave_rmanInit();
+ }
+ }
+ else
+ {
+ $gShave_rmanPluginIsLoaded = false;
+ }
+ }
+}
+