Lektion 8 – Typische Alltagsskripte Teil 3
Wie schon angekündigt schließen wir mit dieser Lektion das erste Kapitel dieses Kurses ab, um im nächsten Kapitel etwas tiefer in die Materie LSL, Programmierung und Gestaltung einzusteigen.
Würde man verschiedene Einwohner von SL fragen, was denn wirklich typisch, einzigartig und vielleicht sogar ein Wahrzeichen von SL wäre, so würden mit Sicherheit viele antworten: “Posebälle”.
Diese sind fast so alt wie LSL selbst und daher sicherlich wert, auch schon einmal grundlegend in einem LSL-Kurs behandelt zu werden.
Damit verbunden müssen wir uns vorher zumindest noch am Rande mit einem weiteren Grundpfeiler von LSL befassen, nämlich dem Permission-System.
Bevor wir jedoch dazu kommen, gilt es noch die Gewinner der Aufgabe der letzten Lektion zu küren.
Die Gewinner der Aufgabe aus Lektion 7
Aufgabe war es, den möglichst kreativsten TipJar zu erstellen, der vom Skriptdesign her auf die vorherigen Lektionen aufbaut. Prämiert werden die besten drei Tipjars. An dieser Stelle zunächst einmal ein herzliches Dankeschön an alle Interessenten und Teilnehmer, nicht nur für die Einsendungen, sondern auch das Feedback!
Platz 1 und damit 500L$ geht an Shea Slocombe, dessen Tipjar nicht nur ein schnuckeliges Design hat, sondern auch ein nettes “Dankeskript”. So spielt er eine Melodie für den Spender ab, bedankt sich mit blinkendem Text und tanzt dabei förmlich noch.
Platz 2 und damit 300L$ geht an z3Ro Magic. Dieser TipJar gibt dem Spender nicht nur einen hübschen Friendship-Bären sondern verfügt sogar noch über ein sehr komplexes und ausgeklügeltes Userlogin-Verfahren. Dieses funktioniert leider noch nicht komplett, da das Permissionsystem fehlt, jedoch muss so viel Mühe und Arbeit unbedingt belohnt werden.
Platz 3 und damit 200L$ geht an Julianmex Jun. Dieser Tipjar weist zwar im Skript kaum Änderungen zu dem hier im Kurs behandelten Skript auf, jedoch hat er ein sehr interessantes und schön anzusehendes Design, welches ich hiermit belohnen möchte.
Das Permission-System
In SL unterscheidet man zwischen zwei Permission- bzw. Berechtigungssystemen, nämlich den Asset-Permissions und den Skript-Permissions.
Erstere sind die Berechtigungen, die die Weitergabe des Objektes regeln, also Copy, Modify und Transfer sowie Move und diese noch einmal explizit aufgeschlüsselt nach den verschiedenen Usern, also grundlegend, Gruppen, nächster Owner etc. Diese können per Skript ausgelesen werden, jedoch nur im God-Mode geändert werden. Die Asset-Permissions sind für uns hier uninteressant.
Die Skript-Permissions regeln, inwieweit ein Skript Einfluss auf bestimmte Avatar- bzw. Objektänderungen bzw. -funktionen Einfluss nehmen darf, so zB ob es einen Avatar animieren, Geld von seinem Konto abbuchen oder seine Kamera tracken darf. Wie man sieht, alles sensible Dinge, die zu Recht explizit abgefragt werden müssen. Für uns hier nur interessant ist die Permission, den Avatar zu animieren, da dies ja unser Poseball erreichen soll.
Um einen Avatar animieren zu können, muss ein Skript also explizit danach fragen. Dadurch öffnet sich beim zu animierenden Avatar ein Fenster wie hier rechts zu sehen, mit welchen er entweder zustimmen, ablehnen oder das Objekt direkt muten kann.
Allerdings wird eine Permission, den Avatar zu animieren automatisch erteilt, wenn man auf diesem Objekt sitzt! Es öffnet sich kein Fenster und die Permission gilt sofort als erteilt.
Diese automatische Zusage trifft auch auf einige andere Permissionabfragen zu. Wenn man bedenkt, dass man Objekte so einstellen kann, dass man bei Linksklick direkt auf diesen sitzt, wird damit schnell klar, warum man nicht einfach so bedenkenlos alles anklicken sollte!
Das Permissionsystem werden wir uns noch genauer in Kapitel 2 ansehen.
Animationen
SL verfügt von vorneherein über einen großen Satz an nativen Animationen. Eine Liste dieser mit ihren Prioritäten findet man zB hier.
Benutzt man den Befehl zum Animieren eines Avatars, den wir gleich noch kennenlernen werden, so kann man mit diesem auch eine der Standardanimationen starten; LSL kennt diese Namen.
Will man eine eigene Animation starten, muss sich diese im Inventar des Prims mit dem Animationsskript befinden. Ein Starten mittels eines Keys wie zB bei Sounds ist nicht möglich.
Natürlich darf eine eigene Animation nicht den selben Namen wie eine der Standardanimationen tragen.
Eigene Animationen kann man zB mit den kostenlosen Programmen Avimator bzw. Qavimator erstellen. Wirklich komfortabel und ausgefeilter sind kostenpflichtige Programme wie Poser.
Beim Hochladen der Animation muss eine Priorität angegeben werden. Diese legt fest, welche Animation Vorrang vor anderen hat. Standard ist 2, die geringste 0 sowie die höchste 4. Die Priorität kann später nicht mehr geändert werden. Wird eine Animation mit höherer Priorität als eine schon laufende gestartet, hat diese Vorrang. Gleiches gilt für Animationen gleicher Priorität; dabei hat die zuletzt gestartete Vorrang. Da es aber auch möglich ist, Animationen nur auf bestimmte Körpersegmente zu beschränken, ist ein gleichzeitiges Laufen mehrerer Animationen durchaus denkbar, zB eine, die nur den linken Arm bewegt, während eine andere flott die Hüften schwingt.
Das Erstellen von Animationen an sich würde den Rahmen hier sprengen; sollte sich jedoch jemand berufen fühlen, darüber mal ein kleines Tutorial zu schreiben, so kann er sich gerne bei mir melden:-)
Posebälle
…sind mit Sicherheit eines der Wahrzeichen von SL und wohl kaum noch wegzudenken. Was tut so ein Poseball eigentlich?
Im Prinzip durchläuft er folgende Schritte: Registriert er, dass sich ein Avatar gesetzt hat, fragt er ihn nach der Permission, ihn animieren zu dürfen, die ja beim Sitzen automatisch erteilt wird, wie wir nun wissen. Dennoch muss das Skript fragen, da es sonst nicht animieren dürfte. Danach stoppt er sofort die eigentlich automatisch startende Standardsitzanimation, um auch Animationen mit einer niedrigeren Priorität als 2 zu ermöglichen. Als nächstes startet er die eigentliche Animation und macht sich selbst unsichtbar.
Steht der Avatar wieder auf, stoppt der Poseball die Animation und macht sich selbst wieder sichtbar.
Und genau diese Schritte werden wir nun gleich mittels LSL nachbauen.
Warum eigentlich Bälle?
Grundsätzlich könnte man natürlich in jede Art von Prim ein Poseballskript einbauen. So macht es zB wenig Sinn, auf einen Stuhl noch einen hässlichen Ball drauf zu setzen.
Geht es allerdings um kein Möbelstück und muss die Position des Avatars dennoch fixiert werden, damit er während der Animation nicht davonläuft, braucht man einen Prim mit Poseballskript. Da Bälle bekanntlich rund sind, sehen sie nicht nur stilvoller aus, sondern man sieht ihnen auch ihre Rotation, sprich Drehung nicht an. So kann man die Drehungswerte des Prims flexibel anpassen ohne dass man ihm dieses sichtbar anmerkt.
Ach, und außerdem sind Posebälle Tradition oder hast du schonmal von einem Posewürfelskript was gehört………..:-)
Der Changed-Event
Dieser für uns neue Event ist einer der wichtigsten, die LSL bietet. Wir werden diesen hier nur ganz kurz am Rande streifen und noch später im Laufe dieses Kurses ausführlicher behandeln. Der changed-Event wird zB dann ausgelöst, wenn man das Objekt ändert zB skaliert oder neu texturiert, es teleportiert wird bzw. die Sim ändert, sich das Objektinventar oder bestimmte Verlinkungen ändern.
Anhand der Schreibweise changed(integer change) sieht man bereits, dass dieser einen Wert als integer empfängt. Dieser Wert teilt LSL genau mit, welches Änderungsereignis eingetreten ist.
Jedoch können manchmal mehrere change-Ereignisse gleichzeitig eintreten. Wie bringt LSL dies in einem einzigen Wert unter?
Mit einer sogenannten Bitmaske. Was das genau bedeutet, braucht uns hier noch nicht zu interessieren; stellen wir uns dies einfach als eine Reihe von ein-/aus-Schaltern vor, die zusammengefasst einen bestimmten integer ergeben. Den jeweiligen Ereignissen bzw. "Schaltern" ist jeweils eine Konstante zugeteilt, um diese Werte besser lesbar zu machen. Will man nun prüfen, welches changed-Ereignis genau eingetreten ist, prüft man den integer change auf eben diese Konstante mit einer if-Abfrage.
Aber Vorsicht, da es sich um eine Bitmaske handelt, darf man nicht mit dem == prüfen, da dieser das Ergebnis verfälschen könnte. Dies würde ja nur zutreffen, wenn genau nur dieses eine Ereignis eingetreten ist. Wurde changed mit mehreren Ereignissen gleichzeitig ausgelöst, haben wir ein Problem. Man prüft daher einen einzelnen Schalter mit einem logischen AND also diesem Zeichen hier & anstatt == .
Wozu der changed-Event im Poseballskript? Setzt sich ein Avatar auf ein Objekt, wird er quasi mit diesem verlinkt. Wie wir nun wissen, wird bei Änderungen am Linkset der changed-Event aufgerufen. Somit können wir also feststellen, wann sich ein Avatar setzt, bzw. wieder aufsteht.
Das Poseballskript
Mit dem nun gesammelten Wissen können wir daran gehen, unser Poseballskript zu betrachten. Wie auch zuvor in Kapitel 1 werde ich wieder einige Details aussparen bzw. neue Befehle nur am Rand streifen. Genauere Informationen gibt es noch später im Verlauf des Kurses, bzw durch die LSL-Wikis, die du wie gewohnt durch Anklicken eines bestimmten Befehls im Skript direkt erreichen kannst.
Wir wissen nun den groben Ablauf eines Poseballskriptes. Zudem haben wir die Erkenntnis gewonnen, dass beim Sitzen bzw. Absteigen eines Avatars vom Poseball, der Avatar mit diesem verlinkt bzw. entlinkt wird und somit der changed-Event mit dem Schalter fürs Linkset ausgelöst wird. Außerdem wissen wir, dass zum Starten bzw. Stoppen von Animationen nach einer Permission gefragt werden muss, welche allerdings wenn der Avatar auf einem Objekt sitzt, so wie hier, danach ohne ein weiteres Abfragefenster direkt erteilt wird.
Also schauen wir uns mal das Skript im folgenden an:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31 default
{
state_entry()
{
llSitTarget(<0,0,0.6>, ZERO_ROTATION); //Sittarget ungleich Null um llAvatarOnSitTarget zu aktivieren
llSetSitText("Dance!"); //Kuchenmenü ändern
llSetText("Affiger Tanz", <1,1,1>, 1.0); //Text setzen
llSetAlpha(1.0, ALL_SIDES); //Poseball sichtbar machen
}
changed(integer change)
{
if(change & CHANGED_LINK) //Hat sich das Linkset geändert?
{
if(llAvatarOnSitTarget() != NULL_KEY) //Es sitzt jemand da kein NULL_KEY
{
llRequestPermissions(llAvatarOnSitTarget(), PERMISSION_TRIGGER_ANIMATION); //Permission abfragen
llStopAnimation("sit"); //Standardsitzanimation abschalten
llStartAnimation(llGetInventoryName(INVENTORY_ANIMATION, 0)); //und stattdessen unsere Animation starten
llSetText("", <0,0,0>, 0.0); //Hovertext abschalten
llSetAlpha(0.0, ALL_SIDES); //und Poseball unsichtbar machen
}
else //NULL_KEY, also Avatar ist abgestiegen
{
llStopAnimation(llGetInventoryName(INVENTORY_ANIMATION, 0)); //Animation stoppen
llResetScript(); //Permission löschen und wieder state_entry aufrufen
}
}
}
}
Kompliziert? Nicht wirklich. Gehen wir es Schritt für Schritt durch:
Im state_entry definieren wir den Grundzustand des Poseballs. In Zeile 5 legen wir zunächst einen Sittarget ungleich ZERO_VECTOR, also ungleich Null fest. Der Sittarget gibt an, wie weit und in welche Richtung versetzt der Avatar vom Zentrum sitzen soll und mit welchem Rot. Ein Sitzoffset von maximal 300m ist dabei möglich. So funktionieren übrigens simple Teleporter. Man setzt sich darauf, der Sittarget "verschiebt" den Avatar in die entsprechende Richtung, maximal 300m und lässt diesen dann sofort wieder aufstehen.
Warum aber muss der Sittarget ungleich ZERO_VECTOR sein? Weil ein ZERO_VECTOR den Sittarget löschen würde. Da wir später aber die Funktion llAvatarOnSitTarget() nutzen wollen und diese nur mit einem definierten Sittarget funktioniert, müssen wir ihn einschalten, sprich ungleich ZERO_VECTOR setzen. Es bietet sich hier sowieso an, den Avatar etwas nach oben zu verschieben, so dass wir nicht mitten im Boden tanzen, wenn wir den Poseball auf den Boden rezzen.
Zeile 6 ändert den Eintrag im Kuchenmenü für Sitzen in unseren Text "Dance!" ab.
Danach setzen wir einen Hovertext und schalten den Poseball wieder sichtbar mittels llSetAlpha, welches wie der Name schon sagt, die Transparenz des Prims regelt, wie gewohnt mit float von 0.0 für unsichtbar bis 1.0 für voll sichtbar und wie schon gesehen mit der Konstante ALL_SIDES für alles Seiten.
Ab Zeile 11 folgt der eigentliche Kern des Skriptes, nämlich der changed-Event.
In Zeile 13 prüfen wir, ob der Event auch wirklich durch eine Änderung des Linksets ausgelöst wurde mittels der Konstante CHANGED_LINK. Da es um eine Bitmaske geht, dieses mit & und nicht ==.
Die Funktion llAvatarOnSitTarget() in Zeile 15 haben wir ja aktiviert durch Setzen des Sittarget in Zeile 5. Diese gibt den Key des Avatars zurück, der auf dem Objekt sitzt, bzw. einen NULL_KEY wenn kein Avatar sitzt, dieser also abgestiegen ist. Das Zeichen != ist das Gegenteil von == . Es besagt, dass etwas nicht zutrifft. Also wenn es kein NULL_KEY ist, gibt es einen Key, das heißt, es sitzt ein Avatar.
Wie gesehen müssen wir nun zuerst den Avatar fragen, ob wir ihn animieren dürfen, was wir in Zeile 17 machen, auch wenn die Permission bei sitzenden Avataren danach automatisch erteilt wird. Danach stoppen wir die automatisch beim Sitzen eintretende Standardsitzanimation, um Prioritätskonflikte zu vermeiden.
In Zeile 19 starten wir die erste im Inventar befindliche Animation. Die Schreibweise mit llGetInventoryName(INVENTORY_ANIMATION, 0) kennen wir bereits aus Lektion 6.
Sie gibt den Namen der ersten sich im Inventar befindlichen Animation als string zurück. Zwar könnten wir den Namen auch direkt einsetzen, aber so sind wir flexibler und müssen das Skript nicht ändern, wenn wir die Animation wechseln.
Danach müssen wir nur noch den Hovertext sowie den Prim unsichtbar machen und wir sind fertig.
Gibt llAvatarOnSitTarget() in Zeile 15 einen NULL_KEY zurück, also sprich wenn der Avatar aufgestanden ist, wird der else-Block ab Zeile 23 ausgelöst. Dieser stoppt zunächst die Animation und setzt dann das Skript zurück.
Woher weiß das Skript, für welchen Avatar es die Animation stoppen soll? Ein Skript merkt sich, für welchen Avatar es Permissions hat. Folglich können auch pro Skript nur Permissions für einen Avatar ermöglicht werden. Die Permissions bleiben solange erhalten, bis man sie löscht, zB mit llResetScript() oder an einen neuen Avatar vergibt. Aber Achtung: Hat man einen Avatar animiert und befragt dann einen anderen Avatar nach Permissions, kann man den vorherigen Avatar nicht mehr ansteuern, dieser würde also bis in alle Ewigkeit rumtanzen, naja, zumindest bis er die Animation selber stoppt, SL neu startet oder die Region wechselt (letzteres erst seit einiger Zeit).
Wir löschen also sicherheitshalber mit llResetScript() die Permission, was zwar unnötig wäre, da wir die Animation sowieso vorher gestoppt haben, aber es bietet noch einen Vorteil:
Wie wir wissen, wird beim Zurücksetzen der state_entry des default-States aufgerufen. Wir ersparen uns also das erneute Abtippen der Befehle, die den Prim wieder sichtbar machen und den Hovertext setzen.
Und das war’s auch schon. Ein einfaches Poseballskript wie hier gezeigt, ist also doch keine so große Kunst, oder?
Zusammenfassung
In dieser Lektion hast du folgendes gesehen:
- Was das Permissionsystem ist
- Dass Skripte für bestimmte Aktionen um Erlaubnis fragen müssen
- Dass bestimmte Erlaubnisse automatisch erteilt werden, wenn man auf dem Objekt mit diesem Skript sitzt
- Dass man dennoch ungeachtet dessen die Permission einholen muss
- Was Standardanimationen sind
- Was es mit Animationsprioritäten auf sich hat
- Dass man eigene Animationen mit externer Software erstellen kann und was beim Upload zu beachten ist
- Wie ein Poseball prinzipiell funktioniert…
- …und warum es meist Bälle sind
- Was der changed-Event ist
- Was eine Bitmaske ist und wie man diese prüft
- Was ein Sittarget ist und wie man diesen aktiviert bzw. deaktiviert
- Das Gegenteil von Gleich (==), Nicht gleich (!=)
- Dass sich ein Skript jeweils nur die Permissions eines Avatars merkt
- Wie man den Siteintrag im Kuchenmenü ändert
- Wie simple Teleporter funktionieren
Mit dieser Lektion beenden wir unsere grundlegende Einführung in LSL und damit auch Kapitel 1.
Im nächsten Kapitel gehen wir etwas detaillierter auf grundlegende Programmiertechniken, die Wikis und natürlich LSL in seinen Details ein.

