Exemple #1
0
    Matrix[] mW; //weight matrix mW[i] is the weight matrix for ith bone

    public SkinnedMesh(Mesh objMesh, GameObject[] objBones)
    {
        Pinocchio.Model pModel  = new Pinocchio.Model(objMesh);
        var             objVers = pModel.vertices.ToArray();

        bones     = new Transform[objBones.Length];
        bindPoses = new Matrix4x4[objBones.Length];

        mH = Matrix.ZeroMatrix(objVers.Length, objVers.Length);
        mP = new Matrix[objBones.Length];
        mW = new Matrix[objBones.Length];
        for (int i = 0; i < objBones.Length; i++)
        {
            mP[i] = Matrix.ZeroMatrix(objVers.Length, 1);
            mW[i] = Matrix.ZeroMatrix(objVers.Length, 1);
        }//initialize matrix

        for (int i = 0; i < objBones.Length; i++)
        {
            bones[i] = objBones[i].transform;
            bones[i].localRotation = Quaternion.identity;
            bindPoses[i]           = bones[i].worldToLocalMatrix * bones[i].parent.localToWorldMatrix;
        }//initialize bones


        //Calculation mW[i] = (mH - L)^-1 HP
        Matrix mM = Matrix.ZeroMatrix(objVers.Length, objVers.Length);
        Matrix mC = Matrix.ZeroMatrix(objVers.Length, objVers.Length);

        for (int i = 0; i < objVers.Length; i++)
        {
            //1. Find mH by calculating distance construct mH and mP
            FindNearestBone(objVers[i].p, objBones, i);
            //2. Calculate Laplacian for this vertex L= MC
            mM[i, i] = 1 / objVers[i].GetArea();
            var sum = 0f;
            for (int j = 0; j < objVers[i].edges.Count; j++)
            {
                var theEdge = objVers[i].edges;
                int n1      = (j - 1) % objVers[i].edges.Count;
                int n2      = (j + 1) % objVers[i].edges.Count;

                Vector3 v1 = objVers[i].p - theEdge[n1].b.p;
                Vector3 v2 = theEdge[j].b.p - theEdge[n1].b.p;
                Vector3 v3 = objVers[i].p - theEdge[n2].b.p;
                Vector3 v4 = theEdge[j].b.p - theEdge[n2].b.p;

                float cos1 = Vector3.Dot(v1, v2) / (v1.magnitude * v2.magnitude);
                float cos2 = Vector3.Dot(v3, v4) / (v3.magnitude * v4.magnitude);

                float cot1 = cos1 / Mathf.Sqrt(1 - Mathf.Pow(cos1, 2));
                float cot2 = cos2 / Mathf.Sqrt(1 - Mathf.Pow(cos2, 2));

                mC[i, theEdge[j].b.index] = (-1 / 2) * (cot1 + cot2);

                sum -= (-1 / 2) * (cot1 + cot2);
            }
            mC[i, i] = sum;
        }
        var mL      = mM * mC;
        var mFactor = mH - mL;

        for (int i = 0; i < objBones.Length; i++)
        {
            var mHP = mH * mP[i];
            mW[i] = mFactor.Invert() * mHP;
        }
        Debug.Log(objMesh.bounds.size.x);
    }
Exemple #2
0
 void CalculateLaplacian(Pinocchio.Model objMesh)
 {
     for (int i = 0; i < objMesh.vertices.Count; i++)
     {
     }
 }