Skip to content

validate_skinCluster_deformer_set

ValidateSkinclusterDeformerSet

Bases: MayaInstancePlugin, OptionalPyblishPluginMixin

Validate skinClusters on meshes have valid member relationships.

In rare cases it can happen that a mesh has a skinCluster in its history but it is not included in the deformer relationship history. If this is the case then FBX will not export the skinning.

Source code in client/ayon_maya/plugins/publish/validate_skinCluster_deformer_set.py
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
class ValidateSkinclusterDeformerSet(plugin.MayaInstancePlugin,
                                     OptionalPyblishPluginMixin):
    """Validate skinClusters on meshes have valid member relationships.

    In rare cases it can happen that a mesh has a skinCluster in its history
    but it is *not* included in the deformer relationship history. If this is
    the case then FBX will not export the skinning.

    """

    order = ValidateContentsOrder
    families = ['fbx']
    label = "Skincluster Deformer Relationships"
    actions = [ayon_maya.api.action.SelectInvalidAction]
    optional = False

    def process(self, instance):
        """Process all the transform nodes in the instance"""
        if not self.is_active(instance.data):
            return
        invalid = self.get_invalid(instance)

        if invalid:
            raise PublishValidationError(
                "Invalid skinCluster relationships found on meshes: {0}"
                .format(invalid)
            )

    @classmethod
    def get_invalid(cls, instance):

        meshes = cmds.ls(instance, type="mesh", noIntermediate=True, long=True)
        invalid = list()

        for mesh in meshes:
            history = cmds.listHistory(mesh) or []
            skins = cmds.ls(history, type="skinCluster")

            # Ensure at most one skinCluster
            assert len(skins) <= 1, "Cannot have more than one skinCluster"

            if skins:
                skin = skins[0]

                # Ensure the mesh is also in the skinCluster set
                # otherwise the skin will not be exported correctly
                # by the FBX Exporter.
                deformer_sets = cmds.listSets(object=mesh, type=2)
                for deformer_set in deformer_sets:
                    used_by = cmds.listConnections(deformer_set + ".usedBy",
                                                   source=True,
                                                   destination=False)

                    # Ignore those that don't seem to have a usedBy connection
                    if not used_by:
                        continue

                    # We have a matching deformer set relationship
                    if skin in set(used_by):
                        break

                else:
                    invalid.append(mesh)
                    cls.log.warning(
                        "Mesh has skinCluster in history but is not included "
                        "in its deformer relationship set: "
                        "{0} (skinCluster: {1})".format(mesh, skin)
                    )

        return invalid

process(instance)

Process all the transform nodes in the instance

Source code in client/ayon_maya/plugins/publish/validate_skinCluster_deformer_set.py
28
29
30
31
32
33
34
35
36
37
38
def process(self, instance):
    """Process all the transform nodes in the instance"""
    if not self.is_active(instance.data):
        return
    invalid = self.get_invalid(instance)

    if invalid:
        raise PublishValidationError(
            "Invalid skinCluster relationships found on meshes: {0}"
            .format(invalid)
        )