WPF AxisAngleRotation3D与XNA CreateFromAxisAngle

时间:2010-12-03 11:20:32

标签: c# wpf xna

我对3D非常愚蠢,就像我的问题可能是:

我在WPF中创建了一个“查看器”程序,可以在屏幕上呈现内容,也可以旋转内容。我将它用于轮换,这符合我的口味:

代码:WPF

Transform3DGroup tg = new Transform3DGroup();
tg.Children.Add(new ScaleTransform3D(sx, sy, 1));
tg.Children.Add(new RotateTransform3D(new AxisAngleRotation3D(new Vector3D(1, 0, 0), rx)));
tg.Children.Add(new RotateTransform3D(new AxisAngleRotation3D(new Vector3D(0, 1, 0), ry)));
tg.Children.Add(new RotateTransform3D(new AxisAngleRotation3D(new Vector3D(0, 0, 1), rz)));
tg.Children.Add(new TranslateTransform3D(x, y, z));
darabka.Transform = tg;
TeljesModell.Children.Add(darabka);

我决定在XNA中制作这个程序,因为这似乎有点快,但是我无法让它工作。

尝试这种方式(Code,XNA):

Pozició = Matrix.CreateScale(sx, sy, 1f);                          //méretezés
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitX, rx);          //forgatás
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitY, ry);
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitZ, rz);
Pozició *= Matrix.CreateTranslation(x, y, z);                      //középpont

我甚至尝试了CreateFromYawPitchRoll,CreateRotationX(YZ),但没有运气,画在屏幕上的东西总是不同地旋转。所以我猜我在这里问大脑是否知道我将在两种技术之间加入什么数学

提前致谢。

编辑:我在其他论坛上试过,我被要求提供详细信息。我也在这里复制/粘贴它们 XNA代码如下:

...
protected override void LoadContent()
{
t3 = new Airplane(); //this is a "zone" object, having zone regions and zone objects in it. all of them together give the zone itself as a static object, where player walks in
Kamera.Példány.Pozició = new Vector3(1362, 627, -757); //starting pozition in the zone - this is camera position so the player's starting pozition. (camera is FPS)
...
}
...
protected override void Update(GameTime gameTime)
{
...
Kameramozgatása();                                                              //kamera mozgatását vezérlő billentyűk
//this moves the FPS camera around
}
...
protected override void Draw(GameTime gameTime)
{
...
ÁltalánosGrafikaiObjektumok.Effect.View = Kamera.Példány.Idenézünk;                 //camera views this
ÁltalánosGrafikaiObjektumok.Effect.Projection = projectionMatrix;                   //... and camera views FROM is set in Kameramozgatása()
...
t3.Rajzolj();  //draw zone object
...
}

区域对象

constructor: set the effect and device to the same as main, set the Pozició (a matrix containing the current position and rotations) to origo
...
public virtual Alapmodel Inicializálás(float x, float y, float z, float rx, float ry, float rz, float sx, float sy)
{
//this initializer starts when the coordinates are from a file and not set with Pozició = Matrix....., so we are to convert. this runs only one time. overrides set the vertex positions and textures
VertexDeclaration = new VertexDeclaration(device, VertexPositionTexture.VertexElements);
Pozició = Matrix.CreateScale(sx, sy, 1f);             //méretezés
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitX, rx);     //forgatás
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitY, ry);
Pozició *= Matrix.CreateFromAxisAngle(Vector3.UnitZ, rz);
Pozició *= Matrix.CreateTranslation(x, y, z);           //középpont
//we set the starting position - nowhere else we do it, from here only the main loop can modify this,... could.. but does not. this is zone, and has only static objects - never moving
}
public void Rajzolj()
{
//this draws the object (what can be a zone or a static object in it)
foreach (EffectPass pass in effect.CurrentTechnique.Passes)
{
  pass.Begin();
  foreach (Elem elem in Elemek)
  {
    //végigmegyünk az elemeken        
    effect.Texture = elem.Textúra;

    //pozicionálás
    effect.World = Pozició;  //we take the initialized position

    effect.CommitChanges(); //this is needed. if you do not use this, the textures will be screwed up
    device.VertexDeclaration = VertexDeclaration;
    device.DrawUserIndexedPrimitives<VertexPositionTexture>(PrimitiveType.TriangleList, Poziciók, 0, Poziciók.Length, elem.Indexek, 0, elem.Indexek.Length / 3);
    }
  pass.End();
  }
}

就是这样。我仍然猜测它是一些转换,而不是绘图代码。其他地方的位置没有改变。我猜测矩阵就像WPF堆叠变换一样 - 我的问题是并且我不知道在两者之间进行转换的数学运算。 WPF代码完美运行,区域中的模型显示良好。 XNA代码在某种程度上是不好的,因为Inicializálás()从x,y,z等转换错误。在里面。在这方面,我确实需要帮助。

提前致谢。

2 个答案:

答案 0 :(得分:1)

我建议不要以有棱有角的方式存储你的方向......

但有时你的问题可以在xna版本中解决,只需首先应用Z旋转,然后是X,然后是Y.

答案 1 :(得分:1)

您也可以使用CreateWorld,但它没有缩放,所以我决定逐步解决这个问题。首先是放置原点,然后缩放,然后旋转缩放,然后缩放缩放和旋转。

如果你有学位,你将使用弧度而不是学位,使用MathHelper.ToRadians(),就像我一样。

如果你来自WPF并且你的旋转角度在那里工作,但是这里没有,尝试将你的角度乘以360/512,然后再将其计算为弧度。你在评论中看到了这个例子,你将把它用于所有的rx,ry和rz。

        Pozició = Matrix.CreateTranslation(Vector3.Zero);                     //alappozíció az origó
        if (sx != 1 || sy != 1) Pozició *= Matrix.CreateScale(sx, sy, 1f);    //méretezés
        if (rx != 0 || ry != 0 || rz != 0) Pozició *= Matrix.CreateFromYawPitchRoll(
                              MathHelper.ToRadians(rx)                        //WPFből: MathHelper.ToRadians(rx * 360f / 512f)
                              , MathHelper.ToRadians(ry)
                              , MathHelper.ToRadians(rz)
                              );
        if (x != 0 || y != 0 || z != 0) Pozició *= Matrix.CreateTranslation(x, y, z);                         //középpont

如果您可以提供更快的公式* 360/512,或者看起来更好的东西,请发表评论。