Kotlinのサンプルを紹介します ②


前回はプロジェクトの作成からブロックの表示まで実装しました。


今回は機能の実装に取り掛かりたいと思います。

実装する機能はブロックの落下と移動です。


ブロックを落下させる


ブロックを落下させるためにブロックに位置情報を持たせます。
基点の四角形の左上の座標を ブロックの位置情報とします。
Blockクラスに以下のメンバ変数を追加します。

xPos = BLOCKSTARTX
yPos = BLOCKSTARTY


あとはどんなふうに落下させるかですね。
カウントをインクリメントしていき一定の値に達したらブロックを動かすこと(y座標の値を更新)にします。
そのときにカウントをリセットします。
Graphicクラスに以下のメンバ変数を追加します。

var blockSleepCnt = 0


Const.ktに以下のパラメーターを追加します。

val BLOCKDOWNCNT = 50


ブロックのy座標の値を更新する処理です。
この処理をGraphicクラスに追加します。

    private fun drawBlock(canvas: Canvas) {
        blockSleepCnt += 1
        if (blockSleepCnt > BLOCKDOWNCNT) {
            updateBlockPos(0, BLOCKSPACE)
            blockSleepCnt = 0
        }

        block.draw(canvas)
    }

    fun updateBlockPos(x: Int, y: Int) {
        block.updatePos(x,y)

    }


Blockクラスに以下の関数を追加します。

    fun updatePos(x: Int, y:Int) {
        xPos += x
        yPos += y
    }

    fun setPos(x: Int, y: Int) {
        xPos = x
        yPos = y
    }


実行するとこうなります。
それにしてもフィールド小さいな。

ブロックの移動


次はブロックの移動です。
画面をタップすることでブロックを移動できるようにします。
タップした場所によって移動する方向を決定します。
MainActivityを以下のように修正します。

class MainActivity : AppCompatActivity() {

    var graphic: Graphic? = null

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        graphic = Graphic(this)
        setContentView(graphic!!)
    }

    // タップを検知 タップされた場所によって移動方向を決定
    override fun onTouchEvent(event: MotionEvent?): Boolean {
        when(event?.action) {
            MotionEvent.ACTION_DOWN -> {
                val x = event.getX()
                val y = event.getY()
                if (x <= FIELDSTARTX) {
                    graphic?.updateBlockPos(-BLOCKSPACE, 0)
                } else if (x >= FIELDSTARTX+FIELDWIDTH) {
                    graphic?.updateBlockPos(BLOCKSPACE, 0)
                } else if (y >= FIELDSTARTY+ FIELDHEIGHT) {
                    graphic?.updateBlockPos(0, BLOCKSPACE)
                }
            }
        }
        return true
    }
}


実行したらこうなりました。


ブロックの落下と移動を実装できました。
ただこの状態だと移動が無制限のため、この動作をフィールド内に制限する必要があります。
ブロックの位置を計算してフィールドの範囲外かどうかをチェックします。
この機能を次回実装したいと思います。