Redpoll's 60
 Home / 3Dプログラミング入門 / 第2章 $§$2-31
第2章 2D空間におけるオブジェクトの運動
$§$2-1 オブジェクトの初期状態$§$2-17 衝突判定 5
$§$2-2 行列による変換の詳細 1$§$2-18 初期状態における頂点情報の取得について
$§$2-3 行列による変換の詳細 2$§$2-19 衝突判定 6 (軸平行な長方形同士の衝突)
$§$2-4 自転と公転$§$2-20 衝突判定 7 (円盤 vs 長方形)
$§$2-5 一体化したオブジェクトの運動 1$§$2-21 衝突判定 8 (回転した長方形同士の衝突)
$§$2-6 一体化したオブジェクトの運動 2$§$2-22 衝突判定 9 (「倉庫番」プログラムの作成)
$§$2-7 一体化したオブジェクトの運動 3$§$2-23 衝突判定 10 (円盤 vs 三角形)
$§$2-8 指定方向へのオブジェクトの移動 1$§$2-24 衝突判定 11 (直線 vs 長方形、円盤、直線)
$§$2-9 指定方向へのオブジェクトの移動 2$§$2-25 円と直線による補間曲線 1
$§$2-10 指定方向へのオブジェクトの移動 3$§$2-26 円と直線による補間曲線 2
$§$2-11 指定方向へのオブジェクトの移動 4 (連射プログラムの実装)$§$2-27 その他の重要事項 1 (UnityのTransformクラスによる記述 ; カメラ移動の基本)
$§$2-12 指定方向へのオブジェクトの移動 5$§$2-28 その他の重要事項 2 (画面に表示されるXY平面の範囲 ; ミニマップの実装)
$§$2-13 衝突判定 1 (点 vs 円盤、長方形 ; ローカル座標からワールド座標への変換 2D)$§$2-29 その他の重要事項 3 (スクリーン座標からワールド座標への変換 2D; スクリーンショットの撮影範囲)
$§$2-14 衝突判定 2$§$2-30 課題 1
$§$2-15 衝突判定 3$§$2-31 課題 2
$§$2-16 衝突判定 4

$§$2-31 課題 2


引き続き本節も読者用の課題であり、ここでの課題はオブジェクトの一体化運動に関するものである。

(本節の課題は小学校低学年向けの算数オリンピック「キッズBee」ファイナルの問題を元に作成したものである)



下図1~3に示される3種類の円盤がある。一番大きな円盤が Red (図1)、中くらいの大きさの円盤が Green (図2)、一番小さい円盤が Blue (図3) であり、いずれも初期状態においてはその中心が原点に置かれている。

  • 図1 Red 初期状態
  • 図2 Green 初期状態
  • 図3 Blue 初期状態

Redは1つしかないがGreenは全部で4つあり、Blueは全部で16個ある。今回はRed、Green、Blueを一体化して運動させるがその階層構造はRedが一番上の親オブジェクト、その下に4つのGreen、さらに各Greenの子オブジェクトとして4つのBlueという構造である (図4)。
親オブジェクトへのアタッチの際には、Red上には4つのGreenを図5のように配置し、各Green上には4つのBlueを図6のように配置する。図7は全てのオブジェクトを一体化した状態である (4つのGreen、16個のBlueをアタッチポジションに移動させた状態。Redは初期状態のままであり、どの円盤も回転はしていない)。

図4 オブジェクトの階層構造
図5

図6
図7 どの円盤も回転はしていない

そして今回の各円盤の回転速度はすべて同じであり、毎フレーム 時計周りに $0.9^\circ$ ずつ回転する。つまり Red、Green、Blueの1フレームあたりの回転角度は時計周りに $0.9^\circ$ であり、どの円盤も400フレームで1回転する

すべてのオブジェクトが一体化した状態(図7の状態)において、下図8のAの位置にある青い円盤上に小さな矢印が乗せられている。図9はこの矢印の初期状態であり、初期状態では x軸マイナス方向を向いている (左図の青い円盤上においても矢印は回転していないので x軸マイナス方向を向いている)。

図8 青い矢印は x軸マイナス方向を向いている
図9 青い矢印(Arrow) 初期状態


上図8の状態からすべての円盤が同時に回転を始めたとする (回転方向は時計周り)。
ここでの課題はすべての円盤が回転を開始してからちょうど300フレーム後に、上記の小さな矢印がどの位置でどの方向を向いているかを確認するプログラムの作成である。

プログラムで使用するインスタンス変数 及び定数は以下のとおり。

i_frameCount
  :  フレーム数をカウントするためのint型インスタンス変数。

i_MOVE
  :  回転開始用のスイッチを表すbool型インスタンス変数 (この変数は使わずに上記の i_frameCount で代用することもできる)。

i_degree
  :  円盤の回転角度を表すfloat型インスタンス変数。

G[0]~G[3]
  :  Red上に4つのGreenを配置する際のアタッチポジションを表す定数配列(Vector2[]型 ; 図10参照)。

B[0]~B[3]
  :  Green上に4つのBlueを配置する際のアタッチポジションを表す定数配列(Vector2[]型 ; 図11参照)。

上でも示したように初期状態のRedに4つのGreenをアタッチする際には下図10のように配置するが、図中の $G_0$~$G_3$ は各Greenのアタッチポジションであり(各円盤の中心)、上記の定数配列 G[0]~G[3] にはこれらの位置がセットされている。
B[0]~B[3] の内容も同様であり、この配列には初期状態のGreenにアタッチする際の4つのBlueのアタッチポジション $B_0$~$B_3$ (図11)がセットされている ($B_0$~$B_3$ も各円盤の中心である)。

図10  G0~G3は各円盤の中心
図11  B0~B3は各円盤の中心

プログラム中においては上記の各円盤 Red、Green、Blue は RedGreenBlue として用意されており、Green は要素数 4 の配列、Blueは要素数 16 の配列である。また 小さな矢印はプログラム中では Arrow として用意されている。

プログラムは Code1 に作成するものとし、上で述べたすべての円盤の回転開始は S キーが押されたときに始まるものとする。Code1は最初の段階では初期化ブロックと S キーが押された際の処理を記述する空のifブロックのみが用意されている。
[Code1]
if (!i_INITIALIZED)
{

    i_INITIALIZED = true;
}


if (Input.GetKeyDown(KeyCode.S))
{
}




(プログラムの解答例については Sec231_Ans.txt を参照。なお この課題のオリジナルは算数の問題なので頭で考えて答えを出すこともできるが、この問題は8才や9才の子供が挑戦するものであるから余程の自信がない限りはプログラミングによる解決を考える方が賢明である。オリジナルの問題については以下のリンクを参照)

(参考資料)
https://www.sansu-olympic.gr.jp/past-question/114/

















© 2020-2024 Redpoll's 60 (All rights reserved)