関数:changed


changed(integer change)

チェンジイベントはプリムやオブジェクトの特定の状態が変化したときに、発生します。変数changeのパラメーターは次に示す値の1つまたは複数のビットフィールドで表現します。
定数 解説
CHANGED_INVENTORY 0x1 オブジェクトのインベントリーが変更された。(これにはアイテムが追加されたり、削除されたり、リネームされたり、ノートカードが編集され、保存された場合も含まれます。)
CHANGED_COLOR 0x2 オブジェクトの色や透明度が変更された。
CHANGED_SHAPE 0x4 オブジェクトの形(例:ボックス→シリンダ への変更など)パスカット、中空の形と大きさ、ひねり、上層部、テーパーが変更された
CHANGED_SCALE 0x8 オブジェクトの大きさが変更された
CHANGED_TEXTURE 0x10 オブジェクトのテクスチャ、オフセット、繰り返し回数、回転、輝き、マッピング、凹凸(ただし、透明度が変更された場合はCHANGED_COLORで通知されます。)が変更された。
CHANGED_LINK 0x20 オブジェクトがリンクされた、またはリンクが解除された。(アバターがオブジェクトにSitしたとき、UnSitしたときも含まれます。)
CHANGED_ALLOWED_DROP 0x40 オブジェクトのコンテンツにアイテムがドロップされた。llAllowInventoryDrop()関数によって許可を与えられた場合だけこの値が返されます。この関数はオブジェクトのモディファイパーミッションを持たない人によってドロップされたアイテムを受け入れることを許可します。
CHANGED_OWNER 0x80 オブジェクトのオーナーが変わった。物が購入されるとき、あるいは、新しく購入された物がrezされるとき、物がグループに譲渡されるとき、この値は無視されます。
CHANGED_REGION 0x100 オブジェクトが存在するSIMが変更された。
CHANGED_TELEPORT 0x200 オブジェクトがテレポートした。
これらの値はビット化されているので、AND演算やOR演算を適用できる。
2つのフラグが同じイベントで認識されることがあります。
例えば「テクスチャーを引き伸ばす」にチェックを入れずにオブジェクトの大きさを変えると、オブジェクトのリサイズにあわせてテクスチャーの大きさ(繰り返し)も変わりますが、こういった場面で起こります。
また、CHANGED_REGIONとCHANGED_TELEPORTは、同時に発生します。
これを常に考慮して、あなたのイベントの内容がすべてのケースで対応する為に"if (change==CHANGED_LINK)" ではなく"if(change&CHANGED_LINK)"を書いてください。
同様に、IF/ELSE("else if (change & CHANGED_SCALE)")を使うと、発生した状態の1つにしか反応しません。
あなたがIFステートメントだけを支持するならば、あなたのchangedイベントはIFステートメントごとにチェックを実行する必要があります、しかし、この方法は非常に珍しい状態も含めてすべての状態に対応できます。

注意:
changeパラメータは、どんなタイプの変化が起こったかについて明示するだけです。
変更されたオブジェクトのバージョンとオリジナルの違いではありません。
何が変わったかを正確に把握する必要があるなら、スクリプトは関連したパラメータを保存し、変化の前後からその値を比較しなければなりません。
timerイベントを通してllGetRot()関数llGetPos()関数を使わなければ、変更されたオブジェクト(プリム)の位置と回転をリアルタイムに検出できません。
位置の変化は、moving_startイベントmoving_endイベントを用いて見つけることもできます。
アバターがオブジェクトに座るとき、彼らはリンクの一部とみなされます。
アバターが物にSitするか、UnSitすると、changed()イベントはパラメータとしてCHANGED_LINKを返します。
どちらであったかについて検出するには、llAvatarOnSitTarget()関数を使ってください。
llAvatarOnSitTarget()関数はアバターがオブジェクトに座っていないならば、NULL_KEYを返しまたはシットターゲットに座っているアバターのキー
を返します。

Example:
default {
   [[state_entry]]() {
       llSitTarget(<0, 0, 0.1>, ZERO_ROTATION);
   }
   
   changed(integer change) {
       if (change & CHANGED_LINK) {
          // llSleep(0.5);
           key av = llAvatarOnSitTarget();
           if (av) {
               llSay(0, "Get off!");
               llUnSit(av);
           }
       }
   }
}

