From 428c5769255401c3019db95947cc673422ebd230 Mon Sep 17 00:00:00 2001 From: Justin Aquadro Date: Wed, 6 Apr 2011 23:54:41 +0000 Subject: [PATCH] Added entity access points into Chunks (as IEntityContainer interface). Added predicate-based find/remove capability to NBT Lists. --- .../SubstrateCS/Source/BlockInterface.cs | 10 -- Substrate/SubstrateCS/Source/Chunk.cs | 116 +++++++++++++++--- .../SubstrateCS/Source/ChunkInterface.cs | 4 +- Substrate/SubstrateCS/Source/ChunkRef.cs | 82 +++++++------ Substrate/SubstrateCS/Source/Entity.cs | 11 ++ Substrate/SubstrateCS/Source/EntityFactory.cs | 9 +- Substrate/SubstrateCS/Source/NBT/NBTValues.cs | 10 ++ 7 files changed, 175 insertions(+), 67 deletions(-) diff --git a/Substrate/SubstrateCS/Source/BlockInterface.cs b/Substrate/SubstrateCS/Source/BlockInterface.cs index 0c34c39..67f68ab 100644 --- a/Substrate/SubstrateCS/Source/BlockInterface.cs +++ b/Substrate/SubstrateCS/Source/BlockInterface.cs @@ -49,14 +49,4 @@ namespace Substrate bool SetTileEntity (int lx, int ly, int lz, TileEntity te); bool ClearTileEntity (int lx, int ly, int lz); } - - public interface IEntity - { - - } - - public interface IEntityCollection - { - List FindAll (Predicate match); - } } diff --git a/Substrate/SubstrateCS/Source/Chunk.cs b/Substrate/SubstrateCS/Source/Chunk.cs index 69aad6e..115df41 100644 --- a/Substrate/SubstrateCS/Source/Chunk.cs +++ b/Substrate/SubstrateCS/Source/Chunk.cs @@ -233,20 +233,6 @@ namespace Substrate } } - /*if (BlockInfo.SchemaTable[_blocks[index]] != BlockInfo.SchemaTable[id]) { - if (BlockInfo.SchemaTable[_blocks[index]] != null) { - ClearTileEntity(lx, ly, lz); - } - - if (BlockInfo.SchemaTable[id] != null) { - TileEntity te = new TileEntity(BlockInfo.SchemaTable[id]); - te.X = BlockGlobalX(lx); - te.Y = BlockGlobalY(ly); - te.Z = BlockGlobalZ(lz); - _tileEntities.Add(te.Root); - } - }*/ - // Update height map if (BlockInfo.BlockTable[id] != null) { @@ -332,6 +318,11 @@ namespace Substrate return c; } + public int CountEntities () + { + return _entities.Count; + } + public int GetHeight (int lx, int lz) { return _heightMap[lz << 4 | lx]; @@ -459,6 +450,7 @@ namespace Substrate #endregion + #region INBTObject Members public Chunk LoadTree (NBT_Value tree) @@ -520,5 +512,101 @@ namespace Substrate } #endregion + + + #region IEntityContainer Members + + public List FindEntities (string id) + { + List set = new List(); + + foreach (NBT_Compound ent in _entities) { + NBT_Value eid; + if (!ent.TryGetValue("id", out eid)) { + continue; + } + + if (eid.ToNBTString().Data != id) { + continue; + } + + Entity obj = EntityFactory.Create(ent); + if (obj != null) { + set.Add(obj); + } + } + + return set; + } + + public List FindEntities (Predicate match) + { + List set = new List(); + + foreach (NBT_Compound ent in _entities) { + Entity obj = EntityFactory.Create(ent); + if (obj == null) { + continue; + } + + if (match(obj)) { + set.Add(obj); + } + } + + return set; + } + + public bool AddEntity (Entity ent) + { + double xlow = _cx * BlockManager.CHUNK_XLEN; + double xhigh = xlow + BlockManager.CHUNK_XLEN; + double zlow = _cz * BlockManager.CHUNK_ZLEN; + double zhigh = zlow + BlockManager.CHUNK_ZLEN; + + Entity.Vector3 pos = ent.Position; + if (!(pos.X >= xlow && pos.X < xhigh && pos.Z >= zlow && pos.Z < zhigh)) { + return false; + } + + _entities.Add(ent.BuildTree()); + return true; + } + + public int RemoveEntities (string id) + { + return _entities.RemoveAll(val => { + NBT_Compound cval = val as NBT_Compound; + if (cval == null) { + return false; + } + + NBT_Value sval; + if (!cval.TryGetValue("id", out sval)) { + return false; + } + + return (sval.ToNBTString().Data == id); + }); + } + + public int RemoveEntities (Predicate match) + { + return _entities.RemoveAll(val => { + NBT_Compound cval = val as NBT_Compound; + if (cval == null) { + return false; + } + + Entity obj = EntityFactory.Create(cval); + if (obj == null) { + return false; + } + + return match(obj); + }); + } + + #endregion } } diff --git a/Substrate/SubstrateCS/Source/ChunkInterface.cs b/Substrate/SubstrateCS/Source/ChunkInterface.cs index 738ac8a..175b999 100644 --- a/Substrate/SubstrateCS/Source/ChunkInterface.cs +++ b/Substrate/SubstrateCS/Source/ChunkInterface.cs @@ -6,7 +6,7 @@ using System.IO; namespace Substrate { - public interface IChunk : IBlockContainer + public interface IChunk : IBlockContainer, IEntityContainer { int X { get; } int Z { get; } @@ -18,6 +18,8 @@ namespace Substrate int CountBlockID (int id); int CountBlockData (int id, int data); + int CountEntities (); + int GetHeight (int lx, int lz); } diff --git a/Substrate/SubstrateCS/Source/ChunkRef.cs b/Substrate/SubstrateCS/Source/ChunkRef.cs index 031c91c..85a3de6 100644 --- a/Substrate/SubstrateCS/Source/ChunkRef.cs +++ b/Substrate/SubstrateCS/Source/ChunkRef.cs @@ -251,6 +251,11 @@ namespace Substrate return GetChunk().CountBlockData(id, data); } + public int CountEntities () + { + return GetChunk().CountEntities(); + } + public int GetHeight (int lx, int lz) { return GetChunk().GetHeight(lx, lz); @@ -280,49 +285,48 @@ namespace Substrate } #endregion - } - /*public bool VerifyTileEntities () + + #region IEntityContainer Members + + public List FindEntities (string id) { - bool pass = true; - - NBT_List telist = GetTree().Root["Level"].ToNBTCompound()["TileEntities"].ToNBTList(); - - foreach (NBT_Value val in telist) { - NBT_Compound tree = val as NBT_Compound; - if (tree == null) { - pass = false; - continue; - } - - if (new NBTVerifier(tree, TileEntity.BaseSchema).Verify() == false) { - pass = false; - continue; - } - - int x = tree["x"].ToNBTInt() & BlockManager.CHUNK_XMASK; - int y = tree["y"].ToNBTInt() & BlockManager.CHUNK_YMASK; - int z = tree["z"].ToNBTInt() & BlockManager.CHUNK_ZMASK; - int id = GetBlockID(x, y, z); - - NBTCompoundNode schema = BlockInfo.SchemaTable[id]; - if (schema == null) { - pass = false; - continue; - } - - pass = new NBTVerifier(tree, schema).Verify() && pass; - } - - return pass; + return GetChunk().FindEntities(id); } - private static bool LocalBounds (int lx, int ly, int lz) + public List FindEntities (Predicate match) { - return lx >= 0 && lx < BlockManager.CHUNK_XLEN && - ly >= 0 && ly < BlockManager.CHUNK_YLEN && - lz >= 0 && lz < BlockManager.CHUNK_ZLEN; - }*/ + return GetChunk().FindEntities(match); + } + + public bool AddEntity (Entity ent) + { + if (GetChunk().AddEntity(ent)) { + MarkDirty(); + return true; + } + return false; + } + + public int RemoveEntities (string id) + { + int ret = GetChunk().RemoveEntities(id); + if (ret > 0) { + MarkDirty(); + } + return ret; + } + + public int RemoveEntities (Predicate match) + { + int ret = GetChunk().RemoveEntities(match); + if (ret > 0) { + MarkDirty(); + } + return ret; + } + + #endregion + } - public class MalformedNBTTreeException : Exception { } } diff --git a/Substrate/SubstrateCS/Source/Entity.cs b/Substrate/SubstrateCS/Source/Entity.cs index 3e56083..0c977a2 100644 --- a/Substrate/SubstrateCS/Source/Entity.cs +++ b/Substrate/SubstrateCS/Source/Entity.cs @@ -7,6 +7,17 @@ namespace Substrate using NBT; using Utility; + public interface IEntityContainer + { + List FindEntities (string id); + List FindEntities (Predicate match); + + bool AddEntity (Entity ent); + + int RemoveEntities (string id); + int RemoveEntities (Predicate match); + } + public class Entity : INBTObject, ICopyable { public class Vector3 diff --git a/Substrate/SubstrateCS/Source/EntityFactory.cs b/Substrate/SubstrateCS/Source/EntityFactory.cs index cb709d9..9f55714 100644 --- a/Substrate/SubstrateCS/Source/EntityFactory.cs +++ b/Substrate/SubstrateCS/Source/EntityFactory.cs @@ -18,15 +18,18 @@ namespace Substrate return null; } - return Activator.CreateInstance(t, new object[] { type} ) as Entity; + return Activator.CreateInstance(t, new object[] { type } ) as Entity; } public static Entity Create (NBT_Compound tree) { - string type = tree["id"].ToNBTString(); + NBT_Value type; + if (!tree.TryGetValue("id", out type)) { + return null; + } Type t; - if (!_registry.TryGetValue(type, out t)) { + if (!_registry.TryGetValue(type.ToNBTString(), out t)) { return null; } diff --git a/Substrate/SubstrateCS/Source/NBT/NBTValues.cs b/Substrate/SubstrateCS/Source/NBT/NBTValues.cs index 9c3c807..4b777b8 100644 --- a/Substrate/SubstrateCS/Source/NBT/NBTValues.cs +++ b/Substrate/SubstrateCS/Source/NBT/NBTValues.cs @@ -398,6 +398,16 @@ namespace Substrate.NBT { return list; } + public List FindAll(Predicate match) + { + return _items.FindAll(match); + } + + public int RemoveAll (Predicate match) + { + return _items.RemoveAll(match); + } + #region IList Members public int IndexOf (NBT_Value item)