2016-04-30 9 views
0

私はXNAの宇宙船の試合をして、私は回して銃を発射しようとしています。私は船にウェイポイントを与えることができるようにそれを得ることを試みる問題に遭遇した。何らかの理由で私は船を動かすことができます、または私はそれを回すことができますが、私はそれを一度に行うことはできません。それは本当に奇妙です。C#XNAムーブメント - 両方を回すことも移動することもできません。

基本的には、回転コードをコメントアウトすると、まっすぐ飛ぶでしょう。さもなければ回転しますが、動きません。

if (GoToWayPoint == true) 
{ 

    //CurrentWayPoint.Normalize(); 
    Pos.Normalize(); 

    float angle = (float)Math.Atan2(CurrentWayPoint.X - Pos.X, CurrentWayPoint.Y - Pos.Y); 

    //Rotate if 
    if (Rotation > angle && Rotation - TurnSpeed >= angle) 
    { 
     Rotation -= TurnSpeed; 
    } 
    else if (Rotation < angle && Rotation + TurnSpeed <= angle) 
    { 
     Rotation += TurnSpeed; 
    } 
    else 
    { 
     Rotation = angle; 
    } 

    //Move forward if it's facing the right direction 
    if (Rotation == angle) 
    { 
     Velocity.X += (float)Math.Cos(Rotation) * TangentialVelocity * Speed; 
     Velocity.Y += (float)Math.Sin(Rotation) * TangentialVelocity * Speed; 
    }   

    if (Pos == CurrentWayPoint || Vector2.Distance(Pos,CurrentWayPoint) < 10) 
    { 
     Pos = CurrentWayPoint; 

     GoToWayPoint = false; 
    } 

} 

//Movement, player controlled 
if (PlayerControlled == true) 
{ 
    KeyboardState NewKey = Keyboard.GetState(); 

    //Move Up 
    if (NewKey.IsKeyDown(Keys.Up) || NewKey.IsKeyDown(Keys.W)) 
    { 
     Velocity.X = (float)Math.Cos(Rotation) * TangentialVelocity * Speed; 
     Velocity.Y = (float)Math.Sin(Rotation) * TangentialVelocity * Speed; 
    } 

    //Move Down 
    if (NewKey.IsKeyDown(Keys.Down) || NewKey.IsKeyDown(Keys.S)) 
    { 
     Velocity.X = (float)Math.Cos(Rotation + Math.PI) * TangentialVelocity; 
     Velocity.Y = (float)Math.Sin(Rotation + Math.PI) * TangentialVelocity; 
    } 

    //Move Right 
    if (NewKey.IsKeyDown(Keys.Right) || NewKey.IsKeyDown(Keys.D)) 
    { 
     Rotation += TurnSpeed; 
    } 

    //Move Left 
    if (NewKey.IsKeyDown(Keys.Left) || NewKey.IsKeyDown(Keys.A)) 
    { 
     Rotation -= TurnSpeed; 
    } 
} 

//Update Movement 
Pos += Velocity; 

//Friction 
float i = Velocity.X; 
float j = Velocity.Y; 

Velocity.X = i -= Friction * i; 
Velocity.Y = j -= Friction * j; 

さらに、矢印キーを使用してGameObjectを制御できるコードがあります。そのコードは正常に動作し、同じタイプコードを使用して前進します。

+0

'(GoToWayPoint == true)'を実行して条件付きの評価をする必要がないことを伝えたいだけです。 'GoToWayPoint'は単独でtrueかfalseに評価されます。 – paste

答えて

1

あなたの問題は、主に次の行にある:その条件がtrueと評価されたとき

if (Rotation == angle) 

あなたの船は前方にのみ移動します。残念ながら、角度はfloatであるため、決して真実ではありません。 2つの浮動小数点数を特に指定しないかぎり、2つの浮動小数点数を等しくすることは非常に難しいです(他の方法もありますが、この場合は無関係です)。あなたがここにangleを計算

float angle = (float)Math.Atan2(CurrentWayPoint.X - Pos.X, CurrentWayPoint.Y - Pos.Y); 

この意志すべての可能性には1.519573617...のように、小数点以下の桁の多くのあなたの価値を与えます。さらに、あなたは一定の量だけ船を回しています。TurnSpeedは、あなたの正確な方向値をスキップし、角度方向を変え、再び無限にスキップします。だからあなたは決して前進しません。

一つはそこまでif文を失うことである。

は、私はあなたが試すことができます私の頭の上から考えることができる2つのソリューションがあります。そうすればあなたのクラフトは間違った方向に進むが、それは動くように方向を調整する。

もう1つは、Rotationangleを比較するためにイプシロンを使用することです。それは次のようになります。

if (Math.Abs(Rotation - angle) < epsilon) 
{ 
    Rotation = angle; 
    // move forward 
} 

山車、余地のすなわちepsilon量を比較したとき、これはあなたの余地のビットを与えます。それはあなたのTurnSpeedが区間全体にジャンプしないように十分に大きくなければなりませんが、正確な方向とそれほど顕著に異なるわけではありません。

-1

あなたは回転を使って移動して撮影しています。より正確には、撮影と移動に同じ角度を使用しています。船の位置を上に移動、

第一/下/右の角度の使用なし/左:

は、次の2つのソリューションを持っています。つまり、コードはif(key up is pressed) ship.position.Y -= ship.speed;のようになります。これは、描画と撮影の角度を解放したことを意味します。

第2に、船の新しい角度変数を作成します。今あなたは2つを持っています(moveAngleshootAngleと言うことができます)。だから、あなたが船をmoveAngleで動かしているときに、どこで撮影するかを計算する必要があるときは、shootAngleを使ってください。残っているすべてのことは、描画する角度を選択することです。

ボーナス:左右のキーを使用して、船が見ている場所から90度歪んでください。

関連する問題