Start manager block & programming UI
This commit is contained in:
parent
200a9eea27
commit
946ebd7d9c
|
@ -2,17 +2,36 @@ package net.shadowfacts.asmr
|
|||
|
||||
import net.fabricmc.api.ModInitializer
|
||||
import net.fabricmc.fabric.api.registry.CommandRegistry
|
||||
import net.minecraft.block.entity.BlockEntityType
|
||||
import net.minecraft.client.MinecraftClient
|
||||
import net.minecraft.item.BlockItem
|
||||
import net.minecraft.item.Item
|
||||
import net.minecraft.server.command.CommandManager
|
||||
import net.minecraft.util.Identifier
|
||||
import net.minecraft.util.registry.Registry
|
||||
import net.shadowfacts.asmr.manager.ManagerBlock
|
||||
import net.shadowfacts.asmr.manager.ManagerBlockEntity
|
||||
import net.shadowfacts.asmr.util.register
|
||||
import java.util.function.Supplier
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
object ASMR: ModInitializer {
|
||||
|
||||
const val modid = "asmr"
|
||||
|
||||
val managerBlock = ManagerBlock()
|
||||
val managerBlockItem = BlockItem(managerBlock, Item.Settings())
|
||||
val managerEntityType = BlockEntityType.Builder.create(Supplier { ManagerBlockEntity() }, managerBlock).build(null)
|
||||
|
||||
override fun onInitialize() {
|
||||
println("hello fabric")
|
||||
|
||||
Registry.BLOCK.register(managerBlock, Identifier(modid, "manager"))
|
||||
Registry.ITEM.register(managerBlockItem, Identifier(modid, "manager"))
|
||||
Registry.BLOCK_ENTITY.register(managerEntityType, Identifier(modid, "manager"))
|
||||
|
||||
CommandRegistry.INSTANCE.register(false) { dispatcher ->
|
||||
val command = CommandManager.literal("uitest").executes {
|
||||
try {
|
||||
|
|
|
@ -0,0 +1,46 @@
|
|||
package net.shadowfacts.asmr.manager
|
||||
|
||||
import net.fabricmc.api.EnvType
|
||||
import net.fabricmc.api.Environment
|
||||
import net.minecraft.block.Block
|
||||
import net.minecraft.block.BlockEntityProvider
|
||||
import net.minecraft.block.BlockState
|
||||
import net.minecraft.block.Material
|
||||
import net.minecraft.block.entity.BlockEntity
|
||||
import net.minecraft.client.MinecraftClient
|
||||
import net.minecraft.entity.player.PlayerEntity
|
||||
import net.minecraft.util.Hand
|
||||
import net.minecraft.util.hit.BlockHitResult
|
||||
import net.minecraft.util.math.BlockPos
|
||||
import net.minecraft.world.BlockView
|
||||
import net.minecraft.world.World
|
||||
import net.shadowfacts.asmr.ui.ManagerViewController
|
||||
import net.shadowfacts.cacao.CacaoScreen
|
||||
import net.shadowfacts.cacao.Window
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
class ManagerBlock: Block(Settings.of(Material.METAL)), BlockEntityProvider {
|
||||
|
||||
@Deprecated("")
|
||||
override fun activate(state: BlockState, world: World, pos: BlockPos, player: PlayerEntity, hand: Hand, hitResult: BlockHitResult?): Boolean {
|
||||
if (world.isClient) {
|
||||
openManagerUI(world.getBlockEntity(pos) as ManagerBlockEntity)
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
@Environment(EnvType.CLIENT)
|
||||
private fun openManagerUI(managerBlockEntity: ManagerBlockEntity) {
|
||||
val vc = ManagerViewController(managerBlockEntity)
|
||||
val screen = CacaoScreen()
|
||||
val window = screen.addWindow(Window(vc))
|
||||
MinecraftClient.getInstance().openScreen(screen)
|
||||
}
|
||||
|
||||
override fun createBlockEntity(world: BlockView): BlockEntity {
|
||||
return ManagerBlockEntity()
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
package net.shadowfacts.asmr.manager
|
||||
|
||||
import net.minecraft.block.entity.BlockEntity
|
||||
import net.shadowfacts.asmr.ASMR
|
||||
import net.shadowfacts.asmr.program.Program
|
||||
import net.shadowfacts.asmr.program.ProgramType.Companion.INT
|
||||
import net.shadowfacts.asmr.program.blocks.ConstantBlock
|
||||
import net.shadowfacts.asmr.program.blocks.PrintBlock
|
||||
import net.shadowfacts.asmr.program.blocks.math.BinaryOperatorBlock
|
||||
import net.shadowfacts.asmr.program.blocks.math.BinaryOperatorBlock.Operation.DIVIDE
|
||||
import net.shadowfacts.cacao.geometry.Point
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
class ManagerBlockEntity: BlockEntity(ASMR.managerEntityType) {
|
||||
|
||||
val program = Program()
|
||||
|
||||
init {
|
||||
val left = program.addBlock(ConstantBlock(INT, 36)) {
|
||||
it.position = Point(0.0, 60.0)
|
||||
}
|
||||
val right = program.addBlock(ConstantBlock(INT, 9)) {
|
||||
it.position = Point(0.0, 120.0)
|
||||
}
|
||||
val divide = program.addBlock(BinaryOperatorBlock(INT, DIVIDE)) {
|
||||
it.left.source = left.output
|
||||
it.right.source = right.output
|
||||
it.position = Point(120.0, 0.0)
|
||||
}
|
||||
val print = program.addBlock(PrintBlock(INT)) {
|
||||
it.input.source = divide.output
|
||||
it.position = Point(240.0, 0.0)
|
||||
}
|
||||
|
||||
program.startBlock.nextExecutableBlock = divide
|
||||
divide.nextExecutableBlock = print
|
||||
}
|
||||
|
||||
fun activate() {
|
||||
program.execute()
|
||||
}
|
||||
|
||||
}
|
|
@ -1,9 +1,11 @@
|
|||
package net.shadowfacts.asmr.program
|
||||
|
||||
import net.shadowfacts.cacao.geometry.Point
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
abstract class ExecutableBlock: ProgramBlock {
|
||||
abstract class ExecutableBlock: ProgramBlock() {
|
||||
|
||||
var nextExecutableBlock: ExecutableBlock? = null
|
||||
|
||||
|
|
|
@ -1,13 +1,16 @@
|
|||
package net.shadowfacts.asmr.program
|
||||
|
||||
import net.shadowfacts.asmr.program.blocks.StartBlock
|
||||
import net.shadowfacts.cacao.geometry.Point
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
class Program {
|
||||
|
||||
var startBlock = StartBlock()
|
||||
var startBlock = StartBlock().apply {
|
||||
position = Point.ORIGIN
|
||||
}
|
||||
val blocks = mutableListOf<ProgramBlock>()
|
||||
|
||||
fun execute() {
|
||||
|
@ -19,4 +22,10 @@ class Program {
|
|||
}
|
||||
}
|
||||
|
||||
fun <Block: ProgramBlock> addBlock(block: Block, init: (Block) -> Unit = {}): Block {
|
||||
init(block)
|
||||
blocks.add(block)
|
||||
return block
|
||||
}
|
||||
|
||||
}
|
|
@ -1,11 +1,15 @@
|
|||
package net.shadowfacts.asmr.program
|
||||
|
||||
import net.shadowfacts.cacao.geometry.Point
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
interface ProgramBlock {
|
||||
abstract class ProgramBlock {
|
||||
|
||||
val inputs: Array<ProgramBlockInput<*>>
|
||||
val outputs: Array<ProgramBlockOutput<*>>
|
||||
var position: Point = Point.ORIGIN
|
||||
|
||||
abstract val inputs: Array<ProgramBlockInput<*>>
|
||||
abstract val outputs: Array<ProgramBlockOutput<*>>
|
||||
|
||||
}
|
|
@ -5,8 +5,8 @@ package net.shadowfacts.asmr.program
|
|||
*/
|
||||
class ProgramType<Type> {
|
||||
companion object {
|
||||
val int = ProgramType<Int>()
|
||||
val float = ProgramType<Float>()
|
||||
val string = ProgramType<String>()
|
||||
val INT = ProgramType<Int>()
|
||||
val FLOAT = ProgramType<Float>()
|
||||
val STRING = ProgramType<String>()
|
||||
}
|
||||
}
|
|
@ -11,7 +11,7 @@ import net.shadowfacts.asmr.program.ProgramType
|
|||
class ConstantBlock<Type: Any>(
|
||||
val type: ProgramType<Type>,
|
||||
val value: Type
|
||||
): ProgramBlock {
|
||||
): ProgramBlock() {
|
||||
|
||||
val output = ProgramBlockOutput(type).apply {
|
||||
value = this@ConstantBlock.value
|
||||
|
|
|
@ -4,6 +4,7 @@ import net.shadowfacts.asmr.program.ExecutableBlock
|
|||
import net.shadowfacts.asmr.program.ProgramBlockInput
|
||||
import net.shadowfacts.asmr.program.ProgramBlockOutput
|
||||
import net.shadowfacts.asmr.program.ProgramType
|
||||
import net.shadowfacts.cacao.geometry.Point
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
|
|
|
@ -8,7 +8,7 @@ import net.shadowfacts.asmr.program.ProgramBlockOutput
|
|||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
class StartBlock: ProgramBlock {
|
||||
class StartBlock: ProgramBlock() {
|
||||
|
||||
override val inputs: Array<ProgramBlockInput<*>> = arrayOf()
|
||||
override val outputs: Array<ProgramBlockOutput<*>> = arrayOf()
|
||||
|
|
|
@ -15,7 +15,7 @@ class BinaryOperatorBlock<Type: Any>(
|
|||
): ExecutableBlock() {
|
||||
|
||||
init {
|
||||
if (type != ProgramType.int && type != ProgramType.float) {
|
||||
if (type != ProgramType.INT && type != ProgramType.FLOAT) {
|
||||
throw RuntimeException("BinaryOperatorBlock type must be int or float")
|
||||
}
|
||||
}
|
||||
|
@ -29,29 +29,29 @@ class BinaryOperatorBlock<Type: Any>(
|
|||
override val outputs: Array<ProgramBlockOutput<*>> = arrayOf(output)
|
||||
|
||||
override fun execute() {
|
||||
if (type == ProgramType.int) {
|
||||
if (type == ProgramType.INT) {
|
||||
val left = left.value as Int
|
||||
val right = right.value as Int
|
||||
output.value = when (operation) {
|
||||
Operation.add -> left + right
|
||||
Operation.subtract -> left - right
|
||||
Operation.multiply -> left * right
|
||||
Operation.divide -> left / right
|
||||
Operation.ADD -> left + right
|
||||
Operation.SUBTRACT -> left - right
|
||||
Operation.MULTIPLY -> left * right
|
||||
Operation.DIVIDE -> left / right
|
||||
} as Type
|
||||
} else if (type == ProgramType.float) {
|
||||
} else if (type == ProgramType.FLOAT) {
|
||||
val left = left.value as Float
|
||||
val right = right.value as Float
|
||||
output.value = when (operation) {
|
||||
Operation.add -> left + right
|
||||
Operation.subtract -> left - right
|
||||
Operation.multiply -> left * right
|
||||
Operation.divide -> left / right
|
||||
Operation.ADD -> left + right
|
||||
Operation.SUBTRACT -> left - right
|
||||
Operation.MULTIPLY -> left * right
|
||||
Operation.DIVIDE -> left / right
|
||||
} as Type
|
||||
}
|
||||
}
|
||||
|
||||
enum class Operation {
|
||||
add, subtract, multiply, divide
|
||||
ADD, SUBTRACT, MULTIPLY, DIVIDE
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,63 @@
|
|||
package net.shadowfacts.asmr.ui
|
||||
|
||||
import net.shadowfacts.asmr.manager.ManagerBlockEntity
|
||||
import net.shadowfacts.cacao.geometry.Rect
|
||||
import net.shadowfacts.cacao.geometry.Size
|
||||
import net.shadowfacts.cacao.util.Color
|
||||
import net.shadowfacts.cacao.util.texture.NinePatchTexture
|
||||
import net.shadowfacts.cacao.view.Label
|
||||
import net.shadowfacts.cacao.view.NinePatchView
|
||||
import net.shadowfacts.cacao.view.View
|
||||
import net.shadowfacts.cacao.viewcontroller.ViewController
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
class ManagerViewController(val managerBlockEntity: ManagerBlockEntity): ViewController() {
|
||||
|
||||
lateinit var panel: View
|
||||
|
||||
override fun viewDidLoad() {
|
||||
panel = view.addSubview(View())
|
||||
val background = panel.addSubview(NinePatchView(NinePatchTexture.PANEL_BG))
|
||||
val label = panel.addSubview(Label("test label"))
|
||||
|
||||
createConstraints {
|
||||
panel.widthAnchor equalTo (view.widthAnchor - 40)
|
||||
panel.heightAnchor equalTo (view.heightAnchor - 40)
|
||||
panel.centerXAnchor equalTo view.centerXAnchor
|
||||
panel.centerYAnchor equalTo view.centerYAnchor
|
||||
|
||||
background.leftAnchor equalTo panel.leftAnchor
|
||||
background.rightAnchor equalTo panel.rightAnchor
|
||||
background.topAnchor equalTo panel.topAnchor
|
||||
background.bottomAnchor equalTo panel.bottomAnchor
|
||||
|
||||
label.centerXAnchor equalTo view.centerXAnchor
|
||||
label.centerYAnchor equalTo view.centerYAnchor
|
||||
}
|
||||
|
||||
createProgramView()
|
||||
}
|
||||
|
||||
private fun createProgramView() {
|
||||
val program = managerBlockEntity.program
|
||||
|
||||
program.blocks.forEach {
|
||||
val blockView = panel.addSubview(View())
|
||||
blockView.backgroundColor = Color.BLACK
|
||||
val title = blockView.addSubview(Label(it.javaClass.simpleName))
|
||||
|
||||
createConstraints {
|
||||
blockView.widthAnchor equalTo (title.widthAnchor + 8)
|
||||
blockView.heightAnchor equalTo (title.heightAnchor + 8)
|
||||
blockView.leftAnchor equalTo (panel.leftAnchor + 4 + it.position.x)
|
||||
blockView.topAnchor equalTo (panel.topAnchor + 4 + it.position.y)
|
||||
|
||||
title.leftAnchor equalTo (blockView.leftAnchor + 4)
|
||||
title.topAnchor equalTo (blockView.topAnchor + 4)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
package net.shadowfacts.asmr.util
|
||||
|
||||
import net.minecraft.util.Identifier
|
||||
import net.minecraft.util.registry.Registry
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
fun <T> Registry<T>.register(obj: T, identifier: Identifier) {
|
||||
Registry.register(this, identifier, obj)
|
||||
}
|
|
@ -13,14 +13,12 @@ class ProgramTests {
|
|||
@Test
|
||||
fun testExecutionFlow() {
|
||||
val program = Program()
|
||||
val one = ConstantBlock(ProgramType.int, 3)
|
||||
program.blocks.add(one)
|
||||
val two = ConstantBlock(ProgramType.int, 7)
|
||||
program.blocks.add(two)
|
||||
val multiply = BinaryOperatorBlock(ProgramType.int, BinaryOperatorBlock.Operation.multiply)
|
||||
multiply.left.source = one.output
|
||||
multiply.right.source = two.output
|
||||
program.blocks.add(multiply)
|
||||
val one = program.addBlock(ConstantBlock(ProgramType.INT, 3))
|
||||
val two = program.addBlock(ConstantBlock(ProgramType.INT, 7))
|
||||
val multiply = program.addBlock(BinaryOperatorBlock(ProgramType.INT, BinaryOperatorBlock.Operation.MULTIPLY)) {
|
||||
it.left.source = one.output
|
||||
it.right.source = two.output
|
||||
}
|
||||
|
||||
program.startBlock.nextExecutableBlock = multiply
|
||||
|
||||
|
|
Loading…
Reference in New Issue