World.cs 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307
  1. using System;
  2. using libsecondlife;
  3. using libsecondlife.Packets;
  4. using System.Collections.Generic;
  5. using System.Text;
  6. using System.Reflection;
  7. using System.IO;
  8. using OpenSim.Physics.Manager;
  9. using OpenSim.Framework.Interfaces;
  10. using OpenSim.Framework.Assets;
  11. using OpenSim.Framework.Terrain;
  12. namespace OpenSim.world
  13. {
  14. public class World : ILocalStorageReceiver
  15. {
  16. public object LockPhysicsEngine = new object();
  17. public Dictionary<libsecondlife.LLUUID, Entity> Entities;
  18. public float[] LandMap;
  19. public ScriptEngine Scripts;
  20. public uint _localNumber=0;
  21. private PhysicsScene phyScene;
  22. private float timeStep= 0.1f;
  23. private libsecondlife.TerrainManager TerrainManager;
  24. public ILocalStorage localStorage;
  25. private Random Rand = new Random();
  26. private uint _primCount = 702000;
  27. private int storageCount;
  28. private Dictionary<uint, SimClient> m_clientThreads;
  29. private ulong m_regionHandle;
  30. private string m_regionName;
  31. private SimConfig m_cfg;
  32. public World(Dictionary<uint, SimClient> clientThreads, ulong regionHandle, string regionName, SimConfig cfg)
  33. {
  34. m_clientThreads = clientThreads;
  35. m_regionHandle = regionHandle;
  36. m_regionName = regionName;
  37. m_cfg = cfg;
  38. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs - creating new entitities instance");
  39. Entities = new Dictionary<libsecondlife.LLUUID, Entity>();
  40. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs - creating LandMap");
  41. TerrainManager = new TerrainManager(new SecondLife());
  42. Avatar.SetupTemplate("avatar-template.dat");
  43. // MainConsole.Instance.WriteLine("World.cs - Creating script engine instance");
  44. // Initialise this only after the world has loaded
  45. // Scripts = new ScriptEngine(this);
  46. Avatar.LoadAnims();
  47. }
  48. public PhysicsScene PhysScene
  49. {
  50. set
  51. {
  52. this.phyScene = value;
  53. }
  54. get
  55. {
  56. return(this.phyScene);
  57. }
  58. }
  59. public void Update()
  60. {
  61. if(this.phyScene.IsThreaded)
  62. {
  63. this.phyScene.GetResults();
  64. }
  65. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  66. {
  67. Entities[UUID].addForces();
  68. }
  69. lock (this.LockPhysicsEngine)
  70. {
  71. this.phyScene.Simulate(timeStep);
  72. }
  73. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  74. {
  75. Entities[UUID].update();
  76. }
  77. //backup world data
  78. this.storageCount++;
  79. if(storageCount> 1200) //set to how often you want to backup
  80. {
  81. this.Backup();
  82. storageCount =0;
  83. }
  84. }
  85. public bool LoadStorageDLL(string dllName)
  86. {
  87. Assembly pluginAssembly = Assembly.LoadFrom(dllName);
  88. ILocalStorage store = null;
  89. foreach (Type pluginType in pluginAssembly.GetTypes())
  90. {
  91. if (pluginType.IsPublic)
  92. {
  93. if (!pluginType.IsAbstract)
  94. {
  95. Type typeInterface = pluginType.GetInterface("ILocalStorage", true);
  96. if (typeInterface != null)
  97. {
  98. ILocalStorage plug = (ILocalStorage)Activator.CreateInstance(pluginAssembly.GetType(pluginType.ToString()));
  99. store = plug;
  100. break;
  101. }
  102. typeInterface = null;
  103. }
  104. }
  105. }
  106. pluginAssembly = null;
  107. this.localStorage = store;
  108. return(store == null);
  109. }
  110. public void RegenerateTerrain()
  111. {
  112. HeightmapGenHills hills = new HeightmapGenHills();
  113. this.LandMap = hills.GenerateHeightmap(200, 4.0f, 80.0f, false);
  114. lock (this.LockPhysicsEngine)
  115. {
  116. this.phyScene.SetTerrain(this.LandMap);
  117. }
  118. m_cfg.SaveMap(this.LandMap);
  119. foreach (SimClient client in m_clientThreads.Values)
  120. {
  121. this.SendLayerData(client);
  122. }
  123. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  124. {
  125. Entities[UUID].LandRenegerated();
  126. }
  127. }
  128. public void RegenerateTerrain(float[] newMap)
  129. {
  130. this.LandMap = newMap;
  131. lock (this.LockPhysicsEngine)
  132. {
  133. this.phyScene.SetTerrain(this.LandMap);
  134. }
  135. m_cfg.SaveMap(this.LandMap);
  136. foreach (SimClient client in m_clientThreads.Values)
  137. {
  138. this.SendLayerData(client);
  139. }
  140. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  141. {
  142. Entities[UUID].LandRenegerated();
  143. }
  144. }
  145. public void LoadPrimsFromStorage()
  146. {
  147. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: LoadPrimsFromStorage() - Loading primitives");
  148. this.localStorage.LoadPrimitives(this);
  149. }
  150. public void PrimFromStorage(PrimData prim)
  151. {
  152. if(prim.LocalID >= this._primCount)
  153. {
  154. _primCount = prim.LocalID + 1;
  155. }
  156. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: PrimFromStorage() - Reloading prim (localId "+ prim.LocalID+ " ) from storage");
  157. Primitive nPrim = new Primitive(m_clientThreads, m_regionHandle, this);
  158. nPrim.CreateFromStorage(prim);
  159. this.Entities.Add(nPrim.uuid, nPrim);
  160. }
  161. public void Close()
  162. {
  163. this.localStorage.ShutDown();
  164. }
  165. public void SendLayerData(SimClient RemoteClient) {
  166. int[] patches = new int[4];
  167. for (int y = 0; y < 16; y++)
  168. {
  169. for (int x = 0; x < 16; x = x + 4)
  170. {
  171. patches[0] = x + 0 + y * 16;
  172. patches[1] = x + 1 + y * 16;
  173. patches[2] = x + 2 + y * 16;
  174. patches[3] = x + 3 + y * 16;
  175. Packet layerpack = TerrainManager.CreateLandPacket(LandMap, patches);
  176. RemoteClient.OutPacket(layerpack);
  177. }
  178. }
  179. }
  180. public void GetInitialPrims(SimClient RemoteClient)
  181. {
  182. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  183. {
  184. if(Entities[UUID].ToString()== "OpenSim.world.Primitive")
  185. {
  186. ((OpenSim.world.Primitive)Entities[UUID]).UpdateClient(RemoteClient);
  187. }
  188. }
  189. }
  190. public void AddViewerAgent(SimClient AgentClient)
  191. {
  192. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Creating new avatar for remote viewer agent");
  193. Avatar NewAvatar = new Avatar(AgentClient, this, m_regionName, m_clientThreads, m_regionHandle);
  194. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Adding new avatar to world");
  195. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Starting RegionHandshake ");
  196. NewAvatar.SendRegionHandshake(this);
  197. PhysicsVector pVec = new PhysicsVector(NewAvatar.position.X, NewAvatar.position.Y, NewAvatar.position.Z);
  198. lock (this.LockPhysicsEngine)
  199. {
  200. NewAvatar.PhysActor = this.phyScene.AddAvatar(pVec);
  201. }
  202. this.Entities.Add(AgentClient.AgentID, NewAvatar);
  203. }
  204. public void AddNewPrim(ObjectAddPacket addPacket, SimClient AgentClient)
  205. {
  206. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: AddNewPrim() - Creating new prim");
  207. Primitive prim = new Primitive(m_clientThreads, m_regionHandle, this);
  208. prim.CreateFromPacket(addPacket, AgentClient.AgentID, this._primCount);
  209. PhysicsVector pVec = new PhysicsVector(prim.position.X, prim.position.Y, prim.position.Z);
  210. PhysicsVector pSize = new PhysicsVector( 0.255f, 0.255f, 0.255f);
  211. if(OpenSim.world.Avatar.PhysicsEngineFlying)
  212. {
  213. lock (this.LockPhysicsEngine)
  214. {
  215. prim.PhysActor = this.phyScene.AddPrim(pVec, pSize);
  216. }
  217. }
  218. //prim.PhysicsEnabled = true;
  219. this.Entities.Add(prim.uuid, prim);
  220. this._primCount++;
  221. }
  222. public void DeRezObject(DeRezObjectPacket DeRezPacket, SimClient AgentClient)
  223. {
  224. //Needs to delete object from physics at a later date
  225. libsecondlife.LLUUID [] DeRezEnts;
  226. DeRezEnts = new libsecondlife.LLUUID[ DeRezPacket.ObjectData.Length ];
  227. int i = 0;
  228. foreach( DeRezObjectPacket.ObjectDataBlock Data in DeRezPacket.ObjectData )
  229. {
  230. //OpenSim.Framework.Console.MainConsole.Instance.WriteLine("LocalID:" + Data.ObjectLocalID.ToString());
  231. foreach (Entity ent in this.Entities.Values)
  232. {
  233. if (ent.localid == Data.ObjectLocalID)
  234. {
  235. DeRezEnts[i++] = ent.uuid;
  236. this.localStorage.RemovePrim(ent.uuid);
  237. KillObjectPacket kill = new KillObjectPacket();
  238. kill.ObjectData = new KillObjectPacket.ObjectDataBlock[1];
  239. kill.ObjectData[0] = new KillObjectPacket.ObjectDataBlock();
  240. kill.ObjectData[0].ID = ent.localid;
  241. foreach (SimClient client in m_clientThreads.Values)
  242. {
  243. client.OutPacket(kill);
  244. }
  245. //Uncommenting this means an old UUID will be re-used, thus crashing the asset server
  246. //Uncomment when prim/object UUIDs are random or such
  247. //2007-03-22 - Randomskk
  248. //this._primCount--;
  249. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Deleted UUID " + ent.uuid);
  250. }
  251. }
  252. }
  253. foreach( libsecondlife.LLUUID uuid in DeRezEnts )
  254. {
  255. lock (Entities)
  256. {
  257. Entities.Remove(uuid);
  258. }
  259. }
  260. }
  261. public bool Backup() {
  262. OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: Backup() - Backing up Primitives");
  263. foreach (libsecondlife.LLUUID UUID in Entities.Keys)
  264. {
  265. Entities[UUID].BackUp();
  266. }
  267. return true;
  268. }
  269. }
  270. }