Second Life in Japan
登録
Advertisement

Scripters_cafeログ


08/06/21[]

ブランコのスクリプトについてのあれこれ。

シンプルなブランコを再現する場合、大きく分けて以下の2つの方法があります。

  1. 物理オブジェクトにしてrotationalimpulseなどで回す
  2. 非物理オブジェクトをうまく回す


物理オブジェクトで回す[]

物理オブジェクトにして回す場合、ずれてしまわないように llSetStatus 関数の STATUS_ROTATE_X フラグなどを使用して回転する軸を制限します。その上で、llApplyRotationalImpulse 関数で回転力を与えるなどして回転させます。

物理オブジェクトなので、わりとリアルでスムーズに揺れます。

ただ、Fakeさん曰く、Havok4になってから STATUS_ROTATE_X などで軸を固定しても何らかのタイミングで軸がずれてしまいやすくなったそうで、ずれの補正や、軸が外れて落下してしまった場合の処理などが必要になりそうです。


非物理オブジェクトをうまく回す[]

非物理オブジェクトを llSetPos や llSetRot を使用して回転させるのですが、普通に記述すると、これらの関数のディレイ(0.2秒)の影響で滑らかに回転しているようには見えません。

そこで、このディレイを回避するためにスレーブ用のスクリプトをいくつか用意し、親スクリプトから回転の角度などを llMessageLinked などでスレーブスクリプトへ送信し、実際の回転処理はスレーブスクリプト側で行わせることによって、見た目上関数のディレイ間隔よりも短い間隔で llSetRot を実行でき、かなり滑らかに動かすことができます。

非物理オブジェクトなので、軸ずれや落下などの問題は発生しませんが、その代わり以下のようなデメリットもあります。

  • スクリプトの数、同時に実行される処理数が増えるので、通常よりもスクリプトの負荷が少しだけ高くなる
  • スレーブスクリプトでの処理が、SIMの状態によって若干遅れる場合がある。1つのスレーブで遅れが発生した場合、見た目上、次のスレーブでの回転位置まで一気に動いてしまい、「カクッ」と動いたように見えてしまう。(滑らかでない)


2つめの問題を回避するためにスレーブ側などで現在位置をチェックするなどの処理を追加することも考えられるのですが、スレーブスクリプトでの処理が多くなると、逆にどんどんスレーブスクリプトでの処理が遅れてしまう悪循環に陥ります。


うまい対策が何かあるのかは、機会があれば調べてみたいところです。


非物理オブジェクトをうまく回す(llRotLookAt)[]

回転のみに話を絞ると、llSetRot ではなく、llRotLookAt という関数を使用することもできます。(TomonekoさんのアイデアだとFakeさんから教えてもらいました。)

llRotLookAt であれば関数のディレイがありませんので、スレーブスクリプトを用意する必要がありません。

また、万が一1回の角度変更処理で多少遅れが生じても、次の角度変更処理が同時に行われるわけではないので、「カクッ」となる度合いを最小にとどめることができます。

Advertisement