Jump to content

  • Log In with Google      Sign In   
  • Create Account

Banner advertising on our site currently available from just $5!


1. Learn about the promo. 2. Sign up for GDNet+. 3. Set up your advert!


Twiltie

Member Since 31 Jan 2013
Offline Last Active Aug 01 2013 06:27 AM

Topics I've Started

XNA Matrix Optimization and Animated Models

31 January 2013 - 08:24 PM

Hi All, this is my first post so please forgive me if this is the wrong section or misdirected! 

 

Now to get down to business. I have been working on a 3d visualization for a simulation in XNA. The graphics are all implemented and I have 

been trying to improve performance. I have isolated that the main performance hog is all the matrix operations done on animated models. (The project is currently CPU Bound) 

 

Specifically this code 

 //Compute all of the bone absolute transforms
for (int i = 0, index = 0; i < model.Bones.Count; i++, index++)
{
    model.Bones[i].ComputeAbsoluteTransform();
    model.boneTransforms[index] = model.Bones[i].AbsoluteTransform;
}

//Determine the skin transforms from the skeleton
for (int s = 0; s < model.ModelExtra.Skeleton.Count; s++)
{
    model.skeleton[s] = model.Bones[model.ModelExtra.Skeleton[s]].SkinTransform 
                  * model.Bones[model.ModelExtra.Skeleton[s]].AbsoluteTransform;
}

 

Even more specifically the compute absolute transform is particularly CPU intensive. 

 

private Matrix _scaleMatrixTemp;
private Matrix _rotationMatrixTemp;
private Matrix _translationMatrixTemp;
private Matrix _transformMatrix;
private Matrix _tempA;
private Matrix _tempB;

/// <summary>
/// Compute the absolute transformation for this bone.
/// </summary>
public void ComputeAbsoluteTransform()
{
   Matrix.CreateScale(ref bindScale, out _scaleMatrixTemp);
   Matrix.CreateFromQuaternion(ref rotation, out _rotationMatrixTemp);
   Matrix.CreateTranslation(ref translation, out _translationMatrixTemp);
   Matrix.Multiply(ref _scaleMatrixTemp, ref _rotationMatrixTemp, out _tempA);
   Matrix.Multiply(ref _tempA, ref _translationMatrixTemp, out _tempB);
   Matrix.Multiply(ref _tempB, ref bindTransform, out _transformMatrix);
   if (Parent != null)
   {
       // This bone has a parent bone
       Matrix.Multiply(ref _transformMatrix, ref Parent.AbsoluteTransform,
              out AbsoluteTransform);
   }
   else
   {   
       // The root bone
       AbsoluteTransform = _transformMatrix;
   }
}

 

I have read about the benefits of using the ref version of Matrix multiply. But is there something I am missing, this still seems to be the most CPU intensive part of the whole application. Is there something I am missing that can be moved to the GPU? Or is this just the price one has to pay for skinned animations?

 

Thanks!


PARTNERS