2

So I am trying to map all the rotation angles present into the range of 0<angle<360, at every key points for all the mesh objects present in the selected group, this is the approach i took to get all the objects but i am struggling at the keypoint partBY KEYPOINT I MEANT THE MARKED PART IN THE IMAGE

import maya.cmds as cmds

grps = []
subgroups = []
objs = []

rotation_keys = set()
attributes = ['rotateX','rotateY','rotateZ']

for i in cmds.ls():

    if "_SET" in i:
        grps.append(i)
        
for g in grps:
    subgroups.append(cmds.listRelatives(g))

for sg in subgroups:
    objs.extend(cmds.listRelatives(sg))


for attrib in attributes:
    for key in cmds.keyframe(obj, attribute = attrib,  q=True, tc=True):
        rotation_keys.append(key)

print(rotation_keys)
    

But after this i am kinda lost, i have already created the function to map the angles tho so i don't have any issue regarding that, but how should i access all of they keys and change rotation values on each of them.

Thanks & Regards Kartikey

2 Answers2

2

I don't have maya anymore but here is how I was saving animated attributes, you will have to adapt the code as it is used inside my set of coding :

def getAnimatedAttr(node=list):
    """

    :param node: object list
    :return: list of animated channels
    """

    myAttrAnimated = []

    for n in node:
        testT = cmds.listConnections(n.transform, type='animCurve', d=True)
        testS = cmds.listConnections(n.shape, type='animCurve', d=True)
        if testT:
            myAttrAnimated += cmds.listConnections(testT, p=True)
        if testS:
            myAttrAnimated += cmds.listConnections(testS, p=True)

    return myAttrAnimated

def saveAnimatedAttr(node=list, presetName='', path=''):
    """

    :param node: list of python object
    :param presetName: string
    :param path: if no path, it go for ncache
    :return: True
    """
    # add a loop if there is a list ?
    attrs = getAnimatedAttr(node)
    tmpDic = {}

    for i in attrs:

        myTicks = cmds.keyframe(node, q=1, at= i.split('.')[-1])

        myValues = cmds.keyframe(node, q=1, at= i.split('.')[-1], valueChange=True)

        tmpDic[i] = zip(myTicks, myValues)

    if path == '':
        path = make_dir()
        path = path + '/{0}.json'.format(presetName)
    else:
        path = path + '/{0}.json'.format(presetName)

    output = path.replace('/', '//')
    js.saveJson(output, tmpDic)

    return True
DrWeeny
  • 2,487
  • 1
  • 14
  • 17
0

So hey everyone , actually I kind of succeeded in writing the program for it , I guess it can be more optimized and we can eliminate few of the loops, but yeah here it is

def angleMapper():
    subgroups = []
    objs = []
   
    grps  = cmds.ls('*_SET')

    for g in grps:
        subgroups.extend(cmds.listRelatives(g))
        
    for sg in subgroups:
        objs.extend(cmds.listRelatives(sg))
    
    data = {obj:[] for obj in objs}

    for obj in data.keys():
        keyframeValue = cmds.keyframe(obj+".rotateX", q=True)
        if keyframeValue is not None:
            data[obj].extend(keyframeValue)
            
    for obj in data.keys():
        keyframeValue = cmds.keyframe(obj+".rotateY", q=True)
        if keyframeValue is not None:
            data[obj].extend(keyframeValue)
            
    for obj in data.keys():
        keyframeValue = cmds.keyframe(obj+".rotateZ", q=True)
        if keyframeValue is not None:
            data[obj].extend(keyframeValue)

    for k,v in data.items():
        data[k] = list(set(data[k]))  

    for k,v in data.items():
        if len(v)>=1:
            for t in v:
            rotateX =  cmds.getAttr(k+'.rotateX', time = t)
            cmds.setKeyframe(k, attribute='rotateX', v= rotateX%360, t=t)
            
    for k,v in data.items():
        if len(v)>=1:
            for t in v:
            rotateY =  cmds.getAttr(k+'.rotateY', time = t)
            cmds.setKeyframe(k, attribute='rotateY', v= rotateY%360, t=t)
    
    for k,v in data.items():
        if len(v)>=1:
            for t in v:
            rotateZ =  cmds.getAttr(k+'.rotateZ', time = t)
            cmds.setKeyframe(k, attribute='rotateZ', v= rotateZ%360, t=t)

Hope it will give you a rough idea, and any help in optimizing it will be great

Thanks

Kartikey

Glauco
  • 1,385
  • 2
  • 10
  • 20
  • You could generate the axis with a simple lost comprehension : rot = [at+ax for at in 'r' for ax in 'xyz'] It looks complicated but it gives you the possibility to replace ',r' by 'trs'. And you will generate translate rotation scale with all axis and then loop all of them – DrWeeny Dec 26 '22 at 16:36
  • 1
    Also to parse all your nodes in the hierarchy of the selection, cmds.ls has -sl -dag and -type flags to get everything – DrWeeny Dec 26 '22 at 16:42