Search code examples
pythoncompiler-errorsmaya

What does it mean for an object to be "in the underworld?"


I have this code:

def block_stacks(num):
    stack = cmds.group(empty=True, name='Stacks#')
    size = num
    for var in range(num):
        i = 0
        r_rot = random.uniform(0,359)
        block = cmds.polyCube(h=0.5, w=0.5, d=0.5, name='block#')
        cmds.parent(block, stack)
        cmds.move(0, 5.38 + i, 0, 'block*')
        cmds.rotate(0, r_rot, 0, 'block*')
        rR= random.uniform(0, 1.0)
        rG= random.uniform(0, 1.0)
        rB= random.uniform(0, 1.0)
        cmds.polyColorPerVertex('block*', rgb=[rR,rG,rB], cdo = True)
        i+=0.5

block_stacks(5)

in Maya's Script Editor. When I run it, the random rotation, and random color work fine, and the block places at the correct location, but it only creates 1 block instead of 5 (like I intend for it to) and says

"Warning: Cannot parent components or objects in the underworld."

multiple times. I have absolutely no idea what this means, and apparently there is no answer anywhere on the entire internet that says what exactly this error is. It still creates the object when I run it, and it doesn't give any red error message. Does anyone know what this means, and why it only makes a stack 1 block high instead of 5 like it's supposed to? I've been trying to fix this for almost 2 hours and I'm pretty much burnt out now.


Solution

  • I believe the error means that you can't parent a dg node (something that has no transform) to a dag node. For example, try parenting an objectSet to a transform. It won't let you, because dg nodes have no transforms themselves and cannot belong in a hierarchy.

    Now it's giving you this error because you're trying to parent the cube's polyCube input, which has no transform! This is being done by accident because you're assuming that cmds.polyCube returns the cube's transform. It does not. In fact, it returns a list of 2 items: the cube's transform, and the cube's polyCube input. And since cmds.parent can accept a list in its first parameter, you are essentially trying to parent the transform AND polyCube to the stack transform. You can easily avoid this by grabbing the command's first index like this: cmds.polyCube()[0]

    Now another issue is that all of the cubes move to the same place. This is because your i variable is INSIDE the for loop. So every iteration i resets to 0 instead of being incremented, thus they all move to the same position.

    Another issue is that in a lot of your commands you are using "block*". Doing this doesn't refer to the block variable, instead it will actually grab all transforms that start with the name "block". In fact you don't need the "*" at all, just pass the variable block.

    With all of this in mind, here's the working code:

    import random
    import maya.cmds as cmds
    
    
    def block_stacks(num):
        stack = cmds.group(empty=True, name='Stacks#')
        i = 0  # Need to move this OUT of the loop otherwise it always resets to 0 and all of the blocks will move to the same place.
    
        for var in range(num):
            r_rot = random.uniform(0,359)
            block = cmds.polyCube(h=0.5, w=0.5, d=0.5, name='block#')[0]  # This command actually returns a list of 2 items, the transform and the polyCube input, so grab the first index.
            cmds.parent(block, stack)
            cmds.move(0, 5.38 + i, 0, block)  # Pass the variable.
            cmds.rotate(0, r_rot, 0, block)
            rR = random.uniform(0, 1.0)
            rG = random.uniform(0, 1.0)
            rB = random.uniform(0, 1.0)
            cmds.polyColorPerVertex(block, rgb=[rR, rG, rB], cdo=True)
            i += 0.5
    
    
    block_stacks(5)