用Unity3D开发2D小游戏 Flappy Bird
来源:互联网 发布:福建广电网络宽带 编辑:程序博客网 时间:2024/05/22 13:15
简介:
最近在学习Unity3D,用了两天时间做了个小游戏打算放上了和大家分享一下,项目名定义为Flapping,是参考Flappy Bird做的,高手勿喷。
这是原本游戏效果图:
这是本项目效果图:
资源下载:
1. 完整源代码下载
2. PC发布版下载
3. Android发布版APK下载
源代码:
源代码里已经打好了注释,主要分为3个C#脚本。第一个是Player.cs,是本游戏最核心脚本,用来初始化场景和控制小鸟;第二个是Pillar.cs,处理柱子被小鸟撞后的特效;第三个是Menu.cs,这是菜单。
Player.cs
using System.Collections;using System.Collections.Generic;using UnityEngine;using UnityEngine.UI;using UnityEngine.SceneManagement;public class Player : MonoBehaviour {// Use this for initializationvoid Start () {// 获取各个对象或组件goBird = transform.Find ("Bird").gameObject;srBird = goBird.GetComponent<SpriteRenderer>();goCamera = GameObject.Find ("Main Camera");goScores = GameObject.Find ("Scores");if (canPlay) {InitBackground ();InitBlocks ();// 重设分数PlayerPrefs.SetInt ("scores", 0);} else {// 显示分数if (goScores) {goScores.transform.GetComponent <Text>().text = "SCORES: "+PlayerPrefs.GetInt("scores");}}}public bool canPlay = true;// 判断是否能开始public float screenHeight = 10; // 屏幕高度public float moveSpeed = 5;// 小鸟移动速度public float upSpeed = 19;// 往上爬速度public float upHeight = 0.9f;// 往上爬高度private float curUpHeight = 0;// 当前高度private bool upping = false;// 判断是否正在攀爬public float flapInterval = 0.1f;// 多长时间需要改变小鸟的样子private float curInterval = 0;// 当前经过的时间public Sprite srUnflap;// 小鸟正常样子public Sprite srFlapped;// 小鸟正在攀爬的样子private GameObject goBird;// 小鸟对象private SpriteRenderer srBird;// 存放小鸟样子private GameObject goCamera; // 摄像头private bool isDead = false;// 判断是否死亡private GameObject goScores;// 分数对象private int scores = 0;// 分数public AudioClip collisionAduio;// 碰撞音效// Update is called once per framevoid Update () {// 判断是否死亡if (!isDead) {UpdateFlap ();// 如果没死就继续更新下一帧if (canPlay) {// 更新动作UpdateMovement ();// 更新分数UpdateScores ();// 更新会动的柱子UpdateMovingBlocks ();}} else {UpdateDieCompleted ();}}private void UpdateMovement() {float s = Time.deltaTime * moveSpeed;transform.Translate (new Vector3 (s, 0, 0));// 重设摄像头位置goCamera.transform.position = new Vector3(transform.position.x,goCamera.transform.position.y,goCamera.transform.position.z);if ((Input.GetKeyUp (KeyCode.Space) || Input.GetButtonUp("Fire1"))) {curUpHeight = 0;upping = true;// 旋转小鸟的角度为45度goBird.transform.eulerAngles = new Vector3 (0,0,45);}// 往上爬if (upping) {float us = upSpeed * Time.deltaTime;if (us + curUpHeight >= upHeight) {us = upHeight - curUpHeight;}transform.Translate (new Vector3(0,us,0));curUpHeight += us;if (curUpHeight >= upHeight) {upping = false;curUpHeight = 0;// 旋转小鸟的角度为正常goBird.transform.eulerAngles = new Vector3 (0,0,0);}}// 如果撞到天花板就往下坠float top = transform.localScale.y / 2 + transform.position.y;if (top >= screenHeight / 2) {upping = false;curUpHeight = 0;// 旋转小鸟的角度为正常goBird.transform.eulerAngles = new Vector3 (0,0,0);}// 如果碰到地板就死亡float bottom = -transform.localScale.y / 2 + transform.position.y;if (bottom <= -screenHeight / 2) {// 小鸟死亡BirdDie ();}}private void BirdDie() {isDead = true;goBird.transform.eulerAngles = new Vector3 (0,0,90);}private void UpdateDieCompleted() {// 如果碰到地板就死亡float bottom = transform.localScale.y / 2 + transform.position.y;if (bottom <= -screenHeight / 2) {DieCompleted ();}}private void DieCompleted() {Destroy (gameObject);// 载入Gameover场景SceneManager.LoadScene ("GameOver");SceneManager.UnloadSceneAsync ("Game_1");}// 改变小鸟样子private void UpdateFlap() {curInterval += Time.deltaTime;if (curInterval >= flapInterval && !upping) {if (srBird.sprite == srUnflap) {srBird.sprite = srFlapped;} else {srBird.sprite = srUnflap;}curInterval = 0;}}// 更新分数private void UpdateScores() {float tail = transform.position.x - transform.localScale.x / 2 - blockWidth;tail = (tail < 0) ? 0 : tail;int killBlocks = (int)(tail / (blockOffset) + ((tail > blockWidth) ? 1 : 0));scores = killBlocks * 10;goScores.transform.GetComponent <Text>().text = "SCORES: "+scores;// 保存分数PlayerPrefs.SetInt ("scores",scores);// 判断游戏是否已经结束if (scores >= (totalBlock * 10)) {DieCompleted ();}}// 柱子public GameObject block;public float blockWidth = 1;//柱子宽度public float blockMinHeight = 1; // 柱子最小高度public float blockOffset = 8;// 柱子距离public float blockExitHeight = 4;// 两柱之间给小鸟通过的缝的距离public float blockNarrow = 0.2f;// 两柱之间给小鸟通过的缝的距离的递减数,越后的柱子的缝越小public int totalBlock = 40;// 柱子数量public int blockClass = 5;// 将所有柱子分为多少组private List<GameObject> movingBlocks = new List<GameObject>(); // 会移动的柱子private float curBlockMoveHeight = 0; // 柱子移动高度public float blockMoveSpeed = 1; // 柱子移动速度private bool isBlockMovingUp= true;// 判断是否正在移动private GameObject CreateBlock(Vector3 pos, Vector3 scale, Vector3 rotation) {GameObject go = GameObject.Instantiate (block).gameObject;go.transform.position = pos;go.transform.localScale = scale;go.transform.Rotate(rotation);return go;}// 初始化柱子private void InitBlocks() {int perClassBlock = totalBlock / blockClass;float x = 0.0f;System.Random rm = new System.Random (); // 随机数for (int i = 0; i < blockClass; ++i) {// 越后的柱子的缝越窄,这就表示游戏越难float narrow = blockExitHeight - i*blockNarrow;float avaliableHeight = screenHeight - narrow;for (int j = 0; j < perClassBlock; ++j, x+=blockOffset) {float height1,height2,y1,y2;height1 = (float)rm.NextDouble() * avaliableHeight;float blockMinHeight2 = blockMinHeight * 2;height1 = (height1 > (avaliableHeight - blockMinHeight2)) ? (avaliableHeight - blockMinHeight2) : height1;height1 = (height1 < blockMinHeight2) ? (blockMinHeight2) : height1; height2 = avaliableHeight - height1;y1 = (screenHeight - height1) / 2;y2 = (screenHeight - height2) / 2;GameObject go1 = CreateBlock (new Vector3(x,y1), new Vector3(1,height1/2,1), new Vector3(0,0,0));GameObject go2 = CreateBlock (new Vector3(x,-y2), new Vector3(1,height2/2,1), new Vector3(0,0,180));// 保存会动的柱子if (j >= perClassBlock - 2) {movingBlocks.Add (go1);movingBlocks.Add (go2);}}}}// 移动会动的柱子private void UpdateMovingBlocks() {float speed = blockMoveSpeed*Time.deltaTime;if (speed + curBlockMoveHeight >= blockMinHeight) {speed = blockMinHeight - curBlockMoveHeight;}curBlockMoveHeight += speed;speed = isBlockMovingUp ? speed : -speed;for (int i = 0; i < movingBlocks.Count; i += 2) {int j = i + 1;Vector3 pos1 = movingBlocks[i].transform.position;Vector3 pos2 = movingBlocks[j].transform.position;Vector3 scale1 = movingBlocks [i].transform.localScale;Vector3 scale2 = movingBlocks [j].transform.localScale;scale1.y -= speed;scale2.y += speed;pos1.y = (screenHeight - scale1.y*2)/2;pos2.y = -(screenHeight - scale2.y*2)/2;movingBlocks [i].transform.position = pos1;movingBlocks [j].transform.position = pos2;movingBlocks [i].transform.localScale = scale1;movingBlocks [j].transform.localScale = scale2;}isBlockMovingUp = curBlockMoveHeight >= blockMinHeight ? !isBlockMovingUp : isBlockMovingUp;curBlockMoveHeight = curBlockMoveHeight >= blockMinHeight ? 0 : curBlockMoveHeight;}// 背景public GameObject background;public float bgWidth = 20;public float bgStartPos = -10;public int bgCount = 50;// 创建背景private void CreateBackground(Vector3 pos, Vector3 scale) {GameObject go = GameObject.Instantiate (background).gameObject;go.transform.position = pos;go.transform.localScale = scale;}// 初始化背景private void InitBackground() {int n = bgCount;for (int i=0; i<n; ++i) {CreateBackground(new Vector3(bgStartPos+i*bgWidth,0,2),new Vector3(1,1,1));}}// 小鸟的碰撞处理void OnCollisionEnter2D(Collision2D col) {if (col.gameObject.tag == "Block") {AudioSource a = GetComponent<AudioSource>();if (!isDead) {BirdDie ();// 发出碰撞声音a.clip = collisionAduio;a.Stop ();}a.Play ();}}}
Pillar.cs
using System.Collections;using System.Collections.Generic;using UnityEngine;public class Pillar : MonoBehaviour {// Use this for initializationvoid Start () {}// Update is called once per framevoid Update () {}public int crushPiece = 5;// 碎片数量public float pieceWidth = 0.8f;// 碎片宽高public GameObject piece;// 碎片对象// 碰撞后弹出碎片private void Crush(Collision2D col) {System.Random rm = new System.Random ();for (int i = 0; i < crushPiece; ++i) {Vector3 pos = new Vector3(col.contacts [0].point.x, col.contacts [0].point.y, 0);Vector3 scale = new Vector3 (pieceWidth,pieceWidth, 1);float fr = (float)rm.NextDouble ();float angle = (float)fr * -180;Vector3 rotation = new Vector3 (0,0,angle);GameObject go = CreatePiece (pos,scale,rotation);go.transform.GetComponent<Rigidbody2D>().AddForce(new Vector2(-fr*2,3) * 100);Destroy (go, 3.0f);}}private GameObject CreatePiece(Vector3 pos, Vector3 scale, Vector3 rotate) {GameObject go = GameObject.Instantiate (piece);go.transform.position = pos;go.transform.localScale = scale;go.transform.eulerAngles = rotate;return go;}void OnCollisionEnter2D(Collision2D col) {if (col.gameObject.tag == "Player") {Crush (col);}}}
Menu.cs
using System.Collections;using System.Collections.Generic;using UnityEngine;using UnityEngine.SceneManagement;public class Menu : MonoBehaviour {public void StartGame() {// 载入游戏SceneManager.LoadScene ("Game_1");SceneManager.UnloadSceneAsync ("Menu");SceneManager.UnloadSceneAsync ("GameOver");}public void QuitGame() {// 退出游戏Application.Quit ();}}
阅读全文
0 0
- 用Unity3D开发2D小游戏 Flappy Bird
- Unity3d开发小游戏Flappy Bird
- 怎样使用Unity3D开发Flappy Bird游戏
- 用Unity开发Flappy Bird
- flappy-bird cocos-2d博客收藏
- Unity 2D Flappy Bird Tutorial
- 【Unity3D基础教程】(三):通过制作Flappy Bird了解Native 2D
- Unity3D基础教程】(四):通过制作Flappy Bird了解Native 2D...
- Flappy bird 小游戏的实现
- JavaScript 实现flappy bird小游戏
- 用Xcode 进行Flappy bird 的iOS开发(2)
- 用Tensorflow训练的AI玩flappy bird小游戏
- 啊哈 phaser制作小游戏flappy bird(2)
- unity3d开发flappy bird之背景设计(一)
- unity3d开发flappy bird之游戏逻辑控制(二)
- “反人类”小游戏《Flappy Bird》今天下线
- 用Xcode 进行Flappy bird 的iOS开发(1)
- 用Xcode 进行Flappy bird 的iOS开发(3)
- 全军出击,银联出台标准二维码产品
- System.arraycopy 与 Arrays.copyOf 分析
- Excel封装类 导成excel 封装思路
- 个人中心,设置头像
- 用友U8二次开发之登录
- 用Unity3D开发2D小游戏 Flappy Bird
- 跨站脚本攻击(XSS)
- 使用_.htaccess_文件禁用_Web_目录列举
- 如何使用MindManager进行高效的工作会议?
- MVC与三层架构
- mybatis报错org.apache.ibatis.binding.BindingException: Invalid bound statement (not found): 解决方法
- 图像识别并用机械手进行抓取
- 静态分页,前台分页
- 浏览器下载文件名称乱码问题