无万向锁,旋转绝对自由。就是不好控制
BTW:这是渲染引擎部件之一。CCamera可以用于设置RenderTarget,而CViewerCamera则是给用户3D漫游用的
public class CCamera

{
Matrix4x4 mViewMatrix, mProjMatrix;

protected Vector mPosition;
protected Quaternion mOri;

protected Vector mFront;
protected Vector mTop;
protected Vector mRight;

double mFovy;
double mNear;
double mFar;
double mAspect;

CFrustum mFrustum = new CFrustum();


/**//// <summary>
/// 摄像机Z
/// </summary>

public Vector Front

{

get
{ return mFront; }
}

/**//// <summary>
/// 摄像机Y
/// </summary>
public Vector Top

{

get
{ return mTop; }
}

/**//// <summary>
/// 摄像机X
/// </summary>
public Vector Right

{

get
{ return mRight; }
}

public Vector Position

{

get
{ return mPosition; }

set
{ mPosition = value; }
}

public Quaternion Orientation

{

get
{ return mOri; }

set
{ mOri = value; }
}

public double Fovy

{

get
{ return mFovy; }

set
{ mFovy = value; }
}

public double Near

{

get
{ return mNear; }

set
{ mNear = value; }
}

public double Far

{

get
{ return mFar; }

set
{ mFar = value; }
}

public double Aspect

{

get
{ return mAspect; }

set
{ mAspect = value; }
}

public CCamera(double aspect)

{
mFar = 2500;
mFovy = 45;
mNear = 1;
mAspect = aspect;
mOri = Quaternion.Inentity;
Update();
}

public void UpdateProjection()

{
mProjMatrix = Matrix4x4.GetProjectionMatrix(mFovy, mAspect, mNear, mFar);
}

public void Update()

{
mViewMatrix = Matrix4x4.GetTranslateMatrix(-mPosition) * mOri.ToMatrix4(new Vector());
mProjMatrix = Matrix4x4.GetProjectionMatrix(mFovy, mAspect, mNear, mFar);
mFrustum.Update(mViewMatrix, mProjMatrix);

Matrix3x3 rot = mOri.ToMatrix3();
mFront = rot * new Vector(0, 0, 1);
mTop = rot * new Vector(0, 1, 0);
mRight = rot * new Vector(1, 0, 0);
}

public Matrix4x4 ProjMatrix

{

get
{ return mProjMatrix; }

set
{ mProjMatrix = value; }
}

public Matrix4x4 ViewMatrix

{

get
{ return mViewMatrix; }

set
{ mViewMatrix = value; }
}
}

public class CViewerCamera : CCamera

{
public CViewerCamera(double aspect)
: base(aspect)

{ }

protected double mMoveSpeed = 2.5;
protected double mTurnSpeed = Math.PI / 45;

public double MoveSpeed

{

get
{ return mMoveSpeed; }

set
{ mMoveSpeed = value; }
}

public double TurnSpeed

{

get
{ return mTurnSpeed; }

set
{ mTurnSpeed = value; }
}

public void MoveAbs(Vector mov)

{
mPosition += mOri.ToMatrix3() * mov;
}
public void MoveFront()

{ mPosition += mFront * mMoveSpeed; }

public void MoveBack()

{ mPosition -= mFront * mMoveSpeed; }

public void MoveLeft()

{ mPosition -= mRight * mMoveSpeed; }

public void MoveRight()

{ mPosition += mRight * mMoveSpeed; }

public void MoveUp()

{
mPosition += mTop * mMoveSpeed;
}

public void MoveDown()

{
mPosition -= mTop * mMoveSpeed;
}

public void TurnLeft()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(0, -1, 0));
mOri.Normalize();
}

public void TurnRight()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(0, 1, 0));
mOri.Normalize();
}

public void TurnUp()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(-1, 0, 0));
mOri.Normalize();
}

public void TurnDown()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(1, 0, 0));
mOri.Normalize();
}

public void RollLeft()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(0, 0, 1));
mOri.Normalize();
}

public void RollRight()

{
mOri *= Quaternion.FromAngleAxis(mTurnSpeed, new Vector(0, 0, -1));
mOri.Normalize();
}

}