詳細
定数(数値) changed()が発生する場合 changed()が発生しない場合
CHANGED_INVENTORY プリムのインベントリにアイテムが追加されたとき。 スクリプトをリセットしたとき
プリムのインベントリーからアイテムが削除されたとき ノーコピーアイテムが手動で移動されドラッグ&ドロップによってプリムからユーザーインベントリーへ戻されたとき。しかし、この操作ではアイテムが削除されない。
プリムのインベントリーのアイテムの名前またはディスクリプション変更したとき。 インベントリーにプリムのオーナーが所有してない新しいアイテムをドロップされllAllowInventoryDrop()関数を使って追加されたとき。
プリムのインヴェントリにあるアイテムのパーミッションが変更されたとき。 llRemoveInventory()関数でアイテムが削除されたとき。しかし、これはバグなのかもしれない。
see: http://jira.secondlife.com/browse/SVC-304
インベントリにあるノートカードの内容が変更され保存されたとき。またはスクリプトがリコンパイルされたとき。
リンクしたオブジェクトの中の他のプリムからインベントリが変更される場合。例えば、ルートプリムから子プリムにアイテムを渡した場合、子プリムの中でこのイベントが起きる。また、逆もまた同様である。
CHANGED_SCALE リンクされているか、されてないかに関わらず、そのプリムがリサイズされた場合。 リンクされたオブジェクトの別のプリムから、同じオブジェクト中の個別のプリムをサイズ変更する場合。具体的にはルートプリムから特定の子プリムのサイズを変更した場合などがこれにあたる。逆もまた、同様である。
リンクされたオブジェクトのルートプリムから全オブジェクトをサイズ変更する場合 リンクされたオブジェクトの子プリムから全オブジェクトをサイズ変更する場合
CHANGED_LINK 2つ以上のプリムをリンクしたとき。 アバターがSitまたはUnSitしたときにアバターの装備品にはイベントは発生しない。
オブジェクトのリンクを全て解除したとき。 アバターが装備品を装着したときには、装備品にはイベントは発生しない。
オブジェクトから1つのプリムのリンクを解除したとき。 他の装備品が装着されたときにはそれまでの装備品にはイベントは発生しない。
オブジェクトにアバターがSitしたとき。 オブジェクトにアバターが座ったときにはアバターの装備品にはイベントが発生しない。
座っていたアバターがオブジェクトから立ち上がったとき。 座っているアバターにオブジェクトを装着してもそのオブジェクトにはイベントは発生しない。
リンクしているオブジェクトをコピーしたとき。 単一のプリムをコピーしたとき。
オブジェクトのプリムのタイプや形を変更したとき。
CHANGED_OWNER アバターがオブジェクトを購入したときにオリジナルのオブジェクトにイベントが発生します。 アバターがオブジェクトのコンテンツを購入したときにはオリジナルのオブジェクトにイベントが発生しません。
アバターがオブジェクトのコピーを購入するときにオリジナルのオブジェクトにイベントは発生します。 次のオーナーが、購入したオブジェクトをREZしたときに、複製のオブジェクトの中でイベントが発生します。
アバターがオブジェクトをTAKEするか、そのオブジェクトをコピーしたとき、オリジナルのオブジェクトにイベントが発生します。
アバターが最初にREZしたときに新たにREZされた複製のオブジェクトにイベントが発生します。(それでも、on_rez()イベントは最初に発生します。)
オブジェクトがコピーされたか購入されたに関わらず、これは起こります
オブジェクトがグループに譲渡されたとき。
CHANGED_REGION アバターが新しいSIM(リージョン)にテレポートした、あるいは直接新しいSIMに入ったとき装備品のルートプリムにイベントが発生します。 アバターが新しいSIMにテレポートしても装備品の子プリムにはイベントは発生しません。
オブジェクトが新しいSIMの中に移動したオブジェクトにイベントが発生します。 新しいSIMにオブジェクトが入っても、オブジェクトの子プリムにはイベントは発生しません。
CHANGED_TELEPORT アバターが現在のSIMであるか、別のSIMであるかとは無関係にテレポートしたときに装備している装備品のルートプリムでイベントが発生する。これは手動で(LMや地図上から)テレポートした場合でもteleport()関数を使った場合でも発生する。 異なる位置にテレポートしても装備品の子プリムにはイベントは発生しない。
llSitTargetを使った"sit teleport技法"を応用したオブジェクトに座ってテレポートしても装備品のどのプリムにもイベントは発生しない。
装着されていないオブジェクトにはどのプリムにもイベントはおきません。
スクリプトが禁止された土地へテレポートした場合は、装備品のイベントキューにイベントはキューされません。
これはその後でスクリプトが許された土地へテレポートしたとしても、イベントが発生することを期待できず、スクリプトが許された土地へのテレポートに対して一度だけイベントが発生することを意味します。
(Second Life 1.16.0 (5)の時点では、これは正しい動作ではありませんが、まるであなたがテレポートされたかのように上手い具合に、一旦スクリプト対応の土地へ移動するなら、スクリプト禁止区域へのテレポートでもイベントが発生こともあります。)
上記のこと以外では、changed()イベントは発生しません。
次のようなケースではchanged()イベントは発生しません。
  • オブジェクトの位置が変更されたとき。(moving_start()イベントmoving_end()イベントを使ってください。)
  • オブジェクトの回転が変更されたとき。
  • オブジェクト自身の名前やディスクリプションが変更されたとき。
  • オブジェクトのグループは変更されたとき。(しかし、グループに譲渡されない場合はCHANGED_OWNERを伴ってイベントが発生する。)
  • 「グループ分担」「誰に対しても移動を許可」「誰に対してもコピーを許可」「売り出し中」「次のオーナーが実行できる操作」のチェックボックスや、売り出し設定を変更したりした時。
  • 「ロック済み」「物理」「臨時」「ファントム」のいずれかを変更したとき。
  • プリムの素材を設定したとき。
  • llSetText()関数を使ったとき。
  • llParticleSystem()関数を使ったとき。
  • オーナーがアタッチしたり、デタッチしたりしたき、装着してた装備にはchanged()イベントは起きません。(attach()イベントを使ってください)
  • 装着者が何かに座っても装着した装備にはchanged()イベントは起きません。
  • オブジェクトを選択したり、編集したりしたとき。

