ソラマメブログ
QRコード
QRCODE
※カテゴリー別のRSSです
アクセスカウンタ
読者登録
メールアドレスを入力して登録する事で、このブログの新着エントリーをメールでお届けいたします。解除は→こちら
現在の読者数 2人
オーナーへメッセージ

  
Posted by at

2008年03月23日

ドアと窓を作ってみる(その2 - 窓編)

今回は窓をつくります。窓といってもただの窓ではありません。中が見えないようにカーテンをつけます。さらに、そのカーテンを開け閉めできるようにします。もちろん誰でも開けられるようでは困るので、特定の人しか開け閉めできないようなカーテンにします。
いままでは、サンプルスクリプトをそのまま入れてスクリプトを動かすことで、スクリプトを使う楽しさを体験してもらうことを狙いとしてきました。今回は一応設計めいたことに挑戦してみましょう。と言っても難しいことはありません。手順を追ってきちんとやっていけばだれにでもできます。

まず、「何をしたいのか(させたいのか)」を明確にしましょう。
そのために「なにをしなければいけないか」、もしくは「なくてはいけないか」もはっきりさせましょう。こういうこと5W1Hに従い「いつ、どこで、だれが、なにを、どうやって」実現するのか整理しておきます。

1)窓にカーテンをつける
 いつ?>常に。どうやって?>カーテンのついた窓のテクスチャーを貼る。
2)カーテンを開ける
 いつ?>窓にタッチしたとき。誰が?>特定のグループのメンバーが。どうやって?>テクスチャーを貼りかえる。
3)カーテンを閉める
 いつ?>窓にタッチしたとき。誰が?>特定のグループのメンバーが。どうやって?>テクスチャーを貼りかえる。
4)特定の人だけカーテンを開けられる
 いつ?>タッチしたとき。どうやって?>タッチした人がグループメンバーかどうか検知する。 

前回のドアの時もそうでしたが、スクリプトには状態 (state) という概念があります。前回のドアの時はドアの開いた状態(state open) と閉まった状態(state close) がありました。また、それ以外に実際のスクリプト上では初期設定を行う default という状態もありました。今回もカーテンの開いた状態と閉まった状態がありますので状態(state)に関してはドアの時と同じです。今回はdefault の状態をカーテンの閉まった状態(close) と考え、default と state open の二つの状態(state)でスクリプトを作ってみたいと思います。

スクリプトを書いていくときに、最初の状態(state) は必ず default が使われます。この default という状態(state)の中でやってもらいたいことをスクリプトを使って書いていきます。やってもらいたいことはさっき書き出したとおりですね。まずは(1)窓にカーテンをつける=カーテンのついた窓のテクスチャーをプリムに貼って窓をつくる。でしたね。今回使うテクスチャーはカーテンが閉まった状態の窓とカーテンが開いた状態の窓、それを内側と外側それぞれ作ります。合計4枚のテクスチャーが必要になるということです。まず、カーテンの閉じた状態の窓のテクスチャーを貼ることにしましょう。

default
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartaincloseout", <1, 1, 0>, <0, 0, 0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainclosein", <1, 1, 0>, <0, 0, 0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
}

"cartaincloseout" が閉じたカーテンのテクスチャー外側、"cartainclosein" が閉じたカーテンのテクスチャー内側です。"Brazillian rosewood" というのは窓枠の部分に貼ったテクスチャーです。SLを始めた時に初期でついてきたテクスチャーの中にありますが、ここはそれぞれ好みで色んなテクスチャーを選んでください。上記スクリプトと、スクリプトの中で指定したテクスチャーをオブジェクトのコンテンツの中に入れると、下の写真のように窓の体裁をなすようになります。
わかりやすいようにコピーして、窓の内側と外側が見えるようにしました。



次にカーテンの開いた状態の窓を作ってみることにしましょう。作り方はカーテンの閉じた状態の窓と全く同じです。
ただし、テクスチャーだけが窓の開いた状態のものに変わります。今回は "cartainopenout" と "cartainopenin" という名前になっています。

