FTransform FFbxDataConverter::ConvertTransform(FbxAMatrix Matrix)
{
	FTransform Out;

	FQuat Rotation = ConvertRotToQuat(Matrix.GetQ());
	FVector Origin = ConvertPos(Matrix.GetT());
	FVector Scale = ConvertScale(Matrix.GetS());

	Out.SetTranslation(Origin);
	Out.SetScale3D(Scale);
	Out.SetRotation(Rotation);

	return Out;
}
示例#2
0
void FbxParser::ProcessLight(FbxNode* pNode, std::vector<GS::Light*>& lights)
{
   FbxLight* llight = (FbxLight*) pNode->GetNodeAttribute();
   if (!llight)
      return  ;

    // Get the light color.
   FbxDouble3 c = llight->Color.Get();
   GS::float4 lcolor( c[0], c[1], c[2], 1.0 );
   float intensity = llight->Intensity.Get();
   if (intensity)
     lcolor= lcolor*(intensity/100);
  
    // to do so far, we only process directional light
    if (llight->LightType.Get() == FbxLight::eDirectional)
	{
		//FbxDouble3 dir = pNode->LclRotation.Get(); 
		FbxAnimEvaluator* lEvaluator = mpFbxScene->GetAnimationEvaluator();

        FbxAMatrix lGlobal;
        lGlobal= lEvaluator->GetNodeGlobalTransform( pNode);

		FbxVector4 rotation = lGlobal.GetR();

		 FbxVector4 tran = lGlobal.GetT();
		 FbxQuaternion quaternion = lGlobal.GetQ();
		 GS::float4 q(quaternion[0], quaternion[1], quaternion[2],quaternion[3]);
		 GS::float4x4 rotMat = GS::quat_rotation_matrix(q);
		 GS::float4 dir(mul(rotMat, GS::float4(0, 0, -1, 1)));
    /* dir(0,0,-1);
   FbxQuaternion quaternion = lGlobal.GetQ();
   quaternion.
   LcLRotation3f quaternion3f(quaternion[0], quaternion[1], quaternion[2], quaternion[3]);
   LcLTransform3f rot3f(quaternion3f);
   LcLVec3f rot_dir = dir * rot3f;*/
	}
}
示例#3
0
// Deform the vertex array in Dual Quaternion Skinning way.
void compute_dual_quaternion_deformation(FbxAMatrix& pGlobalPosition,
    FbxMesh* pMesh,
    FbxTime& pTime,
    FbxVector4* pVertexArray,
    FbxPose* pPose)
{
  // All the links must have the same link mode.
  FbxCluster::ELinkMode lClusterMode = ((FbxSkin*)pMesh->GetDeformer(0, FbxDeformer::eSkin))->GetCluster(0)->GetLinkMode();

  int lVertexCount = pMesh->GetControlPointsCount();
  int lSkinCount = pMesh->GetDeformerCount(FbxDeformer::eSkin);

  FbxDualQuaternion* lDQClusterDeformation = new FbxDualQuaternion[lVertexCount];
  memset(lDQClusterDeformation, 0, lVertexCount * sizeof(FbxDualQuaternion));

  double* lClusterWeight = new double[lVertexCount];
  memset(lClusterWeight, 0, lVertexCount * sizeof(double));

  // For all skins and all clusters, accumulate their deformation and weight
  // on each vertices and store them in lClusterDeformation and lClusterWeight.
  for(int lSkinIndex=0; lSkinIndex<lSkinCount; ++lSkinIndex) {
    FbxSkin * lSkinDeformer = (FbxSkin *)pMesh->GetDeformer(lSkinIndex, FbxDeformer::eSkin);
    int lClusterCount = lSkinDeformer->GetClusterCount();

    for(int lClusterIndex=0; lClusterIndex<lClusterCount; ++lClusterIndex) {
      FbxCluster* lCluster = lSkinDeformer->GetCluster(lClusterIndex);

      if(!lCluster->GetLink()) {
        continue;
      }

      FbxAMatrix lVertexTransformMatrix;
      compute_cluster_deformation(pGlobalPosition, pMesh, lCluster, lVertexTransformMatrix, pTime, pPose);

      FbxQuaternion lQ = lVertexTransformMatrix.GetQ();
      FbxVector4 lT = lVertexTransformMatrix.GetT();
      FbxDualQuaternion lDualQuaternion(lQ, lT);

      int lVertexIndexCount = lCluster->GetControlPointIndicesCount();

      for(int k = 0; k < lVertexIndexCount; ++k) {
        int lIndex = lCluster->GetControlPointIndices()[k];

        // Sometimes, the mesh can have less points than at the time of the skinning
        // because a smooth operator was active when skinning but has been deactivated during export.
        if(lIndex >= lVertexCount) {
          continue;
        }

        double lWeight = lCluster->GetControlPointWeights()[k];

        if(lWeight == 0.0) {
          continue;
        }

        // Compute the influence of the link on the vertex.
        FbxDualQuaternion lInfluence = lDualQuaternion * lWeight;

        if(lClusterMode == FbxCluster::eAdditive) {
          // Simply influenced by the dual quaternion.
          lDQClusterDeformation[lIndex] = lInfluence;

          // Set the link to 1.0 just to know this vertex is influenced by a link.
          lClusterWeight[lIndex] = 1.0;
        } else { // lLinkMode == FbxCluster::eNormalize || lLinkMode == FbxCluster::eTotalOne
          if(lClusterIndex == 0) {
            lDQClusterDeformation[lIndex] = lInfluence;
          } else {
            // Add to the sum of the deformations on the vertex.
            // Make sure the deformation is accumulated in the same rotation direction.
            // Use dot product to judge the sign.
            double lSign = lDQClusterDeformation[lIndex].GetFirstQuaternion().DotProduct(lDualQuaternion.GetFirstQuaternion());

            if(lSign >= 0.0) {
              lDQClusterDeformation[lIndex] += lInfluence;
            } else {
              lDQClusterDeformation[lIndex] -= lInfluence;
            }
          }

          // Add to the sum of weights to either normalize or complete the vertex.
          lClusterWeight[lIndex] += lWeight;
        }
      }//For each vertex
    }//lClusterCount
  }

  //Actually deform each vertices here by information stored in lClusterDeformation and lClusterWeight
  for(int i = 0; i < lVertexCount; i++) {
    FbxVector4 lSrcVertex = pVertexArray[i];
    FbxVector4& lDstVertex = pVertexArray[i];
    double lWeightSum = lClusterWeight[i];

    // Deform the vertex if there was at least a link with an influence on the vertex,
    if(lWeightSum != 0.0) {
      lDQClusterDeformation[i].Normalize();
      lDstVertex = lDQClusterDeformation[i].Deform(lDstVertex);

      if(lClusterMode == FbxCluster::eNormalize) {
        // In the normalized link mode, a vertex is always totally influenced by the links.
        lDstVertex /= lWeightSum;
      } else if(lClusterMode == FbxCluster::eTotalOne) {
        // In the total 1 link mode, a vertex can be partially influenced by the links.
        lSrcVertex *= (1.0 - lWeightSum);
        lDstVertex += lSrcVertex;
      }
    }
  }

  delete [] lDQClusterDeformation;
  delete [] lClusterWeight;
}