DEADSOFTWARE

New blocks structure
authorfredboy <fredboy@protonmail.com>
Sat, 20 Apr 2024 08:14:44 +0000 (15:14 +0700)
committerfredboy <fredboy@protonmail.com>
Sat, 20 Apr 2024 08:22:46 +0000 (15:22 +0700)
15 files changed:
android/assets/json/game_items.json
core/src/ru/deadsoftware/cavedroid/game/GameItems.java
core/src/ru/deadsoftware/cavedroid/game/GameRenderer.java
core/src/ru/deadsoftware/cavedroid/game/actions/updateblock/UpdateGrassAction.kt
core/src/ru/deadsoftware/cavedroid/game/actions/useitem/PlaceBlockItemToBackgroundAction.kt
core/src/ru/deadsoftware/cavedroid/game/actions/useitem/PlaceBlockItemToForegroundAction.kt
core/src/ru/deadsoftware/cavedroid/game/model/block/Block.kt [new file with mode: 0644]
core/src/ru/deadsoftware/cavedroid/game/model/block/BlockAnimationInfo.kt [new file with mode: 0644]
core/src/ru/deadsoftware/cavedroid/game/model/block/BlockDropInfo.kt [new file with mode: 0644]
core/src/ru/deadsoftware/cavedroid/game/model/block/BlockMargins.kt [new file with mode: 0644]
core/src/ru/deadsoftware/cavedroid/game/model/block/CommonBlockParams.kt [new file with mode: 0644]
core/src/ru/deadsoftware/cavedroid/game/objects/Block.kt [deleted file]
core/src/ru/deadsoftware/cavedroid/game/objects/Item.kt
core/src/ru/deadsoftware/cavedroid/game/world/GameWorld.java
core/src/ru/deadsoftware/cavedroid/game/world/GameWorldBlocksLogicControllerTask.kt

index 97e4106ceb6fc15230ae1549ed739c5e24d69f99..48b612fa88543a925313c8310f3a5290cd41408e 100644 (file)
@@ -27,7 +27,8 @@
       "top": 8,
       "sprite_top": 8,
       "meta": "slab",
