框架视图
关键代码
Bird
public class Bird : MonoBehaviour
{
//控制材料中的贴图状态 要知道计时器 每秒总帧数 帧数计算器
//定义计时器变量
public float timer = 0;
//定义帧数量 也就是每秒钟要显示帧数;
public int frameNumber = 10;
//定义帧数计数器
public int frameCount = 0;
//定义两个变量 是否播放动画 是否控制跳跃;
public bool animation = false;
public bool canJump = false;
void Start()
{
//添加刚体组件
//给刚体施加一个向右的力(速度)
// gameObject.GetComponent<Rigidbody>().velocity = new Vector3(5,0,0);
// gameObject.GetComponent<Rigidbody>().velocity = new Vector3(2, 0, 0);
//第二种加力的方法;
// gameObject.GetComponent<Rigidbody>().AddForce(Vector3.right*50,ForceMode.Force);
}
void Update()
{
//判断是否是可以播放动画的时候
//if (animation)
//{
if (GameMannger._intance.gameState ==GameMannger.GAMESTATE_PLAYING)
{
//给一个恒定的速度,测试之用
//Vector3 vel = gameObject.GetComponent<Rigidbody>().velocity;
//gameObject.GetComponent<Rigidbody>().velocity = new Vector3(5, vel.y, vel.z);
//计时
timer += Time.deltaTime;
//如果时间超过每秒钟显示的总帧数 帧数++;时间重新归零
if (timer >= 1.0f / frameNumber)
{
//帧数++;
frameCount++;
// timer -= Time.deltaTime ;
timer -= Time.deltaTime + 0.05f; //加个时间让她抖动的慢点
//定义每帧的下标;取余 framrcount++ 1/3取余是1 2/3取余是2 3/3取余是0 4/3 取余是1 5/3取余是2 6/3取余是0 或者理解理解成0,1,2,0,1,2...
int frameIndex = frameCount % 3;
//更新材质的 偏移值 X;
//怎样去设置这个偏移值 X 的属性呢?
//获取本游戏对象下的 渲染组件 的 材质(材质复数时是数组)的设置 贴图偏移值 x
gameObject.GetComponent<Renderer>().material.SetTextureOffset("_MainTex", new Vector2(0.3333f * frameIndex, 0));//参数1:表示本材质的主要贴图(着色器的主要贴图),参数2:要改变的二维向量;
}
}
//判断是否跳跃的时候才可以跳跃
//if (canJump)
//{
if (GameMannger._intance.gameState == GameMannger.GAMESTATE_PLAYING)
{
//判断点击鼠标 给一个向上的速度 向上跳跃
if (Input.GetMouseButtonDown(0))
{
//添加声音后按下跳跃时播放扇动翅膀的声音
gameObject.GetComponent<AudioSource>().Play();
//获取当前的速度;
Vector3 vel2 = gameObject.GetComponent<Rigidbody>().velocity;
//给y轴向上的速度;
gameObject.GetComponent<Rigidbody>().velocity = new Vector3(vel2.x, 5.0f, vel2.z);
}
}
}
/// <summary>
/// 激活小鸟的方法 用来发送方法来调用的;
/// </summary>
public void getLife() {
gameObject.GetComponent<Rigidbody>().useGravity = true;
gameObject.GetComponent<Rigidbody>().velocity = new Vector3(2,0,0);
}
/// <summary>
/// 接触地面后 加大阻力 不让小鸟再次滚动;
/// </summary>
/// <param name="coll"></param>
void OnCollisionEnter(Collision coll) {
// Debug.Log(coll.gameObject.name);
if (coll.gameObject.name == "back")
{
//this.gameObject.GetComponent<Rigidbody>().velocity = new Vector3(0, 0, 0);
this.gameObject.GetComponent<Rigidbody>().drag = 1000f;
this.gameObject.GetComponent<Rigidbody>().angularDrag = 1000f;
// Debug.Log(this.gameObject.name);
}
}
}
FollowBird
public class FollowBird : MonoBehaviour {
//跟随相机
//定义一个游戏对象用来寻找小鸟的
private GameObject bird;
//为跟随位置定义好的变量
private Transform birdTransform;
//定义好一个偏移值的变量;
Vector3 offset;
void Start () {
//寻找游戏对象 小鸟 并且赋值;
bird = GameObject.FindGameObjectWithTag("Player");//gameobject是单数,不是复数;
birdTransform = bird.transform;
//计算偏移值;
offset = gameObject.GetComponent<Transform>().position - birdTransform.position;
}
void Update () {
Vector3 birdPos = birdTransform.position;
//判断不要将摄像机超出边界;
if (birdPos.y>5f)//上界
{
birdPos.y = 5f;
}
if (birdPos.y<2.5f)
{
birdPos.y =2.5f;
}
//相机位置跟随 不断补偿偏移值;
// gameObject.GetComponent<Transform>().position = birdTransform.position + offset;
gameObject.GetComponent<Transform>().position = birdPos + offset;
}
}
GameMannger
public class GameMannger : MonoBehaviour {
//定义游戏的状态;
public static int GAMESTATE_MENU = 0;
public static int GAMESTATE_PLAYING = 1;
public static int GAMESTATE_END = 2;
//只有3个背景图,不断循环 进入背景2 的时候 把背景1移到背景3 中去
public Transform firstBG;
//每个管道口设置一个触发器,闯过一个得一分;
//定义一个分数的变量;
public int score=0;
//定义一个游戏状态
public int gameState = GAMESTATE_MENU;
//定义一个鸟的游戏对象 并在初始化时赋值
private GameObject bird;
//单例模式
public static GameMannger _intance;
void Awake() {
_intance = this; //单例模式模板 得到的是gamemannger类型;
//给鸟赋值;
bird = GameObject.FindGameObjectWithTag("Player");
}
void Update() {
//判断当前的游戏状态;
if (gameState==GAMESTATE_MENU)
{
//判断是否点击屏幕
if (Input.GetMouseButtonDown(0))
{
//设置游戏的状态
gameState = GAMESTATE_PLAYING;
//播放动画 和 是否能跳跃 对鸟设置重力
//bird.GetComponent<Rigidbody>().useGravity = true;
////添加X轴方向的力;
//bird.GetComponent<Rigidbody>().velocity = new Vector3(1,0,0);
//综上 我们可以封装成一个方法 在此调用方法时 发送一个方法名;
bird.SendMessage("getLife");
}
}
//判断游戏是结束状态,把结束界面显示出来;
if (gameState == GAMESTATE_END)
{
GameMenu._instance.gameObject.SetActive(true);//参数设置为true;
//把分数转递给结束的界面 显示最后得分
GameMenu._instance.UpdateScore(score);
}
}
}
GameMenu
using UnityEngine;
using System.Collections;
using UnityEngine.SceneManagement;
public class GameMenu : MonoBehaviour {
//声明持有两个分数引用的变量;
public GUIText bestScore;
public GUIText nowScore;
//声明持有重新开始的游戏贴图;
public GUITexture startTexture;
//单例模式
public static GameMenu _instance;
void Awake()
{
_instance = this;
this.gameObject.SetActive(false); //默认是不调用的;
}
//更新分数的方法 公开的 才可以调用
public void UpdateScore(float currentScore)
{
//用来获取最高分数的关键词 piayerprefs;
float highScore = PlayerPrefs.GetFloat("score", 0);//参数1:通过key关键词 score查找最高分数 参数2:默认是0;因为第一次没有最高分数,默认值设置为0;
//判断一下 现在传过来的分数跟最高分数对比,更新下最高分;
if (highScore < currentScore)
{
highScore = currentScore;
}
//用来保存最高分数的关键词 PlayerPrefs;
PlayerPrefs.SetFloat("score", highScore);
//将分数显示出来;
bestScore.text = highScore.ToString();
nowScore.text = currentScore.ToString();
//这个方法会被GameMannger调用
//判断结束界面之后重新开始;
//首先判断鼠标点下和游戏处于结束状态
if (Input.GetMouseButtonDown(0)&&GameMannger._intance.gameState==GameMannger.GAMESTATE_END)
{
//获取重新开始游戏贴图的位置 关键语句 GetScreenRect()
Rect rect = startTexture.GetScreenRect();
//再次判断点击的位置是否在区域范围内;
//先获取鼠标的位置
Vector3 mousePos=Input.mousePosition;
//判断鼠标点击的范围
if (mousePos.x>rect.x&&
mousePos.x<(rect.x+rect.width)&&
mousePos.y>rect.y&&
mousePos.y<(rect.y+rect.height)
)
{
////改变游戏状态;
//GameMannger._intance.gameState = GameMannger.GAMESTATE_PLAYING;
////隐藏本界面
//this.gameObject.SetActive(false); //默认是不调用的;
//重新加载场景
SceneManager.LoadScene(0);
}
}
}
}
MoveTrigger
public class MoveTrigger : MonoBehaviour {
//定义一个公开的背景
public Transform currentBG;
//定义持有两个管道的应用
public Pipe pipe1;
public Pipe pipe2;
//触发事件 看谁触发了我,判断后 将背景1 移到背景2去
public void OnTriggerEnter(Collider coll) {
if (coll.tag=="Player")
{
//第一步 得到放在游戏管理器的第一个bg的Transform;
Transform firstBg=GameMannger._intance.firstBG;
//第二步 移动; 改变位置;
currentBG.transform.position = new Vector3(firstBg.position.x+10f,currentBG.transform.position.y,currentBG.transform.position.z);
//第三部 把背景图更新为当前的位置;
GameMannger._intance.firstBG = currentBG;
//第四步 随机生成管道的位置;
//定义 持有管道的引用 调用起方法生成随机位置;
pipe1.RandomGeneratePosition();
pipe2.RandomGeneratePosition();
}
}
}
Pipe
public class Pipe : MonoBehaviour {
void Start () {
//测试是否随机;
RandomGeneratePosition();
}
/// <summary>
/// 让Y轴的位置随机 随机范围是-0.1至-0.4;
/// </summary>
public void RandomGeneratePosition() {
float pos_Y = Random.Range(-0.4f,-0.1f); //参数1:最小值 参数2:最大值;
//本地坐标
gameObject.transform.localPosition = new Vector3(gameObject.transform.localPosition.x,pos_Y,gameObject.transform.position.z);
}
/// <summary>
/// 判断是否通过管道,加一分
/// </summary>
void OnTriggerExit(Collider coll) { //触犯3 个事件 OnTriggerEnter OnTriggerStay OnTriggerExit
if (coll.tag=="Player")
{
//播放得分声音
gameObject.GetComponent<AudioSource>().Play();
//加分 调用单例模式静态的方法 的分数++
GameMannger._intance.score++;
}
}
/// <summary>
/// ongui事件
/// </summary>
void OnGUI() {
//显示分数;
// GUILayout.Label(GameMannger._intance.score.ToString());
GUILayout.Label("Score:"+GameMannger._intance.score);
}
}
PipeCollision
public class PipeCollision : MonoBehaviour {
//定义两个 碰撞的声音 小鸟结束的声音 的变量
public AudioSource hitMusic;
public AudioSource dieMusic;
/// <summary>
/// 检测小鸟碰撞到管道,游戏结束 在结束前播放碰撞的声音
/// </summary>
void OnCollisionEnter(Collision coll)
{
if (coll.gameObject.tag == "Player")
{
//播放碰撞的声音
//gameObject.GetComponent<AudioSource>().Play();
hitMusic.Play();
//播放小鸟结束的声音
dieMusic.Play();
//切换游戏状态
GameMannger._intance.gameState = GameMannger.GAMESTATE_END;
}
}
}