Initial commit
This commit is contained in:
commit
3dac7b989a
2 changed files with 570 additions and 0 deletions
0
README.md
Normal file
0
README.md
Normal file
570
Simple Doors.lsl
Normal file
570
Simple Doors.lsl
Normal file
|
@ -0,0 +1,570 @@
|
|||
list Keys;
|
||||
float configRotTime = 1.0;
|
||||
integer configRotSteps = 2;
|
||||
integer configReverse = 0;
|
||||
integer configRotAngle = 90;
|
||||
string configAxis = "z";
|
||||
integer configAxisCenter= FALSE;
|
||||
integer configAxisCenterDir = 1;
|
||||
string configAxisCenterAxis = "x";
|
||||
float configAutoClose = 0.0;
|
||||
float configDistance = 2.0;
|
||||
//integer configCollide = FALSE;
|
||||
integer configSensor = FALSE;
|
||||
string configDouble = "";
|
||||
string soundOpen = "Door open";
|
||||
string soundClose = "Door close";
|
||||
string soundLock = "Lock";
|
||||
string soundUnlock = "Unlock";
|
||||
string soundKnock = "Door knock";
|
||||
|
||||
integer accessLoaded = FALSE;
|
||||
integer doorLock = FALSE;
|
||||
integer doorClosed = TRUE;
|
||||
integer doorControl = FALSE;
|
||||
key doorActUID = NULL_KEY;
|
||||
float doorActDist = 0.0;
|
||||
float touchTime;
|
||||
float touchDouble = FALSE;
|
||||
integer touchDrag = FALSE;
|
||||
key doubleID = NULL_KEY;
|
||||
|
||||
integer settingsLine = 0;
|
||||
key settingsKey = NULL_KEY;
|
||||
integer settingsSection = 0; // 1=settings, 2=keys
|
||||
|
||||
|
||||
sound(string name)
|
||||
{
|
||||
if (llGetInventoryType(name) == INVENTORY_SOUND) {
|
||||
llPlaySound(name, 1.0);
|
||||
}
|
||||
else if (osIsUUID(name)) {
|
||||
llPlaySound(name, 1.0);
|
||||
}
|
||||
}
|
||||
|
||||
addKey(string data, integer send)
|
||||
{
|
||||
if (llStringLength(data) > 0) {
|
||||
string name = data;
|
||||
name = llStringTrim(name, STRING_TRIM_HEAD);
|
||||
name = llStringTrim(name, STRING_TRIM_TAIL);
|
||||
|
||||
if (llGetSubString(name, 0, 0) == "#") return;
|
||||
Keys = Keys + name;
|
||||
if (send) llMessageLinked(LINK_ALL_OTHERS, 1, name, "addkey");
|
||||
}
|
||||
}
|
||||
|
||||
string trimString(string data)
|
||||
{
|
||||
if (llStringLength(data) > 0) {
|
||||
data = llStringTrim(data, STRING_TRIM_HEAD);
|
||||
data = llStringTrim(data, STRING_TRIM_TAIL);
|
||||
|
||||
if (llGetSubString(data, 0, 0) == "#") return "";
|
||||
else return data;
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
doorMsg(integer status, string part)
|
||||
{
|
||||
if (llStringLength(configDouble) > 0) {
|
||||
llMessageLinked(LINK_ALL_OTHERS, status, configDouble, part);
|
||||
}
|
||||
}
|
||||
|
||||
lock(integer lock, string name) {
|
||||
if (doorLock != lock) {
|
||||
if (!doorLock) {
|
||||
doorLock = TRUE;
|
||||
doorMsg(doorLock, "lock");
|
||||
llSay(0, "/me locked.");
|
||||
sound(soundLock);
|
||||
} else {
|
||||
doorLock = FALSE;
|
||||
doorMsg(doorLock, "lock");
|
||||
llSay(0, "/me unlocked.");
|
||||
sound(soundUnlock);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
loadSettings()
|
||||
{
|
||||
settingsLine = 0;
|
||||
settingsSection = 0;
|
||||
settingsKey = NULL_KEY;
|
||||
|
||||
if (loadSettings(1)) {
|
||||
return;
|
||||
} else {
|
||||
loadSettings(2);
|
||||
}
|
||||
}
|
||||
|
||||
integer loadSettings(integer section)
|
||||
{
|
||||
if (section == 1) {
|
||||
if (llGetInventoryType("Settings") == INVENTORY_NOTECARD) {
|
||||
settingsLine = 0;
|
||||
settingsSection = 1;
|
||||
settingsKey = llGetNotecardLine("Settings", settingsLine);
|
||||
|
||||
return TRUE;
|
||||
} else {
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
else if (section == 2) {
|
||||
if (llGetInventoryType("Access List") == INVENTORY_NOTECARD) {
|
||||
settingsLine = 0;
|
||||
settingsSection = 2;
|
||||
accessLoaded = TRUE;
|
||||
settingsKey = llGetNotecardLine("Access List", settingsLine);
|
||||
|
||||
return TRUE;
|
||||
} else {
|
||||
Keys = [];
|
||||
accessLoaded = FALSE;
|
||||
llMessageLinked(LINK_ALL_OTHERS, 0, "", "getkeys");
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
default
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
state loading;
|
||||
}
|
||||
|
||||
//collision_start(integer total_number)
|
||||
//{
|
||||
// if (llDetectedType(0) & AGENT)
|
||||
// if (!doorLock && doorClosed && configCollide) door();
|
||||
//}
|
||||
|
||||
}
|
||||
|
||||
state loading
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
loadSettings();
|
||||
}
|
||||
|
||||
dataserver(key qid, string data)
|
||||
{
|
||||
if (qid == settingsKey) {
|
||||
if (data != EOF) {
|
||||
if (settingsLine == 0 && settingsSection == 2) {
|
||||
Keys = [];
|
||||
llMessageLinked(LINK_ALL_OTHERS, 0, "", "clearkeys");
|
||||
llSleep(1.0);
|
||||
}
|
||||
|
||||
data = trimString(data);
|
||||
|
||||
if (data != "" && llStringLength(data) > 0) {
|
||||
if (settingsSection == 1) {
|
||||
list part = llParseString2List(data, ["="], []);
|
||||
|
||||
if (llToLower(llList2String(part, 0)) == "time") {
|
||||
if (llList2Float(part, 1) > 0 && llList2Float(part, 1) <= 10)
|
||||
configRotTime = llList2Float(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "steps") {
|
||||
if (llList2Integer(part, 1) > 0)
|
||||
configRotSteps = llList2Integer(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "angle") {
|
||||
if (llAbs(llList2Integer(part, 1)) > 0 && llAbs(llList2Integer(part, 1)) < 360)
|
||||
configRotAngle = llList2Integer(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "axis") {
|
||||
if (llListFindList(["x", "X", "y", "Y", "z", "Z"], llList2List(part, 1, 1)) >= 0) {
|
||||
configAxis = llToLower(llList2String(part, 1));
|
||||
}
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "axisoffset") {
|
||||
if (llToLower(llList2String(part, 1)) == "edge")
|
||||
configAxisCenter = FALSE;
|
||||
else if (llToLower(llList2String(part, 1)) == "center")
|
||||
configAxisCenter = TRUE;
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "axisoffsetbase") {
|
||||
if (llGetSubString(llList2String(part, 1), 0, 0) == "-") {
|
||||
configAxisCenterDir = -1;
|
||||
} else {
|
||||
configAxisCenterDir = 1;
|
||||
}
|
||||
if (llListFindList(["x", "y", "z"], [ llToLower(llGetSubString(llList2String(part, 1), 0, 0)) ]) >= 0) {
|
||||
configAxisCenterAxis = llToLower(llGetSubString(llList2String(part, 1), 0, 0));
|
||||
}
|
||||
else if (llListFindList(["x", "y", "z"], [ llToLower(llGetSubString(llList2String(part, 1), 1, 1)) ]) >= 0) {
|
||||
configAxisCenterAxis = llToLower(llGetSubString(llList2String(part, 1), 1, 1));
|
||||
}
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "autoclose") {
|
||||
if (llList2Float(part, 1) >= 0 && llList2Float(part, 1) <= 300)
|
||||
configAutoClose = llList2Float(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "touchdist") {
|
||||
if (llList2Float(part, 1) >= 0) {
|
||||
configDistance = llList2Float(part, 1);
|
||||
} else {
|
||||
configDistance = 2.0;
|
||||
}
|
||||
}
|
||||
//else if (llToLower(llList2String(part, 0)) == "collision") {
|
||||
// if (llList2Integer(part, 1) >= 0)
|
||||
// configCollide = llList2Integer(part, 1);
|
||||
//}
|
||||
else if (llToLower(llList2String(part, 0)) == "sensor") {
|
||||
if (llList2Integer(part, 1) >= 1)
|
||||
configSensor = llList2Integer(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "double_name") {
|
||||
if (llStringLength(llList2String(part, 1)) > 0) {
|
||||
configDouble = llList2String(part, 1);
|
||||
} else {
|
||||
configDouble = "";
|
||||
}
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "sound_open") {
|
||||
soundOpen = llList2String(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "sound_close") {
|
||||
soundClose = llList2String(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "sound_knock") {
|
||||
soundKnock = llList2String(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "sound_lock") {
|
||||
soundLock = llList2String(part, 1);
|
||||
}
|
||||
else if (llToLower(llList2String(part, 0)) == "sound_unlock") {
|
||||
soundUnlock = llList2String(part, 1);
|
||||
}
|
||||
}
|
||||
else if (settingsSection == 2) {
|
||||
addKey(data, TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
if (settingsSection == 1)
|
||||
settingsKey = llGetNotecardLine("Settings", ++settingsLine);
|
||||
else
|
||||
settingsKey = llGetNotecardLine("Access List", ++settingsLine);
|
||||
} else {
|
||||
if (settingsSection == 1) {
|
||||
llSay(0, "Settings loaded.");
|
||||
loadSettings(2);
|
||||
} else {
|
||||
llSay(0, "Access List loaded. " + (string)llGetListLength(Keys) + " with access.");
|
||||
if (doorClosed) state closed;
|
||||
else state opened;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
state closed
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
doorClosed = TRUE;
|
||||
}
|
||||
|
||||
changed(integer change)
|
||||
{
|
||||
if (change & CHANGED_INVENTORY) {
|
||||
state loading;
|
||||
}
|
||||
}
|
||||
|
||||
touch_start(integer total_number)
|
||||
{
|
||||
if (configDistance > 0.0) {
|
||||
if (llVecDist(llGetPos(), llDetectedPos(0)) <= configDistance) {
|
||||
llResetTime();
|
||||
if (touchDrag) touchDrag = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
touch(integer total_number)
|
||||
{
|
||||
if (configDistance > 0.0) {
|
||||
if (llVecDist(llGetPos(), llDetectedPos(0)) <= configDistance) {
|
||||
if (llGetTime() >= 0.25 && !touchDrag) {
|
||||
touchDrag = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
touch_end(integer total_number)
|
||||
{
|
||||
if (configDistance > 0.0) {
|
||||
if (llVecDist(llGetPos(), llDetectedPos(0)) <= configDistance) {
|
||||
if (touchDrag) {
|
||||
if (llListFindList(Keys, [ llDetectedName(0) ]) > -1) {
|
||||
if (doorLock) lock(FALSE, llDetectedName(0));
|
||||
else lock(TRUE, llDetectedName(0));
|
||||
}
|
||||
llSetTimerEvent(0.0);
|
||||
touchDrag = FALSE;
|
||||
}
|
||||
else if (llGetTime() >= 1) {
|
||||
sound(soundKnock);
|
||||
llSay(0, llDetectedName(0) + " knocks.");
|
||||
llSetTimerEvent(0.0);
|
||||
}
|
||||
else {
|
||||
if (!doorLock) {
|
||||
doorControl = TRUE;
|
||||
doorActUID = llDetectedKey(0);
|
||||
doorActDist = llVecDist(llGetPos(), llDetectedPos(0));
|
||||
state opening;
|
||||
//door(llDetectedKey(0), llVecDist(llGetPos(), llDetectedPos(0)));
|
||||
}
|
||||
else {
|
||||
sound(soundKnock);
|
||||
llSay(0, llDetectedName(0) + " knocks.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
link_message(integer sender, integer num, string name, key id)
|
||||
{
|
||||
if (llStringLength(configDouble) > 0 && name == configDouble) {
|
||||
if (id == "door") {
|
||||
if (doorControl) return;
|
||||
//llOwnerSay("DEBUG: link_message:door: sender=" + (string)sender + ", num=" + (string)num);
|
||||
if (num == FALSE) state opening;
|
||||
}
|
||||
else if (id == "lock") {
|
||||
doorLock = num;
|
||||
}
|
||||
}
|
||||
if (!accessLoaded) {
|
||||
if (id == "clearkeys") {
|
||||
Keys = [];
|
||||
}
|
||||
else if (id == "addkey") {
|
||||
addKey(name, FALSE);
|
||||
}
|
||||
} else {
|
||||
if (id == "getkeys") {
|
||||
integer i;
|
||||
|
||||
for (i = 0; i < llGetListLength(Keys); i++) {
|
||||
llMessageLinked(sender, 1, llList2String(Keys, i), "addkey");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
state opened
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
doorClosed = FALSE;
|
||||
if (configSensor && doorActUID != NULL_KEY) {
|
||||
if (configAxisCenter) llSensorRepeat("", doorActUID, AGENT, doorActDist + 1.5, TWO_PI, 1.0);
|
||||
else llSensorRepeat("", doorActUID, AGENT, doorActDist + 0.5, TWO_PI, 1.0);
|
||||
llSetTimerEvent(0.0);
|
||||
}
|
||||
else if (configAutoClose > 0.0) {
|
||||
llSetTimerEvent(configAutoClose);
|
||||
}
|
||||
}
|
||||
|
||||
changed(integer change)
|
||||
{
|
||||
if (change & CHANGED_INVENTORY) {
|
||||
state loading;
|
||||
}
|
||||
}
|
||||
|
||||
touch_end(integer total_number)
|
||||
{
|
||||
if (configDistance > 0.0) {
|
||||
if (llVecDist(llGetPos(), llDetectedPos(0)) <= configDistance) {
|
||||
doorControl = TRUE;
|
||||
state closing;
|
||||
//if (doorClosed) door(llDetectedKey(0), llVecDist(llGetPos(), llDetectedPos(0)));
|
||||
//else door();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
link_message(integer sender, integer num, string name, key id)
|
||||
{
|
||||
if (llStringLength(configDouble) > 0 && name == configDouble) {
|
||||
if (id == "door") {
|
||||
if (doorControl) return;
|
||||
//llOwnerSay("DEBUG: link_message:door: sender=" + (string)sender + ", num=" + (string)num);
|
||||
if (num == TRUE) state closing;
|
||||
}
|
||||
else if (id == "lock") {
|
||||
doorLock = num;
|
||||
}
|
||||
}
|
||||
if (!accessLoaded) {
|
||||
if (id == "clearkeys") {
|
||||
Keys = [];
|
||||
}
|
||||
else if (id == "addkey") {
|
||||
addKey(name, FALSE);
|
||||
}
|
||||
} else {
|
||||
if (id == "getkeys") {
|
||||
integer i;
|
||||
|
||||
for (i = 0; i < llGetListLength(Keys); i++) {
|
||||
llMessageLinked(sender, 1, llList2String(Keys, i), "addkey");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
no_sensor()
|
||||
{
|
||||
llSensorRemove();
|
||||
state closing;
|
||||
//door();
|
||||
}
|
||||
|
||||
timer()
|
||||
{
|
||||
llSetTimerEvent(0.0);
|
||||
state closing;
|
||||
//if (!doorClosed) door();
|
||||
}
|
||||
}
|
||||
|
||||
state closing
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
integer i;
|
||||
rotation delta;
|
||||
rotation rot = llGetLocalRot();
|
||||
vector pos = llGetLocalPos();
|
||||
vector size = llGetScale();
|
||||
float direction = configRotAngle;
|
||||
|
||||
vector vPosOffset;
|
||||
vector vPosRotOffset;
|
||||
vector vPosOffsetDiff;
|
||||
vector vPosRotDiff;
|
||||
|
||||
//llOwnerSay("DEBUG: Door->Close");
|
||||
doorClosed = TRUE;
|
||||
direction = -configRotAngle;
|
||||
|
||||
llSetTimerEvent(0.0);
|
||||
llSensorRemove();
|
||||
//llCollisionFilter("", NULL_KEY, TRUE);
|
||||
if (doorControl) doorMsg(doorClosed, "door");
|
||||
if (configAxis == "x") delta = llEuler2Rot(<direction / configRotSteps, 0, 0> * DEG_TO_RAD);
|
||||
else if (configAxis == "y") delta = llEuler2Rot(<0, direction / configRotSteps, 0> * DEG_TO_RAD);
|
||||
else if (configAxis == "z") delta = llEuler2Rot(<0, 0, direction / configRotSteps> * DEG_TO_RAD);
|
||||
|
||||
if (configAxisCenter) {
|
||||
if (configAxisCenterAxis == "x") vPosOffset.x = (size.x / 2) * configAxisCenterDir;
|
||||
else if (configAxisCenterAxis == "y") vPosOffset.y = (size.y / 2) * configAxisCenterDir;
|
||||
else if (configAxisCenterAxis == "z") vPosOffset.z = (size.z / 2) * configAxisCenterDir;
|
||||
}
|
||||
|
||||
for (i =0; i < configRotSteps; i++) {
|
||||
rot = delta * rot;
|
||||
pos = llGetLocalPos();
|
||||
|
||||
if (configAxisCenter) {
|
||||
vPosRotOffset = vPosOffset * delta;
|
||||
vPosOffsetDiff = vPosOffset - vPosRotOffset;
|
||||
vPosRotDiff = vPosOffsetDiff * llGetLocalRot();
|
||||
|
||||
llSetLinkPrimitiveParamsFast(LINK_THIS, [PRIM_POSITION, llGetLocalPos() + (vPosOffset - vPosOffset * delta) * llGetLocalRot(),
|
||||
PRIM_ROT_LOCAL, rot]);
|
||||
} else {
|
||||
llSetLinkPrimitiveParamsFast(LINK_THIS, [PRIM_ROT_LOCAL, rot]);
|
||||
}
|
||||
llSleep(configRotTime / configRotSteps);
|
||||
}
|
||||
|
||||
sound(soundClose);
|
||||
doorControl = FALSE;
|
||||
state closed;
|
||||
}
|
||||
}
|
||||
|
||||
state opening
|
||||
{
|
||||
state_entry()
|
||||
{
|
||||
integer i;
|
||||
rotation delta;
|
||||
rotation rot = llGetLocalRot();
|
||||
vector pos = llGetLocalPos();
|
||||
vector size = llGetScale();
|
||||
float direction = configRotAngle;
|
||||
|
||||
vector vPosOffset;
|
||||
vector vPosRotOffset;
|
||||
vector vPosOffsetDiff;
|
||||
vector vPosRotDiff;
|
||||
|
||||
//llOwnerSay("DEBUG: Door->Open");
|
||||
sound(soundOpen);
|
||||
doorClosed = FALSE;
|
||||
direction = configRotAngle;
|
||||
|
||||
//llCollisionFilter("", NULL_KEY, FALSE);
|
||||
if (doorControl) doorMsg(doorClosed, "door");
|
||||
if (configAxis == "x") delta = llEuler2Rot(<direction/configRotSteps, 0, 0> * DEG_TO_RAD);
|
||||
else if (configAxis == "y") delta = llEuler2Rot(<0, direction/configRotSteps, 0> * DEG_TO_RAD);
|
||||
else if (configAxis == "z") delta = llEuler2Rot(<0, 0, direction/configRotSteps> * DEG_TO_RAD);
|
||||
|
||||
if (configAxisCenter) {
|
||||
if (configAxisCenterAxis == "x") vPosOffset.x = (size.x / 2) * configAxisCenterDir;
|
||||
else if (configAxisCenterAxis == "y") vPosOffset.y = (size.y / 2) * configAxisCenterDir;
|
||||
else if (configAxisCenterAxis == "z") vPosOffset.z = (size.z / 2) * configAxisCenterDir;
|
||||
}
|
||||
|
||||
for (i =0; i < configRotSteps; i++) {
|
||||
rot = delta * rot;
|
||||
pos = llGetLocalPos();
|
||||
|
||||
if (configAxisCenter) {
|
||||
vPosRotOffset = vPosOffset * delta;
|
||||
vPosOffsetDiff = vPosOffset - vPosRotOffset;
|
||||
vPosRotDiff = vPosOffsetDiff * llGetLocalRot();
|
||||
|
||||
llSetLinkPrimitiveParamsFast(LINK_THIS, [PRIM_POSITION, llGetLocalPos() + (vPosOffset - vPosOffset * delta) * llGetLocalRot(),
|
||||
PRIM_ROT_LOCAL, rot]);
|
||||
} else {
|
||||
llSetLinkPrimitiveParamsFast(LINK_THIS, [PRIM_ROT_LOCAL, rot]);
|
||||
}
|
||||
llSleep(configRotTime / configRotSteps);
|
||||
}
|
||||
|
||||
doorControl = FALSE;
|
||||
state opened;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in a new issue