Home Website Youtube GitHub

Matching the UE4 Mannequin template to a character on Manny skeleton

Hey all!
I wanted to ask if there’s an automated way to match the Epic Mannequin template guide to my own character model that has the same skeleton hierarchy (and similar orientations) as the mannequin

any help would be appreciated!

EDIT: I changed the rotations so they’re planar btw

the script that match the metahuma is in this module https://github.com/mgear-dev/mgear4/blob/master/release/scripts/mgear/shifter/io.py

is the metahuman_snap()

it attaches to the _drv skeleton. You can edit it to your needs.

def metahuman_snap():
    """Snap and configure metahuman guide to attach to metahuman _drv skeleton
    """
    if pm.ls("root_drv"):
        spine = [[u'root_C0_root', u'root_drv'],
                 [u'body_C0_root', u'pelvis_drv'],
                 [u'spine_C0_spineBase', u'spine_01_drv'],
                 [u'spine_C0_tan0', u'spine_02_drv'],
                 [u'spine_C0_spineTop', u'spine_04_drv'],
                 [u'spine_C0_tan1', u'spine_03_drv'],
                 [u'spine_C0_chest', u'spine_05_drv']]
        leg = [[u'leg_L0_root', u'thigh_l_drv'],
               [u'leg_L0_knee', u'calf_l_drv'],
               [u'leg_L0_ankle', u'foot_l_drv'],
               [u'foot_L0_0_loc', u'ball_l_drv']]
        arm = [[u'clavicle_L0_root', u'clavicle_l_drv'],
               [u'clavicle_L0_tip', u'upperarm_l_drv'],
               [u'arm_L0_elbow', u'lowerarm_l_drv'],
               [u'arm_L0_wrist', u'hand_l_drv']]
        hand = [[u'index_metacarpal_L0_root', u'index_metacarpal_l_drv'],
                [u'middle_metacarpal_L0_root', u'middle_metacarpal_l_drv'],
                [u'ring_metacarpal_L0_root', u'ring_metacarpal_l_drv'],
                [u'pinky_metacarpal_L0_root', u'pinky_metacarpal_l_drv'],
                [u'thumb_L0_root', u'thumb_01_l_drv'],
                [u'thumb_L0_0_loc', u'thumb_02_l_drv'],
                [u'thumb_L0_1_loc', u'thumb_03_l_drv'],
                [u'index_L0_root', u'index_01_l_drv'],
                [u'index_L0_0_loc', u'index_02_l_drv'],
                [u'index_L0_1_loc', u'index_03_l_drv'],
                [u'middle_L0_root', u'middle_01_l_drv'],
                [u'middle_L0_0_loc', u'middle_02_l_drv'],
                [u'middle_L0_1_loc', u'middle_03_l_drv'],
                [u'ring_L0_root', u'ring_01_l_drv'],
                [u'ring_L0_0_loc', u'ring_02_l_drv'],
                [u'ring_L0_1_loc', u'ring_03_l_drv'],
                [u'pinky_L0_root', u'pinky_01_l_drv'],
                [u'pinky_L0_0_loc', u'pinky_02_l_drv'],
                [u'pinky_L0_1_loc', u'pinky_03_l_drv']]
        neck = [[u'neck_C0_root', u'neck_01_drv'],
                [u'neck_C0_neck', u'head_drv'],
                [u'neck_C0_tan0', u'neck_02_drv']]

        def match(a, b):
            a = pm.PyNode(a)
            b = pm.PyNode(b)
            a.setTranslation(b.getTranslation(
                space="world"), space="world")

        locs = spine + leg + arm + hand + neck
        for loc in locs:
            try:
                a = loc[0]
                b = loc[1]
                match(a, b)

                if "_l_" in b:
                    ar = a.replace("_L", "_R")
                    br = b.replace("_l_", "_r_")
                    match(ar, br)
            except pm.MayaNodeError:
                pm.displayWarning(
                    "Can't match position for locator {}. Please check if "
                    "the node exist and the name is not duplicated.".format(a))

        try:
            pm.setAttr("guide.joint_name_rule", r"{description}{side}_drv")
        except pm.MayaAttributeError:
            pm.displayInfo("Please check joint Name Rule before build.")```

Thank you! I’ll need to rework the script to more properly support different orientations (since i fixed certain stuff like non-planar orientations and all), but its a good starting point

If anyone wants to take a gander themselves, here’s what I have so far, which wont really produce a good result just yet.

import os
import json
import sys
import pymel.core as pm
from mgear import shifter
from mgear.core import curve

# Epic Manny snap to skeleton utility function
def manny_snap():
    """Snap and configure metahuman guide to attach to metahuman _drv skeleton
    """
    if pm.ls("root"):
        spine = [[u'root_C0_root', u'root'],
                 [u'body_C0_root', u'pelvis'],
                 [u'spine_C0_spineBase', u'spine_01'],
                 [u'spine_C0_tan0', u'spine_01'],
                 [u'spine_C0_spineTop', u'spine_02'],
                 [u'spine_C0_tan1', u'spine_02'],
                 [u'spine_C0_chest', u'spine_03']]
        leg = [[u'leg_L0_root', u'thigh_l'],
               [u'leg_L0_knee', u'calf_l'],
               [u'leg_L0_ankle', u'foot_l'],
               [u'foot_L0_0_loc', u'ball_l']]
        arm = [[u'clavicle_L0_root', u'clavicle_l'],
               [u'clavicle_L0_tip', u'upperarm_l'],
               [u'arm_L0_elbow', u'lowerarm_l'],
               [u'arm_L0_wrist', u'hand_l']]
        hand = [[u'thumb_L0_root', u'thumb_01_l'],
                [u'thumb_L0_0_loc', u'thumb_02_l'],
                [u'thumb_L0_1_loc', u'thumb_03_l'],
                [u'index_L0_root', u'index_01_l'],
                [u'index_L0_0_loc', u'index_02_l'],
                [u'index_L0_1_loc', u'index_03_l'],
                [u'middle_L0_root', u'middle_01_l'],
                [u'middle_L0_0_loc', u'middle_02_l'],
                [u'middle_L0_1_loc', u'middle_03_l'],
                [u'ring_L0_root', u'ring_01_l'],
                [u'ring_L0_0_loc', u'ring_02_l'],
                [u'ring_L0_1_loc', u'ring_03_l'], 
                [u'pinky_L0_root', u'pinky_01_l'],
                [u'pinky_L0_0_loc', u'pinky_02_l'],
                [u'pinky_L0_1_loc', u'pinky_03_l']]
        neck = [[u'neck_C0_root', u'neck_01'],
                [u'neck_C0_neck', u'head']]

        def match(a, b):
            a = pm.PyNode(a)
            b = pm.PyNode(b)
            a.setTranslation(b.getTranslation(
                space="world"), space="world")
            a.setRotation(b.getRotation(
                space="world"), space="world")

        locs = spine + leg + arm + hand + neck
        for loc in locs:
            try:
                a = loc[0]
                b = loc[1]
                match(a, b)

                if "_l" in b:
                    ar = a.replace("_L", "_R")
                    br = b.replace("_l", "_r")
                    match(ar, br)
            except pm.MayaNodeError:
                pm.displayWarning(
                    "Can't match position for locator {}. Please check if "
                    "the node exist and the name is not duplicated.".format(a))

        try:
            pm.setAttr("guide.joint_name_rule", r"{description}{side}")
        except pm.MayaAttributeError:
            pm.displayInfo("Please check joint Name Rule before build.")
            
manny_snap()
2 Likes