default
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartainopenout", <1, 1, 0>, <0, 0, 0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainopenin", <1, 1, 0>, <0, 0, 0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
}

下の写真をご覧ください。ちゃんとカーテンが開いて窓の向こうの景色が見えますね。わかりやすいようにカーテンを閉めた状態のものと並べてみました。



あとはこの二つの状態をいったりきたりできるようにすればいいわけです。最初に5W1Hで整理したように、タッチしたときに切り替わるようにしたいんでした。そこで窓にタッチしたときに二つの状態を行ったり来たりできるようなスクリプトを追加します。開閉二つの状態と、その間を窓にタッチするたび行ったり来たりできるスクリプトは下記のようになります。
default
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartaincloseout", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainclosein", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
touch_start(integer total_number)
{
state open;
}
}
state open
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartainopenout", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainopenin", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
touch_start(integer total_number)
{
state default;
}
}

見ていただくとわかるとおり、カーテンが閉まった状態(default)の方は touch_start(integer total_number) という部分とstate open; という部分が追加されました。これは「タッチしたときに、state open という状態(state)に移行するということを意味しています。同様にしてカーテンが開いた方の状態(state open)の方も、touch_start(integer total_number) と、こちらは state default; という記述があります。これも同様に「タッチしたときにstate default(つまりカーテンの閉まった状態)に移行しますということです。

上記スクリプトと4種類のテクスチャー(窓の開閉x内と外)を窓のプリム(オブジェク)のコンテンツに入れて家にとりつけてみました。それが下の写真です。



タッチするとちゃんとカーテンが開いて部屋の中が見えます。当然部屋からもカーテンを開けて外を見ることができます。



最後の仕上げはセキュリティーですね。タッチしたときにグループメンバー以外はカーテンを操作できないようにします。
グループメンバーかどうかを検知するには llDetectedGroup(0) という機能を使います。この機能を用いて条件文をつくり、グループメンバーであればカーテンが開き(閉じ)、グループメンバーでない場合は"You are not granted to touch" というメッセージが出るようにします。これを行うために以下の記述を touch_start(integer total_number) に続けて加えます。

