Reconnecting Shader Networks

Sometimes I have to work with files from older, outdated projects that contain nodes that just don’t apply anymore. For example, I have a file with shader networks than contain a unique user created node that my newer version of Maya has NO IDEA how to handle. The problem is if I simply erase these nodes, Maya doesn’t know how to reconnect the color textures, bump maps, etc. So, a script! It’s quick and dirty, but it works.

Maya only knows these nodes as “unknown”,  so I’m finding them by their name suffix. Here the nodes are ‘ONB’ nodes, and fittingly they all have a “_ONB” suffix. (Certainly makes my life easier!)

//delete all the old ONB nodes first
//they are of type 'unknown' now
string $allCWMats[] = `ls -mat`;
string $eachCWMat;
for($eachCWMat in $allCWMats)
{
    if( `match "_ONB" $eachCWMat` == "_ONB" && `nodeType $eachCWMat` == "unknown")
    {
        print("BYE BYE! " + $eachCWMat + "\n");
        select -r $eachCWMat;
        delete $eachCWMat;        
    }
}

//clear $allMats;
string $allMats[] = `ls -mat`;
string $eachMat;
int $numMats = size($allMats);
int $numRndrMats = 0;
select -clear;
print("Number of Materials: " + $numMats + "\n");   
for($eachMat in $allMats)
{ 
    print("Material: " + $eachMat + "\n");
    string $matType = `nodeType $eachMat`;
    print("Material is of type: " + $matType + "\n");  

    //we only want to select top-node materials, i.e materials that AREN'T made up of other materials
    string $conns[] = `listConnections -t shadingEngine $eachMat`;
    int $sizeConns = size($conns);   

    //further specify that the material must have incoming connections, otherwise why bother rendering it (e.g flat lambert materials)
    string $finalMats[] = `listConnections -d off -s on $eachMat`;
    int $sizeFinal = size($finalMats);        
    if(($sizeConns > 0) && ($sizeFinal > 0))
    {
        //select -add $eachMat;
        $numRndrMats++;
        //print("Current Count: " + $numRndrMats + "\n");
        print("\t\tHas connections & connects to Shading Engine... This WILL be used!\n");  

        //create a new material
        //and a shading group to go with it     
        string $flatMatName = $eachMat + "_OVR";  
        //print("Flat Material Name: " + $flatMatName + "\n");        
        string $SGname = $flatMatName + "_SG";

        //create Material        
        string $material = `shadingNode -asShader $matType -name $flatMatName`;
        //create Shading Group
        string $SG = `sets -renderable true -noSurfaceShader true -empty -name $SGname`;       
        //instead of creating new nodes, we only need to connect to the old ones!
        //so we need to find out which connections exist on the old material 
        string $testList[] = `listConnections -d off -s on -c on -p on $eachMat`;
        string $eachConn;        
        for($eachConn in $testList)
        {
            print("Connection: " + $eachConn + "\n");
            string $connInfoList[];
            $connInfoList = `connectionInfo -destinationFromSource $eachConn`;
            string $destinations;
            for($destinations in $connInfoList)
            {
                //if it reaches this point, then the connection has a link to another connection and we should use it            
                print("\tPlug: " + $destinations + "\n");               
                //get the name of the node we want to connect from
                string $fromBuffer[];
                $numFromTokens = `tokenize $eachConn "." $fromBuffer`;
                string $connectFrom = $eachConn;
                print("\t\tConnect From: " + $connectFrom + "\n");                
                //make the name of the node we want to connect to
                string $plugBuffer[];
                $numTokens = `tokenize $destinations "." $plugBuffer`;                              
                string $toConnect = $material + "." + $plugBuffer[1];
                print("\t\tConnect To: " + $toConnect + "\n");               
                //and now connect them!
                if(catch(`connectAttr -f $connectFrom $toConnect`))
                {
                    print("Some error occured, maybe connection can't be modified. Oh well!\n");
                }
                else
                {
                    //Continue on as usual
                }                
            }
        }
        //and now we need to reassign the geometries from the old material to the new material
        print("Each old material: " + $eachMat + "\n");
        print("Each new material: " + $material + "\n");    
        select -clear;
        hyperShade -objects $eachMat;
        string $objList[] = `ls -sl`;
        int $numObjs = size($objList);
        print("\t\t\tNumber of Objects with Material: " + $numObjs + "\n");
        string $eachObj;
        for($eachObj in $objList)
        {
            print("\t\t\tAssign this object: " + $eachObj + " IN" + $eachMat + " TO " + $material + "\n"); 
            select -r $eachObj;
            hyperShade -assign $material;           
        }     
   }
}

 

Leave a Reply

Your email address will not be published. Required fields are marked *