-      "transparent": true
+      "transparent": true,
+      "full_block": "bricks"
     },
     "bricks": {
       "hp": 600,
index eeeeb115da03fad2112abe5b96682373251d083f..8392efdb786602ca0e874d11ce185895ca74c494 100644 (file)
@@ -7,7 +7,7 @@ import com.badlogic.gdx.math.MathUtils;
 import com.badlogic.gdx.utils.ArrayMap;
 import com.badlogic.gdx.utils.GdxRuntimeException;
 import com.badlogic.gdx.utils.JsonValue;
-import ru.deadsoftware.cavedroid.game.objects.Block;
+import ru.deadsoftware.cavedroid.game.model.block.*;
 import ru.deadsoftware.cavedroid.game.objects.Item;
 import ru.deadsoftware.cavedroid.misc.Assets;
 import ru.deadsoftware.cavedroid.misc.utils.AssetLoader;
@@ -33,20 +33,24 @@ public class GameItems {
         return isWater(getBlock(id));
     }
 
+    @Deprecated
     public static boolean isWater(Block block) {
-        return block.getMeta().equals("water");
+        return block instanceof Block.Water;
     }
 
+    @Deprecated
     public static boolean isLava(int id) {
         return isLava(getBlock(id));
     }
 
+    @Deprecated
     public static boolean isLava(Block block) {
-        return block.getMeta().equals("lava");
+        return block instanceof Block.Lava;
     }
 
+    @Deprecated
     public static boolean isSlab(int id) {
-        return getBlock(id).getMeta().equals("slab");
+        return getBlock(id) instanceof Block.Slab;
     }
 
     public static boolean fluidCanFlowThere(int thisId, int thatId) {
@@ -114,7 +118,7 @@ public class GameItems {
     public static void load(AssetLoader assetLoader) {
         JsonValue json = Assets.jsonReader.parse(assetLoader.getAssetHandle("json/game_items.json"));
 
-        TreeSet<Block> blocksSet = new TreeSet<>(Comparator.comparingInt(Block::getId));
+        TreeSet<Block> blocksSet = new TreeSet<>(Comparator.comparingInt(a -> a.getParams().getId()));
         TreeSet<Item> itemsSet = new TreeSet<>(Comparator.comparingInt(Item::getId));
 
 
@@ -144,6 +148,7 @@ public class GameItems {
                 boolean animated = Assets.getBooleanFromJson(block, "animated", false);
                 int frames = Assets.getIntFromJson(block, "frames", 0);
                 int id = Assets.getIntFromJson(block, "id", count);
+                int dropCount = Assets.getIntFromJson(block, "drop_count", 1);
                 String fullBlock = Assets.getStringFromJson(block, "full_block", null);
                 blocksIds.put(key, id);
 
@@ -151,30 +156,37 @@ public class GameItems {
                     count++;
                 }
 
-                Block newBlock = new Block(
+                BlockMargins collMargins = new BlockMargins(left, top, right, bottom);
+                BlockMargins spriteMargins = new BlockMargins(clipX, clipY, clipWidth, clipHeight);
+                BlockDropInfo dropInfo = new BlockDropInfo(drop, dropCount);
+                BlockAnimationInfo animInfo = null;
+                if (animated) {
+                    animInfo = new BlockAnimationInfo(frames);
+                }
+
+                CommonBlockParams params = new CommonBlockParams(
                         id,
                         key,
-                        left,
-                        top,
-                        right,
-                        bottom,
+                        collMargins,
                         hp,
-                        drop,
+                        dropInfo,
                         collision,
                         background,
                         transparent,
                         requiresBlock,
-                        fluid,
-                        meta,
+                        animInfo,
                         texture,
-                        animated,
-                        frames,
-                        clipX,
-                        clipY,
-                        clipWidth,
-                        clipHeight,
-                        fullBlock
+                        spriteMargins
                 );
+
+                Block newBlock = switch (meta) {
+                    case "water" -> new Block.Water(params, 5);
+                    case "lava" -> new Block.Lava(params, 5);
+                    case "slab" -> new Block.Slab(params, fullBlock);
+                    default -> new Block.Normal(params);
+                };
+
+                newBlock.initialize();
                 blocksSet.add(newBlock);
             } catch (GdxRuntimeException e) {
                 Gdx.app.error(TAG, e.getMessage());
@@ -212,7 +224,7 @@ public class GameItems {
             }
         }
 
-        blocksSet.forEach((block -> blocks.put(block.getKey(), block)));
+        blocksSet.forEach((block -> blocks.put(block.getParams().getKey(), block)));
         itemsSet.forEach((item -> items.put(item.getKey(), item)));
     }
 
index ca9cf8b392c231dfc564ef3120eff9ba90469ec2..06e9b624fae8fd2570fae96e342eeb8fe0e2e646 100644 (file)
@@ -15,7 +15,7 @@ import ru.deadsoftware.cavedroid.MainConfig;
 import ru.deadsoftware.cavedroid.game.mobs.Mob;
 import ru.deadsoftware.cavedroid.game.mobs.MobsController;
 import ru.deadsoftware.cavedroid.game.mobs.Player;
-import ru.deadsoftware.cavedroid.game.objects.Block;
+import ru.deadsoftware.cavedroid.game.model.block.Block;
 import ru.deadsoftware.cavedroid.game.objects.Drop;
 import ru.deadsoftware.cavedroid.game.objects.DropController;
 import ru.deadsoftware.cavedroid.game.objects.Item;
index a50c541c9d5df9738e1fd767e1df406cfc775b92..a9397c9ef0e58d0aa26edc9d222cdb3a5141b26f 100644 (file)
@@ -12,7 +12,7 @@ class UpdateGrassAction @Inject constructor(
 
     override fun update(x: Int, y: Int) {
         val blockOnTop = gameWorld.getForeMapBlock(x, y - 1)
-        if (blockOnTop.collision || blockOnTop.fluid) {
+        if (blockOnTop.collision || blockOnTop.isFluid()) {
             gameWorld.setForeMap(x, y, GameItems.getBlockId("dirt"))
         }
     }
index 43eefc98e156bf73d6eb13b8da1338889b4aff9b..e4af8df316ebf58d83e10ecdc28da1aabc3980a6 100644 (file)
@@ -13,7 +13,7 @@ class PlaceBlockItemToBackgroundAction @Inject constructor(
     override fun perform(item: Item, x: Int, y: Int) {
         val block = item.toBlock()
         requireNotNull(block) { "error: trying to place non block item" }
-        gameWorld.placeToBackground(x, y, block.id)
+        gameWorld.placeToBackground(x, y, block.params.id)
     }
 
     companion object {
index 473250e1fd8046508c19043c7c3a3c7a6f79c4d6..978eb00aaf421f7c41f00338a8a2c804e15f99b5 100644 (file)
@@ -13,7 +13,7 @@ class PlaceBlockItemToForegroundAction @Inject constructor(
     override fun perform(item: Item, x: Int, y: Int) {
         val block = item.toBlock()
         requireNotNull(block) { "error: trying to place non block item" }
-        gameWorld.placeToForeground(x, y, block.id)
+        gameWorld.placeToForeground(x, y, block.params.id)
     }
 
     companion object {
diff --git a/core/src/ru/deadsoftware/cavedroid/game/model/block/Block.kt b/core/src/ru/deadsoftware/cavedroid/game/model/block/Block.kt
new file mode 100644 (file)
index 0000000..440d258
--- /dev/null
@@ -0,0 +1,154 @@
+package ru.deadsoftware.cavedroid.game.model.block
+
+import com.badlogic.gdx.graphics.g2d.Sprite
+import com.badlogic.gdx.graphics.g2d.SpriteBatch
+import com.badlogic.gdx.math.Rectangle
+import com.badlogic.gdx.utils.TimeUtils
+import kotlin.contracts.ExperimentalContracts
+import kotlin.contracts.contract
+
+@OptIn(ExperimentalContracts::class)
+sealed class Block {
+
+    abstract val params: CommonBlockParams
+
+    val width: Float get() = 16f - params.collisionMargins.left - params.collisionMargins.right
+    val height: Float get() = 16f - params.collisionMargins.top - params.collisionMargins.bottom
+
+    private val spriteWidth: Float get() = 16f - params.spriteMargins.left - params.spriteMargins.right
+    private val spriteHeight: Float get() = 16f - params.spriteMargins.top - params.spriteMargins.bottom
+
+    private var animation: Array<Sprite>? = null
+
+    private var sprite: Sprite? = null
+        get() {
+            return animation?.get(currentAnimationFrame) ?: field
+        }
+
+    private val currentAnimationFrame: Int
+        get() {
+            return params.animationInfo?.let { animInfo ->
+                ((TimeUtils.millis() / ANIMATION_FRAME_DURATION_MS) % animInfo.framesCount).toInt()
+            } ?: 0
+        }
+
+    fun initialize() {
+        initAnimation()
+        initSprite()
+    }
+
+    private fun initAnimation() {
+        animation = params.animationInfo?.let { animInfo ->
+            requireNotNull(params.texture) { "Cannot derive animation frames from null sprite" }
+            Array(animInfo.framesCount) { y ->
+                val width = 16 - params.spriteMargins.left - params.spriteMargins.right
+                val height = 16 - params.spriteMargins.top - params.spriteMargins.bottom
+                Sprite(params.texture, params.spriteMargins.left, 16 * y + params.spriteMargins.top, width, height)
+                    .apply { flip(false, true) }
+            }
+        }
+    }
+
+    private fun initSprite() {
+        sprite = animation?.get(0) ?: params.texture?.let { tex ->
+            val width = 16 - params.spriteMargins.left - params.spriteMargins.right
+            val height = 16 - params.spriteMargins.top - params.spriteMargins.bottom
+            Sprite(tex, params.spriteMargins.left, params.spriteMargins.top, width, height)
+                .apply { flip(false, true) }
+        }
+    }
+
+    fun requireSprite() = requireNotNull(sprite)
+
+    fun draw(spriter: SpriteBatch, x: Float, y: Float) {
+        sprite?.apply {
+            setBounds(
+                /* x = */ x + params.spriteMargins.left,
+                /* y = */ y + params.spriteMargins.top,
+                /* width = */ spriteWidth,
+                /* height = */ spriteHeight
+            )
+            draw(spriter)
+        }
+    }
+    
+    fun isFluid(): Boolean {
+        contract { returns(true) implies (this@Block is Fluid) }
+        return this is Fluid
+    }
+
+    fun isWater(): Boolean {
+        contract { returns(true) implies (this@Block is Water) }
+        return this is Water
+    }
+
+    fun isLava(): Boolean {
+        contract { returns(true) implies (this@Block is Lava) }
+        return this is Lava
+    }
+
+    fun isSlab(): Boolean {
+        contract { returns(true) implies (this@Block is Slab) }
+        return this is Slab
+    }
+
+    fun getRectangle(x: Int, y: Int): Rectangle {
+        return Rectangle(
+            /* x = */ x * 16f + params.collisionMargins.left,
+            /* y = */ y * 16f + params.collisionMargins.top,
+            /* width = */ width,
+            /* height = */ height
+        )
+    }
+
+
+
+    data class Normal(
+        override val params: CommonBlockParams,
+    ) : Block()
+
+    data class Slab(
+        override val params: CommonBlockParams,
+        val fullBlockKey: String,
+    ): Block()
+
+    abstract class Fluid: Block() {
+        abstract val statesCount: Int
+    }
+    
+    data class Water(
+        override val params: CommonBlockParams,
+        override val statesCount: Int
+    ) : Fluid()
+
+    data class Lava(
+        override val params: CommonBlockParams,
+        override val statesCount: Int
+    ) : Fluid()
+
+    /* Legacy accessors below */
+
+    // collision margins
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val left: Int get() = params.collisionMargins.left
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val right: Int get() = params.collisionMargins.left
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val top: Int get() = params.collisionMargins.left
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val bottom: Int get() = params.collisionMargins.left
+    
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val hp: Int get() = params.hitPoints
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val collision: Boolean get() = params.hasCollision
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val animated: Boolean get() = params.animationInfo != null
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val frames: Int get() = params.animationInfo?.framesCount ?: 0
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) val drop: String get() = params.dropInfo?.itemKey ?: "none"
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun hasDrop() = params.dropInfo != null
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun toJump() = params.hasCollision && params.collisionMargins.top < 8
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun hasCollision() = params.hasCollision
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun isBackground() = params.isBackground
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun isTransparent() = params.isTransparent
+    @Deprecated(LEGACY_ACCESSOR_DEPRECATION) fun getTexture() = sprite
+
+
+    companion object {
+        private const val LEGACY_ACCESSOR_DEPRECATION = "legacy accessors will be removed"
+        private const val ANIMATION_FRAME_DURATION_MS = 100L
+    }
+}
\ No newline at end of file
diff --git a/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockAnimationInfo.kt b/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockAnimationInfo.kt
new file mode 100644 (file)
index 0000000..8d25189
--- /dev/null
@@ -0,0 +1,5 @@
+package ru.deadsoftware.cavedroid.game.model.block
+
+data class BlockAnimationInfo(
+    val framesCount: Int
+)
diff --git a/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockDropInfo.kt b/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockDropInfo.kt
new file mode 100644 (file)
index 0000000..62df2f3
--- /dev/null
@@ -0,0 +1,6 @@
+package ru.deadsoftware.cavedroid.game.model.block
+
+data class BlockDropInfo(
+    val itemKey: String,
+    val count: Int,
+)
diff --git a/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockMargins.kt b/core/src/ru/deadsoftware/cavedroid/game/model/block/BlockMargins.kt
new file mode 100644 (file)
index 0000000..dbd2999
--- /dev/null
@@ -0,0 +1,15 @@
+package ru.deadsoftware.cavedroid.game.model.block
+
+data class BlockMargins(
+    val left: Int,
+    val top: Int,
+    val right: Int,
+    val bottom: Int
+) {
+
+    init {
+        assert(left + right < 16)
+        assert(top + bottom < 16)
+    }
+
+}
diff --git a/core/src/ru/deadsoftware/cavedroid/game/model/block/CommonBlockParams.kt b/core/src/ru/deadsoftware/cavedroid/game/model/block/CommonBlockParams.kt
new file mode 100644 (file)
index 0000000..2f4de93
--- /dev/null
@@ -0,0 +1,22 @@
+package ru.deadsoftware.cavedroid.game.model.block
+
+import com.badlogic.gdx.graphics.Texture
+
+data class CommonBlockParams(
+    @Deprecated(ID_DEPRECATION_MESSAGE) val id: Int,
+    val key: String,
+    val collisionMargins: BlockMargins,
+    val hitPoints: Int,
+    val dropInfo: BlockDropInfo?,
+    val hasCollision: Boolean,
+    val isBackground: Boolean,
+    val isTransparent: Boolean,
+    val requiresBlock: Boolean,
+    val animationInfo: BlockAnimationInfo?,
+    val texture: Texture?,
+    val spriteMargins: BlockMargins,
+) {
+    companion object {
+        private const val ID_DEPRECATION_MESSAGE = "numeric id's will be removed"
+    }
+}
diff --git a/core/src/ru/deadsoftware/cavedroid/game/objects/Block.kt b/core/src/ru/deadsoftware/cavedroid/game/objects/Block.kt
deleted file mode 100644 (file)
index 020caf5..0000000
+++ /dev/null
@@ -1,151 +0,0 @@
-@file:Suppress("DeprecatedCallableAddReplaceWith")
-
-package ru.deadsoftware.cavedroid.game.objects
-
-import com.badlogic.gdx.graphics.Texture
-import com.badlogic.gdx.graphics.g2d.Sprite
-import com.badlogic.gdx.graphics.g2d.SpriteBatch
-import com.badlogic.gdx.math.Rectangle
-import ru.deadsoftware.cavedroid.game.GameItems
-
-private const val ANIMATION_FRAME_DURATION = 100L
-private const val DEPRECATION_MESSAGE =
-        "Deprecated since moved to Kotlin. Use generated getter or kotlin property access."
-
-/**
- * @param left          margin from left edge
- * @param top           margin from top edge
- * @param right         margin from right edge
- * @param bottom        margin from bottom edge
- * @param hp            hit points
- * @param drop          id of an item the block will drop when destroyed
- * @param collision     true if block has collision
- * @param background    true if block should be drawn behind player
- * @param transparent   true if block is transparent and renderer should draw a block behind it
- * @param requiresBlock true if block should break when there is no block with collision under it
- * @param fluid         true if fluid
- * @param meta          extra info for storing
- * @param texture       block's texture
- * @param animated      indicates if block has animation
- * @param frames        number of animation frames. ignored if animated is false
- * @param spriteLeft    block's sprite x on texture
- * @param spriteTop     block's sprite y on texture
- * @param spriteRight   block's sprite right edge on texture
- * @param spriteBottom  block's sprite bottom on texture
- * @param fullBlockKey for slabs. block for two slabs of one kind
- */
-data class Block(
-        val id: Int,
-        val key: String,
-        val left: Int,
-        val top: Int,
-        val right: Int,
-        val bottom: Int,
-        val hp: Int,
-        val drop: String,
-        val collision: Boolean,
-        val background: Boolean,
-        val transparent: Boolean,
-        val requiresBlock: Boolean,
-        val fluid: Boolean,
-        val meta: String,
-        private val texture: Texture?,
-        val animated: Boolean,
-        val frames: Int,
-        private val spriteLeft: Int,
-        private val spriteTop: Int,
-        private val spriteRight: Int,
-        private val spriteBottom: Int,
-        val fullBlockKey: String?,
-) {
-
-    val width = 16 - right - left
-    val height = 16 - top - bottom
-
-    private val spriteWidth = 16 - spriteLeft - spriteRight
-    private val spriteHeight = 16 - spriteTop - spriteBottom
-
-    private val sprite: Sprite?
-        get() {
-            return if (animated) {
-                animation[currentFrame()]
-            } else {
-                field
-            }
-        }
-
-
-    private val animation: Array<Sprite>
-
-    init {
-        if (frames !in 0..Int.MAX_VALUE) {
-            throw IllegalArgumentException("Animation frames must be in range [0, ${Int.MAX_VALUE}]")
-        }
-
-        animation = if (animated) {
-            if (texture == null) {
-                throw IllegalArgumentException("Cannot derive animation frames from null sprite")
-            }
-            Array(frames) { y ->
-                Sprite(texture, spriteLeft, 16 * y + spriteTop, spriteWidth, spriteHeight).apply {
-                    flip(false, true)
-                }
-            }
-        } else {
-            emptyArray()
-        }
-
-        sprite = if (animated) { animation[0] } else {
-            if (texture != null) {
-                Sprite(texture, spriteLeft, spriteTop, spriteWidth, spriteHeight).apply {
-                    flip(false, true)
-                }
-            } else {
-                null
-            }
-        }
-    }
-
-    private fun currentFrame() = if (animated) {
-        ((System.currentTimeMillis() / ANIMATION_FRAME_DURATION) % frames).toInt()
-    } else {
-        0
-    }
-
-    fun requireSprite() = sprite ?: throw IllegalStateException("Sprite is null")
-
-    fun draw(spriter: SpriteBatch, x: Float, y: Float) {
-        requireSprite().apply {
-            setBounds(x + spriteLeft, y + spriteTop, spriteWidth.toFloat(), spriteHeight.toFloat())
-            draw(spriter)
-        }
-    }
-
-    fun getRectangle(x: Int, y: Int) =
-            Rectangle(x * 16f + left, y * 16f + this.top, width.toFloat(), height.toFloat())
-
-    fun hasDrop() = drop != "none"
-
-    fun toJump() = top < 8 && collision
-
-    fun getItem() = GameItems.getItem(GameItems.getBlockKey(id))
-
-    @Deprecated(DEPRECATION_MESSAGE)
-    fun hasCollision() = collision
-
-    @Deprecated(DEPRECATION_MESSAGE)
-    fun isBackground() = background
-
-    @Deprecated(DEPRECATION_MESSAGE)
-    fun isTransparent() = transparent
-
-    @Deprecated(DEPRECATION_MESSAGE)
-    fun isFluid() = fluid
-
-    @Deprecated(DEPRECATION_MESSAGE)
-    fun requiresBlock() = requiresBlock
-
-    @Deprecated("Was renamed to Sprite to comply with variable type.", ReplaceWith("requireSprite()"))
-    fun getTexture() = sprite
-
-}
\ No newline at end of file
index a4c41b0424d62342a42ff00838f2bada8e594623..a2dbfc55bece093129d9a8d5103606705b95d54c 100644 (file)
@@ -2,6 +2,7 @@ package ru.deadsoftware.cavedroid.game.objects
 
 import com.badlogic.gdx.graphics.g2d.Sprite
 import ru.deadsoftware.cavedroid.game.GameItems
+import ru.deadsoftware.cavedroid.game.model.block.Block
 import ru.deadsoftware.cavedroid.misc.utils.SpriteOrigin
 
 data class Item(
index 797e670033ebe4f2abadad58fa96b41cf88b8576..d4a66bcb8ad622ca43193d9df7f9cdb95d24d020 100644 (file)
@@ -4,8 +4,8 @@ import kotlin.Pair;
 import ru.deadsoftware.cavedroid.game.GameItems;
 import ru.deadsoftware.cavedroid.game.GameScope;
 import ru.deadsoftware.cavedroid.game.mobs.MobsController;
+import ru.deadsoftware.cavedroid.game.model.block.Block;
 import ru.deadsoftware.cavedroid.game.model.world.generator.WorldGeneratorConfig;
-import ru.deadsoftware.cavedroid.game.objects.Block;
 import ru.deadsoftware.cavedroid.game.objects.DropController;
 
 import javax.annotation.CheckForNull;
@@ -139,8 +139,8 @@ public class GameWorld {
             setForeMap(x, y, value);
         } else if (GameItems.isSlab(value) && getForeMap(x, y) == value) {
             final Block block = GameItems.getBlock(value);
-            if (block.getFullBlockKey() != null) {
-                setForeMap(x, y, GameItems.getBlockId(block.getFullBlockKey()));
+            if (block instanceof Block.Slab) {
+                setForeMap(x, y, GameItems.getBlockId(((Block.Slab) block).getFullBlockKey()));
             }
         }
     }
index 20f992a59fb0b3d07a1b26d47ddd547acf5aec70..c515330d8b51261d55249ab746b25c0c2f2ea3fb 100644 (file)
@@ -1,7 +1,5 @@
 package ru.deadsoftware.cavedroid.game.world
 
-import com.badlogic.gdx.Gdx
-import com.badlogic.gdx.utils.TimeUtils
 import com.badlogic.gdx.utils.Timer.Task
 import ru.deadsoftware.cavedroid.game.GameScope
 import ru.deadsoftware.cavedroid.game.actions.getRequiresBlockAction
@@ -28,9 +26,9 @@ class GameWorldBlocksLogicControllerTask @Inject constructor(
 
     private fun updateBlock(x: Int, y: Int) {
         val block = gameWorld.getForeMapBlock(x, y)
-        val blockKey = block.key
+        val blockKey = block.params.key
         val action = updateBlockActions[blockKey]
-            ?: updateBlockActions.getRequiresBlockAction().takeIf { block.requiresBlock }
+            ?: updateBlockActions.getRequiresBlockAction().takeIf { block.params.requiresBlock }
 
         action?.update(x, y)
     }