Q & A
Q:オブジェクトの位置や回転が変更したことを検出するにはどうしたらよいか?
A:changeed()イベントを使うことではそれはできません。
オブジェクtが移動したとき、moving_start()イベントmoving_end()イベントのイベントが発生します。
オブジェクトの位置と回転を検出するには、timer()イベントを使うことが最良です。(オブジェクトが装備品でもない限り、当然単純には絶対に回転しませんし、絶えず位置を変化させて、moving_start()イベントmoving_end()イベントを発生させるでしょう。)

Q: ビットごとの演算に関して: 上記ではそのスケールとテクスチャーは、同時に変わって”いるように見える”と述べてますが、それはオブジェクトのサイズの変更によってテクスチャーのサイズを変更する間、CHANGED_TEXTUREとCHANGED_SCALEフラグの両方が常に発生ことを意味しますか?
A: いえ、必要ありません。
それは、時として同時に引き起こされる事を意味します。
これが起こるとき、あるいは、たとえそれが起こることがわかっていても、あなたは予測することができません。
全ての可能性を考慮してコードを製作してください。
仮定は、原因に関する少ない情報しかない失敗をするコードをしばしば生産するでしょう。
上記ではそのことを差して、常に「if (change == CHANGED_LINK)"」よりも、「if (change & |CHANGED_LINK)」の方を
イベントの内容を全ての場合で網羅するように書いて下さいと述べています。
Assumptions will often produce code that fails, with little indication as to why
Q:アバターがオブジェクトを買ったことを検出する方法は存在しないのですか?
A: Yes. Specifying CHANGED_OWNER for change will let you filter the results of changed().
はい、チェンジイベントのCHANGED_OWNERの指定はあなたの求めるイベントの結果を除外してしまいます。
詳しくは詳細セクションを参照してください。
アバターがオブジェクトに支払ったことを検出するにはmomey()イベントを使ってください。

Q: オブジェクトのインベントリから、スクリプトが削除や追加をしたことをイベント経由で知る方法はないのでしょうか?
A:いいえ。唯一の方法は現在のインベントリより先に存在するリストとを規則的に比較するためtimer()イベントを使うことです。

Q: detected系関数(llDetected*)とchanged()イベントと一緒に使うことは出来ますか?
A:いいえdetected系関数はtouche系イベント、衝突系イベント、センサー系イベントで、のみ動作する関数です。

Q:誰が(もしくは何が)そのオブジェクトを変更したのかを検出する方法はありますか?A: ありません。

最終更新2008/02/12 written by CrystalR Runo@Secondlife
最終更新:2008年02月12日 10:22
添付ファイル