Add Solidity flags to BlockState (#818)

* intial

* fix

---------

Co-authored-by: unschlagbar <adrian@kuhlmann@gmx.de>
This commit is contained in:
unschlagbar
2025-05-20 14:54:49 +02:00
committed by GitHub
parent 9fbaee04d6
commit fd8f1d370d
68 changed files with 29369 additions and 1185 deletions

View File

@@ -355,6 +355,7 @@ impl ToTokens for CollisionShape {
pub struct BlockState {
pub id: u16,
pub state_flags: u8,
pub side_flags: u8,
pub instrument: String, // TODO: make this an enum
pub luminance: u8,
pub piston_behavior: PistonBehavior,
@@ -397,6 +398,7 @@ impl BlockState {
let mut tokens = TokenStream::new();
let id = LitInt::new(&self.id.to_string(), Span::call_site());
let state_flags = LitInt::new(&self.state_flags.to_string(), Span::call_site());
let side_flags = LitInt::new(&self.side_flags.to_string(), Span::call_site());
let instrument = self.instrument.clone();
let luminance = LitInt::new(&self.luminance.to_string(), Span::call_site());
let hardness = self.hardness;
@@ -426,6 +428,7 @@ impl BlockState {
BlockState {
id: #id,
state_flags: #state_flags,
side_flags: #side_flags,
instrument: #instrument,
luminance: #luminance,
piston_behavior: #piston_behavior,

View File

@@ -0,0 +1,227 @@
use crate::block_properties::{Axis, Facing, HorizontalFacing};
use pumpkin_util::math::vector3::Vector3;
#[repr(u8)]
#[derive(PartialEq, Clone, Copy, Debug, Hash, Eq)]
pub enum BlockDirection {
Down = 0,
Up,
North,
South,
West,
East,
}
pub struct InvalidBlockFace;
impl TryFrom<i32> for BlockDirection {
type Error = InvalidBlockFace;
fn try_from(value: i32) -> Result<Self, Self::Error> {
match value {
0 => Ok(Self::Down),
1 => Ok(Self::Up),
2 => Ok(Self::North),
3 => Ok(Self::South),
4 => Ok(Self::West),
5 => Ok(Self::East),
_ => Err(InvalidBlockFace),
}
}
}
impl BlockDirection {
pub fn to_index(&self) -> u8 {
match self {
BlockDirection::Down => 0,
BlockDirection::Up => 1,
BlockDirection::North => 2,
BlockDirection::South => 3,
BlockDirection::West => 4,
BlockDirection::East => 5,
}
}
pub fn from_index(index: u8) -> Option<Self> {
match index {
0 => Some(Self::Down),
1 => Some(Self::Up),
2 => Some(Self::North),
3 => Some(Self::South),
4 => Some(Self::West),
5 => Some(Self::East),
_ => None,
}
}
pub fn by_index(index: usize) -> Option<Self> {
Self::all().get(index % Self::all().len()).cloned()
}
pub fn to_offset(&self) -> Vector3<i32> {
match self {
BlockDirection::Down => (0, -1, 0),
BlockDirection::Up => (0, 1, 0),
BlockDirection::North => (0, 0, -1),
BlockDirection::South => (0, 0, 1),
BlockDirection::West => (-1, 0, 0),
BlockDirection::East => (1, 0, 0),
}
.into()
}
pub fn opposite(&self) -> BlockDirection {
match self {
BlockDirection::Down => BlockDirection::Up,
BlockDirection::Up => BlockDirection::Down,
BlockDirection::North => BlockDirection::South,
BlockDirection::South => BlockDirection::North,
BlockDirection::West => BlockDirection::East,
BlockDirection::East => BlockDirection::West,
}
}
pub fn all() -> [BlockDirection; 6] {
[
BlockDirection::Down,
BlockDirection::Up,
BlockDirection::North,
BlockDirection::South,
BlockDirection::West,
BlockDirection::East,
]
}
pub fn update_order() -> [BlockDirection; 6] {
[
BlockDirection::West,
BlockDirection::East,
BlockDirection::Down,
BlockDirection::Up,
BlockDirection::North,
BlockDirection::South,
]
}
pub fn abstract_block_update_order() -> [BlockDirection; 6] {
[
BlockDirection::West,
BlockDirection::East,
BlockDirection::North,
BlockDirection::South,
BlockDirection::Down,
BlockDirection::Up,
]
}
pub fn horizontal() -> [BlockDirection; 4] {
[
BlockDirection::North,
BlockDirection::South,
BlockDirection::West,
BlockDirection::East,
]
}
pub fn is_horizontal(&self) -> bool {
matches!(
self,
BlockDirection::North
| BlockDirection::South
| BlockDirection::West
| BlockDirection::East
)
}
pub fn vertical() -> [BlockDirection; 2] {
[BlockDirection::Down, BlockDirection::Up]
}
pub fn to_horizontal_facing(&self) -> Option<HorizontalFacing> {
match self {
BlockDirection::North => Some(HorizontalFacing::North),
BlockDirection::South => Some(HorizontalFacing::South),
BlockDirection::West => Some(HorizontalFacing::West),
BlockDirection::East => Some(HorizontalFacing::East),
_ => None,
}
}
pub fn to_cardinal_direction(&self) -> HorizontalFacing {
match self {
BlockDirection::North => HorizontalFacing::North,
BlockDirection::South => HorizontalFacing::South,
BlockDirection::West => HorizontalFacing::West,
BlockDirection::East => HorizontalFacing::East,
_ => HorizontalFacing::North,
}
}
pub fn from_cardinal_direction(direction: HorizontalFacing) -> BlockDirection {
match direction {
HorizontalFacing::North => BlockDirection::North,
HorizontalFacing::South => BlockDirection::South,
HorizontalFacing::West => BlockDirection::West,
HorizontalFacing::East => BlockDirection::East,
}
}
pub fn to_axis(&self) -> Axis {
match self {
BlockDirection::North | BlockDirection::South => Axis::Z,
BlockDirection::West | BlockDirection::East => Axis::X,
BlockDirection::Up | BlockDirection::Down => Axis::Y,
}
}
pub fn to_facing(&self) -> Facing {
match self {
BlockDirection::North => Facing::North,
BlockDirection::South => Facing::South,
BlockDirection::West => Facing::West,
BlockDirection::East => Facing::East,
BlockDirection::Up => Facing::Up,
BlockDirection::Down => Facing::Down,
}
}
pub fn rotate_clockwise(&self) -> BlockDirection {
match self {
BlockDirection::North => BlockDirection::East,
BlockDirection::East => BlockDirection::South,
BlockDirection::South => BlockDirection::West,
BlockDirection::West => BlockDirection::North,
BlockDirection::Up => BlockDirection::East,
BlockDirection::Down => BlockDirection::West,
}
}
}
pub trait FacingExt {
fn to_block_direction(&self) -> BlockDirection;
}
impl FacingExt for Facing {
fn to_block_direction(&self) -> BlockDirection {
match self {
Self::North => BlockDirection::North,
Self::South => BlockDirection::South,
Self::West => BlockDirection::West,
Self::East => BlockDirection::East,
Self::Up => BlockDirection::Up,
Self::Down => BlockDirection::Down,
}
}
}
pub trait HorizontalFacingExt {
fn to_block_direction(&self) -> BlockDirection;
}
impl HorizontalFacingExt for HorizontalFacing {
fn to_block_direction(&self) -> BlockDirection {
match self {
Self::North => BlockDirection::North,
Self::South => BlockDirection::South,
Self::West => BlockDirection::West,
Self::East => BlockDirection::East,
}
}
}

View File

@@ -1,7 +1,10 @@
use crate::BlockDirection;
#[derive(Clone, Debug)]
pub struct BlockState {
pub id: u16,
pub state_flags: u8,
pub side_flags: u8,
pub instrument: &'static str,
pub luminance: u8,
pub piston_behavior: PistonBehavior,
@@ -55,6 +58,28 @@ impl BlockState {
pub const fn is_full_cube(&self) -> bool {
self.state_flags & IS_FULL_CUBE != 0
}
///isSideSolidFullSquare() in Java!
pub const fn is_side_solid(&self, side: BlockDirection) -> bool {
match side {
BlockDirection::Down => self.side_flags & DOWN_SIDE_SOLID != 0,
BlockDirection::Up => self.side_flags & UP_SIDE_SOLID != 0,
BlockDirection::North => self.side_flags & NORTH_SIDE_SOLID != 0,
BlockDirection::South => self.side_flags & SOUTH_SIDE_SOLID != 0,
BlockDirection::West => self.side_flags & WEST_SIDE_SOLID != 0,
BlockDirection::East => self.side_flags & EAST_SIDE_SOLID != 0,
}
}
///isSideSolid(..., Direction.UP, SideShapeType.CENTER) in Java!
///Only valid for UP and DOWN sides
pub const fn is_center_solid(&self, side: BlockDirection) -> bool {
match side {
BlockDirection::Down => self.side_flags & DOWN_CENTER_SOLID != 0,
BlockDirection::Up => self.side_flags & UP_CENTER_SOLID != 0,
_ => unreachable!(),
}
}
}
#[derive(Clone, Debug)]
@@ -72,3 +97,12 @@ const REPLACEABLE: u8 = 0b00010000;
const IS_LIQUID: u8 = 0b00100000;
const IS_SOLID: u8 = 0b01000000;
const IS_FULL_CUBE: u8 = 0b10000000;
const DOWN_SIDE_SOLID: u8 = 0b00000001;
const UP_SIDE_SOLID: u8 = 0b00000010;
const NORTH_SIDE_SOLID: u8 = 0b00000100;
const SOUTH_SIDE_SOLID: u8 = 0b00001000;
const WEST_SIDE_SOLID: u8 = 0b00010000;
const EAST_SIDE_SOLID: u8 = 0b00100000;
const DOWN_CENTER_SOLID: u8 = 0b01000000;
const UP_CENTER_SOLID: u8 = 0b10000000;

View File

@@ -122,10 +122,14 @@ pub mod noise_router {
include!(concat!(env!("OUT_DIR"), "/noise_router.rs"));
}
mod block_direction;
pub mod block_state;
mod blocks;
mod collision_shape;
pub use block_direction::BlockDirection;
pub use block_direction::FacingExt;
pub use block_direction::HorizontalFacingExt;
pub use block_state::BlockState;
pub use block_state::BlockStateRef;
pub use blocks::Block;