Improved Locking Door

Written by Kitsune
//          Improved locking door script
//
//              Started by: Eric Linden
//           Modified by: Bjorn Nordlicht
//
//My friend wanted a decent locking door script for his new
//  home but we could only find broken free scripts.
//  This script has been modified so it works well enough.
//
 
//Seconds before open door will close on it's own
float timeout = 360.0;
 
// This number must match the channel number of the lock
// and unlock objects you want to use.  If multiple doors
// have the same channel, then a single lock can lock all of
// them at once.
integer gLockChannel = 243;
 
integer locked = FALSE;
 
door(integer doorState)
{
    rotation rot = llGetRot();
    rotation delta = llEuler2Rot(<0,0,doorState*PI/3>);
    rot = delta * rot;
    llSetRot(rot);
 
    llSleep(0.25); 
    rot = delta * rot;
    llSetRot(rot);
}
 
default
{
    on_rez(integer param)
    {
        llResetScript();
    }
 
    state_entry()
    {
        llOwnerSay("Door: Say lock or unlock on channel "+(string)gLockChannel);
        state closed;
    }
}
 
state closed
{
    on_rez(integer param)
    {
        llResetScript();
    }
 
    state_entry()
    {
        llListen(gLockChannel, "", llGetOwner(), "");
        //Close door
        //    llTriggerSound("Door close", 0.5);
        door(-1);
    }
 
    listen(integer channel, string name, key id, string message)
    {
        if (channel == gLockChannel)
        {
            if (message == "unlock")
            {
                locked = FALSE;
                //llTriggerSound("door unlock", 10.0);
                llSay(0, "unlocked");
            }
            else if(message == "lock")
            {
                locked = TRUE;
                //llTriggerSound("door lock", 10.0);
                llSay(0, "locked");
            }
        }
    }
 
    touch_start(integer total_number)
    {
        key id = llDetectedKey(0);
        if (id == llGetOwner() || !locked)
        {
    //        llTriggerSound("Door open", 0.5);
            state open;
        }
        else
        {
     //       llTriggerSound("Door knock", 0.5);
        }
    }
}
 
state open
{
    on_rez(integer param)
    {
       llResetScript();
    } 
 
    state_entry()
    {
        //Open door
        door(1);
        llSetTimerEvent(timeout);
    }
 
    touch_start(integer num)
    {
        state closed;
    }
 
    timer()
    {
        state closed;
    }
 
}