文章目录
1.一个工程的基本结构:
必包含三个文件夹Assets(资源目录比如声音、图形) Library(库,开发中生成的中途文件) ProjectSettings(“设置”)
2.导入资源、Prefab预制体
关于预制体:把club从scene视图下拉到project,此后改变Prefab即可改变全部。点击学习:怎样使改变Prefab不影响它的全部子
3.地形设计
新建Terrain,工具栏如下
有123个模块。以下重点介绍2.Terrain:
最上方一排七个地形建造工具,选中第一个:做山坡 鼠标直接点击是增高,按住shift降低地形。
Settings:控制山坡的陡缓等形状。
选中第二个:对比与第一个的功能按钮区别发现第一行英文说明这个只能升高山 而不能降低,此外在Settings中多出来了一个Height:控制山坡的高度。(在此提一下上一个功能按键所绘的山高是由新建地形时填写的总高确定)
而跟在后面的“Flatten”控制粉刷到某一海平高度。
选中第三个:用来平滑地形边缘/尖锐部分
第四个:贴图,新建第一个贴图会粉刷掉整个地形,后续贴图需手动粉刷区域。通过调节Settings控制美观(插入是否生硬、是否应平滑…)
4.刚体和碰撞检测机制
以创建一个刚体Cube(?)为例,右侧:
解释:
1.物体质量(比如1kg的球和100kg的球砸下来的感觉肯定是不同的)
2.下落阻力
3.转动阻力
4.是否使用重力加速度(取消选择,那么物体在空中将不会下落)
5.锁定运动中的x/y/z轴
6.锁定转动中的x/y/z轴
关于Add ->Collider:有很多种,其中
Box Collider盒子碰撞器和Sphere Collider球体碰撞器以及Capsule Collider胶囊体是比较节约性能的,平时尽量选用这三种。
最耗费性能的是Add->Physics->Mesh Collider,尽量避免。
获得两个物体能够发生碰撞的条件:
至少两者都有碰撞器(Collider)并且其中一者有正常刚体(Rigidbody)
(详细条件参考:unity官方文档)
碰撞信息取得:
函数
//创建一个新方法
private void OnCollisionEnter(Collision collision){
print(collision.collider)//获取主角是和哪个碰撞体发生了碰撞
}
触发检测
什么是触发器?
创建一个Box Collider,取消勾选 is Trigger,则碰撞器变成了触发器(区别:是只可以碰撞or可以穿越)
移除Mesh Renderer控件,使触发器变成透明区(它多不需要实体显示
触发检测函数: OnTriggerEnter,OnTriggerExit,OnTriggerStay
5.unity中的四种灯光
[原]Unity3D深入浅出 - 光源组件(Light) https://www.cnblogs.com/tonge/p/3899981.html
关于:创建的点光源为什么不亮。。。位置。。还是空间位置。。
6.创建动画:火焰火堆
其实就是点光源放在灯柱上,改变光线颜色+粒子系统
粒子系统
1.右键创建Effects–Particle…
2.火焰碎片素材导入
3.调整
4.创建动画(火光闪烁
lightmapping 光照贴图,做光照烘焙
用途:节约性能,把提前计算好的光照动画保存下,不再即时计算。
在应用之前,灯光原本是这样的:(所谓即时计算)
以下光照烘焙:
不知道为什么我做的没效果 - - 成功案例比如在山谷内烘焙之后取消显示Light,山谷已经自带灯光。
7.导航系统
1.烘焙网格
window–Animation创建
8.角色人物
1.通过NavMeshAgent使人物根据导航系统而移动
选中人物文件-右侧Add Component–创建Nav Mesh Agent,
解释:
Angular Speed:人物转向速度
框选:手动调整,使控件大小与人物尽量贴合。
9.控制摄像机的跟随,角色的动画播放
1.摄像机:手动调整
2.动画播放:
Project中右键创建一个Animator Controller(动画状态机),重命名为HeroController用来控制人物的动画。选中Hero,在右侧栏看到组件Animator–Controller。把状态机拖进去。
那么如何修改状态机呢?
选中Hero 选择Animator,直接把动画素材拖入状态转换界面(下图右侧),在图中左侧新建变量float-speed(速度)
建立动画间转换关系。
解释:
取消勾选 意为动画可以随时发生
从idle–walk:当speed>0
从walk–idle:当speed<0.1
walk–run同理
这里采取由“速度变化”进行状态转换。自然要用到Animotar组件,在Hero脚本中调用该组件
public Animator anim; //调用
anim.SetFloat("speed", agent.velocity.magnitude); //通过Animator组件获取速度,magnitude速度大小
返回主面板,把该组件直接鼠标拖入脚本的变量初始值。
——————————————————————————————————————
10.附八个脚本:
1.hero: 获取组件:寻路导航组件、人物动画组件、钥匙接口 碰撞检测。
2.Menu:接入“开始游戏”按钮、音频。
3.KeyTip:→检测key亮度
4. AutoInstantiate:判断是否生成二者。生成传送门的步骤。
5. AutoDestroy:生成钥匙的步骤
6.BtnClick:开始按钮点击触发事件:开始游戏—英雄组件启用—修改脚本FollowTarget—修改脚本AutoInstantiate
7. FollowTarget:摄像机移动、计数。
8.Pass:画板、计数、检测是否过关。
BtnClick
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class BtnClick : MonoBehaviour {
public Button startBtn; // 开始游戏按钮
public GameObject heroObj;//英雄组件
public GameObject Cam;//相机组件
public GameObject thisCan;//画板组件
public Text MainText;//文本框组件
void Start () {
startBtn.onClick.AddListener(delegate () {
//按钮“按下”事件
heroObj.SetActive(true);//英雄组件启用
//heroObj.transform.position = new Vector3(10, 0, 0.57f);
Transform heroTrans =heroObj.transform;//获取英雄的transform
Cam.GetComponent<FollowTarget>().hero= heroTrans;//修改相机追随点
heroObj.GetComponent<AutoInstantiate>().NeedKey = true;//修改英雄组件的AutoInstantiate自动生成脚本的needKey值 使脚本生成key
heroObj.GetComponent<AutoInstantiate>().NeedFinish = true;//修改英雄组件的AutoInstantiate自动生成脚本的needFinish值 使脚本生成出口
Cam.GetComponent<FollowTarget>().setOffset();//调用相机组件FollowTarget的setOffset函数 设置位置偏移
MainText.GetComponent<RectTransform>().anchoredPosition=new Vector2(-230,200);//修改文本框组件在画板的位置
Cam.GetComponent<FollowTarget>().IfBegin = true;//修改相机组件FollowTarget脚本的Ifbegin值 开始计时
startBtn.gameObject.SetActive(false);//卸载按钮组件
});
}
}
hero
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI; //引入导航组件的命名空间
public class hero : MonoBehaviour {
public NavMeshAgent agent; //寻路导航组件 (烘焙
public Animator anim;//获取人物动画组件,保存后直接在主界面拖拽组件来赋值
public bool getKey = false;//玩家是否获得钥匙
void Update () {
if (Input.GetMouseButtonDown(0)) //当按下鼠标左键
{
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition); //定义一个射线,取鼠标点击的位置(一转换)
RaycastHit hit; //保存碰撞信息
if (Physics.Raycast(ray,out hit))