written by Nathan 'jesterKing' Letwory
TLDR; the generated script is here.
In this script we'll retarget all image texture paths to a new path. We'll
iterate over all RenderMaterial
s and find all the image based textures.
To actually change the file paths we need to use the SetParameter
method on
each texture we find.
In this script you'll see how to:
rhinoscriptsyntax
to browse for a folderGetParameter
in conjunction with System.Convert
SetParameter
to change values on RenderContent
BeginChange
and EndChange
We will handle all RenderContent
that are image-based. Since a
RenderContent
, including RenderTexture
s can have child content we need to
recurse through the entire ancestry to ensure we handle all cases.
We start by asking for the first child content of the given RenderContent
. It
will be an instance of some RenderContent
if there is anything, otherwise
None
. For each child content we handle we'll recurse, then when back we make
the change and finally ask for the next sibling.
To make the change we first get the current filename of the child
RenderContent
. We need to use the GetParameter
method to retrieve the value.
There is one important issue to take note of: GetParameter
returns values as
object
s. These implement the IConvertible
interface. To get to the actual
data we need to somehow convert this. A straight cast is not possible, but we
can use the Convert
mechanism. We know we need a string so we can use
System.Convert.ToString
.
For changes to stick on RenderContent
in Rhino we need to bracket them between
proper BeginChange
and EndChange
calls on the content. For BeginChange
we
give the Program
change context, since we are changing the data through the
script.
def handle_render_content(render_content, target):
child = render_content.FirstChild
while child:
handle_render_content(child, target)
if child.IsImageBased():
child.BeginChange(Rhino.Render.RenderContent.ChangeContexts.Program)
source_path = System.Convert.ToString(child.GetParameter("filename"))
source_file = os.path.basename(source_path)
child.SetParameter("filename", target + os.sep + source_file)
child.EndChange()
child = child.NextSibling
To iterate over all the RenderMaterial
s available in our document we iterate over the RhinoDoc
table called RenderMaterials
:
for render_material in scriptcontext.doc.RenderMaterials:
<<handle render content>>
handle_render_content(render_material, target)
target = rhinoscriptsyntax.BrowseForFolder()
Since we need to use GetParameter
on a RenderContent
it is important that we
convert the data we get to the correct data type. GetParameter
returns an
object
that implements the IConvertible
interface. We can't directly cast
from this object, instead we have to use the Convert
mechanism. For this we
import the System.Convert
.
For the folder choose dialog we import rhinoscriptsyntax
, and to access the
RenderMaterial
table of the document we import scriptcontext
.
import os
import rhinoscriptsyntax
import scriptcontext
import Rhino.Render
import System.Convert
<<method to handle render content>>
<<ask for target path>>
<<iterate over all rendermaterials>>
And that's that.