In looking at setting automatic calculations for teleporter destinations I demonstrated how the rotation of the teleporter affects the final destination. This post addresses that issue and also looks at the rotation of the avatar at the destination.
Rotation in Second Life is a complex subject and I’ll leave the Second Life Wiki entry on rotation to explain the various ins and outs. A full understanding of the subject can be hard to grasp but I would suggest if you get anything from that page then attempt to get the right hand rule. This really can supply good clarification of axis direction and rotation when building. To achieve the rotation adjustment in the teleporter script however; well I’ll just give you the solution and say that it works.
The teleporter script as it was in the last post ended up with a calculation whereby the prim position was subtracted from the destination vector, resulting in the correct sit target offset to achieve the destination.
llSitTarget(destination – llGetPos(), ZERO_ROTATION);
To adjust the offset so that it allows for the rotation of the prim the result of the calculation is divided by the rotation, this being accessed with the function llGetRot. Note that the initial calculation is first enclosed in parentheses as shown.
llSitTarget((destination – llGetPos()) / llGetRot(), ZERO_ROTATION);
This adjustment has the avatar reaching the required destination whatever the rotation of the teleporter prim.
For many teleportations the above will suffice but there is one more aspect of the teleport that can be addressed; the avatar’s rotation once the llUnSit function has been applied (i.e. the way they face at the end of the teleportation). In terms of working in the OpenSim environment this is a moot point because the avatar unsits into the rotation the avatar was prior to the “sitting”. The only way to force where the avatar is facing at the end of the teleport would be to somehow force the way they face at the beginning of it, possibly through structural arrangements around the teleporter.
With Second Life however the avatar unsits in the rotation they assume during the “sitting” phase of the teleport so the orientation of the avatar at the destination can be set. This is not necessarily of consequence as the avatar does reach the required destination but for myself; if I can face the avatar in a particular direction then all the better as it can be a good indicator of where I want the avatar to go (or look) once they have completed the teleport.
First up the fact that the llSitTarget rotation is relative to the teleporter prim must be addressed and this is done in a similar manner to the solution applied to the offset. To demonstrate the issue, the following shows the rotation of the avatar when the prim has no rotation. Notice that the avatar lands (unsits from the prim) facing along the X axis in the positive direction (relative to both global and local positioning).
Rotate the prim however, in this case 45° on the Z axis and even though the destination is adjusted the avatar’s landing rotation alines with the local X axis not the global.
To adjust the rotation therefore, the llSitTarget rotation is divided by the prim rotation as shown.
llSitTarget((destination – llGetPos()) / llGetRot(), ZERO_ROTATION / llGetRot());
With the rotation adjusted so that the teleporter’s local rotation no longer affects the result, the code for setting the llSitTarget rotation to that other than ZERO_ROTATION can be added.
To facilitate ease of use a vector is initiated at the beginning of the script using degrees (as used in the Build window). The degrees are translated to a euler vector, expressed as radians, and then into a rotation; both in the state_entry event. This rotation is then applied to the llSitTarget function. The example below uses the final script from Setting Teleporter Destinations.
vector destination = <80.0, 206.0, 81.5>;
vector rotDegrees = <0.0, 0.0, 90.0>; // Rotation in degrees, X, Y and Z
llSetText(“Click to Teleport“, <1.0, 1.0, 0.8>, 1.0);
vector rotRadians = rotDegrees * DEG_TO_RAD; // Changes the degrees to radians (euler vector)
rotation avatarRot = llEuler2Rot(rotRadians); // Changes the euler vector to a rotation
llSitTarget((destination – llGetPos()) / llGetRot(), avatarRot / llGetRot()); // Sets the sit target
//Remainder of script
The vector rotDegrees designates the X, Y and/or Z values of rotation that the avatar will assume when seated. Because the avatar will unseat into a standing position the final value, i.e the value for the Z axis, is the one that will define which way the avatar faces when they reach the destination. Three examples of different Z values are shown below.
With the avatar orientated at the final destination this concludes the final post on using the sit functions to create a teleporter. I do hope that it was of some value to those that followed the series. If there are other queries around creating teleporters in this manner do feel free to ask in comments and I will attempt to address your questions.