From ab5556055e6104d3e5c18faf7f6f9e44b518839f Mon Sep 17 00:00:00 2001 From: Teravus Ovares Date: Wed, 7 May 2008 18:23:46 +0000 Subject: [PATCH] * Theoretically, everything is in place for scripted take controls... Theoretically. * I've still got to test, it's still theoretical code :D. Good thing it isn't enabled by default! --- .../Region/Environment/Scenes/SceneEvents.cs | 5 + .../Environment/Scenes/ScenePresence.cs | 104 +++++++++++++++++- .../Common/LSL_BuiltIn_Commands.cs | 36 +++++- .../Common/ScriptEngineBase/EventManager.cs | 4 +- .../Common/ScriptServerInterfaces.cs | 2 +- 5 files changed, 143 insertions(+), 8 deletions(-) diff --git a/OpenSim/Region/Environment/Scenes/SceneEvents.cs b/OpenSim/Region/Environment/Scenes/SceneEvents.cs index 2feed78fbb..d409f4e368 100644 --- a/OpenSim/Region/Environment/Scenes/SceneEvents.cs +++ b/OpenSim/Region/Environment/Scenes/SceneEvents.cs @@ -602,5 +602,10 @@ namespace OpenSim.Region.Environment.Scenes handlerAvatarKill(KillerObjectLocalID, DeadAvatar); } } + + internal void TriggerControlEvent(uint p, LLUUID scriptUUID, uint p_3, uint p_4) + { + throw new Exception("The method or operation is not implemented."); + } } } diff --git a/OpenSim/Region/Environment/Scenes/ScenePresence.cs b/OpenSim/Region/Environment/Scenes/ScenePresence.cs index 66363b76c2..fdafd7fd80 100644 --- a/OpenSim/Region/Environment/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Environment/Scenes/ScenePresence.cs @@ -81,6 +81,7 @@ namespace OpenSim.Region.Environment.Scenes private List m_animationSeqs = new List(); private Dictionary scriptedcontrols = new Dictionary(); private ScriptControlled IgnoredControls = ScriptControlled.CONTROL_ZERO; + private ScriptControlled LastCommands = ScriptControlled.CONTROL_ZERO; public Vector3 lastKnownAllowedPosition = new Vector3(); public bool sentMessageAboutRestrictedParcelFlyingDown = false; @@ -819,6 +820,7 @@ namespace OpenSim.Region.Environment.Scenes { if (scriptedcontrols.Count > 0) { + SendControlToScripts(flags, LastCommands); flags = this.RemoveIgnoredControls(flags, IgnoredControls); } @@ -2435,7 +2437,7 @@ namespace OpenSim.Region.Environment.Scenes } } - public void SendMovementEventsToScript(int controls, int accept, int pass_on, uint Obj_localID, LLUUID Script_item_LLUUID) + public void RegisterControlEventsToScript(int controls, int accept, int pass_on, uint Obj_localID, LLUUID Script_item_LLUUID) { ScriptControllers obj = new ScriptControllers(); @@ -2489,6 +2491,106 @@ namespace OpenSim.Region.Environment.Scenes } + + public void UnRegisterControlEventsToScript(uint Obj_localID, LLUUID Script_item_LLUUID) + { + lock (scriptedcontrols) + { + if (scriptedcontrols.ContainsKey(Script_item_LLUUID)) + { + scriptedcontrols.Remove(Script_item_LLUUID); + IgnoredControls = ScriptControlled.CONTROL_ZERO; + foreach (ScriptControllers scData in scriptedcontrols.Values) + { + IgnoredControls |= scData.ignoreControls; + } + } + } + } + + internal void SendControlToScripts(uint flags, ScriptControlled lastFlags) + { + + ScriptControlled allflags = ScriptControlled.CONTROL_ZERO; + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_POS) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_POS) != 0) + { + allflags |= ScriptControlled.CONTROL_FWD; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_NEG) != 0) + { + allflags |= ScriptControlled.CONTROL_BACK; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_POS) != 0) + { + allflags |= ScriptControlled.CONTROL_UP; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0) + { + allflags |= ScriptControlled.CONTROL_DOWN; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_POS) != 0) + { + allflags |= ScriptControlled.CONTROL_LEFT; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_NEG) != 0) + { + allflags |= ScriptControlled.CONTROL_RIGHT; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_YAW_POS) != 0) + { + allflags |= ScriptControlled.CONTROL_ROT_RIGHT; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_YAW_NEG) != 0) + { + allflags |= ScriptControlled.CONTROL_ROT_LEFT; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_ML_LBUTTON_DOWN) != 0) + { + allflags |= ScriptControlled.CONTROL_ML_LBUTTON; + } + if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_UP) != 0 || (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_DOWN) != 0) + { + allflags |= ScriptControlled.CONTROL_LBUTTON; + } + ScriptControlled held = ScriptControlled.CONTROL_ZERO; + ScriptControlled change = ScriptControlled.CONTROL_ZERO; + + foreach (ScriptControlled DCF in Enum.GetValues(typeof (ScriptControlled))) + { + // Held + if ((lastFlags & DCF) != 0 && (allflags & DCF) != 0) + { + held |= DCF; + continue; + } + // Not held recently + if ((lastFlags & DCF) != 0 && (allflags & DCF) == 0) + { + change |= DCF; + continue; + } + // Newly pressed. + if ((lastFlags & DCF) == 0 && (allflags & DCF) != 0) + { + change |= DCF; + continue; + } + + } + + lock (scriptedcontrols) + { + foreach (LLUUID scriptUUID in scriptedcontrols.Keys) + { + ScriptControllers scriptControlData = scriptedcontrols[scriptUUID]; + ScriptControlled localHeld = held & scriptControlData.eventControls; + ScriptControlled localChange = change & scriptControlData.eventControls; + m_scene.EventManager.TriggerControlEvent(scriptControlData.objID, scriptUUID, (uint)localHeld, (uint)localChange); + } + } + LastCommands = allflags; + //foreach (Dir_ControlFlags DCF in Enum.GetValues(typeof (Dir_ControlFlags))) + } internal uint RemoveIgnoredControls(uint flags, ScriptControlled Ignored) { if (Ignored == ScriptControlled.CONTROL_ZERO) diff --git a/OpenSim/Region/ScriptEngine/Common/LSL_BuiltIn_Commands.cs b/OpenSim/Region/ScriptEngine/Common/LSL_BuiltIn_Commands.cs index e8e4f806b5..1f23d00edf 100644 --- a/OpenSim/Region/ScriptEngine/Common/LSL_BuiltIn_Commands.cs +++ b/OpenSim/Region/ScriptEngine/Common/LSL_BuiltIn_Commands.cs @@ -1936,25 +1936,53 @@ namespace OpenSim.Region.ScriptEngine.Common public void llTakeControls(int controls, int accept, int pass_on) { + if (!m_host.TaskInventory.ContainsKey(InventorySelf())) + { + return; + } + if (m_host.TaskInventory[InventorySelf()].PermsGranter != LLUUID.Zero) { ScenePresence presence = World.m_innerScene.ScenePresences[m_host.TaskInventory[InventorySelf()].PermsGranter]; - if ((m_host.TaskInventory[InventorySelf()].PermsMask & BuiltIn_Commands_BaseClass.PERMISSION_TAKE_CONTROLS) != 0) + if (presence != null) { - presence.SendMovementEventsToScript(controls, accept, pass_on, m_localID, m_itemID); + if ((m_host.TaskInventory[InventorySelf()].PermsMask & BuiltIn_Commands_BaseClass.PERMISSION_TAKE_CONTROLS) != 0) + { + presence.RegisterControlEventsToScript(controls, accept, pass_on, m_localID, m_itemID); + } } } m_host.AddScriptLPS(1); - NotImplemented("llTakeControls"); + //NotImplemented("llTakeControls"); } public void llReleaseControls() { m_host.AddScriptLPS(1); - NotImplemented("llReleaseControls"); + + if (!m_host.TaskInventory.ContainsKey(InventorySelf())) + { + return; + } + + if (m_host.TaskInventory[InventorySelf()].PermsGranter != LLUUID.Zero) + { + + ScenePresence presence = World.m_innerScene.ScenePresences[m_host.TaskInventory[InventorySelf()].PermsGranter]; + if (presence != null) + { + if ((m_host.TaskInventory[InventorySelf()].PermsMask & BuiltIn_Commands_BaseClass.PERMISSION_TAKE_CONTROLS) != 0) + { + // Unregister controls from Presence + presence.UnRegisterControlEventsToScript(m_localID, m_itemID); + // Remove Take Control permission. + m_host.TaskInventory[InventorySelf()].PermsMask &= ~BuiltIn_Commands_BaseClass.PERMISSION_TAKE_CONTROLS; + } + } + } } public void llAttachToAvatar(int attachment) diff --git a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventManager.cs b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventManager.cs index 77a4048687..f8f38a17fe 100644 --- a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventManager.cs +++ b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventManager.cs @@ -225,9 +225,9 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase myScriptEngine.m_EventQueueManager.AddToScriptQueue(localID, itemID, "no_sensor", EventQueueManager.llDetectNull); } - public void control(uint localID, LLUUID itemID) + public void control(uint localID, LLUUID itemID, LLUUID agentID, uint held, uint change) { - myScriptEngine.m_EventQueueManager.AddToScriptQueue(localID, itemID, "control", EventQueueManager.llDetectNull); + myScriptEngine.m_EventQueueManager.AddToScriptQueue(localID, itemID, "control", EventQueueManager.llDetectNull, new object[] { new LSL_Types.LSLString(agentID.ToString()), new LSL_Types.LSLInteger(held), new LSL_Types.LSLInteger(change)}); } public void email(uint localID, LLUUID itemID) diff --git a/OpenSim/Region/ScriptEngine/Common/ScriptServerInterfaces.cs b/OpenSim/Region/ScriptEngine/Common/ScriptServerInterfaces.cs index 1edd3bd825..be42539d73 100644 --- a/OpenSim/Region/ScriptEngine/Common/ScriptServerInterfaces.cs +++ b/OpenSim/Region/ScriptEngine/Common/ScriptServerInterfaces.cs @@ -54,7 +54,7 @@ namespace OpenSim.Region.ScriptEngine.Common void on_rez(uint localID, LLUUID itemID); void sensor(uint localID, LLUUID itemID); void no_sensor(uint localID, LLUUID itemID); - void control(uint localID, LLUUID itemID); + void control(uint localID, LLUUID itemID, LLUUID agentID, uint held, uint change); void money(uint LocalID, LLUUID agentID, int amount); void email(uint localID, LLUUID itemID); void at_target(uint localID, uint handle, LLVector3 targetpos, LLVector3 atpos);