如何用 Kotlin + 动画 快速实现一款游戏,快速上手!这些日子利用闲暇时间使用Kotlin + 动画开发了一款小游

前言

前些日子开发过一款小游戏,kotlin快速实现一款小游戏,糖果雨来啦,但由于时间的原因,只开发完成了基础版。如今,我对它进行了升级,新增了进阶版与困难版,分享给大家。

成果展示

现在这款游戏包含三个版本,分别为:

基础版:糖果只会在屏幕最上方生成,然后从上往下掉落。 进阶版:糖果只会在屏幕中间生成,然后向四周发散 困难版:糖果会在屏幕四个角随机生成,然后向大致对角方向发散。 基础版进阶版困难版

你可以通过点击糖果捕捉器apk 下载地址github进行下载安装apk来体验一下该游戏。

实现细节

这里关于引导动画的实现,糖果的生成、掉落与收集就不再次展开分析了,具体实现细节请参考上一篇文章kotlin快速实现一款小游戏,糖果雨来啦。

接下里将重点讲解一下进阶版与困难版的实现原理。

进阶版

具体实现主要分为两步:

动态生成一个View,居中展示。 生成随机坐标,计算平移距离。 利用属性动画将View向四周平移出屏幕。

TextView(this).apply { //1. 设置为居中 layoutParams = ConstraintLayout.LayoutParams(tvWidth, tvHeight).apply { bottomToBottom = ConstraintSet.PARENT_ID topToTop = ConstraintSet.PARENT_ID startToStart = ConstraintSet.PARENT_ID endToEnd = ConstraintSet.PARENT_ID } //2. 设置糖果背景 background = ContextCompat.getDrawable(this@AdvancedActivity, generateRandomCandy()) //3. 添加到视图 viewBinding.root.addView(this) }

动态生成一个TextView,设置其属性让其居中,然后设置糖果的背景,并添加到视图中。

在对其添加属性动画前,我们需要为它确定一个随机坐标。这里我们利用获取到的屏幕宽高来随机生成一个屏幕内坐标。

fun generateRandomX(leftRange: Int = 0, rightRange: Int = getScreenWidth()): Int { return (leftRange..rightRange).random() } fun generateRandomY(leftRange: Int = 0, rightRange: Int = getScreenHeight()): Int { return (leftRange..rightRange).random() }

我们将屏幕分成四块,生成的随机坐标点随机分布在这四块区域中。

在确定了随机坐标后,接着我们就需要通过这个随机坐标来计算出需平移的距离。

我们以随机坐标点位于左上方区域来举例:

我们利用相似三角形来确定需要平移的距离,取两个相同大小的三角形来计算:

X轴平移的距离为:halfScreenWidth - x) * -2。 Y轴平移的距离为:(halfScreenHeight - y) * -2。

除了左上区域,剩下的其他三个区域分别为:

右上区域左下区域右下区域

将这四个区域合起来的总的计算方法为:

