Example #1
0
static void get_range(const char **s)
{
  range_from = get_add(s);
  if ( **s != '-' )
  {
    range_to = range_from;
  }
  else
  {
    (*s)++;
    skip_space(s);
    range_to = get_add(s);
  }
}
Example #2
0
static void map_cmd(const char **s)
{
  if ( **s == '*' )
  {
    range_from = 32;
    range_to = 255;
    map_to = 32;
    is_exclude = 0;
    
    (*s)++;
    skip_space(s);
  }
  else if ( **s == '~' )
  {
    is_exclude = 1;
    map_to = 0;	/*will be ignored */
    
    (*s)++;
    skip_space(s);
    get_range(s);
    
  }
  else 
  {
    is_exclude = 0;
    get_range(s);
    map_to = range_from;
    if ( **s == '>')
    {
      (*s)++;
      skip_space(s);
      map_to = get_add(s);
    }
  }
}
Example #3
0
	ColumnContainer::PacketType ColumnContainer::ToChunkData () const {
		
		//	This gives all chunks from
		//	bottom-to-top which are not
		//	all air
		bool chunks [16];
		std::memset(chunks,0,sizeof(chunks));
		//	This gives all chunks from
		//	bottom-to-top which require the
		//	"add" array
		bool add [16];
		std::memset(add,0,sizeof(add));
		
		//	Scan all blocks to determine
		//
		//	A.	Which chunks we need to send.
		//	B.	Which of A need the add array.
		Word chunk=0;
		Word next_chunk=16*16*16;
		for (Word i=0;i<(16*16*16*16);++i) {
		
			//	Maintain record of which
			//	chunk we're in
			if (i==next_chunk) {
			
				next_chunk+=16*16*16;
				++chunk;
			
			}
			
			//	Type of this block
			auto type=Blocks[i].GetType();
			
			//	Are we sending this chunk?
			if (type!=0) {
			
				//	YES
				
				chunks[chunk]=true;
				
				//	Is the block type too large
				//	for one byte?  I.e. do we have
				//	to send the add array for this
				//	chunk?
				if (type>std::numeric_limits<Byte>::max()) add[chunk]=true;
			
			}
		
		}
		
		//	Do we have to send skylight?
		bool skylight=HasSkylight(id.Dimension);
		
		//	Determine the masks that we'll be
		//	sending, the start offset of the
		//	"add" array, as well as the distance
		//	between arrays
		Word add_offset=0;
		UInt16 primary_mask=0;
		UInt16 add_mask=0;
		Word spacing=0;
		for (Word i=0;i<16;++i) if (chunks[i]) {
		
			//	The "spacing" of arrays, i.e.
			//	if the block type array starts
			//	at index 0, at what index does the
			//	metadata array begin?
			spacing+=16*16*16;
		
			UInt16 mask=1<<i;
		
			//	Add bit in appropriate
			//	position to mask
			primary_mask|=mask;
			
			//	Offset the start of the
			//	"add" array appropriately
			add_offset+=16*16*16*2;
			if (skylight) add_offset+=(16*16*16)/2;
			
			//	If the "add" array will be
			//	sent for this chunk, update
			//	the mask
			if (add[i]) add_mask|=mask;
		
		}
		
		//	Create a buffer on the stack big
		//	enough to hold the largest possible
		//	packet in Mojang format
		Byte column [(16*16*16*16*3)+(16*16)];
		
		//	Loop and convert
		Word offset=0;
		Word nibble_offset=spacing;
		spacing/=2;
		chunk=0;
		next_chunk=16*16*16;
		bool even=true;
		for (Word i=0;i<(16*16*16*16);++i) {
		
			//	Advance to next chunk if
			//	necessary
			if (i==next_chunk) {
			
				next_chunk+=16*16*16;
				++chunk;
			
			}
			
			//	Skip null chunks
			if (!chunks[chunk]) {
			
				i+=(16*16*16)-1;
				
				continue;
			
			}
			
			//	Current block
			const auto & b=Blocks[i];
			
			//	Write non-"add" byte of block
			//	type
			column[offset++]=static_cast<Byte>(b.GetType());
			Word curr=nibble_offset;
			//	Write nibbles
			if (even) {
			
				//	Metadata
				column[curr]=b.GetMetadata()<<4;
				//	Light
				column[curr+=spacing]=b.GetLight()<<4;
				//	Skylight (if applicable)
				if (skylight) column[curr+spacing]=b.GetSkylight()<<4;
				//	"Add" (if applicable)
				if (add[chunk]) column[add_offset]=get_add(b)<<4;
			
			} else {
			
				//	Metadata
				column[curr]|=b.GetMetadata();
				//	Light
				column[curr+=spacing]|=b.GetLight();
				//	Skylight (if applicable)
				if (skylight) column[curr+spacing]|=b.GetSkylight();
				//	"Add" (if applicable)
				if (add[chunk]) column[add_offset++]|=get_add(b);
				
				//	After every odd/even pair,
				//	we move onto the next full
				//	byte
				++nibble_offset;
			
			}
			
			even=!even;
		
		}
		
		//	Copy biomes
		std::memcpy(
			column+add_offset,
			Biomes,
			sizeof(Biomes)
		);
		
		//	Prepare a packet
		PacketType retr;
		retr.X=id.X;
		retr.Z=id.Z;
		retr.Continuous=true;
		retr.Primary=primary_mask;
		retr.Add=add_mask;
		retr.Data=Deflate(
			column,
			column+add_offset+sizeof(Biomes)
		);
		
		return retr;
	
	}