Add Wooden Hopper GUI, recipe, advancement, item spawning
This commit is contained in:
parent
c7a2c7f0f4
commit
b8d374b982
|
@ -1,6 +1,9 @@
|
||||||
package net.shadowfacts.extrahoppers
|
package net.shadowfacts.extrahoppers
|
||||||
|
|
||||||
import net.fabricmc.api.ModInitializer
|
import net.fabricmc.api.ModInitializer
|
||||||
|
import net.fabricmc.fabric.api.container.ContainerFactory
|
||||||
|
import net.fabricmc.fabric.api.container.ContainerProviderRegistry
|
||||||
|
import net.shadowfacts.extrahoppers.block.wood.WoodHopperContainer
|
||||||
import net.shadowfacts.extrahoppers.init.EHBlockEntities
|
import net.shadowfacts.extrahoppers.init.EHBlockEntities
|
||||||
import net.shadowfacts.extrahoppers.init.EHBlocks
|
import net.shadowfacts.extrahoppers.init.EHBlocks
|
||||||
import net.shadowfacts.extrahoppers.init.EHItems
|
import net.shadowfacts.extrahoppers.init.EHItems
|
||||||
|
@ -8,13 +11,11 @@ import net.shadowfacts.extrahoppers.init.EHItems
|
||||||
object ExtraHoppers: ModInitializer {
|
object ExtraHoppers: ModInitializer {
|
||||||
|
|
||||||
override fun onInitialize() {
|
override fun onInitialize() {
|
||||||
println("--------------------")
|
|
||||||
println("hello from extra hoppers")
|
|
||||||
println("--------------------")
|
|
||||||
|
|
||||||
EHBlocks.init()
|
EHBlocks.init()
|
||||||
EHBlockEntities.init()
|
EHBlockEntities.init()
|
||||||
EHItems.init()
|
EHItems.init()
|
||||||
|
|
||||||
|
ContainerProviderRegistry.INSTANCE.registerFactory(WoodHopperContainer.ID, ContainerFactory(WoodHopperContainer.Companion::create))
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -0,0 +1,15 @@
|
||||||
|
package net.shadowfacts.extrahoppers
|
||||||
|
|
||||||
|
import net.fabricmc.api.ClientModInitializer
|
||||||
|
import net.fabricmc.fabric.api.client.screen.ContainerScreenFactory
|
||||||
|
import net.fabricmc.fabric.api.client.screen.ScreenProviderRegistry
|
||||||
|
import net.shadowfacts.extrahoppers.block.wood.WoodHopperContainer
|
||||||
|
import net.shadowfacts.extrahoppers.block.wood.WoodHopperScreen
|
||||||
|
|
||||||
|
object ExtraHoppersClient: ClientModInitializer {
|
||||||
|
|
||||||
|
override fun onInitializeClient() {
|
||||||
|
ScreenProviderRegistry.INSTANCE.registerFactory(WoodHopperContainer.ID, ContainerScreenFactory(WoodHopperScreen.Companion::create))
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -1,13 +1,15 @@
|
||||||
package net.shadowfacts.extrahoppers.block.wood
|
package net.shadowfacts.extrahoppers.block.wood
|
||||||
|
|
||||||
|
import net.fabricmc.fabric.api.block.FabricBlockSettings
|
||||||
|
import net.fabricmc.fabric.api.container.ContainerProviderRegistry
|
||||||
import net.minecraft.block.*
|
import net.minecraft.block.*
|
||||||
import net.minecraft.block.entity.Hopper
|
import net.minecraft.block.entity.Hopper
|
||||||
import net.minecraft.entity.Entity
|
import net.minecraft.entity.Entity
|
||||||
import net.minecraft.entity.EntityContext
|
import net.minecraft.entity.EntityContext
|
||||||
import net.minecraft.entity.LivingEntity
|
|
||||||
import net.minecraft.entity.player.PlayerEntity
|
import net.minecraft.entity.player.PlayerEntity
|
||||||
import net.minecraft.item.ItemPlacementContext
|
import net.minecraft.item.ItemPlacementContext
|
||||||
import net.minecraft.item.ItemStack
|
import net.minecraft.sound.BlockSoundGroup
|
||||||
|
import net.minecraft.stat.Stats
|
||||||
import net.minecraft.state.StateManager
|
import net.minecraft.state.StateManager
|
||||||
import net.minecraft.state.property.Properties
|
import net.minecraft.state.property.Properties
|
||||||
import net.minecraft.util.*
|
import net.minecraft.util.*
|
||||||
|
@ -23,7 +25,7 @@ import net.shadowfacts.extrahoppers.block.base.BlockWithEntity
|
||||||
/**
|
/**
|
||||||
* @author shadowfacts
|
* @author shadowfacts
|
||||||
*/
|
*/
|
||||||
class WoodHopperBlock: BlockWithEntity<WoodHopperBlockEntity>(Settings.of(Material.WOOD)) {
|
class WoodHopperBlock: BlockWithEntity<WoodHopperBlockEntity>(FabricBlockSettings.of(Material.WOOD).strength(2f, 3f).sounds(BlockSoundGroup.WOOD).nonOpaque().build()) {
|
||||||
companion object {
|
companion object {
|
||||||
val ID = Identifier("extrahoppers", "wood_hopper")
|
val ID = Identifier("extrahoppers", "wood_hopper")
|
||||||
|
|
||||||
|
@ -83,28 +85,28 @@ class WoodHopperBlock: BlockWithEntity<WoodHopperBlockEntity>(Settings.of(Materi
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onUse(state: BlockState, world: World, pos: BlockPos, player: PlayerEntity, hand: Hand, hitResult: BlockHitResult): ActionResult {
|
override fun onUse(state: BlockState, world: World, pos: BlockPos, player: PlayerEntity, hand: Hand, hitResult: BlockHitResult): ActionResult {
|
||||||
// todo: container
|
if (!world.isClient) {
|
||||||
return super.onUse(state, world, pos, player, hand, hitResult)
|
player.incrementStat(Stats.INSPECT_HOPPER)
|
||||||
|
ContainerProviderRegistry.INSTANCE.openContainer(WoodHopperContainer.ID, player) { buf ->
|
||||||
|
buf.writeBlockPos(pos)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ActionResult.SUCCESS
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onBlockRemoved(oldState: BlockState, world: World, pos: BlockPos, newState: BlockState, bl: Boolean) {
|
override fun onBlockRemoved(oldState: BlockState, world: World, pos: BlockPos, newState: BlockState, bl: Boolean) {
|
||||||
if (oldState.block != newState.block) {
|
if (oldState.block != newState.block) {
|
||||||
getBlockEntity(world, pos)?.also {
|
getBlockEntity(world, pos)?.also {
|
||||||
// todo: spawn items
|
ItemScatterer.spawn(world, pos, it)
|
||||||
// ItemScatterer.spawn(world, pos, it)
|
|
||||||
world.updateHorizontalAdjacent(pos, this)
|
world.updateHorizontalAdjacent(pos, this)
|
||||||
}
|
}
|
||||||
}
|
|
||||||
super.onBlockRemoved(oldState, world, pos, newState, bl)
|
super.onBlockRemoved(oldState, world, pos, newState, bl)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getRenderType(blockState: BlockState?): BlockRenderType {
|
|
||||||
return BlockRenderType.MODEL
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onEntityCollision(state: BlockState, world: World, pos: BlockPos, entity: Entity) {
|
override fun onEntityCollision(state: BlockState, world: World, pos: BlockPos, entity: Entity) {
|
||||||
getBlockEntity(world, pos)?.also {
|
getBlockEntity(world, pos)?.also {
|
||||||
// todo: handle entity collision
|
it.onEntityCollision(entity)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3,15 +3,19 @@ package net.shadowfacts.extrahoppers.block.wood
|
||||||
import net.minecraft.block.entity.BlockEntity
|
import net.minecraft.block.entity.BlockEntity
|
||||||
import net.minecraft.block.entity.Hopper
|
import net.minecraft.block.entity.Hopper
|
||||||
import net.minecraft.block.entity.HopperBlockEntity
|
import net.minecraft.block.entity.HopperBlockEntity
|
||||||
|
import net.minecraft.entity.Entity
|
||||||
|
import net.minecraft.entity.ItemEntity
|
||||||
import net.minecraft.entity.player.PlayerEntity
|
import net.minecraft.entity.player.PlayerEntity
|
||||||
import net.minecraft.inventory.Inventories
|
import net.minecraft.inventory.Inventories
|
||||||
import net.minecraft.inventory.Inventory
|
import net.minecraft.inventory.Inventory
|
||||||
import net.minecraft.inventory.SidedInventory
|
import net.minecraft.inventory.SidedInventory
|
||||||
import net.minecraft.item.ItemStack
|
import net.minecraft.item.ItemStack
|
||||||
import net.minecraft.nbt.CompoundTag
|
import net.minecraft.nbt.CompoundTag
|
||||||
|
import net.minecraft.util.BooleanBiFunction
|
||||||
import net.minecraft.util.DefaultedList
|
import net.minecraft.util.DefaultedList
|
||||||
import net.minecraft.util.Tickable
|
import net.minecraft.util.Tickable
|
||||||
import net.minecraft.util.math.Direction
|
import net.minecraft.util.math.Direction
|
||||||
|
import net.minecraft.util.shape.VoxelShapes
|
||||||
import net.shadowfacts.extrahoppers.init.EHBlockEntities
|
import net.shadowfacts.extrahoppers.init.EHBlockEntities
|
||||||
import net.shadowfacts.extrahoppers.util.toVec3d
|
import net.shadowfacts.extrahoppers.util.toVec3d
|
||||||
|
|
||||||
|
@ -50,7 +54,15 @@ class WoodHopperBlockEntity: BlockEntity(EHBlockEntities.WOOD_HOPPER), Inventory
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun insertAndExtract() {
|
fun onEntityCollision(entity: Entity) {
|
||||||
|
if (entity is ItemEntity) {
|
||||||
|
if (VoxelShapes.matchesAnywhere(VoxelShapes.cuboid(entity.boundingBox.offset(-pos.x.toDouble(), -pos.y.toDouble(), -pos.z.toDouble())), inputAreaShape, BooleanBiFunction.AND)) {
|
||||||
|
insertAndExtract()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun insertAndExtract(extractor: (() -> Boolean)? = null) {
|
||||||
val world = world
|
val world = world
|
||||||
if (world == null || world.isClient) return
|
if (world == null || world.isClient) return
|
||||||
|
|
||||||
|
@ -58,7 +70,7 @@ class WoodHopperBlockEntity: BlockEntity(EHBlockEntities.WOOD_HOPPER), Inventory
|
||||||
if (!isInvEmpty && insert()) {
|
if (!isInvEmpty && insert()) {
|
||||||
didWork = true
|
didWork = true
|
||||||
}
|
}
|
||||||
if (!isFull() && HopperBlockEntity.extract(this)) {
|
if (!isFull() && ((extractor != null && extractor()) || HopperBlockEntity.extract(this))) {
|
||||||
didWork = true
|
didWork = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,74 @@
|
||||||
|
package net.shadowfacts.extrahoppers.block.wood
|
||||||
|
|
||||||
|
import net.minecraft.container.Container
|
||||||
|
import net.minecraft.container.Slot
|
||||||
|
import net.minecraft.entity.player.PlayerEntity
|
||||||
|
import net.minecraft.entity.player.PlayerInventory
|
||||||
|
import net.minecraft.inventory.Inventory
|
||||||
|
import net.minecraft.item.ItemStack
|
||||||
|
import net.minecraft.util.Identifier
|
||||||
|
import net.minecraft.util.PacketByteBuf
|
||||||
|
import net.shadowfacts.extrahoppers.init.EHBlocks
|
||||||
|
|
||||||
|
class WoodHopperContainer(syncId: Int, playerInv: PlayerInventory, val hopperInv: Inventory): Container(null, syncId) {
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
val ID = Identifier("extrahoppers", "wood_hopper")
|
||||||
|
|
||||||
|
fun create(syncId: Int, identifier: Identifier, player: PlayerEntity, buf: PacketByteBuf): WoodHopperContainer {
|
||||||
|
val pos = buf.readBlockPos()
|
||||||
|
val blockEntity = EHBlocks.WOOD_HOPPER.getBlockEntity(player.world, pos)!!
|
||||||
|
return WoodHopperContainer(syncId, player.inventory, blockEntity)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
init {
|
||||||
|
addSlot(Slot(hopperInv, 0, 80, 20))
|
||||||
|
|
||||||
|
// player inv
|
||||||
|
for (y in 0 until 3) {
|
||||||
|
for (x in 0 until 9) {
|
||||||
|
addSlot(Slot(playerInv, x + y * 9 + 9, 8 + x * 18, 51 + y * 18))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// hotbar
|
||||||
|
for (x in 0 until 9) {
|
||||||
|
addSlot(Slot(playerInv, x, 8 + x * 18, 109))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun canUse(player: PlayerEntity): Boolean {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun close(player: PlayerEntity) {
|
||||||
|
super.close(player)
|
||||||
|
|
||||||
|
hopperInv.onInvClose(player)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun transferSlot(player: PlayerEntity, slotIndex: Int): ItemStack {
|
||||||
|
var remaining = ItemStack.EMPTY
|
||||||
|
val slot = slots[slotIndex]
|
||||||
|
if (slot != null && slot.hasStack()) {
|
||||||
|
val slotStack = slot.stack
|
||||||
|
remaining = slotStack.copy()
|
||||||
|
if (slotIndex < hopperInv.invSize) {
|
||||||
|
if (!insertItem(slotStack, hopperInv.invSize, slots.size, true)) {
|
||||||
|
return ItemStack.EMPTY;
|
||||||
|
}
|
||||||
|
} else if (!insertItem(slotStack, 0, hopperInv.invSize, false)) {
|
||||||
|
return ItemStack.EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (slotStack.isEmpty) {
|
||||||
|
slot.stack = ItemStack.EMPTY;
|
||||||
|
} else {
|
||||||
|
slot.markDirty()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return remaining
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,37 @@
|
||||||
|
package net.shadowfacts.extrahoppers.block.wood
|
||||||
|
|
||||||
|
import com.mojang.blaze3d.platform.GlStateManager
|
||||||
|
import net.minecraft.client.MinecraftClient
|
||||||
|
import net.minecraft.client.gui.screen.ingame.ContainerScreen
|
||||||
|
import net.minecraft.entity.player.PlayerInventory
|
||||||
|
import net.minecraft.text.LiteralText
|
||||||
|
import net.minecraft.util.Identifier
|
||||||
|
|
||||||
|
class WoodHopperScreen(container: WoodHopperContainer, playerInv: PlayerInventory): ContainerScreen<WoodHopperContainer>(container, playerInv, LiteralText("Wooden Hopper")) {
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
val BACKGROUND = Identifier("extrahoppers", "textures/gui/wood_hopper.png")
|
||||||
|
|
||||||
|
fun create(container: WoodHopperContainer): WoodHopperScreen {
|
||||||
|
return WoodHopperScreen(container, MinecraftClient.getInstance().player!!.inventory)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
init {
|
||||||
|
containerHeight = 133
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun drawForeground(mouseX: Int, mouseY: Int) {
|
||||||
|
font.draw(title.asFormattedString(), 8f, 6f, 0x404040)
|
||||||
|
font.draw(playerInventory.displayName.asFormattedString(), 8f, containerHeight - 94f, 0x404040)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun drawBackground(f: Float, i: Int, j: Int) {
|
||||||
|
GlStateManager.color4f(1f, 1f, 1f, 1f)
|
||||||
|
minecraft!!.textureManager.bindTexture(BACKGROUND)
|
||||||
|
val x = (width - containerWidth) / 2
|
||||||
|
val y = (height - containerHeight) / 2
|
||||||
|
blit(x, y, 0, 0, containerWidth, containerHeight)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
Binary file not shown.
After Width: | Height: | Size: 5.8 KiB |
|
@ -0,0 +1,35 @@
|
||||||
|
{
|
||||||
|
"parent": "minecraft:recipes/root",
|
||||||
|
"rewards": {
|
||||||
|
"recipes": [
|
||||||
|
"extrahoppers:wood_hopper"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"criteria": {
|
||||||
|
"has_logs_and_chest": {
|
||||||
|
"trigger": "minecraft:inventory_changed",
|
||||||
|
"conditions": {
|
||||||
|
"items": [
|
||||||
|
{
|
||||||
|
"tag": "minecraft:logs"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"item": "minecraft:chest"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"has_the_recipe": {
|
||||||
|
"trigger": "minecraft:recipe_unlocked",
|
||||||
|
"conditions": {
|
||||||
|
"recipe": "extrahoppers:wood_hopper"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"requirements": [
|
||||||
|
[
|
||||||
|
"has_logs_and_chest",
|
||||||
|
"has_the_recipe"
|
||||||
|
]
|
||||||
|
]
|
||||||
|
}
|
|
@ -0,0 +1,19 @@
|
||||||
|
{
|
||||||
|
"type": "minecraft:block",
|
||||||
|
"pools": [
|
||||||
|
{
|
||||||
|
"rolls": 1,
|
||||||
|
"entries": [
|
||||||
|
{
|
||||||
|
"type": "minecraft:item",
|
||||||
|
"name": "extrahoppers:wood_hopper"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"conditions": [
|
||||||
|
{
|
||||||
|
"condition": "minecraft:survives_explosion"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
|
@ -0,0 +1,19 @@
|
||||||
|
{
|
||||||
|
"type": "minecraft:crafting_shaped",
|
||||||
|
"pattern": [
|
||||||
|
"L L",
|
||||||
|
"LCL",
|
||||||
|
" L "
|
||||||
|
],
|
||||||
|
"key": {
|
||||||
|
"C": {
|
||||||
|
"item": "minecraft:chest"
|
||||||
|
},
|
||||||
|
"L": {
|
||||||
|
"tag": "minecraft:logs"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"result": {
|
||||||
|
"item": "extrahoppers:wood_hopper"
|
||||||
|
}
|
||||||
|
}
|
|
@ -9,6 +9,12 @@
|
||||||
"adapter": "kotlin",
|
"adapter": "kotlin",
|
||||||
"value": "net.shadowfacts.extrahoppers.ExtraHoppers"
|
"value": "net.shadowfacts.extrahoppers.ExtraHoppers"
|
||||||
}
|
}
|
||||||
|
],
|
||||||
|
"client": [
|
||||||
|
{
|
||||||
|
"adapter": "kotlin",
|
||||||
|
"value": "net.shadowfacts.extrahoppers.ExtraHoppersClient"
|
||||||
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"depends": {
|
"depends": {
|
||||||
|
|
Loading…
Reference in New Issue