Jump to content

[1.10.2] Checking blocks around player


DasKaktus

Recommended Posts

Hi.

 

Is there a simplier way to check if the blocks around(with 1 spacce inbetween) the player is air than the following code.

The code seems so ugly..

 

BlockPos posStart = player.getPosition();
if(world.getBlockState(posStart.north(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.north(2).east(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.north(2).east(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.north(2).west(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.north(2).west(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.south(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.south(2).east(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.south(2).east(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.south(2).west(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.south(2).west(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.west(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.west(2).north(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.west(2).south(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.east(2)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.east(2).north(1)).getBlock() == Blocks.AIR &&
world.getBlockState(posStart.east(2).south(1)).getBlock() == Blocks.AIR){								

}

Not all things in the world are red, there are round objects too!

Link to comment
Share on other sites

For-loops are your friend.

Reference another method that returns a boolean.

public boolean checkBlocks(World world, BlockPos playerPos){
//Check in x-axis
for(int x = -2; x < 3; x++){
	//Check in z-axis
	for(int z = -2; z < 3; z++){
		//Only get the blocks that are 2 blocks out (For loop -can- be used here instead)
		if(x != -1 || x != 0 || x != 1 || z != -1 || z != 0 || z != 1){
			//Create a new BlockPos based on our offsets
			BlockPos pos = new BlockPos(playerPos.getX()+x, playerPos.getY(), playerPos.getZ()+z);
			//If ANY block is not air, return false
			if(world.getBlockState(pos).getBlock != Blocks.AIR){
				return false;
			}
			//If all blocks are air, return true
			return true;
		}
	}
}
return false;
}

Also previously known as eAndPi.

"Pi, is there a station coming up where we can board your train of thought?" -Kronnn

Published Mods: Underworld

Handy links: Vic_'s Forge events Own WIP Tutorials.

Link to comment
Share on other sites

There are two options:

  • Loop from -2 to +2 on both the x and z axes and use
    BlockPos#add(int, int, int)

    to add the x and z offsets to the starting position

  • Call
    BlockPos#getAllInBoxMutable

    with -2,0,-2 and +2,0,+2 as the arguments and iterate through the returned value

Please don't PM me to ask for help. Asking your question in a public thread preserves it for people who are having the same problem in the future.

Link to comment
Share on other sites

To clarify.

 

I need a function to check if these 3 conditions are met:

Player standing on obsidian.

There are redstone around the player.

Outside of the redstone there should be air blocks.

 

So what do you think of this:

 

public boolean checkRitualOuter(World world, BlockPos playerpos){
boolean isInside = false;
BlockPos pos1 = new BlockPos(playerpos.getX()-2, playerpos.getY(), playerpos.getZ()-2);
BlockPos pos2 = new BlockPos(playerpos.getX()+2, playerpos.getY(), playerpos.getZ()+2);
BlockPos pos3 = new BlockPos(playerpos.getX()-1, playerpos.getY(), playerpos.getZ()-1);
BlockPos pos4 = new BlockPos(playerpos.getX()+1, playerpos.getY(), playerpos.getZ()+1);				

for (BlockPos p1 : BlockPos.getAllInBox(pos1, pos2)) {
	isInside = false;
	for (BlockPos p2 : BlockPos.getAllInBox(pos3, pos4)) {
		if(p1 == p2){
			isInside = true;
		}
	}
	if(!isInside){
		if(world.getBlockState(p1).getBlock() != Blocks.AIR){
			return false;
		}
	}else{
		if(p1 == playerpos && world.getBlockState(playerpos.down(1)).getBlock() != Blocks.OBSIDIAN){
			return false;
		}else{
			if(world.getBlockState(p1).getBlock() != Blocks.REDSTONE_WIRE){
				return false;
			}
		}
	}
}
return true;		
}

Not all things in the world are red, there are round objects too!

Link to comment
Share on other sites

I'd personally recommend this implementation:

 

/**
* Checks that the player is standing on obsidian and surrounded by the following pattern of blocks:
* <p>
* A A A A A
* A R R R A
* A R P R A
* A R R R A
* A A A A A
* <p>
* Where A is air, R is redstone and P is the player.
*
* @param player The player
* @return Is the player surrounded by the correct pattern?
*/
public static boolean isValid(EntityPlayer player) {
final World world = player.getEntityWorld();
final BlockPos playerPos = new BlockPos(player);

// The block under the player must be obsidian
if (!(world.getBlockState(playerPos.down()).getBlock() == Blocks.OBSIDIAN)) return false;

// Iterate from -2,0,-2 to +2,0,+2
for (int x = -2; x <= 2; x++) {
	for (int z = -2; z <= 2; z++) {
		final BlockPos pos = playerPos.add(x, 0, z);
		final IBlockState state = world.getBlockState(pos);

		// If this is the outer layer, the block must be air
		if ((Math.abs(x) == 2 || Math.abs(z) == 2) && state.getBlock() != Blocks.AIR) return false;

		// If this is the inner layer, the block must be redstone
		if ((x != 0 && z != 0) && state.getBlock() != Blocks.REDSTONE_WIRE) return false;
	}
}

// All blocks are correct, the pattern is valid
return true;
}

 

Edit: This code is incorrect. I've linked the correct code below.

Please don't PM me to ask for help. Asking your question in a public thread preserves it for people who are having the same problem in the future.

Link to comment
Share on other sites

I'd personally recommend this implementation:

 

/**
* Checks that the player is standing on obsidian and surrounded by the following pattern of blocks:
* <p>
* A A A A A
* A R R R A
* A R P R A
* A R R R A
* A A A A A
* <p>
* Where A is air, R is redstone and P is the player.
*
* @param player The player
* @return Is the player surrounded by the correct pattern?
*/
public static boolean isValid(EntityPlayer player) {
final World world = player.getEntityWorld();
final BlockPos playerPos = new BlockPos(player);

// The block under the player must be obsidian
if (!(world.getBlockState(playerPos.down()).getBlock() == Blocks.OBSIDIAN)) return false;

// Iterate from -2,0,-2 to +2,0,+2
for (int x = -2; x <= 2; x++) {
	for (int z = -2; z <= 2; z++) {
		final BlockPos pos = playerPos.add(x, 0, z);
		final IBlockState state = world.getBlockState(pos);

		// If this is the outer layer, the block must be air
		if ((Math.abs(x) == 2 || Math.abs(z) == 2) && state.getBlock() != Blocks.AIR) return false;

		// If this is the inner layer, the block must be redstone
		if ((x != 0 && z != 0) && state.getBlock() != Blocks.REDSTONE_WIRE) return false;
	}
}

// All blocks are correct, the pattern is valid
return true;
}

 

Wow, that was clean looking.

Not all things in the world are red, there are round objects too!

Link to comment
Share on other sites

Now that I've actually tested it, my previous code was incorrect. The correct code can be found here.

 

This returns the first invalid position (so it can be displayed to the player) rather than just whether the pattern is valid.

Please don't PM me to ask for help. Asking your question in a public thread preserves it for people who are having the same problem in the future.

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.