touch_start(integer total_number)
{
if(llDetectedGroup(0);)
{
state open; ((閉める場合は state defualt; )
}
else
{
llSay(0, "You are not granted to touch");
}

これを入れて完成させたスクリプトが下記のものです。

default
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartaincloseout", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainclosein", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
touch_start(integer total_number)
{
if(llDetectedGroup(0))
{
state open;
}
else
{
llSay(0, "You are not granted to touch");
}
}
}
state open
{
state_entry()
{
llSetPrimitiveParams([PRIM_TEXTURE, 1, "cartainopenout", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 3, "cartainopenin", <1.0, 1.0, 0.0>, <0.0, 0.0, 0.0>, 0.0]);
llSetPrimitiveParams([PRIM_TEXTURE, 0, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 2, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 4, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
llSetPrimitiveParams([PRIM_TEXTURE, 5, "Brazillian rosewood", <1,1,0>, <0,0,0>, 0]);
}
touch_start(integer total_number)
{
if(llDetectedGroup(0))
{
state default;
}
else
{
llSay(0, "You are not granted to touch");
}
}}

スクリプト全般に言えることですが、中で使われている括弧( { や   }  )の数に気をつけてください。
ちゃんと正しい場所に使われているか。もしくは前の括弧と後の括弧の数が合っているかなどです。実際にスクリプトを書くときには In World (SL内)でエディターを使って書いていきますので、括弧に限らず誤りがあると保存するときにエラーが出て知らせてくれます。よくある文法エラーとしてはこの括弧の間違いや、セミコロンのつけ忘れ、もしくはいらないところにつけてる、などがあります。この辺は習うより慣れろで実際に使っているうちに誤りも少なくなってくるでしょう。

長い記事でしたが、ようやく終了です。グループ限定のセキュリティーの方もちゃんと動いてくれました。(下写真)



家づくりが一段落したので、今度は久しぶりに Avimatar で遊んでみましょう。前回は静止ポーズでしたが、次は動きのあるものに挑戦です。題材としては、もはや旬は過ぎた感は否めませんが小島よしおですw お楽しみに。  

Posted by Jamaica at 08:37Comments(3)家づくり

2008年03月20日

ドアと窓を作ってみる(その1 - ドア編)

家づくりの最後はドアと窓です。まずはドアから作ってみましょう。
ドアの基本的な機能として、普段は閉じていて侵入者を防ぐ、家の主もしくは関係者が来たときは開いて中に入れる、中に入った後は再び閉まる、といったところでしょうか。スクリプトを入れる前にまず、ドアをつくります。右クリックから「作成」を選び、ボックスを作っておいてから、それを伸ばして一枚の板にしてドアにします。テクスチャーはとりあえずあるものの中から適当に張っておきましょう。もちろん自分でカッコ良いドアのテクスチャーを作ってはってもOKです。わたしはとりあえず間に合わせてで下の写真のようなものを作ってみました。



このドアにスクリプトを入れてみます。スクリプトは下記のものをコピー・ペーストして使ってください。
やり方はオブジェクトの編集メニューからコンテンツのタブを選び「新しいスクリプト」ボタンを押します。するとHello Avatar! というスクリプトが出てきますので、これをすべて消して下記のスクリプトをそこにコピー・ペーストします。保存をすることを忘れないでください。名前もNew ScriptとなっているのをDoorScriptとか何か適当な名前に直しておきましょう。
最初から3行目の vector MOVE_TO=<1.0,-1.0,0.0>; の数値は作るドアの大きさ、取り付ける場所などによって微妙に変わってきます。実際にドアの開閉をしながら微調整をしてみてください。
llSetText("Staff Only", <1.0,1.0,1.0>,1.0); はドアの上にStaff Only という文字を表示させるためのものです。この表示が必要ない場合はこの命令自体をとってしまうか、Staff Only を消して "" だけにしてください。
ドアは開けてから5秒後に自動的に閉まるように設定されています。開けてから閉まるまでの間隔を調整するのは llSetTimerEvent(5.0); の値を 5.0 から変えてやります。また、5秒経たなくてもタッチすれば閉まるようになっています。

rotation rot;
vector pos;
vector MOVE_TO = <1.0,-1.0,0.0>;

default
{
state_entry()
{
llSetText("Staff Only",<1.0,1.0,1.0>,1.0);
llSetSitText("");
llSetTouchText("Enter");
pos = llGetLocalPos();
rot = llGetRot();
state close;
}
}

state open
{
state_entry()
{
llSetRot( rot*llEuler2Rot(<0.0,0.0,90.0>*DEG_TO_RAD));
llSetPos( pos+MOVE_TO);
llSetTimerEvent(5.0);
}

touch_start(integer total_number)
{
state close;
}
timer()
{
llSetTimerEvent(0);
state close;
}
}

state close
{
state_entry()
{
llSetRot(rot);
llSetPos(pos);
}

touch_start(integer total_number)
{
if(llDetectedGroup(0))
{state open;}
else
{llSay(0,"You are not allowed to enter.");}
}
}

スクリプトをコンテンツタブに入れ、ドアの完成ですが、このときグループ設定をどうするかを確認しましょう。今回のドアスクリプトはオブジェクトに設定されたグループと同じグループの人だけがドア操作できるようになっています。それ以外の人がドアにタッチすると "You are not allowed to enter" というメッセージが出るようになっています。オブジェクト(プリム)にはそれを作成したときに作者がアクティブにしていたグループが設定されています。オブジェクトのグループ設定を変えたい場合は編集メニューの一般というタブを選びグループの設定を変えることができます。(下の写真参照)



さあ、これでドアの完成です。ちゃんと開いていますね^^



次回は窓をつくります。中が見えないようにカーテンをかけて、さらにそれが開け閉めできるようにします。  

Posted by Jamaica at 15:22Comments(4)家づくり