Skip to main content

steel_core/behavior/blocks/container/
beehive_block.rs

1//! Beehive block behavior implementation.
2
3use std::sync::Weak;
4
5use steel_macros::block_behavior;
6use steel_registry::blocks::BlockRef;
7use steel_registry::blocks::block_state_ext::BlockStateExt;
8use steel_registry::blocks::properties::{
9    BlockStateProperties, Direction, EnumProperty, IntProperty,
10};
11use steel_registry::vanilla_block_entity_types;
12use steel_utils::{BlockPos, BlockStateId};
13
14use crate::behavior::block::{BlockBehavior, BlockEntityCreation};
15use crate::behavior::context::BlockPlaceContext;
16use crate::block_entity::BLOCK_ENTITIES;
17use crate::world::{LevelReader, World};
18
19/// Behavior for beehive and bee nest blocks.
20// TODO: Implement full vanilla beehive interactions, bee release, smoke/fire handling, loot/data components, and ticking.
21#[block_behavior]
22pub struct BeehiveBlock {
23    block: BlockRef,
24}
25
26const HORIZONTAL_FACING: &EnumProperty<Direction> = &BlockStateProperties::HORIZONTAL_FACING;
27const LEVEL_HONEY: &IntProperty = &BlockStateProperties::LEVEL_HONEY;
28
29impl BeehiveBlock {
30    /// Creates a new beehive block behavior.
31    #[must_use]
32    pub const fn new(block: BlockRef) -> Self {
33        Self { block }
34    }
35}
36
37impl BlockBehavior for BeehiveBlock {
38    fn get_state_for_placement(&self, context: &BlockPlaceContext<'_>) -> Option<BlockStateId> {
39        Some(
40            self.block
41                .default_state()
42                .set_value(HORIZONTAL_FACING, context.horizontal_direction().opposite()),
43        )
44    }
45
46    fn new_block_entity(
47        &self,
48        level: Weak<World>,
49        pos: BlockPos,
50        state: BlockStateId,
51    ) -> BlockEntityCreation {
52        BlockEntityCreation::from_registered_factory(BLOCK_ENTITIES.create(
53            &vanilla_block_entity_types::BEEHIVE,
54            level,
55            pos,
56            state,
57        ))
58    }
59
60    fn has_analog_output_signal(&self, _state: BlockStateId) -> bool {
61        true
62    }
63
64    fn get_analog_output_signal(
65        &self,
66        state: BlockStateId,
67        _world: &dyn LevelReader,
68        _pos: BlockPos,
69        _direction: Direction,
70    ) -> i32 {
71        state.get_value(LEVEL_HONEY).into()
72    }
73}