目录
1.准备场景
2.让小球动起来
3.用鼠标把小球甩出去
4.加入鼠标点击小球的判断
5.小球与冰块的碰撞测试
6.撞击后销毁冰块
编辑
7.显示游戏计时
8.显示扔球次数
9.显示剩余冰块个数
10.游戏结束
11.完整代码
下载源码 UnityPackage
最终效果:
1.准备场景
点击下载素材
步骤 :
-
将素材图片统一放进文件夹
Materials
里 -
在场景中放置背景图和边框图,调整到合适位置
-
在场景中放置球和冰块,调整到合适位置
2.让小球动起来
步骤 :
-
创建一个脚本
HitIce
,并挂载在小球上 -
给小球添加
Rigibody2D组件
-
使用
Rigibody2D组件
的AddForce()方法,编写一段简单脚本 -
给小球添加
球形碰撞器
,给边框加上多边形碰撞器 Polygon Collider 2D
-
给冰块预制体,添加
盒状碰撞器
,调整合适大小 -
给冰块预制体,添加
Rigibody2D组件
,调整重力大小为0
void Start()
{
// 让小球向右上方移动
this.GetComponent<Rigidbody2D>().AddForce(new Vector2(100, 100));
}
3.用鼠标把小球甩出去
修改脚本如下:
// 记录鼠标按下位置
Vector2 startPos;
// 记录鼠标松开位置
Vector2 endPos;
// 记录鼠标方向向量
Vector2 force;
void Start()
{
// 让小球向右上方移动
//this.GetComponent<Rigidbody2D>().AddForce(new Vector2(100, 100));
}
void Update()
{
// 按下鼠标左键
if (Input.GetMouseButtonDown(0))
{
startPos = Input.mousePosition;
}
if (Input.GetMouseButtonUp(0))
{
endPos = Input.mousePosition;
// 位移方向 = 终点方向 - 起始方向
force = endPos - startPos;
// 向鼠标位移方向施加力
this.GetComponent<Rigidbody2D>().AddForce(force * 2);
}
}
4.加入鼠标点击小球的判断
实现点:
-
RaycastHit2D() 的射线检测
-
是否点击到小球的bool开关
修改脚本如下:
Vector2 startPos; // 记录鼠标按下位置
Vector2 endPos; // 记录鼠标松开位置
Vector2 force; // 记录鼠标方向向量
RaycastHit2D hitInfo; // 射线检测到的信息
bool isClick; // 是否点击到小球
void Start()
{
// 让小球向右上方移动
//this.GetComponent<Rigidbody2D>().AddForce(new Vector2(100, 100));
}
void Update()
{
// 按下鼠标左键
if (Input.GetMouseButtonDown(0))
{
startPos = Input.mousePosition;
// 以鼠标点击的位置向鼠标深处发射一条射线
hitInfo = Physics2D.Raycast(Camera.main.ScreenToWorldPoint(Input.mousePosition), Vector2.zero);
// 判断射线是否检测到碰撞体
if(hitInfo.collider != null)
{
// 判断检测的到物体名称是否与小球相等
if(hitInfo.collider.name == this.name)
{
isClick = true;
}
}
}
// 松开鼠标左键
if (Input.GetMouseButtonUp(0) && isClick)
{
endPos = Input.mousePosition;
// 位移方向 = 终点方向 - 起始方向
force = endPos - startPos;
// 向鼠标位移方向施加力
this.GetComponent<Rigidbody2D>().AddForce(force * 2);
isClick = false;
}
}
5.小球与冰块的碰撞测试
步骤:
-
在小球的脚本里,定义一个全局变量Score
-
创建一个
PengZhuang
的脚本,挂载在冰块预制体上 -
添加OnCollisionEnter2D()
-
跨脚本访问全局变量,赋值++,并打印
private void OnCollisionEnter2D(Collision2D coll)
{
if (coll.gameObject.name == "qiu")
{
HitIce hitIce = coll.gameObject.GetComponent<HitIce>();
hitIce.score++;
Debug.Log(hitIce.score);
}
}
6.撞击后销毁冰块
冰块检测到小球碰撞到后,延迟一秒销毁自己
Destroy(游戏对象,延迟时间);
7.显示游戏计时
步骤:
-
新建两个文本UI,摆放到上方
-
在
HitIce
脚本加上计时代码
public Text timerText;
void Update()
{
// Time.time => 游戏运行了多长时间
// ToString("f2")转为string,格式为保留两位小数
timerText.GetComponent<Text>().text = Time.time.ToString("f2");
}
8.显示扔球次数
步骤:
-
新建两个文本UI,摆放到中间
-
在点击小球的方法中,更改扔球次数的文本
public Text countText;
// 点中小球次数加1
count++;
countText.GetComponent<Text>().text = count.ToString();
9.显示剩余冰块个数
步骤:
-
新建两个文本UI,摆放到右上角
-
创建一个读取剩余冰块个数的方法,获取子对象的总数
-
在Start()和Update()中调用
/// <summary>
/// 获取剩余冰块总数
/// </summary>
private void GetResidualIceCount()
{
// 获取BINGKUAI的子对象 => transform.childCount
int residualIceCount = GameObject.Find("BINGKUAI").transform.childCount;
residualText.GetComponent<Text>().text = residualIceCount.ToString();
}
void Start()
{
GetResidualIceCount();
// 让小球向右上方移动
//this.GetComponent<Rigidbody2D>().AddForce(new Vector2(100, 100));
}
void Update()
{
GetResidualIceCount();
10.游戏结束
步骤:
-
新建一个UI文本,Game Over!红色字样,放在屏幕中间
-
在GetResidualIceCount() 中判断冰块总数是否为0
-
将显示Game Over! 并 将计时调整为0
// 游戏结束
gameOverText.GetComponent<Text>().text = "Game Over!";
timerText.GetComponent<Text>().text = "0";
11.完整代码
1.HitIce
public class HitIce : MonoBehaviour
{
public Text timerText; // 计时的UI文本
public Text countText; // 扔球次数的UI文本
public Text residualText; // 剩余冰块的UI文本
public Text gameOverText; // 游戏结束的UI文本
public int score; // 分数(小球碰撞的次数)
Vector2 startPos; // 记录鼠标按下位置
Vector2 endPos; // 记录鼠标松开位置
Vector2 force; // 记录鼠标方向向量
RaycastHit2D hitInfo; // 射线检测到的信息
bool isClick; // 是否点击到小球
int count; // 扔球次数
void Start()
{
GetResidualIceCount();
// 让小球向右上方移动
//this.GetComponent<Rigidbody2D>().AddForce(new Vector2(100, 100));
}
void Update()
{
int residualIceCount = GetResidualIceCount();
if (residualIceCount > 0)
{
BallControl();
}
else
{
// 游戏结束
gameOverText.GetComponent<Text>().text = "Game Over!";
timerText.GetComponent<Text>().text = "0";
}
}
/// <summary>
/// 获取剩余冰块总数
/// </summary>
private int GetResidualIceCount()
{
// Time.time => 游戏运行了多长时间
// ToString("f2")转为string,格式为保留两位小数
timerText.GetComponent<Text>().text = Time.time.ToString("f2");
// 获取BINGKUAI的子对象 => transform.childCount
int residualIceCount = GameObject.Find("BINGKUAI").transform.childCount;
residualText.GetComponent<Text>().text = residualIceCount.ToString();
return residualIceCount;
}
/// <summary>
/// 鼠标控制小球
/// </summary>
private void BallControl()
{
// 按下鼠标左键
if (Input.GetMouseButtonDown(0))
{
startPos = Input.mousePosition;
// 以鼠标点击的位置向鼠标深处发射一条射线
hitInfo = Physics2D.Raycast(Camera.main.ScreenToWorldPoint(Input.mousePosition), Vector2.zero);
// 判断射线是否检测到碰撞体
if (hitInfo.collider != null)
{
// 判断检测的到物体名称是否与小球相等
if (hitInfo.collider.name == this.name)
{
isClick = true;
score = 0;
}
}
}
// 松开鼠标左键
if (Input.GetMouseButtonUp(0) && isClick)
{
endPos = Input.mousePosition;
// 位移方向 = 终点方向 - 起始方向
force = endPos - startPos;
// 向鼠标位移方向施加力
this.GetComponent<Rigidbody2D>().AddForce(force * 2);
isClick = false;
// 点中小球次数加1
count++;
countText.GetComponent<Text>().text = count.ToString();
}
}
}
2.PengZhuang
public class PengZhuang : MonoBehaviour
{
void Start()
{
}
void Update()
{
}
private void OnCollisionEnter2D(Collision2D coll)
{
if (coll.gameObject.name == "qiu")
{
HitIce hitIce = coll.gameObject.GetComponent<HitIce>();
hitIce.score++;
Debug.Log(hitIce.score);
Destroy(this.gameObject,0.5f);
}
}
}