1.随机生成Tile(一)
在GameManager中添加随机生成砖块和从资源池取出物体的代码
public enum ObjectType
{
Tile,
Item,
Coin,
Enemy,
Bullet
}
//tile池子
public Queue tilePool = new Queue();
public Queue itemPool = new Queue();
public Queue coinPool = new Queue();
public Queue enemyPool = new Queue();
public Queue bulletPool = new Queue();
///
/// 随机生成砖块
///
void GenerateTile()
{
GameObject go = GetInactiveObject(ObjectType.Tile);
}
///
/// 从池子取物体
///
///
///
public GameObject GetInactiveObject(ObjectType type)
{
switch (type)
{
case ObjectType.Tile:
return tilePool.Dequeue();
case ObjectType.Item:
return itemPool.Dequeue();
case ObjectType.Coin:
return coinPool.Dequeue();
case ObjectType.Enemy:
return enemyPool.Dequeue();
case ObjectType.Bullet:
return bulletPool.Dequeue();
default:
return null;
}
}
在GameSetting中给每个砖块添加权重(生成的概率)
2.随机生成Tile(二)
给所有tile赋值,然后在GameManager中计算它们的权值并且随机生成
//获取权值所有
void GetAllWeight()
{
float sum = 0;
sum += advance.normalTile.weight;
sum += advance.brokenTile.weight;
sum += advance.oneTimeOnly.weight;
sum += advance.springTile.weight;
sum += advance.movingVertically.weight;
sum += advance.movingHorizontally.weight;
totalsum = sum;
}
///
/// 随机生成砖块
///
void GenerateTile()
{
GameObject go = GetInactiveObject(ObjectType.Tile);
float rand = Random.Range(0, totalsum);
}
private void Start()
{
//sum赋值
GetAllWeight();
//初始化对象池
GenerateTilePool();
//生成物体
for (int i = 0; i < initialSize; i++)
{
GenerateTile();
}
}
3.随机生成Tile(三)
GameManager中添加通过权值来设置tile类型的代码
int SetTileByRandomNumber(float number)
{
if (number <= advance.normalTile.weight)
return 0;
else if (number <= (advance.normalTile.weight + advance.brokenTile.weight))
return 1;
else if (number <= (advance.normalTile.weight + advance.brokenTile.weight + advance.oneTimeOnly.weight))
return 2;
else if (number <= (advance.normalTile.weight + advance.brokenTile.weight + advance.oneTimeOnly.weight + advance.springTile.weight))
return 3;
else if (number <= (advance.normalTile.weight + advance.brokenTile.weight + advance.oneTimeOnly.weight + advance.springTile.weight + advance.movingHorizontally.weight))
return 4;
else if (number <= (advance.normalTile.weight + advance.brokenTile.weight + advance.oneTimeOnly.weight + advance.springTile.weight + advance.movingHorizontally.weight + advance.movingVertically.weight))
return 5;
return -1;
}
4.随机生成Tile(四)
完善随机生成砖块
///
/// 随机生成砖块
///
void GenerateTile()
{
GameObject go = GetInactiveObject(ObjectType.Tile);
float rand = Random.Range(0, totalsum);
int randNumber = SetTileByRandomNumber(rand);
Vector2 pos = new Vector2(Random.Range(-4.5f, 4.5f), currentY);
switch (randNumber)
{
case 0:
go.transform.position = pos;
currentY += Random.Range(advance.normalTile.minHeight, advance.normalTile.maxHeight);
go.name = "0";
go.SetActive(true);
break;
case 1:
go.transform.position = pos;
currentY += Random.Range(advance.brokenTile.minHeight, advance.brokenTile.maxHeight);
go.name = "1";
go.SetActive(true);
break;
case 2:
go.transform.position = pos;
currentY += Random.Range(advance.oneTimeOnly.minHeight, advance.oneTimeOnly.maxHeight);
go.name = "2";
go.SetActive(true);
break;
case 3:
go.transform.position = pos;
currentY += Random.Range(advance.springTile.minHeight, advance.springTile.maxHeight);
go.name = "3";
go.SetActive(true);
break;
case 4:
go.transform.position = pos;
currentY += Random.Range(advance.movingHorizontally.minHeight, advance.movingHorizontally.maxHeight);
go.name = "4";
go.SetActive(true);
break;
case 5:
go.transform.position = pos;
currentY += Random.Range(advance.movingVertically.minHeight, advance.movingVertically.maxHeight);
go.name = "5";
go.SetActive(true);
break;
default:
break;
}
}
运行程序如下
5.回收Tile
在主相机下建立一个回收池
在GameManager中添加下面的方法
public GameObject floor;
public void AddInActiveObjectToPool(GameObject go,ObjectType type)
{
go.SetActive(false);
switch (type)
{
case ObjectType.Tile:
tilePool.Enqueue(go);
//TODO:生成tile
break;
case ObjectType.Item:
itemPool.Enqueue(go);
break;
case ObjectType.Coin:
coinPool.Enqueue(go);
break;
case ObjectType.Enemy:
enemyPool.Enqueue(go);
break;
case ObjectType.Bullet:
bulletPool.Enqueue(go);
break;
default:
break;
}
}
在Tile中进行调用
private void Update()
{
if (GameManager.Instance.floor.transform.position.y > transform.position.y + 1)
{
GetComponent().gravityScale = 0f;
GameManager.Instance.AddInActiveObjectToPool(gameObject, ObjectType.Tile);
}
}
运行程序结果如下,下面的tile都被回收
6.砖块水平竖直移动
在Tile脚本中添加代码,让tile可以自己移动
//方块的移动速度和距离
float speed;
float distance;
Vector3 startPos;
int direction; //0:left & up 1:right & down
void Init()
{
sp = GetComponent();
tileType = int.Parse(gameObject.name);
switch (tileType)
{
case 0:
sp.sprite = sprites[0];
break;
case 1:
sp.sprite = sprites[1];
break;
case 2:
sp.sprite = sprites[2];
break;
case 3:
sp.sprite = sprites[3];
break;
case 4:
sp.sprite = sprites[4];
speed = GameManager.Instance.advance.movingHorizontally.speed;
distance = GameManager.Instance.advance.movingHorizontally.distance;
startPos = transform.position;
break;
case 5:
sp.sprite = sprites[5];
speed = GameManager.Instance.advance.movingVertically.speed;
distance = GameManager.Instance.advance.movingVertically.distance;
startPos = transform.position;
break;
default:
break;
}
}
private void Update()
{
switch (tileType)
{
case 4:
if (direction == 0)
{
transform.Translate(new Vector2(-speed * Time.deltaTime, 0));
if (startPos.x - transform.position.x > distance)
{
direction = 1;
}
}
else
{
transform.Translate(new Vector2(speed * Time.deltaTime, 0));
if (startPos.x - transform.position.x < -distance)
{
direction = 0;
}
}
break;
case 5:
if (direction == 0)
{
transform.Translate(new Vector2(0,-speed * Time.deltaTime));
if (startPos.y - transform.position.y > distance)
{
direction = 1;
}
}
else
{
transform.Translate(new Vector2(0,speed * Time.deltaTime));
if (startPos.y - transform.position.y < -distance)
{
direction = 0;
}
}
break;
default:
break;
}
}
运行结果如下
7.设置游戏状态
在GameManager中添加三种状态并添加游戏结束的代码
public enum GameState
{
PAUSED,
RUNNING,
GAMEOVER
}
//游戏状态
public GameState gameState = GameState.PAUSED;
//结束游戏
public void EndGame()
{
if(gameState != GameState.GAMEOVER)
{
gameState = GameState.GAMEOVER;
//TODO:save data UI
}
}
在Player脚本中进行调用
private void OnTriggerEnter2D(Collider2D collision)
{
if (collision.tag == "Platform")
{
Jump(1);
}
if(collision.tag == "Floor")
{
GameManager.Instance.EndGame();
}
}
运行程序结果如下
8.无限生成Tile
在GameManager中添加重新生成tile的方法
///
/// 当一个tile销毁时,调用此方法
///
void CreateTile()
{
if(gameState != GameState.GAMEOVER)
{
GenerateTile();
//添加道具
//难度曲线
//分数
}
}
并在砖块销毁的时候进行调用
运行程序结果如下
9.Item的开发(一)
在场景中创建道具并添加PowerUp的脚本
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PowerUp : MonoBehaviour
{
public int itemType;
SpriteRenderer sp;
//图片
public Sprite[] sprites;
//技能时间
public float[] powerTime;
private void OnEnable()
{
Init();
}
void Init()
{
sp = GetComponent();
itemType = int.Parse(gameObject.name);
sp.sprite = sprites[itemType];
}
}
10.Item的开发(二)
完善PowerUp脚本
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PowerUp : MonoBehaviour
{
public int itemType;
SpriteRenderer sp;
//图片
public Sprite[] sprites;
//技能时间
public float[] powerTime;
//技能释放物体
public GameObject[] used;
GameObject player;
private void OnEnable()
{
Init();
}
void Init()
{
sp = GetComponent();
itemType = int.Parse(gameObject.name);
sp.sprite = sprites[itemType];
}
public void OnTriggerEnter2D(Collider2D collision)
{
if (collision.tag == "Player")
{
player = collision.gameObject;
//隐藏
sp.enabled = false;
//速度为0
player.GetComponent().velocity = Vector2.zero;
//让重力不影响我们的运动
player.GetComponent().isKinematic = true;
//无敌
GetComponent().enabled = false;
//显示图片
used[itemType].SetActive(true);
//fly
StartCoroutine("StopFly");
}
}
IEnumerator StopFly()
{
}
}
11.Item的开发(三)
完善PowerUp脚本,让Player添加道具飞行
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PowerUp : MonoBehaviour
{
public int itemType;
public SpriteRenderer sp;
//图片
public Sprite[] sprites;
//技能时间
public float[] powerTime;
//技能释放物体
public GameObject[] used;
GameObject player;
bool fly;
private void OnEnable()
{
Init();
}
void Init()
{
sp.enabled = true;
itemType = int.Parse(gameObject.name);
sp.sprite = sprites[itemType];
fly = false;
}
public void OnTriggerEnter2D(Collider2D collision)
{
if (collision.tag == "Player")
{
player = collision.gameObject;
//隐藏
sp.enabled = false;
//速度为0
player.GetComponent().velocity = Vector2.zero;
//让重力不影响我们的运动
player.GetComponent().isKinematic = true;
//无敌
GetComponent().enabled = false;
//显示图片
used[itemType].SetActive(true);
//fly
fly = true;
StartCoroutine("StopFly");
}
}
IEnumerator StopFly()
{
yield return new WaitForSeconds(powerTime[itemType]);
player.GetComponent().isKinematic = false;
GetComponent().enabled = true;
used[itemType].SetActive(false);
fly = false;
}
private void Update()
{
if (fly)
{
player.transform.Translate(new Vector2(0, 12 * Time.deltaTime));
}
else if (GameManager.Instance.floor.transform.position.y > transform.position.y + 1)
{
GameManager.Instance.AddInActiveObjectToPool(gameObject, ObjectType.Item);
}
}
}
运行程序结果如下