Getting a list of all shaders in a render tree

Here’s a Python snippet that gets all the shaders in the render tree for a specific material. As usual, I always feel that my Python snippet could be made more pythonic; for now, this will have to do…

PS The Shader reference page has a VBScript example, but that doesn’t work anymore because it was written before ShaderParameters were introduced.

from sipyutils import si		# win32com.client.Dispatch('XSI.Application')

import win32com.client
coll = win32com.client.Dispatch( "XSI.Collection" )

def doit( s, coll ):

	for p in s.Parameters:
		if p.Source and p.Source.IsClassOf( C.siShaderParameterID ):
			print p.Source.Parent.Name
			coll.Add( p.Source.Parent )
			doit( p.Source.Parent, coll )
	for l in s.TextureLayers:
		for y in l.Parameters:
			if y.Source and y.Source.IsClassOf( C.siShaderParameterID ):
				print y.Source.Parent.Name
				coll.Add( y.Source.Parent )
				doit( y.Source.Parent, coll )

# Get a material or shader to use as a starting point
mat = si.Dictionary.GetObject("Sources.Materials.DefaultLib.Architectural")
doit( mat, coll )

coll.Unique = True
coll.Add( mat.AllImageClips.GetAsText() )

This snippet worked for this [nonsensical test] render tree: