提供:Japanese Scratch-Wiki
Scratch 2.0でクローン機能が導入された結果、大量のスプライトを作成することなく、プロジェクトでさまざま処理を効果的に実現できるようになった。クローンは、スプライトのインスタンスであり、スプライトから多くの属性 (プロパティ) を引き継ぎながら、別のオブジェクトとして存在する。通常、プロジェクト内で親スプライトとクローンが果たす役割は多少違うことが多いが、クローンと親となるスプライトは、ほぼすべてのイベントブロック (トリガー) に同じように反応してしまう。そのため、スプライトのみに動作させるつもりでイベントを指定しても、クローンでも同じスクリプトが実行されるという問題が発生する。
基本的な考え方
次のスクリプトを例に考えてみよう:
このスプライトが押されたとき::events hat x座標を (0) 、y座標を ((-100) から (100) までの乱数) にする (10) 回繰り返す x座標を (3) ずつ変える end
「このスプライトが押されたとき」という名前に反して、クローンの作成元スプライトにこのスクリプトが存在する場合、スプライトだけでなくクローンがクリックされたときも実行されてしまう。このスクリプトをスプライトのみに適用し、クローンには適用しないようにするには、どうすればよいだろうか。これには、プライベート変数 (ローカル変数) を利用し、それぞれのトリガー (イベントブロック) を親スプライトまたは子クローンのどちらで実行するか指定するという方法が考えられる。
プライベート変数として作成した変数は、同じ名前であっても、スプライトやクローンごとに別のものとして扱われる。たとえば、「速度」という名前のプライベート変数を持つクローンが3つ存在するとき、それぞれのクローンは別の速度をもつことができる。
同様に、親スプライトでは変数に特定の文字列(「スプライト」など)を指定しておき、クローンでは別の文字列(「クローン」など)を指定することも可能である。これを利用すれば、スクリプトを親スプライトで実行するか、子であるクローンで実行するかを変数の値によって分岐できる。
スクリプト例
緑の旗 がクリックされたときは、その時点で存在するクローンはただちに削除されるので、親となるスプライトだけが存在している。スプライトのローカル変数に親スプライトを表す値を入れるのは、このタイミングが適切である。
親スプライトと異なるふるまいをするクローンの作成
@greenFlag が押されたとき::events hat [オブジェクトの種類 v] を [スプライト] にする // "オブジェクトの種類"は、ローカル変数にしておく (「このスプライトのみ」をチェック)
ここで、「オブジェクトの種類」にいれた文字列「スプライト」は、このスプライトがスプライトであることを表している。「オブジェクトの種類」は、かならずプライベート変数にしておくこと。次に、クローンを作成して、この変数にそれぞれのクローンがクローンであることを表す値を入れておく必要がある:
クローンされたとき // 親スプライトはこのスクリプトを実行しない。クローンのみ実行 [オブジェクトの種類 v] を [クローン] にする
このスクリプトでは、親スプライトの値は変わらない代わりに、個々のクローンでの変数の値が「クローン」に設定される。
以上で、スプライト、クローンそれぞれの種類を変数に格納できたので、あとはこれをもし () なら ブロックで場合分けして、イベントにスプライトだけ (あるいはクローンだけ) が反応するようにすればよい。
[すーっと消える v] を受け取ったとき もし <(オブジェクトの種類) = [クローン]> なら // クローンだけが以下を実行する (10) 回繰り返す [幽霊 v] の効果を (10) ずつ変える end end
親スプライトの「オブジェクトの種類」変数には、「クローン」ではなく「スプライト」を入れたので、上のスクリプトの「もし () なら」内のブロックは、クローンだけで実行される。 このような変数によって処理を分岐する方法は、クローンで何らかの問題が発生している場合のデバッグでも、大いに役に立つ。
クローンごとに異なるふるまいを設定する
次に、1つのスプライトから複数種類のクローンを作成する例を示す。プライベート変数「オブジェクトの種類」に値を設定するのは、各クローンを作成する前であることに注意してほしい。
この例では、クローンに送られたメッセージを親スプライトでは無視するので、各クローンの生成が終わった後、クローンにメッセージが送られる前に、変数「オブジェクトの種類」に親スプライトであることを示す値「スプライト」を設定している。
@greenFlag が押されたとき::events hat [オブジェクトの種類 v] を [ゴースト] にする // 「オブジェクトの種類」は、プライベート変数にしておくこと [自分自身 v] のクローンを作る [オブジェクトの種類 v] を [ゴーストバスターズ] にする [自分自身 v] のクローンを作る [オブジェクトの種類 v] を [スプライト] にする
[ゴーストを送り込む v] を受け取ったとき // 以下のスクリプトは、クローンのみで動作する もし <(オブジェクトの種類) = [ゴースト]> なら [おばけのうめき声 v] の音を鳴らす end もし <(オブジェクトの種類) = [ゴーストバスターズ]> なら // ...クローンの種類によって処理を変えることもできる [気をつけろ!] と言う end
クローンのプライベート変数「オブジェクトの種類」の値は、その時点の親スプライトでの値が継承される。また、クローン作成後の親スプライトでは「オブジェクトの種類」に「スプライト」という文字が指定されているため、メッセージをうけとったときのイベントは実行されない。このテクニックを使えば、1つのスプライトから独自のふるまいをするクローンを複数作成できる。