From f1cece106436208d02788818c7aa88ce9acf1aa8 Mon Sep 17 00:00:00 2001 From: minjaesong Date: Tue, 10 Aug 2021 16:56:22 +0900 Subject: [PATCH] multiblock fixtures can now emit/consume multiple wiring types --- .../terrarum/gameworld/WorldSimulator.kt | 30 +++++++++++++++---- .../modulebasegame/gameactors/FixtureBase.kt | 20 +++++++++---- .../gameactors/FixtureLogicSignalEmitter.kt | 15 ++++++---- 3 files changed, 49 insertions(+), 16 deletions(-) diff --git a/src/net/torvald/terrarum/gameworld/WorldSimulator.kt b/src/net/torvald/terrarum/gameworld/WorldSimulator.kt index e8fdfea38..7bcfcaa1b 100644 --- a/src/net/torvald/terrarum/gameworld/WorldSimulator.kt +++ b/src/net/torvald/terrarum/gameworld/WorldSimulator.kt @@ -11,10 +11,12 @@ import net.torvald.terrarum.gamecontroller.KeyToggler import net.torvald.terrarum.gameitem.ItemID import net.torvald.terrarum.modulebasegame.TerrarumIngame.Companion.inUpdateRange import net.torvald.terrarum.modulebasegame.gameactors.ActorHumanoid +import net.torvald.terrarum.modulebasegame.gameactors.BlockBoxIndex +import net.torvald.terrarum.modulebasegame.gameactors.Electric import net.torvald.terrarum.modulebasegame.gameactors.FixtureBase -import net.torvald.terrarum.worlddrawer.BlocksDrawer -import net.torvald.terrarum.worlddrawer.WorldCamera import org.khelekore.prtree.* +import java.util.* +import kotlin.collections.ArrayList import kotlin.math.roundToInt /** @@ -453,16 +455,34 @@ object WorldSimulator { private val wiresimOverscan = 60 + /** + * @return List of FixtureBases, safe to cast into Electric + */ private fun wiresimGetSourceBlocks(): List = Terrarum.ingame!!.actorContainerActive.filter { - it is FixtureBase && it.inUpdateRange(world) && it.wireEmitterType.isNotBlank() + it is FixtureBase && it is Electric && it.inUpdateRange(world) && it.wireEmitterTypes.isNotEmpty() } as List private fun simulateWires(delta: Float) { wiresimGetSourceBlocks().let { sources -> // signal-emitting fixtures must set emitState of its own tiles via update() sources.forEach { - // TODO + (it as Electric).wireEmitterTypes.forEach { wireType, bbi -> + traverseWireGraph(world, it, wireType, bbi) + } + } + } + } + + private fun traverseWireGraph(world: GameWorld, fixture: FixtureBase, wireType: String, bbi: BlockBoxIndex) { + fixture.worldBlockPos?.let { + val branchesVisited = ArrayList() + val branchingStack = Stack() + val startPoint = it + fixture.blockBoxIndexToPoint2i(bbi) + branchingStack.push(startPoint) + + while (branchingStack.isNotEmpty()) { + } } } @@ -487,7 +507,7 @@ object WorldSimulator { WireConStatus.BRANCH // 1111 ) - data class wireGraphBranch( + data class WireGraphBranch( val x: Int, val y: Int, val con: Byte diff --git a/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureBase.kt b/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureBase.kt index 24598576f..d2aebb883 100644 --- a/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureBase.kt +++ b/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureBase.kt @@ -14,6 +14,14 @@ import net.torvald.terrarum.gameworld.GameWorld import net.torvald.terrarum.ui.UICanvas import org.dyn4j.geometry.Vector2 +typealias BlockBoxIndex = Int + +interface Electric { + val wireEmitterTypes: HashMap + val wireEmission: HashMap + val wireConsumption: HashMap +} + /** * Created by minjaesong on 2016-06-17. */ @@ -29,15 +37,15 @@ open class FixtureBase( var blockBox: BlockBox = blockBox0 protected set // something like TapestryObject will want to redefine this + fun blockBoxIndexToPoint2i(it: BlockBoxIndex): Point2i = this.blockBox.width.let { w -> Point2i(it % w, it / w) } + + - open val wireEmitterType = "" - open val wireEmission = Vector2() - open val wireConsumption = Vector2() - /** - * Block-wise position of this fixture when it's placed on the world. Null if it's not on the world + * Tile-wise position of this fixture when it's placed on the world, top-left origin. Null if it's not on the world */ - protected var worldBlockPos: Point2i? = null + var worldBlockPos: Point2i? = null + private set init { if (mainUI != null) diff --git a/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureLogicSignalEmitter.kt b/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureLogicSignalEmitter.kt index 8716a1125..75ae89c9d 100644 --- a/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureLogicSignalEmitter.kt +++ b/src/net/torvald/terrarum/modulebasegame/gameactors/FixtureLogicSignalEmitter.kt @@ -7,10 +7,12 @@ import net.torvald.terrarum.gameactors.AVKey import net.torvald.terrarumsansbitmap.gdx.TextureRegionPack import org.dyn4j.geometry.Vector2 -class FixtureLogicSignalEmitter(nameFun: () -> String) : FixtureBase(BlockBox(BlockBox.NO_COLLISION, 1, 1), nameFun = nameFun) { +class FixtureLogicSignalEmitter(nameFun: () -> String) + : FixtureBase(BlockBox(BlockBox.NO_COLLISION, 1, 1), nameFun = nameFun), Electric { - override val wireEmitterType = "digital_bit" - override val wireEmission = Vector2(1.0, 0.0) + override val wireEmitterTypes: HashMap = HashMap() + override val wireEmission: HashMap = HashMap() + override val wireConsumption: HashMap = HashMap() init { density = 1400.0 @@ -20,6 +22,9 @@ class FixtureLogicSignalEmitter(nameFun: () -> String) : FixtureBase(BlockBox(Bl sprite!!.setRowsAndFrames(1, 1) actorValue[AVKey.BASEMASS] = MASS + + wireEmitterTypes["digital_bit"] = 0 + wireEmission[0] = Vector2(1.0, 0.0) } override fun dispose() { } @@ -31,8 +36,8 @@ class FixtureLogicSignalEmitter(nameFun: () -> String) : FixtureBase(BlockBox(Bl override fun update(delta: Float) { // set emit worldBlockPos?.let { (x, y) -> - WireCodex.getAll().filter { it.renderClass == "signal" }.forEach { prop -> - world?.setWireEmitStateOf(x, y, prop.id, wireEmission) + WireCodex.getAll().filter { it.accepts == "digital_bit" }.forEach { prop -> + world?.setWireEmitStateOf(x, y, prop.id, wireEmission[0]!!) } } }