Merge branch 'master' of ssh://opensimulator.org/var/git/opensim

bullet-2.82
Diva Canto 2014-05-23 16:20:04 -07:00
commit 227685bea4
14 changed files with 474 additions and 136 deletions

View File

@ -134,6 +134,7 @@ what it is today.
* Micheil Merlin
* Mike Osias (IBM)
* Mike Pitman (IBM)
* mikemig
* mikkopa/_someone - RealXtend
* Misterblue
* Mircea Kitsune

View File

@ -46,6 +46,11 @@ namespace OpenSim.Framework.Console
// private readonly object m_syncRoot = new object();
private const string LOGLEVEL_NONE = "(none)";
// Used to extract categories for colourization.
private Regex m_categoryRegex
= new Regex(
@"^(?<Front>.*?)\[(?<Category>[^\]]+)\]:?(?<End>.*)", RegexOptions.Singleline | RegexOptions.Compiled);
private int m_cursorYPosition = -1;
private int m_cursorXPosition = 0;
private StringBuilder m_commandLine = new StringBuilder();
@ -280,11 +285,8 @@ namespace OpenSim.Framework.Console
string outText = text;
if (level != LOGLEVEL_NONE)
{
string regex = @"^(?<Front>.*?)\[(?<Category>[^\]]+)\]:?(?<End>.*)";
Regex RE = new Regex(regex, RegexOptions.Multiline);
MatchCollection matches = RE.Matches(text);
{
MatchCollection matches = m_categoryRegex.Matches(text);
if (matches.Count == 1)
{

View File

@ -0,0 +1,286 @@
/*
* Copyright (c) Contributors, http://opensimulator.org/
* See CONTRIBUTORS.TXT for a full list of copyright holders.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* * Neither the name of the OpenSimulator Project nor the
* names of its contributors may be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
using System;
using System.Collections.Generic;
using log4net.Config;
using Nini.Config;
using NUnit.Framework;
using OpenMetaverse;
using OpenSim.Framework;
using OpenSim.Framework.Servers;
using OpenSim.Framework.Servers.HttpServer;
using OpenSim.Region.CoreModules.Avatar.Chat;
using OpenSim.Region.CoreModules.Framework;
using OpenSim.Region.CoreModules.Framework.EntityTransfer;
using OpenSim.Region.CoreModules.ServiceConnectorsOut.Simulation;
using OpenSim.Region.Framework.Scenes;
using OpenSim.Services.Interfaces;
using OpenSim.Tests.Common;
using OpenSim.Tests.Common.Mock;
namespace OpenSim.Region.CoreModules.Avatar.Chat.Tests
{
[TestFixture]
public class ChatModuleTests : OpenSimTestCase
{
[TestFixtureSetUp]
public void FixtureInit()
{
// Don't allow tests to be bamboozled by asynchronous events. Execute everything on the same thread.
// We must do this here so that child agent positions are updated in a predictable manner.
Util.FireAndForgetMethod = FireAndForgetMethod.RegressionTest;
}
[TestFixtureTearDown]
public void TearDown()
{
// We must set this back afterwards, otherwise later tests will fail since they're expecting multiple
// threads. Possibly, later tests should be rewritten so none of them require async stuff (which regression
// tests really shouldn't).
Util.FireAndForgetMethod = Util.DefaultFireAndForgetMethod;
}
private void SetupNeighbourRegions(TestScene sceneA, TestScene sceneB)
{
// XXX: HTTP server is not (and should not be) necessary for this test, though it's absence makes the
// CapabilitiesModule complain when it can't set up HTTP endpoints.
// BaseHttpServer httpServer = new BaseHttpServer(99999);
// MainServer.AddHttpServer(httpServer);
// MainServer.Instance = httpServer;
// We need entity transfer modules so that when sp2 logs into the east region, the region calls
// EntityTransferModuleto set up a child agent on the west region.
// XXX: However, this is not an entity transfer so is misleading.
EntityTransferModule etmA = new EntityTransferModule();
EntityTransferModule etmB = new EntityTransferModule();
LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule();
IConfigSource config = new IniConfigSource();
config.AddConfig("Chat");
IConfig modulesConfig = config.AddConfig("Modules");
modulesConfig.Set("EntityTransferModule", etmA.Name);
modulesConfig.Set("SimulationServices", lscm.Name);
SceneHelpers.SetupSceneModules(new Scene[] { sceneA, sceneB }, config, lscm);
SceneHelpers.SetupSceneModules(sceneA, config, new CapabilitiesModule(), etmA, new ChatModule());
SceneHelpers.SetupSceneModules(sceneB, config, new CapabilitiesModule(), etmB, new ChatModule());
}
/// <summary>
/// Tests chat between neighbour regions on the east-west axis
/// </summary>
/// <remarks>
/// Really, this is a combination of a child agent position update test and a chat range test. These need
/// to be separated later on.
/// </remarks>
[Test]
public void TestInterRegionChatDistanceEastWest()
{
TestHelpers.InMethod();
// TestHelpers.EnableLogging();
UUID sp1Uuid = TestHelpers.ParseTail(0x11);
UUID sp2Uuid = TestHelpers.ParseTail(0x12);
Vector3 sp1Position = new Vector3(6, 128, 20);
Vector3 sp2Position = new Vector3(250, 128, 20);
SceneHelpers sh = new SceneHelpers();
TestScene sceneWest = sh.SetupScene("sceneWest", TestHelpers.ParseTail(0x1), 1000, 1000);
TestScene sceneEast = sh.SetupScene("sceneEast", TestHelpers.ParseTail(0x2), 1001, 1000);
SetupNeighbourRegions(sceneWest, sceneEast);
ScenePresence sp1 = SceneHelpers.AddScenePresence(sceneEast, sp1Uuid);
TestClient sp1Client = (TestClient)sp1.ControllingClient;
// If we don't set agents to flying, test will go wrong as they instantly fall to z = 0.
// TODO: May need to create special complete no-op test physics module rather than basic physics, since
// physics is irrelevant to this test.
sp1.Flying = true;
// When sp1 logs in to sceneEast, it sets up a child agent in sceneWest and informs the sp2 client to
// make the connection. For this test, will simplify this chain by making the connection directly.
ScenePresence sp1Child = SceneHelpers.AddChildScenePresence(sceneWest, sp1Uuid);
TestClient sp1ChildClient = (TestClient)sp1Child.ControllingClient;
sp1.AbsolutePosition = sp1Position;
ScenePresence sp2 = SceneHelpers.AddScenePresence(sceneWest, sp2Uuid);
TestClient sp2Client = (TestClient)sp2.ControllingClient;
sp2.Flying = true;
ScenePresence sp2Child = SceneHelpers.AddChildScenePresence(sceneEast, sp2Uuid);
TestClient sp2ChildClient = (TestClient)sp2Child.ControllingClient;
sp2.AbsolutePosition = sp2Position;
// We must update the scenes in order to make the root new root agents trigger position updates in their
// children.
sceneWest.Update(1);
sceneEast.Update(1);
// Check child positions are correct.
Assert.AreEqual(
new Vector3(sp1Position.X + sceneEast.RegionInfo.RegionSizeX, sp1Position.Y, sp1Position.Z),
sp1ChildClient.SceneAgent.AbsolutePosition);
Assert.AreEqual(
new Vector3(sp2Position.X - sceneWest.RegionInfo.RegionSizeX, sp2Position.Y, sp2Position.Z),
sp2ChildClient.SceneAgent.AbsolutePosition);
string receivedSp1ChatMessage = "";
string receivedSp2ChatMessage = "";
sp1ChildClient.OnReceivedChatMessage
+= (message, type, fromPos, fromName, fromAgentID, ownerID, source, audible) => receivedSp1ChatMessage = message;
sp2ChildClient.OnReceivedChatMessage
+= (message, type, fromPos, fromName, fromAgentID, ownerID, source, audible) => receivedSp2ChatMessage = message;
TestUserInRange(sp1Client, "ello darling", ref receivedSp2ChatMessage);
TestUserInRange(sp2Client, "fantastic cats", ref receivedSp1ChatMessage);
sp1Position = new Vector3(30, 128, 20);
sp1.AbsolutePosition = sp1Position;
sceneEast.Update(1);
// Check child position is correct.
Assert.AreEqual(
new Vector3(sp1Position.X + sceneEast.RegionInfo.RegionSizeX, sp1Position.Y, sp1Position.Z),
sp1ChildClient.SceneAgent.AbsolutePosition);
TestUserOutOfRange(sp1Client, "beef", ref receivedSp2ChatMessage);
TestUserOutOfRange(sp2Client, "lentils", ref receivedSp1ChatMessage);
}
/// <summary>
/// Tests chat between neighbour regions on the north-south axis
/// </summary>
/// <remarks>
/// Really, this is a combination of a child agent position update test and a chat range test. These need
/// to be separated later on.
/// </remarks>
[Test]
public void TestInterRegionChatDistanceNorthSouth()
{
TestHelpers.InMethod();
// TestHelpers.EnableLogging();
UUID sp1Uuid = TestHelpers.ParseTail(0x11);
UUID sp2Uuid = TestHelpers.ParseTail(0x12);
Vector3 sp1Position = new Vector3(128, 250, 20);
Vector3 sp2Position = new Vector3(128, 6, 20);
SceneHelpers sh = new SceneHelpers();
TestScene sceneNorth = sh.SetupScene("sceneNorth", TestHelpers.ParseTail(0x1), 1000, 1000);
TestScene sceneSouth = sh.SetupScene("sceneSouth", TestHelpers.ParseTail(0x2), 1000, 1001);
SetupNeighbourRegions(sceneNorth, sceneSouth);
ScenePresence sp1 = SceneHelpers.AddScenePresence(sceneNorth, sp1Uuid);
TestClient sp1Client = (TestClient)sp1.ControllingClient;
// If we don't set agents to flying, test will go wrong as they instantly fall to z = 0.
// TODO: May need to create special complete no-op test physics module rather than basic physics, since
// physics is irrelevant to this test.
sp1.Flying = true;
// When sp1 logs in to sceneEast, it sets up a child agent in sceneNorth and informs the sp2 client to
// make the connection. For this test, will simplify this chain by making the connection directly.
ScenePresence sp1Child = SceneHelpers.AddChildScenePresence(sceneSouth, sp1Uuid);
TestClient sp1ChildClient = (TestClient)sp1Child.ControllingClient;
sp1.AbsolutePosition = sp1Position;
ScenePresence sp2 = SceneHelpers.AddScenePresence(sceneSouth, sp2Uuid);
TestClient sp2Client = (TestClient)sp2.ControllingClient;
sp2.Flying = true;
ScenePresence sp2Child = SceneHelpers.AddChildScenePresence(sceneNorth, sp2Uuid);
TestClient sp2ChildClient = (TestClient)sp2Child.ControllingClient;
sp2.AbsolutePosition = sp2Position;
// We must update the scenes in order to make the root new root agents trigger position updates in their
// children.
sceneNorth.Update(1);
sceneSouth.Update(1);
// Check child positions are correct.
Assert.AreEqual(
new Vector3(sp1Position.X, sp1Position.Y - sceneNorth.RegionInfo.RegionSizeY, sp1Position.Z),
sp1ChildClient.SceneAgent.AbsolutePosition);
Assert.AreEqual(
new Vector3(sp2Position.X, sp2Position.Y + sceneSouth.RegionInfo.RegionSizeY, sp2Position.Z),
sp2ChildClient.SceneAgent.AbsolutePosition);
string receivedSp1ChatMessage = "";
string receivedSp2ChatMessage = "";
sp1ChildClient.OnReceivedChatMessage
+= (message, type, fromPos, fromName, fromAgentID, ownerID, source, audible) => receivedSp1ChatMessage = message;
sp2ChildClient.OnReceivedChatMessage
+= (message, type, fromPos, fromName, fromAgentID, ownerID, source, audible) => receivedSp2ChatMessage = message;
TestUserInRange(sp1Client, "ello darling", ref receivedSp2ChatMessage);
TestUserInRange(sp2Client, "fantastic cats", ref receivedSp1ChatMessage);
sp1Position = new Vector3(30, 128, 20);
sp1.AbsolutePosition = sp1Position;
sceneNorth.Update(1);
// Check child position is correct.
Assert.AreEqual(
new Vector3(sp1Position.X, sp1Position.Y - sceneNorth.RegionInfo.RegionSizeY, sp1Position.Z),
sp1ChildClient.SceneAgent.AbsolutePosition);
TestUserOutOfRange(sp1Client, "beef", ref receivedSp2ChatMessage);
TestUserOutOfRange(sp2Client, "lentils", ref receivedSp1ChatMessage);
}
private void TestUserInRange(TestClient speakClient, string testMessage, ref string receivedMessage)
{
receivedMessage = "";
speakClient.Chat(0, ChatTypeEnum.Say, testMessage);
Assert.AreEqual(testMessage, receivedMessage);
}
private void TestUserOutOfRange(TestClient speakClient, string testMessage, ref string receivedMessage)
{
receivedMessage = "";
speakClient.Chat(0, ChatTypeEnum.Say, testMessage);
Assert.AreNotEqual(testMessage, receivedMessage);
}
}
}

View File

@ -428,7 +428,7 @@ namespace OpenSim.Region.CoreModules.Avatar.InstantMessage
/// <summary>
/// delegate for sending a grid instant message asynchronously
/// </summary>
public delegate void GridInstantMessageDelegate(GridInstantMessage im, MessageResultNotification result, UUID prevRegionID);
public delegate void GridInstantMessageDelegate(GridInstantMessage im, MessageResultNotification result);
protected virtual void GridInstantMessageCompleted(IAsyncResult iar)
{
@ -442,138 +442,87 @@ namespace OpenSim.Region.CoreModules.Avatar.InstantMessage
{
GridInstantMessageDelegate d = SendGridInstantMessageViaXMLRPCAsync;
d.BeginInvoke(im, result, UUID.Zero, GridInstantMessageCompleted, d);
d.BeginInvoke(im, result, GridInstantMessageCompleted, d);
}
/// <summary>
/// Recursive SendGridInstantMessage over XMLRPC method.
/// This is called from within a dedicated thread.
/// The first time this is called, prevRegionHandle will be 0 Subsequent times this is called from
/// itself, prevRegionHandle will be the last region handle that we tried to send.
/// If the handles are the same, we look up the user's location using the grid.
/// If the handles are still the same, we end. The send failed.
/// Internal SendGridInstantMessage over XMLRPC method.
/// </summary>
/// <param name="prevRegionHandle">
/// Pass in 0 the first time this method is called. It will be called recursively with the last
/// regionhandle tried
/// </param>
protected virtual void SendGridInstantMessageViaXMLRPCAsync(GridInstantMessage im, MessageResultNotification result, UUID prevRegionID)
/// <remarks>
/// This is called from within a dedicated thread.
/// </remarks>
private void SendGridInstantMessageViaXMLRPCAsync(GridInstantMessage im, MessageResultNotification result)
{
UUID toAgentID = new UUID(im.toAgentID);
PresenceInfo upd = null;
bool lookupAgent = false;
UUID regionID;
bool needToLookupAgent;
lock (m_UserRegionMap)
{
if (m_UserRegionMap.ContainsKey(toAgentID))
{
upd = new PresenceInfo();
upd.RegionID = m_UserRegionMap[toAgentID];
needToLookupAgent = !m_UserRegionMap.TryGetValue(toAgentID, out regionID);
// We need to compare the current regionhandle with the previous region handle
// or the recursive loop will never end because it will never try to lookup the agent again
if (prevRegionID == upd.RegionID)
{
lookupAgent = true;
}
}
else
{
lookupAgent = true;
}
}
// Are we needing to look-up an agent?
if (lookupAgent)
while (true)
{
// Non-cached user agent lookup.
PresenceInfo[] presences = PresenceService.GetAgents(new string[] { toAgentID.ToString() });
if (presences != null && presences.Length > 0)
if (needToLookupAgent)
{
foreach (PresenceInfo p in presences)
PresenceInfo[] presences = PresenceService.GetAgents(new string[] { toAgentID.ToString() });
UUID foundRegionID = UUID.Zero;
if (presences != null)
{
if (p.RegionID != UUID.Zero)
foreach (PresenceInfo p in presences)
{
upd = p;
break;
if (p.RegionID != UUID.Zero)
{
foundRegionID = p.RegionID;
break;
}
}
}
// If not found or the found region is the same as the last lookup, then message is undeliverable
if (foundRegionID == UUID.Zero || foundRegionID == regionID)
break;
else
regionID = foundRegionID;
}
if (upd != null)
GridRegion reginfo = m_Scenes[0].GridService.GetRegionByUUID(m_Scenes[0].RegionInfo.ScopeID, regionID);
if (reginfo == null)
{
// check if we've tried this before..
// This is one way to end the recursive loop
//
if (upd.RegionID == prevRegionID)
{
// m_log.Error("[GRID INSTANT MESSAGE]: Unable to deliver an instant message");
HandleUndeliverableMessage(im, result);
return;
}
m_log.WarnFormat("[GRID INSTANT MESSAGE]: Unable to find region {0}", regionID);
break;
}
else
// Try to send the message to the agent via the retrieved region.
Hashtable msgdata = ConvertGridInstantMessageToXMLRPC(im);
msgdata["region_handle"] = 0;
bool imresult = doIMSending(reginfo, msgdata);
// If the message delivery was successful, then cache the entry.
if (imresult)
{
// m_log.Error("[GRID INSTANT MESSAGE]: Unable to deliver an instant message");
HandleUndeliverableMessage(im, result);
lock (m_UserRegionMap)
{
m_UserRegionMap[toAgentID] = regionID;
}
result(true);
return;
}
// If we reach this point in the first iteration of the while, then we may have unsuccessfully tried
// to use a locally cached region ID. All subsequent attempts need to lookup agent details from
// the presence service.
needToLookupAgent = true;
}
if (upd != null)
{
GridRegion reginfo = m_Scenes[0].GridService.GetRegionByUUID(m_Scenes[0].RegionInfo.ScopeID,
upd.RegionID);
if (reginfo != null)
{
Hashtable msgdata = ConvertGridInstantMessageToXMLRPC(im);
// Not actually used anymore, left in for compatibility
// Remove at next interface change
//
msgdata["region_handle"] = 0;
bool imresult = doIMSending(reginfo, msgdata);
if (imresult)
{
// IM delivery successful, so store the Agent's location in our local cache.
lock (m_UserRegionMap)
{
if (m_UserRegionMap.ContainsKey(toAgentID))
{
m_UserRegionMap[toAgentID] = upd.RegionID;
}
else
{
m_UserRegionMap.Add(toAgentID, upd.RegionID);
}
}
result(true);
}
else
{
// try again, but lookup user this time.
// Warning, this must call the Async version
// of this method or we'll be making thousands of threads
// The version within the spawned thread is SendGridInstantMessageViaXMLRPCAsync
// The version that spawns the thread is SendGridInstantMessageViaXMLRPC
// If we reached this point then the message was not deliverable. Remove the bad cache entry and
// signal the delivery failure.
lock (m_UserRegionMap)
m_UserRegionMap.Remove(toAgentID);
// This is recursive!!!!!
SendGridInstantMessageViaXMLRPCAsync(im, result,
upd.RegionID);
}
}
else
{
m_log.WarnFormat("[GRID INSTANT MESSAGE]: Unable to find region {0}", upd.RegionID);
HandleUndeliverableMessage(im, result);
}
}
else
{
HandleUndeliverableMessage(im, result);
}
// m_log.Error("[GRID INSTANT MESSAGE]: Unable to deliver an instant message");
HandleUndeliverableMessage(im, result);
}
/// <summary>
@ -584,7 +533,6 @@ namespace OpenSim.Region.CoreModules.Avatar.InstantMessage
/// <returns>Bool if the message was successfully delivered at the other side.</returns>
protected virtual bool doIMSending(GridRegion reginfo, Hashtable xmlrpcdata)
{
ArrayList SendParams = new ArrayList();
SendParams.Add(xmlrpcdata);
XmlRpcRequest GridReq = new XmlRpcRequest("grid_instant_message", SendParams);

View File

@ -4133,7 +4133,10 @@ namespace OpenSim.Region.Framework.Scenes
/// <returns>true if we handled it.</returns>
public virtual bool IncomingUpdateChildAgent(AgentPosition cAgentData)
{
//m_log.Debug(" XXX Scene IncomingChildAgentDataUpdate POSITION in " + RegionInfo.RegionName);
// m_log.DebugFormat(
// "[SCENE PRESENCE]: IncomingChildAgentDataUpdate POSITION for {0} in {1}, position {2}",
// cAgentData.AgentID, Name, cAgentData.Position);
ScenePresence childAgentUpdate = GetScenePresence(cAgentData.AgentID);
if (childAgentUpdate != null)
{

View File

@ -2754,7 +2754,34 @@ namespace OpenSim.Region.Framework.Scenes
part.AddSittingAvatar(this);
cameraAtOffset = part.GetCameraAtOffset();
if (!part.IsRoot && cameraAtOffset == Vector3.Zero)
cameraAtOffset = part.ParentGroup.RootPart.GetCameraAtOffset();
bool cameraEyeOffsetFromRootForChild = false;
cameraEyeOffset = part.GetCameraEyeOffset();
if (!part.IsRoot && cameraEyeOffset == Vector3.Zero)
{
cameraEyeOffset = part.ParentGroup.RootPart.GetCameraEyeOffset();
cameraEyeOffsetFromRootForChild = true;
}
if ((cameraEyeOffset != Vector3.Zero && !cameraEyeOffsetFromRootForChild) || cameraAtOffset != Vector3.Zero)
{
if (!part.IsRoot)
{
cameraEyeOffset = cameraEyeOffset * part.RotationOffset;
cameraAtOffset += part.OffsetPosition;
}
cameraEyeOffset += part.OffsetPosition;
}
// m_log.DebugFormat(
// "[SCENE PRESENCE]: Using cameraAtOffset {0}, cameraEyeOffset {1} for sit on {2} by {3} in {4}",
// cameraAtOffset, cameraEyeOffset, part.Name, Name, Scene.Name);
forceMouselook = part.GetForceMouselook();
// An viewer expects to specify sit positions as offsets to the root prim, even if a child prim is

View File

@ -147,6 +147,7 @@ namespace OpenSim.Region.Physics.BasicPhysicsPlugin
terrainHeight = _heightMap[(int)actor.Position.Y * (int)m_regionExtent.Y + (int)actor.Position.X];
float height = terrainHeight + actor.Size.Z;
// Console.WriteLine("height {0}, actorPosition {1}", height, actorPosition);
if (actor.Flying)
{

View File

@ -6846,12 +6846,18 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api
{
m_host.AddScriptLPS(1);
m_host.SetCameraEyeOffset(offset);
if (m_host.ParentGroup.RootPart.GetCameraEyeOffset() == Vector3.Zero)
m_host.ParentGroup.RootPart.SetCameraEyeOffset(offset);
}
public void llSetCameraAtOffset(LSL_Vector offset)
{
m_host.AddScriptLPS(1);
m_host.SetCameraAtOffset(offset);
if (m_host.ParentGroup.RootPart.GetCameraAtOffset() == Vector3.Zero)
m_host.ParentGroup.RootPart.SetCameraAtOffset(offset);
}
public void llSetLinkCamera(LSL_Integer link, LSL_Vector eye, LSL_Vector at)

View File

@ -162,7 +162,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.CodeTools
m_braceCount++;
// line number
m_CSharpLine += 3;
m_CSharpLine += 9;
// here's the payload
retstr += GenerateLine();

View File

@ -444,7 +444,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.CodeTools
// return compileScript;
// }
private static string CreateCSCompilerScript(
public static string CreateCSCompilerScript(
string compileScript, string className, string baseClassName, ParameterInfo[] constructorParameters)
{
compileScript = string.Format(
@ -472,7 +472,7 @@ namespace SecondLife
return compileScript;
}
private static string CreateVBCompilerScript(string compileScript, string className, string baseClassName)
public static string CreateVBCompilerScript(string compileScript, string className, string baseClassName)
{
compileScript = String.Empty +
"Imports OpenSim.Region.ScriptEngine.Shared: Imports System.Collections.Generic: " +

View File

@ -31,6 +31,7 @@ using System.Collections.Generic;
using Microsoft.CSharp;
using NUnit.Framework;
using OpenSim.Region.ScriptEngine.Shared.CodeTools;
using OpenSim.Region.ScriptEngine.Shared.ScriptBase;
using OpenSim.Tests.Common;
namespace OpenSim.Region.ScriptEngine.Shared.CodeTools.Tests
@ -66,9 +67,10 @@ namespace OpenSim.Region.ScriptEngine.Shared.CodeTools.Tests
m_CSCodeProvider = new CSharpCodeProvider();
m_compilerParameters = new CompilerParameters();
string rootPath = Path.Combine(Path.GetDirectoryName(System.AppDomain.CurrentDomain.BaseDirectory), "bin");
string rootPath = Path.Combine(Path.GetDirectoryName(System.AppDomain.CurrentDomain.BaseDirectory));
m_compilerParameters.ReferencedAssemblies.Add(Path.Combine(rootPath, "OpenSim.Region.ScriptEngine.Shared.dll"));
m_compilerParameters.ReferencedAssemblies.Add(Path.Combine(rootPath, "OpenSim.Region.ScriptEngine.Shared.Api.Runtime.dll"));
m_compilerParameters.ReferencedAssemblies.Add(Path.Combine(rootPath, "OpenMetaverseTypes.dll"));
m_compilerParameters.GenerateExecutable = false;
}
@ -90,7 +92,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.CodeTools.Tests
/// Test the C# compiler error message can be mapped to the correct
/// line/column in the LSL source when an undeclared variable is used.
/// </summary>
//[Test]
[Test]
public void TestUseUndeclaredVariable()
{
TestHelpers.InMethod();
@ -106,25 +108,37 @@ namespace OpenSim.Region.ScriptEngine.Shared.CodeTools.Tests
}";
CSCodeGenerator cg = new CSCodeGenerator();
string output = "using OpenSim.Region.ScriptEngine.Shared; using System.Collections.Generic;\n" +
"namespace SecondLife { " +
"public class Script : OpenSim.Region.ScriptEngine.Shared.ScriptBase.ScriptBaseClass {\n" +
"public Script() { } " +
cg.Convert(input) +
"} }\n";
string output = cg.Convert(input);
output = Compiler.CreateCSCompilerScript(output, "script1", typeof(ScriptBaseClass).FullName, null);
// System.Console.WriteLine(output);
Dictionary<KeyValuePair<int, int>, KeyValuePair<int, int>> positionMap = cg.PositionMap;
m_compilerResults = m_CSCodeProvider.CompileAssemblyFromSource(m_compilerParameters, output);
//
// foreach (KeyValuePair<int, int> key in positionMap.Keys)
// {
// KeyValuePair<int, int> val = positionMap[key];
//
// System.Console.WriteLine("{0},{1} => {2},{3}", key.Key, key.Value, val.Key, val.Value);
// }
//
// foreach (CompilerError compErr in m_compilerResults.Errors)
// {
// System.Console.WriteLine("Error: {0},{1} => {2}", compErr.Line, compErr.Column, compErr);
// }
Assert.AreEqual(new KeyValuePair<int, int>(5, 21),
positionMap[new KeyValuePair<int, int>(m_compilerResults.Errors[0].Line, m_compilerResults.Errors[0].Column)]);
Assert.AreEqual(
new KeyValuePair<int, int>(5, 21),
positionMap[new KeyValuePair<int, int>(m_compilerResults.Errors[0].Line, m_compilerResults.Errors[0].Column)]);
}
/// <summary>
/// Test that a string can be cast to string and another string
/// concatenated.
/// </summary>
//[Test]
[Test]
public void TestCastAndConcatString()
{
TestHelpers.InMethod();
@ -143,15 +157,20 @@ default
}
}";
// System.Console.WriteLine(input);
CSCodeGenerator cg = new CSCodeGenerator();
string output = "using OpenSim.Region.ScriptEngine.Shared; using System.Collections.Generic;\n" +
"namespace SecondLife { " +
"public class Script : OpenSim.Region.ScriptEngine.Shared.ScriptBase.ScriptBaseClass {\n" +
"public Script() { } " +
cg.Convert(input) +
"} }\n";
string output = cg.Convert(input);
output = Compiler.CreateCSCompilerScript(output, "script1", typeof(ScriptBaseClass).FullName, null);
// System.Console.WriteLine(output);
m_compilerResults = m_CSCodeProvider.CompileAssemblyFromSource(m_compilerParameters, output);
// foreach (CompilerError compErr in m_compilerResults.Errors)
// {
// System.Console.WriteLine("Error: {0}", compErr);
// }
Assert.AreEqual(0, m_compilerResults.Errors.Count);
}
}

View File

@ -574,7 +574,11 @@ namespace OpenSim.Tests.Common
public static ScenePresence AddChildScenePresence(Scene scene, UUID agentId)
{
AgentCircuitData acd = GenerateAgentData(agentId);
return AddChildScenePresence(scene, GenerateAgentData(agentId));
}
public static ScenePresence AddChildScenePresence(Scene scene, AgentCircuitData acd)
{
acd.child = true;
// XXX: ViaLogin may not be correct for child agents

View File

@ -62,14 +62,23 @@ namespace OpenSim.Tests.Common.Mock
public event Action<RegionInfo, Vector3, Vector3> OnReceivedMoveAgentIntoRegion;
public event Action<ulong, IPEndPoint> OnTestClientInformClientOfNeighbour;
public event TestClientOnSendRegionTeleportDelegate OnTestClientSendRegionTeleport;
public event Action<ISceneEntity, PrimUpdateFlags> OnReceivedEntityUpdate;
public event OnReceivedChatMessageDelegate OnReceivedChatMessage;
public event Action<GridInstantMessage> OnReceivedInstantMessage;
public event Action<UUID> OnReceivedSendRebakeAvatarTextures;
public delegate void TestClientOnSendRegionTeleportDelegate(
ulong regionHandle, byte simAccess, IPEndPoint regionExternalEndPoint,
uint locationID, uint flags, string capsURL);
public delegate void OnReceivedChatMessageDelegate(
string message, byte type, Vector3 fromPos, string fromName,
UUID fromAgentID, UUID ownerID, byte source, byte audible);
// disable warning: public events, part of the public API
#pragma warning disable 67
@ -466,6 +475,34 @@ namespace OpenSim.Tests.Common.Mock
SentImageNotInDatabasePackets = new List<ImageNotInDatabasePacket>();
}
/// <summary>
/// Trigger chat coming from this connection.
/// </summary>
/// <param name="channel"></param>
/// <param name="type"></param>
/// <param name="message"></param>
public bool Chat(int channel, ChatTypeEnum type, string message)
{
ChatMessage handlerChatFromClient = OnChatFromClient;
if (handlerChatFromClient != null)
{
OSChatMessage args = new OSChatMessage();
args.Channel = channel;
args.From = Name;
args.Message = message;
args.Type = type;
args.Scene = Scene;
args.Sender = this;
args.SenderUUID = AgentId;
handlerChatFromClient(this, args);
}
return true;
}
/// <summary>
/// Attempt a teleport to the given region.
/// </summary>
@ -550,6 +587,9 @@ namespace OpenSim.Tests.Common.Mock
string message, byte type, Vector3 fromPos, string fromName,
UUID fromAgentID, UUID ownerID, byte source, byte audible)
{
// Console.WriteLine("mmm {0} {1} {2}", message, Name, AgentId);
if (OnReceivedChatMessage != null)
OnReceivedChatMessage(message, type, fromPos, fromName, fromAgentID, ownerID, source, audible);
}
public void SendInstantMessage(GridInstantMessage im)

View File

@ -3082,6 +3082,7 @@
<Match path="Asset/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/Attachments/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/AvatarFactory/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/Chat/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/Friends/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/Inventory/Archiver/Tests" pattern="*.cs" recurse="true"/>
<Match path="Avatar/Inventory/Transfer/Tests" pattern="*.cs" recurse="true"/>