private fun calculatePosition(x: Int, y: Int): Pair<Int, Int> { //利用相似三角形来确定平移距离,现在是取一个相同大小的相似三角形。 return if (x <= halfScreenWidth) { if (y <= halfScreenHeight) { //left_top Pair((halfScreenWidth - x) * -2, (halfScreenHeight - y) * -2) } else { //left_bottom Pair((halfScreenWidth - x) * -2, (y - halfScreenHeight) * 2) } } else { if (y <= halfScreenHeight) { //right_top Pair((x - halfScreenWidth) * 2, (halfScreenHeight - y) * -2) } else { //right_bottom Pair(((x - halfScreenWidth) * 2).toInt(), (y - halfScreenHeight) * 2) } } }

问题

如上所述,我们利用两个相同的相似三角形来计算平移距离,看起来很美好,但实际调式过程中,发现很多时候糖果无法平移出手机屏幕,因为平移的距离不够。

像这种情况,即使我们用了两个相同的相似三角形来计算平移距离,平移距离还是不够,造成糖果无法平移出手机屏幕。

那怎么办呢?

这里我们采取一个递归算法,来保证我们计算出的平移距离能够支持糖果平移出屏幕。

/** * 取一个相同大小的三角形的话,还是有可能平移不出屏幕,应该避免这个情况 */ private fun checkTransitionXy(transitionXyPair: Pair<Int, Int>): Pair<Int, Int> { //递归的终止条件 if (transitionXyPair.first.absoluteValue > (halfScreenWidth + tvWidth) || transitionXyPair.second.absoluteValue > (halfScreenHeight + tvHeight) ) { return transitionXyPair } return checkTransitionXy( Pair( (transitionXyPair.first * 1.1).toInt(), (transitionXyPair.second * 1.1).toInt() ) ) }

递归的终止条件就是判断X轴的平移距离或者Y轴的平移距离能够平移出屏幕,不满足该终止条件则将平移距离不停的放大。

介绍完了进阶版的实现原理,接着我们来看看困难版的实现原理。

困难版

相对比基础版与进阶版,困难版的发球点增加到四个,分别位于屏幕的四周。糖果会随机从这四个点生成,然后向大致对角方向发散。

所以同样,我们将屏幕分成四块。

enum class Direction { LEFT_TOP, RIGHT_TOP, LEFT_BOTTOM, RIGHT_BOTTOM }

通过 Direction.values().random()来随机确定糖果的初始坐标位于哪一块区域中,然后通过设置LayoutParams属性来让其位于四个角中。

TextView(this).apply { //1.设置糖果背景 background = ContextCompat.getDrawable(this@DifficultActivity, generateRandomCandy()) //2.确定初始位置 tv.layoutParams = when (Direction.values().random()) { Direction.LEFT_TOP -> { ConstraintLayout.LayoutParams(tvWidth, tvHeight).apply { startToStart = ConstraintSet.PARENT_ID topToTop = ConstraintSet.PARENT_ID } } Direction.LEFT_BOTTOM -> { ConstraintLayout.LayoutParams(tvWidth, tvHeight).apply { startToStart = ConstraintSet.PARENT_ID bottomToBottom = ConstraintSet.PARENT_ID } } Direction.RIGHT_TOP -> { ConstraintLayout.LayoutParams(tvWidth, tvHeight).apply { endToEnd = ConstraintSet.PARENT_ID topToTop = ConstraintSet.PARENT_ID } } Direction.RIGHT_BOTTOM -> { ConstraintLayout.LayoutParams(tvWidth, tvHeight).apply { endToEnd = ConstraintSet.PARENT_ID bottomToBottom = ConstraintSet.PARENT_ID } } } //3.添加到视图中 viewBinding.root.addView(this) }

接着就是计算平移的距离了。

因为是向对角发散,所以随机坐标是生成在对角区域,也就是左上区域对右下区域,右上区域对左下区域。

我们还是以左上区域来举例:

这里我们简单点直接利用两个相似三角形来计算平移距离:

X轴平移距离为:x * 2。 Y轴平移距离为:y * 2。

其它三个区域这边就不展开分析了,总的计算方法为:

/** * x, y 是指生成的随机坐标点的坐标 * * 移动的距离是两个相似三角形相加 */ private fun calculatePosition(x: Int, y: Int): Pair<Int, Int> { return if (x > halfScreenWidth) { if (y > halfScreenHeight) { //right_bottom Pair(x * 2, y * 2) } else { //right_top Pair(x * 2, -2 * (screenHeight - y)) } } else { if (y > halfScreenHeight) { //left_bottom Pair(-2 * (screenWidth - x), 2 * y) } else { //left_top Pair(-2 * (screenWidth - x), -2 * (screenHeight - y)) } } }

因为随机坐标点是在对角,所以两个三角形相加的平移距离就够支持糖果平移出屏幕了,当然你也可以参考进阶版采取递归算法来计算平移距离,那也会更加的精准。

总结

在完成了进阶版与困难版后,糖果捕捉器这款游戏也变得更加完整,当然后续还可以进行更多的升级,比如:让用户来定义糖果的生成速度,定义糖果的掉落速度,后续有时间的话,会对它进行再次升级。

如果你想查看游戏的所有代码,可以点击Github Candy-Catch进行查阅。如果可以,欢迎你给我点个小星星。

你可以通过点击糖果捕捉器apk 下载地址github进行下载安装该apk来进行体验一下该游戏。

到此本篇文章就结束啦,如果你有任何疑问或者不同的想法,欢迎在评论区留言与我一起探讨。

其实分享文章的最大目的正是等待着有人指出我的错误,如果你发现哪里有错误,请毫无保留的指出即可,虚心请教。

另外,如果你觉得文章不错,对你有所帮助,请帮我点个赞,就当鼓励,谢谢~

相关知识

Spine打造游戏2D动画的高效利器
如何快速上手一款新游戏——新手玩家的成长之路
安卓手机游戏编程学什么
如何用java编写手游
手机游戏都用什么语言编程
做手机游戏用什么编程
Android应用开发:基础小游戏开发
游戏动画设计师是干什么的,游戏中动画的设计师具体职责是什么?
动画游戏大全
安卓手机游戏编程用什么软件做的

网址: 如何用 Kotlin + 动画 快速实现一款游戏,快速上手!这些日子利用闲暇时间使用Kotlin + 动画开发了一款小游 http://www.hyxgl.com/newsview357133.html

推荐资讯