Android Studioで応用範囲の広いゲームのひな形みたいなものを作りたくてただ背景が動くだけのものを作ってみました
まずres/drawableに画像を用意
いつものように『いらすとや』さんからお借りしてます
www.irasutoya.com
次にactivity_main.xmlの編集
画面全体をSurfaceViewにします
<?xml version="1.0" encoding="utf-8"?> <androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> <SurfaceView android:id="@+id/surfaceview" android:layout_width="match_parent" android:layout_height="match_parent" app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintHorizontal_bias="0.0" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="1.0" /> </androidx.constraintlayout.widget.ConstraintLayout>
次にMainActivity.ktの編集
import android.content.Context import android.content.res.Resources import android.graphics.Bitmap import android.graphics.BitmapFactory import android.graphics.Canvas import android.os.Bundle import android.util.DisplayMetrics import android.view.SurfaceHolder import android.view.SurfaceView import android.view.WindowManager import androidx.appcompat.app.AppCompatActivity var SCREEN_WIDTH = 0 var SCREEN_HEIGHT = 0 var isRunning = false class MainActivity : AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) val surfaceView: SurfaceView = findViewById(R.id.surfaceview) PlayView(this, surfaceView) //SurfaceViewのインスタンスを生成 GetScreenSize(this) //スクリーンサイズの取得 } //スクリーンサイズの取得 fun GetScreenSize(context: Context) { val vm: WindowManager = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager val display = vm.defaultDisplay val metric = DisplayMetrics() display.getMetrics(metric) SCREEN_WIDTH = metric.widthPixels SCREEN_HEIGHT = metric.heightPixels } } // SurfaceViewを継承したクラス class PlayView: SurfaceView, SurfaceHolder.Callback { private var surfaceHolder: SurfaceHolder? = null constructor(context: Context, surfaceView: SurfaceView) : super(context) { surfaceHolder = surfaceView.holder // コールバック surfaceHolder!!.addCallback(this) } override fun surfaceCreated(p0: SurfaceHolder) { val playgame = PlayGame(surfaceHolder!!, resources) //ゲームスタート isRunning = true playgame.start() } override fun surfaceChanged(p0: SurfaceHolder, p1: Int, p2: Int, p3: Int) { } override fun surfaceDestroyed(p0: SurfaceHolder) { } } //ゲームのThreadクラス class PlayGame:Thread{ private var holder : SurfaceHolder private var resources : Resources private var backBitmap : Bitmap private var backPosx = 0 private var backPosy = 0 constructor(holder: SurfaceHolder, resources: Resources) { this.holder = holder this.resources = resources backBitmap = BitmapFactory.decodeResource(resources, R.drawable.sougen) } override fun run() { while(isRunning){ if(holder == null) return val canvas = holder.lockCanvas() if(canvas != null){ try { synchronized(holder){ BackGround(canvas) //背景を表示 //////// 新しい関数を追加 ///////// } } finally { holder.unlockCanvasAndPost(canvas) } } } } private fun BackGround(canvas: Canvas){ val backVelocity = 5 //背景の移動速度 backPosx= backPosx - backVelocity if(backPosx < -backBitmap.width){ backPosx = 0 } canvas.drawBitmap(backBitmap,backPosx.toFloat(),backPosy.toFloat(),null) //背景をloop表示 if(backPosx < -(backBitmap.width-SCREEN_WIDTH) || backBitmap.width < SCREEN_WIDTH) { canvas.drawBitmap(backBitmap,(backPosx + backBitmap.width).toFloat(), backPosy.toFloat(),null) canvas.drawBitmap(backBitmap,(backPosx + backBitmap.width*2).toFloat(), backPosy.toFloat(),null) } } }
あとは画面を横に固定します
everydayisagoodday.hatenadiary.com
実行すると
新しい機能を付けたいときは関数を作ってPlayGameクラスの新しい関数を追加のところで呼べばOKです