GP11 チーム制作 02

やることリスト

今週はスクリプトからゲームオブジェクトを動かす方法について学ぶ。

とりあえず Cube を動かしてみよう。

まず新規プロジェクトを作成する。

Cube を作成する。 Hierarchy ビュー上部にある Create メニューから Cube を選べばよい。

スクリプトを作成する。 Project ビュー上部にある Create メニューから Javascript を選べばよい。スクリプトファイルの名前は TestMotor としておこう。

スクリプトの内容は次のようにする。

function Update () {
    transform.x = Mathf.Sin(Time.time * 2.0) * 5.0;
}

TestMortorスクリプトをドラッグ&ドロップで Cube に与える。

実行する。 Cube が左右に動けば成功。

フレームと Update について把握しよう

「フレーム」とは……Unity におけるフレームと Update

Update 関数の中でゲームオブジェクトの状態を更新することで、動きを作りだすことができる。

動きを作り出す際に重要になるのが時間の概念。 Unity で時間を扱うには Time クラスを使う。この中でも最も使用頻度が高いのが Time.timeTime.deltaTime.

Time.time - 開始時点からの時間(秒数)を得る。

Time.deltaTime - 前の Update から今の Update までの差分の時間(秒数)を得る。

deltaTime と time

何かを動かす場合、あるいは経過時間を計測する場合には、必ず Time.timeTime.deltaTime を使うようにしよう。

トランスフォームについて知ろう。

トランスフォーム (Transform) とは「変形」を意味する単語。 3D CG の文脈では、まあ単に変形の事を指して言うこともあるけど、たいていは位置回転スケーリングの3要素のことを指す。

Inspector 上ではこんな感じで表示されている。

Transform

これをスクリプトからアクセスする方法について解説する。

位置 (position) へのアクセス

transform.position 経由でアクセスできる。いちばん簡単なのは、X, Y, Z のそれぞれの要素に別々にアクセスする方法。例えば次のコードのようにすると、秒間 1.5 の速度でX軸+方向へ移動する。

function Update () {
    transform.position.x = Time.time * 1.5;
}

また Vector3 型の値を代入することでも更新できる(というかむしろこちらがスタンダードなアクセス方法)。上のコードと下のコードはまったく同じ動きをする。

function Update () {
    transform.position = Vector3(Time.time * 1.5, 0, 0);
}

三角関数を使って縦にぴょんぴょん動かしてみよう。

function Update () {
    transform.position.y = Mathf.Abs(Mathf.Sin(Time.time * 6.0));
}

回転 (rotation) へのアクセス

transform.rotation 経由でアクセスできる……が、クオータニオンを使わなければならない。これがちょっと難しい。詳しくは次で解説する。

スケールへのアクセス

transform.localRotation 経由でアクセスできる。例えば次のようにすると横方向にブヨブヨと拡大縮小する。

function Update () {
    transform.localScale.x = Mathf.Sin(Time.time * 6.0) + 1.5;
}

クオータニオンで回転を表現しよう

クオータニオンとは日本語で四元数とも呼ばれる数学上の概念。高校数学で虚数単位 i について習ったと思うけど(今は習わない?)、この虚数単位を i, j, k の3つにまで拡張したという恐ろしいもの。これは回転を表現するのに都合が良いということを、ちょっと昔の偉い人が見つけた。今では CG とか航空機の制御とか、そういう分野で必ず使われる概念になっている。

まあ数学的にどうこうという話はさておき、 Unity では Quaternion クラスに便利な道具が色々揃っているので、中身は知らなくても、どう使うのかさえ把握しておけばよい。

軸周りの回転を表現する

Quaternion.AngleAxis を使うと、ある軸を中心にした回転を表現することができる。例えば次のようにするとY軸周りに秒間120度の角速度で回転する。

function Update () {
    transform.rotation = Quaternion.AngleAxis(Time.time * 120.0, Vector3(0, 1, 0));
}

回転を合成する

クオータニオンは掛け算によって回転を合成できるという便利な特性がある。例えば「Y軸周りに秒間120度の回転」と「X軸周りに秒間77度の回転」を合成するには次のようにする。

function Update () {
    transform.rotation = Quaternion.AngleAxis(Time.time * 120.0, Vector3(0, 1, 0)) *
                         Quaternion.AngleAxis(Time.time * 77.0,  Vector3(1, 0, 0));
}

回転の順序を意識しよう

回転というのは移動とは違って回転する順序によって結果が異なる(身近な物を手にとって、実際に回転させてみよう!)。なので、どういう順序で回転させるかがとても重要になる。

クオータニオンの掛け算によって回転を合成するとき、掛け算の右側が最初の回転、左側が次の回転として扱われる。例えば上の例では、X軸周りに回転してから、Y軸周りの回転が発生する。

回転の合成を使ったときに、イメージと異なる結果が得られたら、回転の順序が間違っていないかどうかを確かめるようにしよう。