Your browser does not seem to support JavaScript. As a result, your viewing experience will be diminished, and you have been placed in read-only mode.
Please download a browser that supports JavaScript, or enable it if it's disabled (i.e. NoScript).
Hi all, I'm trying to see if I can access the polygon data from generators that I create within the Python Generator. E.g. the default python generator creates a cube, is it possible to print out the polygon count of that cube?
GetCache() returns None as there doesn't seem to be any cache yet. What is the designated way to do this? Is CurrentStateToObject an optimal way?
The default python generator returns a parametric object (c4d.Ocube). So you have to convert it to a editable poly in the generator itself. So you don't need a cso in your script but in the generator when using parametric objects.
Python Generator
import c4d #Welcome to the world of Python def main(): c = c4d.BaseObject(c4d.Ocube) return c4d.utils.SendModelingCommand(command = c4d.MCOMMAND_CURRENTSTATETOOBJECT,list = [c], bc = c4d.BaseContainer(), mode = c4d.MODELINGCOMMANDMODE_ALL, doc = doc, flags = 0)[0]
script
import c4d doc = c4d.documents.GetActiveDocument() gen =doc.GetActiveObject() print gen.GetCache()
Hi,
there are two different things here at play.
import c4d def get_cumlative_polygon_count(op): """ Returns the cumlative polygon count of the passed node and its descendants. Will also inspcect caches. Args: op (c4d.BaseObject): The node to evaluate the polygon count for. Returns: int: The cumlative polygon count of the passed node and its descendants. """ if not isinstance(op, c4d.BaseObject): return 0 # Op is not a polygon object, walk down the cache chain. if not isinstance(op, c4d.PolygonObject): cache = op.GetCache() res = get_cumlative_polygon_count(cache) if cache else 0 # else get the polygon count else: res = op.GetPolygonCount() # Evaluate the children for child in op.GetChildren(): res += get_cumlative_polygon_count(child) return res def main(): """ """ print get_cumlative_polygon_count(op) if __name__=='__main__': main()
import c4d # Welcome to the world of Python def get_cumlative_polygon_count(op): """ Returns the cumlative polygon count of the passed node and its descendants. Will also inspcect caches. Args: op (c4d.BaseObject): The node to evaluate the polygon count for. Returns: int: The cumlative polygon count of the passed node and its descendants. """ if not isinstance(op, c4d.BaseObject): return 0 # Op is not a polygon object, walk down the cache chain. if not isinstance(op, c4d.PolygonObject): cache = op.GetCache() res = get_cumlative_polygon_count(cache) if cache else 0 # else get the polygon count else: res = op.GetPolygonCount() # Evaluate the children for child in op.GetChildren(): res += get_cumlative_polygon_count(child) return res def main(): """ """ cube = c4d.BaseObject(c4d.Ocube) msg = "Cube polygon count before document execution:" print msg, get_cumlative_polygon_count(cube) temp_doc = c4d.documents.BaseDocument() temp_doc.InsertObject(cube) temp_doc.ExecutePasses(bt=None, animation=False, expressions=False, caches=True, flags=0) msg = "Cube polygon count after document execution:" print msg, get_cumlative_polygon_count(cube) cube.Remove() return cube
Cheers zipit
Hi @orestiskon
So if you want to have a new generator within your own generator you need to evaluate this generator.
def main(): # Create a Cube Generator in memory cube = c4d.BaseObject(c4d.Ocube) if cube is None: raise RuntimeError("Failed to create a cube") # Creates a temporary document that will be used to evaluate the cache of the object tempDoc = c4d.documents.BaseDocument() if tempDoc is None: raise RuntimeError("Failed to create a temporary doc") # Inserts the cube that exists only in memory into our tempo doc tempDoc.InsertObject(cube) # Computes cache from the document (aka compute the cache for our cube generator) tempDoc.ExecutePasses(bt=c4d.threading.GeGetCurrentThread(), animation=False, expressions=False, caches=True, flags=c4d.BUILDFLAGS_EXPORT) # Retrieve a copy of the cache (don't return directly the cache, since this cache belongs to the other document) clonedCube = cube.GetCache().GetClone(c4d.COPYFLAGS_NONE) return clonedCube
Cheers, Maxime.
Wow much obliged for all the replies everyone, it is really helpful! I think evaluating in a tempdocument is what I was looking for. I have another question about best practices:
In zipit's example the original cube is removed from the temp document after use. Is there a reason to do that? Does it help with performance and/or memory management?
I did that for the same reason @m_adam created a copy in his version: A node can only be member of one document at a time and also only be inserted exactly one time into the same document (long way of saying that Cinema is monohierachical).