由于今天没有边看视频边写,事情有一点多,我就在一起总结了。这第三个游戏是横版跳跃游戏,其实仔细想想和第三个游戏差不多,其模型的给予大大降低了我们制作游戏的难度。我会从第一步到最后一步慢慢滤清思路,而不像昨天一样列出重点后写一坨。44:30
-
加入材质包
-
拉入过关所需台阶,并赋予其不同颜色,tag也要改变,以便于做出区别。游戏的规则是人和台阶不同颜色的时候会死,因此设置触发器也要有相应的判断依据,tag应运而生。
-
拉入Player,日常创建PlayerCharacter,且将角色mode拉入,在根目录加上rigiBody和BoxCollider,将BoxCollider和任务较好的重叠。
-
创建PlayerCharacter脚本,写入基本方法,如Move、Jump、Die、ChangeColorState等
-
由于角色的任何动作都依附于其物理脚本,这里创建各类型变量,并进行连接。如rigiBody、Renderer、Animator
-
在移动过程中,速度依旧是原来那么定义,不同的是我们只对x上的速度进行直接的定义,因为我们是横版跳跃游戏,有一个轴的速度是没有用的,另外一个轴的值只和跳跃和下落有关。这里在取到物体的速度后,要点儿出x速度,等式右边也是一样:
vel.x = (Vector3.left * speed).x;
不要忘了创建speed变量来控制速度的大小
其实这里出现了一些小插曲,因为物体面向方向的问题,我点出的z速度并不是老师点处的z速度,我等效的根据面向方向点出了x轴速度并重新给原物体赋值速度。 -
创建Controller脚本,创建PlayerCharacter型变量之后取到此脚本依附组件以调用其方法。在上一个脚本后我们已经写完了move函数,这里就是需要调用move函数让物体动起来
-
有的脚本不是在本组件上而是在根节点的组件上,这时候要是想通过创建变量得到这个组件就需要用GetConponentInChildren方法来得到组件。
-
我们在运行后发现游戏内的角色有滚动的现象。这个时候我们就要锁定游戏中rigiBody的xyz轴rotate,并锁定z轴,让它稳定的存在于我们所限定的游戏空间内。
10.这时候为了让静止的标准角色动起来就要创建Animator脚本并在角色的根节点或者创建Anamator脚本的运行组件,直接将run拖到里面,就能让角色跑起来。创建了动画脚本后不要忘了拖入动画控件内哦 -
拖入相机,这个相机***比较奇怪。先说基本的,把角色的根组件拖到相机的目标脚本内,这样相机就会跟随。但相机由三个部分组成***,第一部分是不能随意拖动的,这个部分确定了相机和物体的相对关系,第二个部分可以调整相机相对于物体的位置,第三个就是相机本身了。这个比较特殊 ,相机还需要好好看U3d基础,不然还很迷糊
-
然后角色会跑了,就要让角色跳起来,因为这个游戏由二段跳的功能,就要对其跳跃次数进行计数,即jumpCount。和判断是否在地面的 isGround
-
jump函数
public void Jump()
{
if (!isAlive)//判断是否成活
{
return;
}
if (jumpCount < 2)//限制其最多跳跃两次
{
if (jumpCount == 0)//第一次跳跃
{
rigid.velocity = new Vector3(rigid.velocity.x, 0, rigid.velocity.z);//其实一般情况下不需要这段代码,这段代码是应对特殊情况用的,主要作用于第二次跳跃。作用是清空y轴速度让其以y轴速度为0为初始条件进行跳跃(AddForce)
rigid.AddForce(Vector3.up * jumpForce, ForceMode.Impulse);//脉冲型AddForce,并取jumpforce
}
else if (jumpCount == 1)
{
rigid.velocity = new Vector3(rigid.velocity.x, 0, rigid.velocity.z);//第一段跳后按空格实现第二段跳的时候先让y速度变为零之后以此为基础i进行第二次跳跃
rigid.AddForce(Vector3.up * doubleForce, ForceMode.Impulse);//第一段和第二段跳的舜力是不同的
}
jumpCount++;//跳跃计数变多,超过1则停止跳跃
}
}
也不要忘记写完了跳跃方法,要在controller中进行调用,并调用input中的getkeydown来得到我们按下的键盘以此触发方法
13.可是,我们在进行第一次跳跃之后,就不能再进行跳跃。这是因为我们没用清空我们的jumpCount。我们要再Character脚本中写入这个方法:
private void OnCollisionEnter(Collision collision)
{
jumpCount = 0;
collisionRet = collision;//这个是碰撞物体,在之后用于调用碰撞物体的tag以判断是否应该死亡
}
14.这里在Character中有个奇怪的方法:Colloder
public bool GroundCheck()
{
Collider[] colliders = Physics.OverlapSphere(transform.position, 0.3f);//0.3f和物体大小有关
//本函数一旦被调用,将会返回以参数1为原点和参数2为半径的球体内“满足一定条件”的碰撞体集合,此时我们把这个球体称为 3D相交球。
for (int i = 0; i < colliders.Length; i++)
{
if (colliders[i].gameObject != gameObject)//判断跳跃后是否落在同一块台阶上,要是在同一块就不算是落地。跳起来的时候其半径内只有角色本身,因此只有相同的时候才能判断不在地板,只要有有一个不相等就说明多了接触物,即在地板上。
{
return true;
}
}
return false;//循环结束后,要是都没有就没有落地
}
15.继续设置双向Animator控件,创建触发器OnGround,要是跳起来后在空中,OnGround为false则可以判断为跳跃动画。
并在update中写入onGround = GroundCheck(); animator.SetBool("OnGround", onGround);
先判断,再把得到的bool类型变量写入就可以得到想要的动画。这里有一个细节就是在跳跃状态转换为奔跑状态的时候不能勾选 Has Exit Time这一项,要是这一次的跳跃动作没完成,要可能在台阶上完成跳跃动作,多滑稽,所以不要勾选。
16、我们需要通过碰撞结果来判断角色是否死亡,检测是在update中:
private void OnCollisionEnter(Collision collision)
{
jumpCount = 0;
collisionRet = collision;
}
private void OnCollisionStay(Collision collision)
{
collisionRet = collision;
}
private void OnCollisionExit(Collision collision)
{
collisionRet = null;
}
分别表示进入持续和离开,对碰撞触发器进行调整。
在update中进行刷新的判断函数:
private void Update()
{
if (!isAlive)
{
return;
}
if (collisionRet != null)//要是存在碰撞物体
{
if (collisionRet.gameObject.CompareTag("Red"))//要是碰撞的台阶标签为红
{
if (colorCurrent != TransColor.Red)//要是角色的颜色不为红色
{
Die();//死亡
}
}
else if (collisionRet.gameObject.CompareTag("Green"))
{
if (colorCurrent != TransColor.Green)
{
Die();
}
}
else//碰到黑色的
{
Die();
}
}
onGround = GroundCheck();
animator.SetBool("OnGround", onGround);
}
17、死亡函数的书写:
public void Die()
{
isAlive = false;
render.enabled = false;//停止对角色的渲染
rigid.velocity = Vector3.zero;//速度清零
Invoke("Restart", 2);//几秒后执行这个项目
}
public void Restart()//重新开始
{
UnityEngine.SceneManagement.SceneManager.LoadScene("Start");//调用
}
判断死亡的标志:public bool isAlive;
要记着在所有动作的前面都要判断是否死亡。
判断本身色彩变化的逻辑:
public void ChangeColorState()
{
if (!isAlive)
{
return;
}
if (colorCurrent==TransColor.Red)//本体颜色为红色
{
colorCurrent = TransColor.Green;//本体颜色变为绿色
render.material.color = Color.green;//渲染材质变为绿色
}
else if (colorCurrent==TransColor.Green)
{
colorCurrent = TransColor.Red;
render.material.color = Color.red;
}
animator.SetTrigger("ChangeColor");//触发animator中的ChangeColor触发器
}
加入死亡特效:public ParticleSystem dieParticle;
//粒子特效,在唤醒的时候stop的时候play
在砖块中可以加movepoint脚本,让砖块上下移动,嘿嘿嘿。这里需要注意的是因为上下移动需要两个目标点,来回平移,目标点是以tag来判断的,需要创建两个组件放在scene中当作Waypoint。因此要创建新的Waypoint标签,不过这都是根据给出的脚本写出的。
最后再复习一下,怎么插入音乐
首先实例化控件:public AudioClip PickMusic;
再在需要插入声音的脚本或者直接唤醒播放音乐:
AudioSource.PlayClipAtPoint(PickMusic, transform.position);