package ru.dbotthepony.mc.otm.block.matter

import net.minecraft.core.BlockPos
import net.minecraft.world.Containers
import net.minecraft.world.item.context.BlockPlaceContext
import net.minecraft.world.level.BlockGetter
import net.minecraft.world.level.Level
import net.minecraft.world.level.block.Block
import net.minecraft.world.level.block.EntityBlock
import net.minecraft.world.level.block.entity.BlockEntity
import net.minecraft.world.level.block.state.BlockState
import net.minecraft.world.level.block.state.StateDefinition
import net.minecraft.world.level.block.state.properties.BooleanProperty
import net.minecraft.world.phys.shapes.CollisionContext
import net.minecraft.world.phys.shapes.VoxelShape
import ru.dbotthepony.mc.otm.block.RotatableMatteryBlock
import ru.dbotthepony.mc.otm.block.entity.matter.PatternStorageBlockEntity
import ru.dbotthepony.mc.otm.block.getShapeForEachState
import ru.dbotthepony.mc.otm.core.get
import ru.dbotthepony.mc.otm.shapes.BlockShapes

class PatternStorageBlock : RotatableMatteryBlock(), EntityBlock {
	override fun newBlockEntity(blockPos: BlockPos, blockState: BlockState): BlockEntity? {
		return PatternStorageBlockEntity(blockPos, blockState)
	}

	override fun createBlockStateDefinition(builder: StateDefinition.Builder<Block, BlockState>) {
		builder.add(*PATTERN_STORAGE_DISKS_PROPS)
		super.createBlockStateDefinition(builder)
	}

	override fun getStateForPlacement(context: BlockPlaceContext): BlockState? {
		var state = super.getStateForPlacement(context) ?: return null

		for (prop in PATTERN_STORAGE_DISKS_PROPS)
			state = state.setValue(prop, false)

		return state
	}

	override fun onRemove(
		oldBlockState: BlockState,
		level: Level,
		blockPos: BlockPos,
		newBlockState: BlockState,
		movedByPiston: Boolean
	) {
		if (!oldBlockState.`is`(newBlockState.block)) {
			val blockentity = level.getBlockEntity(blockPos)

			if (blockentity is PatternStorageBlockEntity) {
				Containers.dropContents(level, blockPos, blockentity.container)
				level.updateNeighbourForOutputSignal(blockPos, this)
			}
		}

		super.onRemove(oldBlockState, level, blockPos, newBlockState, movedByPiston)
	}

	private val shapes = getShapeForEachState(rotationProperty) { BlockShapes.PATTERN_STORAGE.rotateFromNorth(it[rotationProperty]).computeShape() }

	@Suppress("override_deprecation")
	override fun getShape(
		state: BlockState,
		blockGetter: BlockGetter,
		pos: BlockPos,
		context: CollisionContext
	): VoxelShape {
		return shapes[state]!!
	}

	companion object {
		val PATTERN_STORAGE_DISKS_PROPS = arrayOf(
			BooleanProperty.create("disk_0") as BooleanProperty,
			BooleanProperty.create("disk_1") as BooleanProperty,
			BooleanProperty.create("disk_2") as BooleanProperty,
			BooleanProperty.create("disk_3") as BooleanProperty,
			BooleanProperty.create("disk_4") as BooleanProperty,
			BooleanProperty.create("disk_5") as BooleanProperty,
			BooleanProperty.create("disk_6") as BooleanProperty,
			BooleanProperty.create("disk_7") as BooleanProperty
		)
	}
}
