diff --git a/OpenSim/Framework/IClientAPI.cs b/OpenSim/Framework/IClientAPI.cs index f806da496c..965e68eacc 100755 --- a/OpenSim/Framework/IClientAPI.cs +++ b/OpenSim/Framework/IClientAPI.cs @@ -648,6 +648,9 @@ namespace OpenSim.Framework { Vector3 StartPos { get; set; } float StartFar { get; set; } + float FOV { get; set; } + int viewHeight { get; set; } + int viewWidth { get; set; } UUID AgentId { get; } diff --git a/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs b/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs index 2e5fdc3926..9742de1a38 100755 --- a/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/LLClientView.cs @@ -385,7 +385,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP protected Dictionary m_groupPowers = new(); protected int m_terrainCheckerCount; protected uint m_agentFOVCounter; - + protected IAssetService m_assetService; protected bool m_supportViewerCache = false; @@ -405,6 +405,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP set { m_startpos = value; } } public float StartFar { get; set; } + public float FOV { get; set; } = 1.25f; + public int viewHeight { get; set; } = 480; + public int viewWidth { get; set; } = 640; + public UUID AgentId { get { return m_agentId; } } public UUID ScopeId { get { return m_scopeId; } } @@ -11595,7 +11599,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP if (genCounter == 0 || genCounter > m_agentFOVCounter) { m_agentFOVCounter = genCounter; - OnAgentFOV?.Invoke(this, fovPacket.FOVBlock.VerticalAngle); + FOV = fovPacket.FOVBlock.VerticalAngle; + OnAgentFOV?.Invoke(this, FOV); } } @@ -11751,6 +11756,12 @@ namespace OpenSim.Region.ClientStack.LindenUDP private void HandleAgentHeightWidth(Packet Pack) { + AgentHeightWidthPacket hwPacket = (AgentHeightWidthPacket)Pack; + if (hwPacket.AgentData.AgentID.NotEqual(m_agentId) || hwPacket.AgentData.SessionID.NotEqual(m_sessionId)) + return; + + viewHeight = hwPacket.HeightWidthBlock.Height; + viewWidth = hwPacket.HeightWidthBlock.Width; } diff --git a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs index 6ab9d43e95..dcb366e233 100755 --- a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs +++ b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs @@ -525,7 +525,9 @@ namespace OpenSim.Region.OptionalModules.Agent.InternetRelayClientView.Server } public float StartFar { get; set; } - + public float FOV { get; set; } = 1.25f; + public int viewHeight { get; set; } = 480; + public int viewWidth { get; set; } = 640; public bool TryGet(out T iface) { iface = default(T); diff --git a/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs b/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs index 22efe75039..068e28530c 100755 --- a/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs +++ b/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs @@ -567,6 +567,9 @@ namespace OpenSim.Region.OptionalModules.World.NPC } public float StartFar { get; set; } + public float FOV { get; set; } = 1.25f; + public int viewHeight { get; set; } = 480; + public int viewWidth { get; set; } = 640; public virtual UUID AgentId { diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs index b305802228..0b3134a7f6 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs @@ -13339,6 +13339,45 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api return LSL_Rotation.Identity; } + public LSL_Float llGetCameraFOV() + { + if (m_item.PermsGranter.IsZero()) + return LSL_Float.Zero; + + if ((m_item.PermsMask & ScriptBaseClass.PERMISSION_TRACK_CAMERA) == 0) + { + Error("llGetCameraAspect", "No permissions to track the camera"); + return LSL_Float.Zero; + } + + ScenePresence presence = World.GetScenePresence(m_item.PermsGranter); + if (presence is not null && presence.ControllingClient is not null) + { + return new LSL_Float(presence.ControllingClient.FOV); + } + return 1.4f; + } + + public LSL_Float llGetCameraAspect() + { + if (m_item.PermsGranter.IsZero()) + return 1f; + + if ((m_item.PermsMask & ScriptBaseClass.PERMISSION_TRACK_CAMERA) == 0) + { + Error("llGetCameraAspect", "No permissions to track the camera"); + return 1f; + } + + ScenePresence presence = World.GetScenePresence(m_item.PermsGranter); + if (presence is not null && presence.ControllingClient is not null) + { + int h = presence.ControllingClient.viewHeight; + return new LSL_Float(h > 0 ? (float)presence.ControllingClient.viewWidth / h : 1.0f); + } + return 1f; + } + public void llSetPrimURL(string url) { Deprecated("llSetPrimURL", "Use llSetPrimMediaParams instead"); diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Interface/ILSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/ILSL_Api.cs index dbe822a5d0..fb6f2c58ff 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Interface/ILSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/ILSL_Api.cs @@ -129,6 +129,8 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces LSL_Integer llGetAttached(); LSL_List llGetAttachedList(LSL_Key id); LSL_List llGetBoundingBox(string obj); + LSL_Float llGetCameraAspect(); + LSL_Float llGetCameraFOV(); LSL_Vector llGetCameraPos(); LSL_Rotation llGetCameraRot(); LSL_Vector llGetCenterOfMass(); diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Stub.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Stub.cs index ed392758b5..ccda2911f4 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Stub.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/LSL_Stub.cs @@ -512,6 +512,18 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase return m_LSL_Functions.llGetBoundingBox(obj); } + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public LSL_Float llGetCameraAspect() + { + return m_LSL_Functions.llGetCameraAspect(); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public LSL_Float llGetCameraFOV() + { + return m_LSL_Functions.llGetCameraFOV(); + } + [MethodImpl(MethodImplOptions.AggressiveInlining)] public LSL_Vector llGetCameraPos() {