diff --git a/paper-api/src/main/java/org/bukkit/block/Block.java b/paper-api/src/main/java/org/bukkit/block/Block.java index d309e28d7..32f5d2631 100644 --- a/paper-api/src/main/java/org/bukkit/block/Block.java +++ b/paper-api/src/main/java/org/bukkit/block/Block.java @@ -817,4 +817,11 @@ public interface Block extends Metadatable, Translatable, net.kyori.adventure.tr return this.getBlockData().getDestroySpeed(itemStack, considerEnchants); } // Paper end - destroy speed API + + /** + * Checks if the block can suffocate. + * + * @return {@code true} if the block can suffocate + */ + boolean isSuffocating(); } diff --git a/paper-api/src/main/java/org/bukkit/block/BlockState.java b/paper-api/src/main/java/org/bukkit/block/BlockState.java index 2c430a7fb..ce7cdcf0c 100644 --- a/paper-api/src/main/java/org/bukkit/block/BlockState.java +++ b/paper-api/src/main/java/org/bukkit/block/BlockState.java @@ -5,12 +5,16 @@ import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.World; import org.bukkit.block.data.BlockData; +import org.bukkit.entity.Entity; +import org.bukkit.inventory.ItemStack; import org.bukkit.material.MaterialData; import org.bukkit.metadata.Metadatable; import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.Contract; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; +import org.jetbrains.annotations.Unmodifiable; +import java.util.Collection; /** * Represents a captured state of a block, which will not change @@ -226,14 +230,14 @@ public interface BlockState extends Metadatable { * @deprecated Magic value */ @Deprecated(since = "1.6.2", forRemoval = true) - public byte getRawData(); + byte getRawData(); /** * @param data The new data value for the block. * @deprecated Magic value */ @Deprecated(since = "1.6.2", forRemoval = true) - public void setRawData(byte data); + void setRawData(byte data); /** * Returns whether this state is placed in the world. @@ -246,7 +250,6 @@ public interface BlockState extends Metadatable { */ boolean isPlaced(); - // Paper start /** * Checks if this block state is collidable. * @@ -261,7 +264,7 @@ public interface BlockState extends Metadatable { * @throws IllegalStateException if this block state is not placed */ @NotNull - default java.util.@org.jetbrains.annotations.Unmodifiable Collection getDrops() { + default @Unmodifiable Collection getDrops() { return this.getDrops(null); } @@ -274,7 +277,7 @@ public interface BlockState extends Metadatable { * @throws IllegalStateException if this block state is not placed */ @NotNull - default java.util.@org.jetbrains.annotations.Unmodifiable Collection getDrops(@Nullable org.bukkit.inventory.ItemStack tool) { + default @Unmodifiable Collection getDrops(@Nullable ItemStack tool) { return this.getDrops(tool, null); } @@ -288,6 +291,14 @@ public interface BlockState extends Metadatable { * @throws IllegalStateException if this block state is not placed */ @NotNull - java.util.@org.jetbrains.annotations.Unmodifiable Collection getDrops(@Nullable org.bukkit.inventory.ItemStack tool, @Nullable org.bukkit.entity.Entity entity); - // Paper end + @Unmodifiable + Collection getDrops(@Nullable ItemStack tool, @Nullable Entity entity); + + /** + * Checks if the block state can suffocate. + * + * @return {@code true} if the block state can suffocate + * @throws IllegalStateException if this block state is not placed + */ + boolean isSuffocating(); } diff --git a/paper-api/src/main/java/org/bukkit/block/BlockType.java b/paper-api/src/main/java/org/bukkit/block/BlockType.java index b7aa24cf4..ae42c2ddc 100644 --- a/paper-api/src/main/java/org/bukkit/block/BlockType.java +++ b/paper-api/src/main/java/org/bukkit/block/BlockType.java @@ -121,7 +121,6 @@ import org.bukkit.block.data.type.WallHangingSign; import org.bukkit.block.data.type.WallSign; import org.bukkit.block.data.type.WallSkull; import org.bukkit.inventory.ItemType; -import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Unmodifiable; diff --git a/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java index e9ca19c86..a4d5c65ed 100644 --- a/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java +++ b/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java @@ -697,6 +697,11 @@ public class CraftBlock implements Block { return this.getNMS().getBlock().getDescriptionId(); } + @Override + public boolean isSuffocating() { + return this.getNMS().isSuffocating(this.world, this.position); + } + // Paper start @Override public com.destroystokyo.paper.block.BlockSoundGroup getSoundGroup() { diff --git a/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java b/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java index c0a765977..196835bdf 100644 --- a/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java +++ b/paper-server/src/main/java/org/bukkit/craftbukkit/block/CraftBlockState.java @@ -75,6 +75,7 @@ public class CraftBlockState implements BlockState { // Returns null if weakWorld is not available and the BlockState is not placed. // If this returns a World instead of only a GeneratorAccess, this implies that this BlockState is placed. + @Nullable public LevelAccessor getWorldHandle() { if (this.weakWorld == null) { return this.isPlaced() ? this.world.getHandle() : null; @@ -177,7 +178,7 @@ public class CraftBlockState implements BlockState { @Override public Material getType() { - return this.data.getBukkitMaterial(); // Paper - optimise getType calls + return this.data.getBukkitMaterial(); } public void setFlags(int flags) { @@ -357,7 +358,6 @@ public class CraftBlockState implements BlockState { return new CraftBlockState(this, location); } - // Paper start @Override public boolean isCollidable() { return this.data.getBlock().hasCollision; @@ -381,5 +381,10 @@ public class CraftBlockState implements BlockState { return java.util.Collections.emptyList(); } } - // Paper end + + @Override + public boolean isSuffocating() { + this.requirePlaced(); + return this.data.isSuffocating(this.getWorldHandle(), this.position); + } }