Пример #1
0
    public static void RetrievePersistentData(UltimateRope rope)
    {
        RopeData ropeData = s_hashInstanceID2RopeData[rope.GetInstanceID()];

        // Attributes

        foreach(FieldInfo fieldInfo in rope.GetType().GetFields())
        {
            fieldInfo.SetValue(rope, ropeData.m_hashFieldName2Value[fieldInfo.Name]);
        }

        // Physics

        if(ropeData.m_bDeleted)
        {
            rope.DeleteRope();
        }
        else
        {
            // Set rope tranform info

            SetTransformInfo(ropeData.m_transformInfoRope, rope.gameObject);

            // Set rope start transform info

            if(rope.RopeStart != null)
            {
                if(ropeData.m_transformInfoStart.goObject == null)
                {
                    rope.RopeStart = new GameObject(ropeData.m_transformInfoStart.strObjectName);
                }

                SetTransformInfo(ropeData.m_transformInfoStart, rope.RopeStart);
            }

            // Delete all dynamic links to reset them, so that even after creating/deleting/breaking links during playmode they get recreated correctly after playmode

            if(rope.RopeType != UltimateRope.ERopeType.ImportBones)
            {
                rope.DeleteRopeLinks();
            }

            int nLinearLinkIndex = 0;

            for(int nNode = 0; nNode < rope.RopeNodes.Count; nNode++)
            {
                if(rope.RopeType != UltimateRope.ERopeType.ImportBones)
                {
                    for(int nJoint = 0; nJoint < rope.RopeNodes[nNode].linkJoints.Length; nJoint++)
                    {
                        rope.RopeNodes[nNode].linkJointBreaksProcessed[nJoint] = ropeData.m_aaJointsProcessed[nNode][nJoint];
                    }

                    if(rope.RopeNodes[nNode].goNode != null)
                    {
                        if(ropeData.m_transformInfoSegments[nNode].goObject == null)
                        {
                            rope.RopeNodes[nNode].goNode = new GameObject(ropeData.m_transformInfoSegments[nNode].strObjectName);
                        }

                        SetTransformInfo(ropeData.m_transformInfoSegments[nNode], rope.RopeNodes[nNode].goNode);
                    }
                }

                if(rope.RopeType != UltimateRope.ERopeType.ImportBones)
                {
                    rope.RopeNodes[nNode].segmentLinks = new GameObject[rope.RopeNodes[nNode].nTotalLinks];
                }

                for(int nLink = 0; nLink < rope.RopeNodes[nNode].segmentLinks.Length; nLink++)
                {
                    if(rope.RopeType != UltimateRope.ERopeType.ImportBones)
                    {
                        if(rope.RopeType == UltimateRope.ERopeType.Procedural)
                        {
                            rope.RopeNodes[nNode].segmentLinks[nLink] = new GameObject(ropeData.m_aLinkTransformInfo[nLinearLinkIndex].strObjectName);
                        }
                        else if(rope.RopeType == UltimateRope.ERopeType.LinkedObjects)
                        {
                            rope.RopeNodes[nNode].segmentLinks[nLink] = GameObject.Instantiate(rope.LinkObject) as GameObject;
                            rope.RopeNodes[nNode].segmentLinks[nLink].name = ropeData.m_aLinkTransformInfo[nLinearLinkIndex].strObjectName;
                        }

                        rope.RopeNodes[nNode].segmentLinks[nLink].AddComponent<UltimateRopeLink>();
                        rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent = (rope.FirstNodeIsCoil() && nNode == 0) ? rope.CoilObject.transform : rope.gameObject.transform;

                        if(rope.RopeNodes[nNode].bIsCoil == false)
                        {
                            rope.RopeNodes[nNode].segmentLinks[nLink].AddComponent<Rigidbody>();
                            rope.RopeNodes[nNode].segmentLinks[nLink].rigidbody.isKinematic = ropeData.m_aLinkTransformInfo[nLinearLinkIndex].bExtensibleKinematic || ropeData.m_aLinkTransformInfo[nLinearLinkIndex].bLinkMarkedKinematic;
                        }
                    }

                    SetTransformInfo(ropeData.m_aLinkTransformInfo[nLinearLinkIndex], rope.RopeNodes[nNode].segmentLinks[nLink]);

                    if(rope.RopeType == UltimateRope.ERopeType.ImportBones)
                    {
                        rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent = rope.ImportedBones[nLinearLinkIndex].bIsStatic ? rope.ImportedBones[nLinearLinkIndex].tfNonBoneParent : rope.transform;
                    }

                    if(ropeData.m_aLinkTransformInfo[nLinearLinkIndex].bExtensibleKinematic)
                    {
                        UltimateRopeLink ropeLink = rope.RopeNodes[nNode].segmentLinks[nLink].GetComponent<UltimateRopeLink>();

                        if(ropeLink != null) ropeLink.ExtensibleKinematic = true;
                        
                        rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent   = nNode > rope.m_nFirstNonCoilNode ? rope.RopeNodes[nNode - 1].goNode.transform : rope.RopeStart.transform;
                        rope.RopeNodes[nNode].segmentLinks[nLink].transform.position = rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent.position;

                        Vector3 v3WorldForward = rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent.TransformDirection(rope.RopeNodes[nNode].m_v3LocalDirectionForward);
                        Vector3 v3WorldUp      = rope.RopeNodes[nNode].segmentLinks[nLink].transform.parent.TransformDirection(rope.RopeNodes[nNode].m_v3LocalDirectionUp);
                        rope.RopeNodes[nNode].segmentLinks[nLink].transform.rotation = Quaternion.LookRotation(v3WorldForward, v3WorldUp);
                    }

                    nLinearLinkIndex++;
                }
            }

            rope.SetupRopeLinks();

            // Mesh

            SkinnedMeshRenderer skin = rope.GetComponent<SkinnedMeshRenderer>();

            if(ropeData.m_bSkin == false)
            {
                if(skin != null)
                {
                    UnityEngine.Object.DestroyImmediate(skin);
                }
            }
            else
            {
                if(skin == null)
                {
                    skin = rope.gameObject.AddComponent<SkinnedMeshRenderer>();
                }

                int nVertices          = ropeData.m_av3SkinVertices.Length;
                int nTrianglesRope     = ropeData.m_anSkinTrianglesRope.Length;
                int nTrianglesSections = ropeData.m_anSkinTrianglesSections.Length;

                Vector3[]    av3SkinVertices         = new Vector3   [nVertices];
                Vector2[]    av2SkinMapping          = new Vector2   [nVertices];
                Vector4[]    av4SkinTangents         = ropeData.m_av4SkinTangents != null ? new Vector4[ropeData.m_av4SkinTangents.Length] : null;
		        BoneWeight[] aSkinBoneWeights        = new BoneWeight[nVertices];
		        int[]        anSkinTrianglesRope     = new int       [nTrianglesRope];
                int[]        anSkinTrianglesSections = new int       [nTrianglesSections];
                Matrix4x4[]  amtxSkinBindPoses       = new Matrix4x4 [ropeData.m_amtxSkinBindPoses.Length];

                Mesh mesh = new Mesh();

                RopeData.MakeSkinDeepCopy(ropeData.m_av3SkinVertices, ropeData.m_av2SkinMapping, ropeData.m_av4SkinTangents, ropeData.m_aSkinBoneWeights, ropeData.m_anSkinTrianglesRope, ropeData.m_anSkinTrianglesSections, ropeData.m_amtxSkinBindPoses,
                                          av3SkinVertices,            av2SkinMapping,            av4SkinTangents,            aSkinBoneWeights,            anSkinTrianglesRope,            anSkinTrianglesSections,            amtxSkinBindPoses);

                Transform[] aBones = new Transform[rope.TotalLinks];

                nLinearLinkIndex = 0;

                for(int nNode = 0; nNode < rope.RopeNodes.Count; nNode++)
                {
                    for(int nLink = 0; nLink < rope.RopeNodes[nNode].segmentLinks.Length; nLink++)
                    {
                        aBones[nLinearLinkIndex++] = rope.RopeNodes[nNode].segmentLinks[nLink].transform;
                    }
                }

                mesh.vertices    = av3SkinVertices;
		        mesh.uv          = av2SkinMapping;
		        mesh.boneWeights = aSkinBoneWeights;
		        mesh.bindposes   = amtxSkinBindPoses;

                mesh.subMeshCount = 2;
                mesh.SetTriangles(anSkinTrianglesRope,     0);
                mesh.SetTriangles(anSkinTrianglesSections, 1);
		        mesh.RecalculateNormals();

                if(av4SkinTangents != null)
                {
                    if(av4SkinTangents.Length == nVertices)
                    {
                        mesh.tangents = av4SkinTangents;
                    }
                }

                skin.bones      = aBones;
                skin.sharedMesh = mesh;

                Material[] ropeMaterials = new Material[2];
                ropeMaterials[0] = rope.RopeMaterial;
                ropeMaterials[1] = rope.RopeSectionMaterial;

		        skin.materials  = ropeMaterials;
            }
        }
    }