我正在尝试编码两个合适的键来以适当的速度更新船舶旅行的前/后方向位置,我想出的是: 在Cmodel:
//Update method
public void Update(Vector3 position, Vector3 orientation)
{
//TO DO - Create an updated version of this.local matrix
this.local *= Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z);
this.local *= Matrix.CreateTranslation(position.X, position.Y, position.Z);
}
比在Game1:
protected override void Update(GameTime gameTime)
{
// Allows the game to exit
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
this.Exit();
// TODO: Add your update logic here
//Update the camera
camera.Update();
KeyboardState keyState = Keyboard.GetState();
// The time since Update was called last.
float elapsed = (float)gameTime.ElapsedGameTime.TotalSeconds;
float RotationAngle = 0;
RotationAngle += elapsed;
float circle = MathHelper.Pi * 2;
RotationAngle = RotationAngle % circle;
Vector3 orientation = new Vector3(0, 0, 0);
Vector3 position = new Vector3(0, 0, 0);
if (keyState.IsKeyDown(Keys.W))
orientation.X = RotationAngle;
if (keyState.IsKeyDown(Keys.S))
orientation.X = -RotationAngle;
if (keyState.IsKeyDown(Keys.A))
orientation.Y = RotationAngle;
if (keyState.IsKeyDown(Keys.D))
orientation.Y = -RotationAngle;
if (keyState.IsKeyDown(Keys.Z))
orientation.Z = RotationAngle;
if (keyState.IsKeyDown(Keys.X))
orientation.Z = -RotationAngle;
//TO DO - Code two suitable keys to update position in the forward/backward direction of Ship travel at a suitable velocity
if (keyState.IsKeyDown(Keys.F))
position.Z = 1f;
if (keyState.IsKeyDown(Keys.B))
position.Z = 1f;
//Update the first model i.e. the Ship
scene[0].Update(position, orientation);
base.Update(gameTime);
}
事情就是当我向左或向右旋转船头时,这些按钮仍然像背部一样工作,朝向我(相机)。 Iadd让它向后移动并向船的“鼻子”方向前进,船的方向?
ANSWER !!!! 我必须做的就是让它与不同的矩阵相乘:旋转首先比翻译和结束本地!谢谢大家的答案。这真是坐在我头上的大时间!
this.local = Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z) * Matrix.CreateTranslation(position.X, position.Y, position.Z) * this.local;
答案 0 :(得分:0)
记住你在学校的数学课!你的“船”在某一点,你有速度/距离和角度你想要移动它。这里有一些pseude代码可以提供帮助:
float a = math.rad(angle);
float newX = currentX + math.sin(a) * distanceToMove;
float newZ = currentZ - math.cos(a) * distanceToMove;
这是一个基本的矢量计算,我现在对轴不确定,但如果你用X,Y和Z修补一下,你应该搞清楚!对不起,如果上面的公式是错误的,那是很久以前因为我实际上做了这样的数学;)
答案 1 :(得分:0)
我可能不对,因为我在AS3中做过这个。
当你旋转船时,你需要重新计算它的运动。
为了简化,如果只有X
和Y
,那么按键会移动10个单位(无论你的单位是多少(例如像素))。将船舶旋转到某个角度时,需要重新计算其在X
和Y
轴上的移动。
他的移动功能如下:
Ship.X += Math.Cos(currentAngle) * Ship.DefaultMoveUnits;
Ship.Y += Math.Sin(currentAngle) * Ship.DefaultMoveUnits;
XYZ
的原则相同。
答案 2 :(得分:0)
为了向前移动,您需要获得船的方向。这不是问题,因为您已经在代码中设置了方向:Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z);
使用此RotationMatrix,您可以提取船首指向的方向所需的值:
//this method uses 'orientation' as the current orientation of the ship
public Vector3 GetForward()
{
Matrix rotation = Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z);
//i don't know the matrix structure of XNA, but it should be possible
//to access each field seperately
//M13 is here: row 1, column 3
//M23 is here: row 2, column 3 and so on
return new Vector3(rotation.M13, rotation.M23, rotation.M33);
}
//now that you got the appropriate vector
//you just can move into the direction of this vector like
Vector3 position = new Vector3(0, 0, 0);
if(keyState.IsKeyDown(Keys.F))
{
position += ship.GetForward();
}
position *= elapsed;
//update the position of the ship here
您可以使用相同的方法获取向右和向上的向量,只需使用旋转矩阵的其他列:
public Vector3 GetRight()
{
Matrix rotation = Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z);
return new Vector3(rotation.M11, rotation.M21, rotation.M31);
}
public Vector3 GetUp()
{
Matrix rotation = Matrix.CreateFromYawPitchRoll(orientation.Y, orientation.X, orientation.Z);
return new Vector3(rotation.M12, rotation.M22, rotation.M32);
}
您可以通过否定相应的向量来获取所有其他方向(向后,向左,向下)。因此,为了获得向后的方向,请使用-GetForward()
。
答案 3 :(得分:0)
为了使其成功,我所要做的就是改变矩阵乘法:
this.local = Matrix.CreateFromYawPitchRoll(orientation.Y,orientation.X,orientation.Z)* Matrix.CreateTranslation(position.X,position.Y,position.Z)* this.local;