// ############################################################################################# /// Function:<summary> /// /// </summary> /// /// In: <param name="_block"></param> /// Out: <returns> /// /// </returns> // ############################################################################################# public int CheckDuplicate(int _block) { block_info info = BlockInfo[_block]; // get the block bool NotSpace = false; for (int i = 0; i < 6; i++) { if (info[i] != -1) { NotSpace = true; break;; } } if (!NotSpace) { FreeBlock(_block); return(1); } // Now check the CRC lookup.... BlockCRCLookup.Remove(info.CRC); // if its NOT a space, compare with all orther blocks uint crc = info.UpdateCRC(); int newblock = -1; if (BlockCRCLookup.TryGetValue(crc, out newblock)) { FreeBlock(_block); BlockInfo[newblock].Ref++; return(newblock); } BlockCRCLookup.Add(crc, _block); return(_block); }
// ############################################################################################# /// Function:<summary> /// Add a block /// </summary> /// /// In: <param name="_blk"></param> /// // ############################################################################################# int AddBlockInfo(block_info _blk) { _blk.Ref++; int index = BlockInfo.Count; BlockInfo.Add(_blk); return(index); }
// ############################################################################################# /// Function:<summary> /// Copy the given block details into this block. Does not effect Ref. /// </summary> /// /// In: <param name="_src"></param> /// // ############################################################################################# public void Copy(block_info _src) { for (int i = 0; i < 6; i++) { Faces[i] = _src[i]; } Flags1 = _src.Flags1; Flags2 = _src.Flags2; }
// ############################################################################################# /// Function:<summary> /// Reset the map /// </summary> /// /// In: <param name="_width"></param> /// <param name="_height"></param> /// <param name="_depth"></param> /// // ############################################################################################# public void Reset(int _width, int _height, int _depth, int _groundlevel) { Width = _width; Height = _height; Depth = _depth; GroundLevel = _groundlevel; BlockCRCLookup = new Dictionary <uint, int>(); BlockInfo = new List <block_info>(); FreeList = new Stack <int>(); map = new MapColumn[_width * _height]; BlockInfo.Add(new block_info()); // block "0" is empty BlockInfo[0].Ref = 1; BlockInfo[0].UpdateCRC(); BlockCRCLookup.Add(BlockInfo[0].CRC, 0); BlockInfo.Add(new block_info()); // block "1" is "almost" empty BlockInfo[1].Ref = (_width * _height * GroundLevel) + 1;; BlockInfo[1].Flags1 |= 0x80000000; // always set this - it's cleared on save BlockInfo[1].UpdateCRC(); BlockCRCLookup.Add(BlockInfo[1].CRC, 1); block_info b = new block_info(); // block "2" is pavement; b.Lid = Pavement; b.Ref = (_width * _height) + 1; BlockInfo.Add(b); CheckDuplicate(2); for (int y = 0; y < _height; y++) { int index = y * Width; for (int x = 0; x < _width; x++) { map[x + index] = new MapColumn(); for (int g = 0; g < GroundLevel; g++) { map[x + index].Add(1); // Water level has nothing by default } map[x + index].Add(2); // Build pavement at ground level (one block up) } } }
// ############################################################################################# /// Function:<summary> /// Create all the block infos we need to generate the map /// </summary> // ############################################################################################# private void BuildBlockInfos() { block_info b; Pavement = 7; // pavement block Road = 3; Grass = 54; Water = 0; // actual "water block" anymore Field1 = 61; Field2 = 59; Field3 = 64; Concrete = 11; Residential = 2; Comercial = 6; Industrial = 50; Airport=11; AirportRunway=3; MountainLow=8; MountainMed=9; MountainHigh=10; HighResidential = 42; // Don't reset the map, REF counts are still valid //BlockInfo = new List<block_info>(); //AddBlockInfo( new block_info() ); // block "0" is empty //b = new block_info(); // block "1" is pavement; //b.Lid = Pavement; //Pavement = AddBlockInfo(b); block_info p = BlockInfo[2]; p.Lid = Pavement; Pavement = 2; // Make a road block b = new block_info(); // block "1" is pavement; b.Lid = Road; Road = AddBlockInfo(b); CheckDuplicate(Road); // Make a grass block b = new block_info(); // block "1" is pavement; b.Lid = Grass; Grass = AddBlockInfo(b); CheckDuplicate(Grass); // Make a water block b = new block_info(); // block "1" is pavement; b.Lid = Water; Water = AddBlockInfo(b); CheckDuplicate(Water); // Make a Field1 block b = new block_info(); // block "1" is pavement; b.Lid = Field1; Field1 = AddBlockInfo(b); CheckDuplicate(Field1); // Make a Field2 block b = new block_info(); // block "1" is pavement; b.Lid = Field2; Field2 = AddBlockInfo(b); CheckDuplicate(Field2); // Make a Field3 block b = new block_info(); // block "1" is pavement; b.Lid = Field3; Field3 = AddBlockInfo(b); CheckDuplicate(Field3); // Make a Residential block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 22; // roof? b.Base = 22; // roof? b.Left = Residential; b.Right = Residential; b.Top = Residential; b.Bottom = Residential; Residential = AddBlockInfo(b); CheckDuplicate(Residential); // Make a Comercial block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 13; // roof? b.Base = 14; // roof? b.Left = Comercial; b.Right = Comercial; b.Top = Comercial; b.Bottom = Comercial; Comercial = AddBlockInfo(b); CheckDuplicate(Comercial); // Make a Industrial block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 43; // roof? b.Base = 43; // roof? b.Left = Industrial; b.Right = Industrial; b.Top = Industrial; b.Bottom = Industrial; Industrial = AddBlockInfo(b); CheckDuplicate(Industrial); // Make a Concrete block b = new block_info(); // block "1" is pavement; b.Lid = Concrete; // roof? Concrete = AddBlockInfo(b); CheckDuplicate(Concrete); // Make an Airport block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 43; // roof? b.Base = 43; // roof? b.Left = Airport; b.Right = Airport; b.Top = Airport; b.Bottom = Airport; Airport = AddBlockInfo(b); CheckDuplicate(Airport); // Make a AirportRunway block b = new block_info(); // block "1" is pavement; b.Lid = AirportRunway; // roof? AirportRunway = AddBlockInfo(b); CheckDuplicate(AirportRunway); // Make an MountainLow block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 31; // roof? b.Base = 31; // roof? b.Left = MountainLow; b.Right = MountainLow; b.Top = MountainLow; b.Bottom = MountainLow; MountainLow = AddBlockInfo(b); CheckDuplicate(MountainLow); // Make an MountainMid block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 24; // roof? b.Base = 24; // roof? b.Left = MountainMed; b.Right = MountainMed; b.Top = MountainMed; b.Bottom = MountainMed; MountainMed = AddBlockInfo(b); CheckDuplicate(MountainMed); // Make an MountainHigh block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 11; // roof? b.Base = 11; // roof? b.Left = MountainHigh; b.Right = MountainHigh; b.Top = MountainHigh; b.Bottom = MountainHigh; MountainHigh = AddBlockInfo(b); CheckDuplicate(MountainHigh); // Make an HighResidential block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 37; b.Base = 37; b.Left = HighResidential; b.Right = HighResidential; b.Top = HighResidential; b.Bottom = HighResidential; HighResidential = AddBlockInfo(b); CheckDuplicate(HighResidential); }
// ############################################################################################# /// Function:<summary> /// Add a block /// </summary> /// /// In: <param name="_blk"></param> /// // ############################################################################################# int AddBlockInfo(block_info _blk) { _blk.Ref++; int index = BlockInfo.Count; BlockInfo.Add(_blk); return index; }
// ############################################################################################# /// Function:<summary> /// Reset the map /// </summary> /// /// In: <param name="_width"></param> /// <param name="_height"></param> /// <param name="_depth"></param> /// // ############################################################################################# public void Reset(int _width, int _height, int _depth, int _groundlevel) { Width = _width; Height = _height; Depth = _depth; GroundLevel = _groundlevel; BlockCRCLookup = new Dictionary<uint, int>(); BlockInfo = new List<block_info>(); FreeList = new Stack<int>(); map = new MapColumn[_width * _height]; BlockInfo.Add(new block_info()); // block "0" is empty BlockInfo[0].Ref = 1; BlockInfo[0].UpdateCRC(); BlockCRCLookup.Add(BlockInfo[0].CRC,0); BlockInfo.Add(new block_info()); // block "1" is "almost" empty BlockInfo[1].Ref = (_width * _height * GroundLevel) + 1; ; BlockInfo[1].Flags1|=0x80000000; // always set this - it's cleared on save BlockInfo[1].UpdateCRC(); BlockCRCLookup.Add(BlockInfo[1].CRC,1); block_info b = new block_info(); // block "2" is pavement; b.Lid = Pavement; b.Ref = (_width * _height)+1; BlockInfo.Add(b); CheckDuplicate(2); for (int y = 0; y < _height; y++) { int index = y*Width; for (int x = 0; x < _width; x++) { map[x + index] = new MapColumn(); for(int g=0;g<GroundLevel;g++){ map[x + index].Add(1); // Water level has nothing by default } map[x + index].Add(2); // Build pavement at ground level (one block up) } } }
// ############################################################################################# /// Constructor: <summary> /// Create a new block by copying another one - except the Ref. /// </summary> /// /// In: <param name="_src">Source block tocopy</param> /// // ############################################################################################# public block_info(block_info _src) { Copy(_src); Ref = 0; }
// ############################################################################################# /// Function:<summary> /// Create all the block infos we need to generate the map /// </summary> // ############################################################################################# private void BuildBlockInfos() { block_info b; Pavement = 7; // pavement block Road = 3; Grass = 54; Water = 0; // actual "water block" anymore Field1 = 61; Field2 = 59; Field3 = 64; Concrete = 11; Residential = 2; Comercial = 6; Industrial = 50; Airport = 11; AirportRunway = 3; MountainLow = 8; MountainMed = 9; MountainHigh = 10; HighResidential = 42; // Don't reset the map, REF counts are still valid //BlockInfo = new List<block_info>(); //AddBlockInfo( new block_info() ); // block "0" is empty //b = new block_info(); // block "1" is pavement; //b.Lid = Pavement; //Pavement = AddBlockInfo(b); block_info p = BlockInfo[2]; p.Lid = Pavement; Pavement = 2; // Make a road block b = new block_info(); // block "1" is pavement; b.Lid = Road; Road = AddBlockInfo(b); CheckDuplicate(Road); // Make a grass block b = new block_info(); // block "1" is pavement; b.Lid = Grass; Grass = AddBlockInfo(b); CheckDuplicate(Grass); // Make a water block b = new block_info(); // block "1" is pavement; b.Lid = Water; Water = AddBlockInfo(b); CheckDuplicate(Water); // Make a Field1 block b = new block_info(); // block "1" is pavement; b.Lid = Field1; Field1 = AddBlockInfo(b); CheckDuplicate(Field1); // Make a Field2 block b = new block_info(); // block "1" is pavement; b.Lid = Field2; Field2 = AddBlockInfo(b); CheckDuplicate(Field2); // Make a Field3 block b = new block_info(); // block "1" is pavement; b.Lid = Field3; Field3 = AddBlockInfo(b); CheckDuplicate(Field3); // Make a Residential block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 22; // roof? b.Base = 22; // roof? b.Left = Residential; b.Right = Residential; b.Top = Residential; b.Bottom = Residential; Residential = AddBlockInfo(b); CheckDuplicate(Residential); // Make a Comercial block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 13; // roof? b.Base = 14; // roof? b.Left = Comercial; b.Right = Comercial; b.Top = Comercial; b.Bottom = Comercial; Comercial = AddBlockInfo(b); CheckDuplicate(Comercial); // Make a Industrial block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 43; // roof? b.Base = 43; // roof? b.Left = Industrial; b.Right = Industrial; b.Top = Industrial; b.Bottom = Industrial; Industrial = AddBlockInfo(b); CheckDuplicate(Industrial); // Make a Concrete block b = new block_info(); // block "1" is pavement; b.Lid = Concrete; // roof? Concrete = AddBlockInfo(b); CheckDuplicate(Concrete); // Make an Airport block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 43; // roof? b.Base = 43; // roof? b.Left = Airport; b.Right = Airport; b.Top = Airport; b.Bottom = Airport; Airport = AddBlockInfo(b); CheckDuplicate(Airport); // Make a AirportRunway block b = new block_info(); // block "1" is pavement; b.Lid = AirportRunway; // roof? AirportRunway = AddBlockInfo(b); CheckDuplicate(AirportRunway); // Make an MountainLow block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 31; // roof? b.Base = 31; // roof? b.Left = MountainLow; b.Right = MountainLow; b.Top = MountainLow; b.Bottom = MountainLow; MountainLow = AddBlockInfo(b); CheckDuplicate(MountainLow); // Make an MountainMid block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 24; // roof? b.Base = 24; // roof? b.Left = MountainMed; b.Right = MountainMed; b.Top = MountainMed; b.Bottom = MountainMed; MountainMed = AddBlockInfo(b); CheckDuplicate(MountainMed); // Make an MountainHigh block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 11; // roof? b.Base = 11; // roof? b.Left = MountainHigh; b.Right = MountainHigh; b.Top = MountainHigh; b.Bottom = MountainHigh; MountainHigh = AddBlockInfo(b); CheckDuplicate(MountainHigh); // Make an HighResidential block (full cube) b = new block_info(); // block "1" is pavement; b.Lid = 37; b.Base = 37; b.Left = HighResidential; b.Right = HighResidential; b.Top = HighResidential; b.Bottom = HighResidential; HighResidential = AddBlockInfo(b); CheckDuplicate(HighResidential); }
// ############################################################################################# /// Function:<summary> /// Adds a block at x,y,z, making it unique if it has to /// </summary> /// /// In: <param name="_x">x coordinate</param> /// <param name="_y">y coordinate</param> /// <param name="_z">z coordinate</param> /// <param name="_block">block to set</param> /// // ############################################################################################# public void Add(int _x, int _y, int _z, int _block) { int info_index = MakeUnique(_x, _y, _z); block_info info = BlockInfo[info_index]; info.Copy(BlockInfo[_block]); // Left int b = Get(_x - 1, _y, _z); if (b != -1) { int newindex = MakeUnique(_x - 1, _y, _z); BlockInfo[newindex].Right = -1; info.Left = -1; CompressBlock(_x - 1, _y, _z); } // Right b = Get(_x + 1, _y, _z); if (b != -1) { int newindex = MakeUnique(_x + 1, _y, _z); BlockInfo[newindex].Left = -1; info.Right = -1; CompressBlock(_x + 1, _y, _z); } // Bottom b = Get(_x, _y + 1, _z); if (b != -1) { int newindex = MakeUnique(_x, _y + 1, _z); BlockInfo[newindex].Top = -1; info.Bottom = -1; CompressBlock(_x, _y + 1, _z); } // Top b = Get(_x, _y - 1, _z); if (b != -1) { int newindex = MakeUnique(_x, _y - 1, _z); BlockInfo[newindex].Bottom = -1; info.Top = -1; CompressBlock(_x, _y - 1, _z); } // Lid b = Get(_x, _y, _z + 1); if (b != -1) { int newindex = MakeUnique(_x, _y, _z + 1); BlockInfo[newindex].Base = -1; info.Lid = -1; CompressBlock(_x, _y, _z + 1); } // Base b = Get(_x, _y, _z - 1); if (b != -1) { int newindex = MakeUnique(_x, _y, _z - 1); BlockInfo[newindex].Lid = -1; info.Base = -1; CompressBlock(_x, _y, _z - 1); } CompressBlock(_x, _y, _z); }