スプライトの移動、回転、拡大縮小を行う

ページ更新日 :
ページ作成日 :

検証環境

Windows
  • Windows 11
Unity エディター
  • 2020.3.25f1
入力システムパッケージ
  • 1.2.0

この Tips の前提設定

この Tips の説明の前提として以下の設定を事前に行っています。

スプライトを動かす

ゲームではコントローラーを使ってキャラクターを動かしたりすることが多いので、 今回はキーボードを使って画面上に表示されているスプライトを動かしてみたいと思います。

スクリプトを変えればキーボード以外にもゲームパッドなどで動かすこともできます。 各入力については入力系の Tips にまとめていますのでそちらを参考にしてください。

スプライトの配置

ビューにスプライトを1つ配置します。スプライトの配置手順については前の Tips を参考にしてください。 とりあえずビュー上で見えるようなものであれば画像の種類や大きさは何でもいいです。

操作説明のテキストも置いていますが今回の動作には影響ありません。

キーボードでスプライトを動かせるスクリプトを作成する

入力操作によってスプライトを動かすにはスクリプトを作成する必要がありますのでプロジェクトにスクリプトを作成してください。 名前は任意ですがここでは SpriteMove とします。

スクリプトを作成し開いたら以下のように入力します。 今回のスクリプトは移動対象のスプライトにアタッチする前提の処理となっています。

using UnityEngine;
using UnityEngine.InputSystem;  // 追加

public class SpriteMove : MonoBehaviour
{
  // 一定時間ごとに呼ばれます
  void FixedUpdate()
  {
    // キーボードの情報を取得
    var keyboard = Keyboard.current;
    if (keyboard == null)
    {
      Debug.Log("キーボードがありません。");
      return;
    }

    // スプライトの移動処理
    // Translate メソッドでスプライトの位置が移動します
    // Space.World を指定すると回転の影響をうけません
    if (keyboard.leftArrowKey.isPressed)
    {
      transform.Translate(-0.1f, 0, 0, Space.World);
    }
    if (keyboard.rightArrowKey.isPressed)
    {
      transform.Translate(0.1f, 0, 0, Space.World);
    }
    if (keyboard.upArrowKey.isPressed)
    {
      transform.Translate(0, 0.1f, 0, Space.World);
    }
    if (keyboard.downArrowKey.isPressed)
    {
      transform.Translate(0, -0.1f, 0, Space.World);
    }

    // スプライトの回転処理
    // Rotate メソッドでスプライトが回転します
    if (keyboard.spaceKey.isPressed)
    {
      transform.Rotate(0, 0, 5f);
    }

    // スプライトの拡大縮小
    // メソッドはないので localScale プロパティに倍率をかけます
    if (keyboard.aKey.isPressed)
    {
      transform.localScale *= 1.02f;
    }
    if (keyboard.zKey.isPressed)
    {
      transform.localScale /= 1.02f;
    }
  }
}

定期的にスプライトを動かすためには Update メソッドに処理を記述するのですが、 今回は FixedUpdate を作成してそこに記述をしています。

詳しくは別の機会に説明しますが、Update メソッドは実行している環境によって1秒間に呼ばれる回数が異なります。 そのため実行環境によって動くスピードが変わる可能性があります。 FixedUpdate メソッドは1秒間に呼ばれる回数が設定値によって決まっているのでどの環境でも同じスピードでスプライトを動かすことができます。

public class SpriteMove : MonoBehaviour
{
  // 一定時間ごとに呼ばれます
  void FixedUpdate()
  {
    // :
  }
}

今回キーボードで動かす想定なので Keyboard.current でキーボードの情報を取得しています。 ここのコードを変えればマウスやゲームパッドで取得することもできます。

変える場合は以下の Tips を参考にしてください。

// キーボードの情報を取得
var keyboard = Keyboard.current;
if (keyboard == null)
{
  Debug.Log("キーボードがありません。");
  return;
}

SpriteMove クラスで継承している MonoBehaviour クラスにはアタッチしているオブジェクトの情報が含まれており、 transform プロパティにアクセスするとオブジェクトの位置情報などを操作できます。

Transform.Translate メソッドを呼ぶとオブジェクトの位置を現在位置から移動させることができます。 それぞれカーソルキーに合わせて X 座標と Y 座標を移動させています。

Space.World を指定した場合、次に説明する回転の影響を受けずに移動することができます。

// スプライトの移動処理
// Translate メソッドでスプライトの位置が移動します
// Space.World を指定すると回転の影響をうけません
if (keyboard.leftArrowKey.isPressed)
{
  transform.Translate(-0.1f, 0, 0, Space.World);
}
if (keyboard.rightArrowKey.isPressed)
{
  transform.Translate(0.1f, 0, 0, Space.World);
}
if (keyboard.upArrowKey.isPressed)
{
  transform.Translate(0, 0.1f, 0, Space.World);
}
if (keyboard.downArrowKey.isPressed)
{
  transform.Translate(0, -0.1f, 0, Space.World);
}

Transform.Rotate メソッドを呼ぶとオブジェクトを現在の状態から回転させることができます。 引数は指定した軸に対する回転量となります。X 軸は左右、Y 軸は上下に向かう軸であり、Z 軸は奥に向かう軸となってます。 そのため 2D では Z 軸に対して回転を掛けると時計回り、反時計回りに回転するようになります。

// スプライトの回転処理
// Rotate メソッドでスプライトが回転します
if (keyboard.spaceKey.isPressed)
{
  transform.Rotate(0, 0, 5f);
}

ちなみに先ほど Translate メソッドで Space.World を指定していましたが、 これを指定してしないと回転方向に合わせて移動方向も回転するようになります。

例えば下の図は Space.World を指定している場合で、45°回転した状態で右移動操作をしています。

次の図は Space.World を指定していしないで 45°回転した状態で右移動操作をしています。

このように Space.World を指定しない場合は回転した向きに合わせて移動方向も変化します。 これは 3D やラジコン操作的なものを実装するのに有効です。

拡大縮小については現在のスケールに対してスケールの増減を行うメソッドがありませんので、 localScale プロパティに対して計算を行います。

単純に現在の値に倍率をかければキーの押下に合わせて拡大縮小が行えます。 Vector2 で設定すれば X 方向のみ拡大、Y 方向のみ拡大なども可能です。

// スプライトの拡大縮小
// メソッドはないので localScale プロパティに倍率をかけます
if (keyboard.aKey.isPressed)
{
  transform.localScale *= 1.02f;
}
if (keyboard.zKey.isPressed)
{
  transform.localScale /= 1.02f;
}

スクリプトを保存したらスプライトにアタッチしてください。 ヒエラルキー上のスプライトの名前はファイル名と同じになっていますので必要であれば分かりやすいように変えてください。

後はゲームを実行してキーボードで動作するか確認してみてください。

縦や横のシューティングゲームで自機を動かすようなものならこれで十分かと思います。 もちろん敵の動きなども自動で計算するようにすれば同じようなコードで動かすことができます。