From d18d37faf6ef879ddc6e87899a72b55696f0486a Mon Sep 17 00:00:00 2001 From: Jak Daniels Date: Wed, 24 Dec 2014 16:29:19 +0000 Subject: [PATCH] Many changes to support per region configuration and project name change --- CHANGES.txt | 5 + CONTRIBUTORS.txt | 4 +- Module/BirdsModule/{Boid.cs => Birds.cs} | 94 +++++++------- Module/BirdsModule/{Util.cs => BirdsUtil.cs} | 3 +- Module/BirdsModule/FlockingModel.cs | 27 ++-- Module/BirdsModule/FlockingModule.cs | 126 ++++++++++--------- Module/BirdsModule/FlockingView.cs | 33 ++--- Module/BirdsModule/FlowMap.cs | 29 ++--- README.md | 77 ++++++------ config/OpenSimBirds.ini | 16 +++ config/OpenSimBirds.ini.example | 16 +++ 11 files changed, 242 insertions(+), 188 deletions(-) rename Module/BirdsModule/{Boid.cs => Birds.cs} (85%) rename Module/BirdsModule/{Util.cs => BirdsUtil.cs} (96%) create mode 100644 config/OpenSimBirds.ini create mode 100644 config/OpenSimBirds.ini.example diff --git a/CHANGES.txt b/CHANGES.txt index 11f4b60..61da5e2 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -20,3 +20,8 @@ refactored the code added some more config items to set the region border size (no go zone) and the max height added support to the module for varregions + +24/12/2014 + renamed the modeul to OpenSimBirds, changed all references to [Bb]oids to [Bb]irds in code + change the configuration to use own ini file and to setup per region configurations + changed Util class to BirdsUtil to avoid clash with OpenSim.Util diff --git a/CONTRIBUTORS.txt b/CONTRIBUTORS.txt index f938b2a..3195333 100644 --- a/CONTRIBUTORS.txt +++ b/CONTRIBUTORS.txt @@ -1,5 +1,5 @@ -The following people have contributed to the development of the OpenSimBoids module +The following people have contributed to the development of the OpenSimBirds module * Jon Cundill - initial implementation -* Jak Daniels - refactor for opensim 0.8.x and varregions +* Jak Daniels - refactor for opensim 0.8.x and varregions and per region configuration diff --git a/Module/BirdsModule/Boid.cs b/Module/BirdsModule/Birds.cs similarity index 85% rename from Module/BirdsModule/Boid.cs rename to Module/BirdsModule/Birds.cs index afa26ea..2b7916c 100644 --- a/Module/BirdsModule/Boid.cs +++ b/Module/BirdsModule/Birds.cs @@ -1,5 +1,5 @@ /* - * Copyright (c) Contributors, https://github.com/jonc/osboids + * Copyright (c) Contributors, https://github.com/jonc/osbirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -31,7 +31,7 @@ using OpenMetaverse; namespace Flocking { - public class Boid + public class Bird { private static readonly ILog m_log = LogManager.GetLogger (System.Reflection.MethodBase.GetCurrentMethod ().DeclaringType); private string m_id; @@ -43,33 +43,33 @@ namespace Flocking private FlockingModel m_model; private FlowMap m_flowMap; - private int m_regionX; - private int m_regionY; - private int m_regionZ; + private int m_regionX; + private int m_regionY; + private int m_regionZ; private float m_regionBorder; /// - /// Initializes a new instance of the class. + /// Initializes a new instance of the class. /// /// - /// L. the initial position of this boid + /// L. the initial position of this bird /// /// - /// Ms. max speed this boid can attain + /// Ms. max speed this bird can attain /// /// - /// Mf. max force / acceleration this boid can extert + /// Mf. max force / acceleration this bird can extert /// - public Boid (string id, FlockingModel model, FlowMap flowMap) + public Bird (string id, FlockingModel model, FlowMap flowMap) { m_id = id; m_acc = Vector3.Zero; m_vel = new Vector3 (m_rndnums.Next (-1, 1), m_rndnums.Next (-1, 1), m_rndnums.Next (-1, 1)); m_model = model; - m_flowMap = flowMap; - m_regionX = m_flowMap.LengthX; - m_regionY = m_flowMap.LengthY; - m_regionZ = m_flowMap.LengthZ; + m_flowMap = flowMap; + m_regionX = m_flowMap.LengthX; + m_regionY = m_flowMap.LengthY; + m_regionZ = m_flowMap.LengthZ; m_regionBorder = m_flowMap.Border; } @@ -87,15 +87,15 @@ namespace Flocking } /// - /// Moves our boid in the scene relative to the rest of the flock. + /// Moves our bird in the scene relative to the rest of the flock. /// - /// - /// Boids. all the other chaps in the scene + /// + /// Birds. all the other chaps in the scene /// - public void MoveInSceneRelativeToFlock (List boids) + public void MoveInSceneRelativeToFlock (List birds) { // we would like to stay with our mates - Flock (boids); + Flock (birds); // our first priority is to not hurt ourselves AvoidObstacles (); @@ -119,13 +119,13 @@ namespace Flocking /// our desire to move towards the flock centre /// /// - void Flock (List boids) + void Flock (List birds) { - // calc the force vectors on this boid - Vector3 sep = Separate (boids); // Separation - Vector3 ali = Align (boids); // Alignment - Vector3 coh = Cohesion (boids); // Cohesion + // calc the force vectors on this bird + Vector3 sep = Separate (birds); // Separation + Vector3 ali = Align (birds); // Alignment + Vector3 coh = Cohesion (birds); // Cohesion // Arbitrarily weight these forces //TODO: expose these consts @@ -135,7 +135,7 @@ namespace Flocking //coh.mult(1.0); coh *= 1.0f; - // Add the force vectors to the current acceleration of the boid + // Add the force vectors to the current acceleration of the bird //acc.add(sep); m_acc += sep; //acc.add(ali); @@ -159,7 +159,7 @@ namespace Flocking m_vel += m_acc; // Limit speed //m_vel.limit(maxspeed); - m_vel = Util.Limit (m_vel, m_model.MaxSpeed); + m_vel = BirdsUtil.Limit (m_vel, m_model.MaxSpeed); m_loc += m_vel; // Reset accelertion to 0 each cycle m_acc *= 0.0f; @@ -209,7 +209,7 @@ namespace Flocking //steer = target.sub(desired,m_vel); steer = Vector3.Subtract (desired, m_vel); //steer.limit(maxforce); // Limit to maximum steering force - steer = Util.Limit (steer, m_model.MaxForce); + steer = BirdsUtil.Limit (steer, m_model.MaxForce); } else { steer = Vector3.Zero; } @@ -257,7 +257,7 @@ namespace Flocking // or try decreasing our acceleration // or turn around - coz where we came from was OK if (m_loc.X < m_regionBorder || m_loc.X > m_regionX - m_regionBorder) - m_vel.X = -m_vel.X; + m_vel.X = -m_vel.X; if (m_loc.Y < m_regionBorder || m_loc.Y > m_regionY - m_regionBorder) m_vel.Y = -m_vel.Y; if (m_loc.Z < 21 || m_loc.Z > m_regionZ ) @@ -265,19 +265,19 @@ namespace Flocking } /// - /// Separate ourselves from the specified boids. + /// Separate ourselves from the specified birds. /// keeps us a respectable distance from our closest neighbours whilst still /// being part of our local flock /// - /// - /// Boids. all the boids in the scene + /// + /// Birds. all the birds in the scene /// - Vector3 Separate (List boids) + Vector3 Separate (List birds) { Vector3 steer = new Vector3 (0, 0, 0); int count = 0; - // For every boid in the system, check if it's too close - foreach (Boid other in boids) { + // For every bird in the system, check if it's too close + foreach (Bird other in birds) { float d = Vector3.Distance (m_loc, other.Location); // If the distance is greater than 0 and less than an arbitrary amount (0 when you are yourself) if ((d > 0) && (d < m_model.DesiredSeparation)) { @@ -301,24 +301,24 @@ namespace Flocking steer *= m_model.MaxSpeed; steer -= m_vel; //steer.limit(maxforce); - steer = Util.Limit (steer, m_model.MaxForce); + steer = BirdsUtil.Limit (steer, m_model.MaxForce); } return steer; } /// - /// Align our boid within the flock. - /// For every nearby boid in the system, calculate the average velocity + /// Align our bird within the flock. + /// For every nearby bird in the system, calculate the average velocity /// and move us towards that - this keeps us moving with the flock. /// - /// - /// Boids. all the boids in the scene - we only really care about those in the neighbourdist + /// + /// Birds. all the birds in the scene - we only really care about those in the neighbourdist /// - Vector3 Align (List boids) + Vector3 Align (List birds) { Vector3 steer = new Vector3 (0, 0, 0); int count = 0; - foreach (Boid other in boids) { + foreach (Bird other in birds) { float d = Vector3.Distance (m_loc, other.Location); if ((d > 0) && (d < m_model.NeighbourDistance)) { steer += other.Velocity; @@ -336,7 +336,7 @@ namespace Flocking steer *= m_model.MaxSpeed; steer -= m_vel; //steer.limit(maxforce); - steer = Util.Limit (steer, m_model.MaxForce); + steer = BirdsUtil.Limit (steer, m_model.MaxForce); } return steer; @@ -344,18 +344,18 @@ namespace Flocking /// /// MAintain the cohesion of our local flock - /// For the average location (i.e. center) of all nearby boids, calculate our steering vector towards that location + /// For the average location (i.e. center) of all nearby birds, calculate our steering vector towards that location /// - /// - /// Boids. the boids in the scene + /// + /// Birds. the birds in the scene /// - Vector3 Cohesion (List boids) + Vector3 Cohesion (List birds) { Vector3 sum = Vector3.Zero; // Start with empty vector to accumulate all locations int count = 0; - foreach (Boid other in boids) { + foreach (Bird other in birds) { float d = Vector3.Distance (m_loc, other.Location); if ((d > 0) && (d < m_model.NeighbourDistance)) { sum += other.Location; // Add location diff --git a/Module/BirdsModule/Util.cs b/Module/BirdsModule/BirdsUtil.cs similarity index 96% rename from Module/BirdsModule/Util.cs rename to Module/BirdsModule/BirdsUtil.cs index b988eb6..9b32ee2 100644 --- a/Module/BirdsModule/Util.cs +++ b/Module/BirdsModule/BirdsUtil.cs @@ -1,5 +1,6 @@ /* * Copyright (c) Contributors, https://github.com/jonc/osboids + * https://github.com/JakDaniels/OpenSimBirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -29,7 +30,7 @@ using OpenMetaverse; namespace Flocking { - public class Util + public class BirdsUtil { public static Vector3 Limit (Vector3 initial, float maxLen) { diff --git a/Module/BirdsModule/FlockingModel.cs b/Module/BirdsModule/FlockingModel.cs index 93fae10..77bf813 100644 --- a/Module/BirdsModule/FlockingModel.cs +++ b/Module/BirdsModule/FlockingModel.cs @@ -1,5 +1,6 @@ /* * Copyright (c) Contributors, https://github.com/jonc/osboids + * https://github.com/JakDaniels/OpenSimBirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -32,13 +33,13 @@ namespace Flocking { public class FlockingModel { - private List m_flock = new List(); + private List m_flock = new List(); private FlowMap m_flowMap; private float m_maxSpeed; private float m_maxForce; private float m_neighbourDistance; private float m_desiredSeparation; - private float m_tolerance; + private float m_tolerance; private float m_border; private Random m_rnd = new Random(Environment.TickCount); @@ -49,7 +50,7 @@ namespace Flocking if( value < m_flock.Count ) { m_flock.RemoveRange( 0, m_flock.Count - value ); } else while( value > m_flock.Count ) { - AddBoid( "boid"+m_flock.Count); + AddBird( "Bird"+m_flock.Count); } } } @@ -59,15 +60,15 @@ namespace Flocking m_maxForce = maxForce; m_neighbourDistance = neighbourDistance; m_desiredSeparation = desiredSeparation; - m_tolerance = tolerance; + m_tolerance = tolerance; m_border = border; } - void AddBoid (string name) + void AddBird (string name) { - Boid boid = new Boid (name, this, m_flowMap); + Bird Bird = new Bird (name, this, m_flowMap); - // find an initial random location for this Boid + // find an initial random location for this Bird // somewhere not within an obstacle int xInit = m_rnd.Next(m_flowMap.LengthX); int yInit = m_rnd.Next(m_flowMap.LengthY); @@ -79,8 +80,8 @@ namespace Flocking zInit = m_rnd.Next(m_flowMap.LengthZ); } - boid.Location = new Vector3 (Convert.ToSingle(xInit), Convert.ToSingle(yInit), Convert.ToSingle(zInit)); - m_flock.Add (boid); + Bird.Location = new Vector3 (Convert.ToSingle(xInit), Convert.ToSingle(yInit), Convert.ToSingle(zInit)); + m_flock.Add (Bird); } public float MaxSpeed { @@ -108,14 +109,14 @@ namespace Flocking { m_flowMap = flowMap; for (int i = 0; i < num; i++) { - AddBoid ("boid"+i ); + AddBird ("Bird"+i ); } } - public List UpdateFlockPos () + public List UpdateFlockPos () { - foreach (Boid b in m_flock) { - b.MoveInSceneRelativeToFlock(m_flock); // Passing the entire list of boids to each boid individually + foreach (Bird b in m_flock) { + b.MoveInSceneRelativeToFlock(m_flock); // Passing the entire list of Birds to each Bird individually } return m_flock; diff --git a/Module/BirdsModule/FlockingModule.cs b/Module/BirdsModule/FlockingModule.cs index 8e77297..e1d10da 100644 --- a/Module/BirdsModule/FlockingModule.cs +++ b/Module/BirdsModule/FlockingModule.cs @@ -1,5 +1,6 @@ /* * Copyright (c) Contributors, https://github.com/jonc/osboids + * https://github.com/JakDaniels/OpenSimBirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -26,9 +27,11 @@ */ using System; using System.Timers; +using System.Net; +using System.IO; +using System.Text; using System.Collections.Generic; using OpenMetaverse; -using System.IO; using Nini.Config; using System.Threading; using log4net; @@ -38,19 +41,18 @@ using OpenSim.Framework; using OpenSim.Framework.Console; using Mono.Addins; -[assembly: Addin("BoidsModule", "0.1")] +[assembly: Addin("OpenSimBirds", "0.2")] [assembly: AddinDependency("OpenSim", "0.5")] namespace Flocking { - [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule")] + [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "OpenSimBirds")] public class FlockingModule : INonSharedRegionModule { #region Fields private static readonly ILog m_log = LogManager.GetLogger (System.Reflection.MethodBase.GetCurrentMethod ().DeclaringType); - static object m_sync = new object(); - public string m_name = "BoidsModule"; + public string m_name = "OpenSimBirds"; private Scene m_scene; private FlockingModel m_model; private FlockingView m_view; @@ -59,7 +61,7 @@ namespace Flocking private uint m_frame = 0; private int m_frameUpdateRate = 1; private int m_chatChannel = 118; - private string m_boidPrim; + private string m_birdPrim; private int m_flockSize = 100; private float m_maxSpeed; private float m_maxForce; @@ -68,49 +70,67 @@ namespace Flocking private float m_tolerance; private float m_borderSize; private int m_maxHeight; + static object m_sync = new object(); + + public IConfigSource m_config; private UUID m_owner; #endregion #region IRegionModuleBase implementation + public string Name { get { return m_name; } } + public Type ReplaceableInterface { get { return null; } } + public bool IsSharedModule { get { return false; } } + public void Initialise (IConfigSource source) { - //check if we are in the ini files - //if so get some physical constants out of them and pass into the model - IConfig config = source.Configs ["Boids"]; - if (config != null) { - m_chatChannel = config.GetInt ("chat-channel", 118); - m_boidPrim = config.GetString ("boid-prim", "boidPrim"); - m_flockSize = config.GetInt ("flock-size", 100); - m_maxSpeed = config.GetFloat("max-speed", 3f); - m_maxForce = config.GetFloat("max-force", 0.25f); - m_neighbourDistance = config.GetFloat("neighbour-dist", 25f); - m_desiredSeparation = config.GetFloat("desired-separation", 20f); - m_tolerance = config.GetFloat("tolerance", 5f); - m_borderSize = config.GetFloat("border-size", 5f); - m_maxHeight = config.GetInt("max-height", 256); - m_enabled = config.GetBoolean("enabled", false); - } - - if (m_enabled) - { - m_log.InfoFormat("[BOIDS] Enabled on channel {0} with Flock Size {1}", m_chatChannel, m_flockSize); - //m_ready = true; - return; - } + m_config = source; } - public void PostInitialise() - { - } - public void AddRegion (Scene scene) { - m_scene = scene; - m_log.InfoFormat ("[BOIDS]: Adding {0}", scene.RegionInfo.RegionName); + m_log.InfoFormat("[{0}]: Adding region '{1}' to this module", m_name, scene.RegionInfo.RegionName); + + string moduleConfigFile = Path.Combine(Util.configDir(), "../addon-modules/" + m_name + "/config/" + m_name + ".ini"); + m_log.InfoFormat("[{0}]: Loading from config file {1}", m_name, moduleConfigFile); + try + { + m_config = new IniConfigSource(moduleConfigFile); + } + catch (Exception) + { + m_log.InfoFormat("[{0}]: No module config file '{1}' was found! Tide in this region is set to Disabled", m_name, moduleConfigFile); + m_enabled = false; + m_config = null; + return; + } + IConfig cnf = m_config.Configs[scene.RegionInfo.RegionName]; + + if (cnf == null) + { + m_log.InfoFormat("[{0}]: No region section [{1}] found in config file {2}. Tide in this region is set to Disabled", m_name, scene.RegionInfo.RegionName, moduleConfigFile); + m_enabled = false; + return; + } + + m_enabled = cnf.GetBoolean("BirdsEnabled", false); + if (m_enabled) { + m_chatChannel = cnf.GetInt("BirdsChatChannel", 118); + m_birdPrim = cnf.GetString("BirdsPrim", "birdPrim"); + m_flockSize = cnf.GetInt("BirdsFlockSize", 100); + m_maxSpeed = cnf.GetFloat("BirdsMaxSpeed", 3f); + m_maxForce = cnf.GetFloat("BirdsMaxForce", 0.25f); + m_neighbourDistance = cnf.GetFloat("BirdsNeighbourDistance", 25f); + m_desiredSeparation = cnf.GetFloat("BirdsDesiredSeparation", 20f); + m_tolerance = cnf.GetFloat("BirdsTolerance", 5f); + m_borderSize = cnf.GetFloat("BirdsRegionBorderSize", 5f); + m_maxHeight = cnf.GetInt("BirdsMaxHeight", 256); + + m_log.InfoFormat("[{0}] Enabled on channel {1} with Flock Size {2}", m_name, m_chatChannel, m_flockSize); + //register commands RegisterCommands(); @@ -121,7 +141,9 @@ namespace Flocking // init module m_model = new FlockingModel(m_maxSpeed, m_maxForce, m_neighbourDistance, m_desiredSeparation, m_tolerance, m_borderSize); m_view = new FlockingView(scene); - m_view.BoidPrim = m_boidPrim; + m_view.BirdPrim = m_birdPrim; + m_frame = 0; + m_scene = scene; } } @@ -147,7 +169,8 @@ namespace Flocking public void RemoveRegion (Scene scene) { - if (m_enabled) { + m_log.InfoFormat("[{0}]: Removing region '{1}' from this module", m_name, scene.RegionInfo.RegionName); + if (m_enabled) { m_ready = false; scene.EventManager.OnFrame -= FlockUpdate; scene.EventManager.OnChatFromClient -= SimChatSent; @@ -164,19 +187,6 @@ namespace Flocking } } - public string Name { - get { return m_name; } - } - - public bool IsSharedModule { - get { return false; } - } - - public Type ReplaceableInterface - { - get { return null; } - } - #endregion #region EventHandlers @@ -187,13 +197,13 @@ namespace Flocking return; } - //m_log.InfoFormat("update my boids"); + //m_log.InfoFormat("update my birds"); // work out where everyone has moved to // and tell the scene to render the new positions lock( m_sync ) { - List boids = m_model.UpdateFlockPos (); - m_view.Render (boids); + List birds = m_model.UpdateFlockPos (); + m_view.Render (birds); } } @@ -244,8 +254,8 @@ namespace Flocking AddCommand ("start", "", "Start Flocking", HandleStartCmd); AddCommand ("size", "num", "Adjust the size of the flock ", HandleSetSizeCmd); AddCommand ("stats", "", "show flocking stats", HandleShowStatsCmd); - AddCommand ("prim", "name", "set the prim used for each boid to that passed in", HandleSetPrimCmd); - AddCommand ("framerate", "num", "[debugging] only update boids every frames", HandleSetFrameRateCmd); + AddCommand ("prim", "name", "set the prim used for each bird to that passed in", HandleSetPrimCmd); + AddCommand ("framerate", "num", "[debugging] only update birds every frames", HandleSetFrameRateCmd); } private bool ShouldHandleCmd () @@ -268,7 +278,7 @@ namespace Flocking if (inWorld) { IClientAPI ownerAPI = null; if (m_scene.TryGetClient (m_owner, out ownerAPI)) { - ownerAPI.SendBlueBoxMessage (m_owner, "Boids", response); + ownerAPI.SendBlueBoxMessage (m_owner, "Birds", response); } } else { MainConsole.Instance.Output (response); @@ -316,7 +326,7 @@ namespace Flocking { if (ShouldHandleCmd ()) { bool inWorld = IsInWorldCmd (ref args); - ShowResponse ("Num Boids = " + m_model.Size, inWorld); + ShowResponse ("Num Birds = " + m_model.Size, inWorld); } } @@ -325,7 +335,7 @@ namespace Flocking if (ShouldHandleCmd ()) { string primName = args[1]; lock(m_sync) { - m_view.BoidPrim = primName; + m_view.BirdPrim = primName; m_view.Clear(); } } diff --git a/Module/BirdsModule/FlockingView.cs b/Module/BirdsModule/FlockingView.cs index 69efe82..7cccd4d 100644 --- a/Module/BirdsModule/FlockingView.cs +++ b/Module/BirdsModule/FlockingView.cs @@ -1,5 +1,6 @@ /* * Copyright (c) Contributors, https://github.com/jonc/osboids + * https://github.com/JakDaniels/OpenSimBirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -36,7 +37,7 @@ namespace Flocking { private Scene m_scene; private UUID m_owner; - private String m_boidPrim; + private String m_birdPrim; private Dictionary m_sogMap = new Dictionary (); @@ -50,8 +51,8 @@ namespace Flocking m_owner = owner; } - public String BoidPrim { - set{ m_boidPrim = value;} + public String BirdPrim { + set{ m_birdPrim = value;} } public void Clear () @@ -64,36 +65,36 @@ namespace Flocking m_sogMap.Clear(); } - public void Render (List boids) + public void Render (List birds) { - foreach (Boid boid in boids) { - DrawBoid (boid); + foreach (Bird bird in birds) { + DrawBird (bird); } } - private void DrawBoid (Boid boid) + private void DrawBird (Bird bird) { - SceneObjectPart existing = m_scene.GetSceneObjectPart (boid.Id); + SceneObjectPart existing = m_scene.GetSceneObjectPart (bird.Id); SceneObjectGroup sog; if (existing == null) { - SceneObjectGroup group = findByName (m_boidPrim); - sog = CopyPrim (group, boid.Id); - m_sogMap [boid.Id] = sog; + SceneObjectGroup group = findByName (m_birdPrim); + sog = CopyPrim (group, bird.Id); + m_sogMap [bird.Id] = sog; m_scene.AddNewSceneObject (sog, false); } else { sog = existing.ParentGroup; } - Quaternion rotation = CalcRotationToEndpoint (sog, sog.AbsolutePosition, boid.Location); - sog.UpdateGroupRotationPR( boid.Location, rotation); + Quaternion rotation = CalcRotationToEndpoint (sog, sog.AbsolutePosition, bird.Location); + sog.UpdateGroupRotationPR( bird.Location, rotation); } private static Quaternion CalcRotationToEndpoint (SceneObjectGroup copy, Vector3 sv, Vector3 ev) { //llSetRot(llRotBetween(<1,0,0>,llVecNorm(targetPosition - llGetPos()))); - // boid wil fly x forwards and Z up + // bird wil fly x forwards and Z up Vector3 currDirVec = Vector3.UnitX; Vector3 desiredDirVec = Vector3.Subtract (ev, sv); @@ -132,8 +133,8 @@ namespace Flocking private SceneObjectGroup MakeDefaultPrim (string name) { PrimitiveBaseShape shape = PrimitiveBaseShape.CreateSphere (); - shape.Scale = new Vector3 (0.5f, 0.5f, 0.5f); - + shape.Scale = new Vector3 (0.5f, 0.5f, 0.5f); + SceneObjectGroup prim = new SceneObjectGroup(m_owner, new Vector3((float)m_scene.RegionInfo.RegionSizeX / 2, (float)m_scene.RegionInfo.RegionSizeY / 2, 25f), shape); prim.Name = name; prim.DetachFromBackup (); diff --git a/Module/BirdsModule/FlowMap.cs b/Module/BirdsModule/FlowMap.cs index e08b2c1..3c4b6c7 100644 --- a/Module/BirdsModule/FlowMap.cs +++ b/Module/BirdsModule/FlowMap.cs @@ -1,5 +1,6 @@ /* * Copyright (c) Contributors, https://github.com/jonc/osboids + * https://github.com/JakDaniels/OpenSimBirds * See CONTRIBUTORS.TXT for a full list of copyright holders. * * Redistribution and use in source and binary forms, with or without @@ -33,20 +34,20 @@ namespace Flocking { public class FlowMap { - private Scene m_scene; - private float[, ,] m_flowMap; - private uint regionX; - private uint regionY; - private uint regionZ; + private Scene m_scene; + private float[, ,] m_flowMap; + private uint regionX; + private uint regionY; + private uint regionZ; private float regionBorder; public FlowMap (Scene scene, int maxHeight, float borderSize) { - m_scene = scene; - regionX = m_scene.RegionInfo.RegionSizeX; - regionY = m_scene.RegionInfo.RegionSizeY; - regionZ = (uint)maxHeight; - regionBorder = borderSize; + m_scene = scene; + regionX = m_scene.RegionInfo.RegionSizeX; + regionY = m_scene.RegionInfo.RegionSizeY; + regionZ = (uint)maxHeight; + regionBorder = borderSize; m_flowMap = new float[regionX, regionY, regionZ]; } @@ -58,9 +59,9 @@ namespace Flocking } public int LengthZ { get {return (int)regionZ;} - } - public int Border { - get {return (int)regionBorder;} + } + public int Border { + get {return (int)regionBorder;} } public void Initialise() { @@ -140,7 +141,7 @@ namespace Flocking public bool IsOutOfBounds(Vector3 targetPos) { bool retVal = false; if( targetPos.X < regionBorder || - targetPos.X > regionX - regionBorder || + targetPos.X > regionX - regionBorder || targetPos.Y < regionBorder || targetPos.Y > regionY - regionBorder || targetPos.Z < regionBorder || diff --git a/README.md b/README.md index bf2c701..fc530e9 100644 --- a/README.md +++ b/README.md @@ -1,45 +1,56 @@ -Region Module - ability to control flocks of prims within an OpenSim scene +INonSharedRegion Module - ability to control flocks of prims within an OpenSim scene To build from source -Add OpenSimBoids source tree under opensim/addon-modules +Add OpenSimBirds source tree under opensim/addon-modules ./runprebuild.sh against opensim root to build this module into the solution then xbuild, or build within Visual Studio / Monodevelop to produce the binaries -OpenSimBoids has no external dependencies other than the dlls currently included in opensim. -The project generates a single dll - OpenSimBoids.Modules.dll which is copied into opensim/bin as part of the build step +OpenSimBirds has no external dependencies other than the dlls currently included in opensim. +The project generates a single dll - OpenSimBirds.Modules.dll which is copied into opensim/bin as part of the build step Configuration -To become active, the module needs to be both referenced and enabled in the ini files. Otherwise it does nothing on startup +To become active, the module needs enabled in the ini file. Otherwise it does nothing on startup. +If you are running multiple regions on one simulator you can have different Birds +settings per region in the configuration file, in the exact same way you can +customize per Region setting in Regions.ini -Entry is as follows and in addition various config parameters are available to control the flock dynamics. +The configuration file for this module is in: +addon-modules/OpenSimBirds/config/OpenSimBirds.ini - [Boids] - - enabled = true ;removing the Boids group or setting enabled=false will switch off the module - flock-size = 100 ;the number of Boids to flock - max-speed = 3 ;how far each boid can travel per update - max-force = 0.25 ;the maximum acceleration allowed to the current velocity of the boid - neighbour-dist = 25 ;max distance for other boids to be considered in the same flock as us - desired-separation = 20 ;how far away from other boids we would like to stay - tolerance = 5 ;how close to the edges of things can we get without being worried - border-size = 5 ;how close to the edge of a region can we get? - max-height = 256 ;how high are we allowed to flock - boid-prim = fish01 ;By default the module will create a flock of plain wooden spheres, - ;however this can be overridden to the name of an existing prim that - ;needs to already exist in the scene - i.e. be rezzed in the region. +and follows the same format as a Regions.ini file, where you specify setting for +each region using the [Region Name] section heading. + +Here is an example config: + +;; Set the Birds settings per named region + + [Test Region 1] + + BirdsEnabled = True ;set to false to disable the module in this region + BirdsFlockSize = 100 ;the number of birds to flock + BirdsMaxSpeed = 3 ;how far each bird can travel per update + BirdsMaxForce = 0.25 ;the maximum acceleration allowed to the current velocity of the bird + BirdsNeighbourDistance = 25 ;max distance for other birds to be considered in the same flock as us + BirdsDesiredSeparation = 20 ;how far away from other birds we would like to stay + BirdsTolerance = 5 ;how close to the edges of things can we get without being worried + BirdsBorderSize = 5 ;how close to the edge of a region can we get? + BirdsMaxHeight = 256 ;how high are we allowed to flock + BirdsPrim = seagull01 ;By default the module will create a flock of plain wooden spheres, + ;however this can be overridden to the name of an existing prim that + ;needs to already exist in the scene - i.e. be rezzed in the region. Various runtime commands control the flocking module behaviour - described below. These can either be invoked from the Console or in world by directing them to a chat channel. To specify which channel to use: - chat-channel = 118 the chat channel to listen for boid commands on + chat-channel = 118 the chat channel to listen for Bird commands on @@ -48,29 +59,24 @@ Runtime Commands The following commands, which can either be issued on the Console, or via a chat channel in-world, control the behaviour of the flock at runtime - flock-stop or /118 stop ;stop all flocking and remove boids from the region + flock-stop or /118 stop ;stop all flocking and remove birds from the region flock-start or /118 start ;start the flocking simulation flock-size or /118 size ;change the size of the flock - flock-prim or /118 prim ;change the boid prim to one already rezzed in the scene + flock-prim or /118 prim ;change the bird prim to one already rezzed in the scene flock-framerate or /118 framerate ;only update the flock positions every frames - ;only really useful for photography and debugging boid + ;only really useful for photography and debugging bird ;behaviour -Boid prims +Bird prims -Any currently rezzed in-scene-object can be used as the boid prim. However fps is very much affected by the +Any currently rezzed in-scene-object can be used as the bird prim. However fps is very much affected by the complexity of the entity to use. It is easier to throw a single prim (or sculpty) around the scene than it is to throw the constituent parts of a 200 linked prim dragon. Tests show that <= 500 single prims can be flocked effectively - depending on system and network However maybe <= 300 simple linksets can perform as well. -I intend to allow inventory items and UUIDs to represent the boids - this is not written yet however. - - - - -Prebuilt binaries etc.. to follow +I intend to allow inventory items and UUIDs to represent the birds - this is not written yet however. Please Note @@ -79,16 +85,13 @@ This module is currently only tested against opensim master. If it is found to w then that behaviour ought to be considered as a bug - which I will attempt to fix in the next git push. -Status - -probably made it to alpha by now ... - Next Steps -I want to improve the ability of the boids to avoid obstacles within the scene. Current avoidance is pretty basic, and +I want to improve the ability of the birds to avoid obstacles within the scene. Current avoidance is pretty basic, and only functions correctly about fifty percent of the time. Need to improve this without increasing computational cost. Licence: all files released under a BSD licence +If you have any question please contact Jak Daniels, jak@ateb.co.uk diff --git a/config/OpenSimBirds.ini b/config/OpenSimBirds.ini new file mode 100644 index 0000000..121c393 --- /dev/null +++ b/config/OpenSimBirds.ini @@ -0,0 +1,16 @@ +;; Set the Birds settings per named region + +[Test Region 1] + + BirdsEnabled = True ;set to false to disable the module in this region + BirdsFlockSize = 100 ;the number of birds to flock + BirdsMaxSpeed = 3 ;how far each bird can travel per update + BirdsMaxForce = 0.25 ;the maximum acceleration allowed to the current velocity of the bird + BirdsNeighbourDistance = 25 ;max distance for other birds to be considered in the same flock as us + BirdsDesiredSeparation = 20 ;how far away from other birds we would like to stay + BirdsTolerance = 5 ;how close to the edges of things can we get without being worried + BirdsBorderSize = 5 ;how close to the edge of a region can we get? + BirdsMaxHeight = 256 ;how high are we allowed to flock + BirdsPrim = seagull01 ;By default the module will create a flock of plain wooden spheres, + ;however this can be overridden to the name of an existing prim that + ;needs to already exist in the scene - i.e. be rezzed in the region. diff --git a/config/OpenSimBirds.ini.example b/config/OpenSimBirds.ini.example new file mode 100644 index 0000000..b21ef85 --- /dev/null +++ b/config/OpenSimBirds.ini.example @@ -0,0 +1,16 @@ +;; Set the Birds settings per named region + +[Test Region 1] + + BirdsEnabled = True ;set to false to disable the module in this region + BirdsFlockSize = 100 ;the number of birds to flock + BirdsMaxSpeed = 3 ;how far each bird can travel per update + BirdsMaxForce = 0.25 ;the maximum acceleration allowed to the current velocity of the bird + BirdsNeighbourDistance = 25 ;max distance for other birds to be considered in the same flock as us + BirdsDesiredSeparation = 20 ;how far away from other birds we would like to stay + BirdsTolerance = 5 ;how close to the edges of things can we get without being worried + BirdsBorderSize = 5 ;how close to the edge of a region can we get? + BirdsMaxHeight = 256 ;how high are we allowed to flock + BirdsPrim = seagull01 ;By default the module will create a flock of plain wooden spheres, + ;however this can be overridden to the name of an existing prim that + ;needs to already exist in the scene - i.e. be rezzed in the region.