GUILayout l l l GUILayoutButton params GUILayout Option
GUILayout布局 l l l GUILayout布局默认会伸展控件的尺寸。Button等控件支持 params GUILayout. Option[] options可变参数数组,可以通过 GUILayout. Width(30)返回一个设置控件宽度的GUILayout. Option 对象, Height()、 Min. Width()、Min. Height()等同理。例子: GUILayout. Button("Test", GUILayout. Width(500), GUILayout. Hei ght(30)) GUILayout采用线性布局,类似于Stack. Panel,默认是纵向布局。 通过GUILayout. Begin. Horizontal(); 开启和 GUILayout. End. Horizontal()结束一个横向排列区域,同理 Begin. Vertical() 、End. Vertical()。 如果嫌控件太挤,可以使用GUILayout. Space(30); 增加若干像素 的间隙。
常用GUI控件 1 l l l 密码框:pwd = GUILayout. Password. Field(pwd, ‘*’),第二个参数 为掩码字符,注意帧刷新的问题。 Button只有鼠标抬起才会返回true,这样用Button做发射子弹就 不能按下一直发射,可以使用Repeat. Button,这样按下期间会一 直返回true。案例:Button和Repeat. Button实现游戏对象移动。 Tab页: elected. Tool. Bar. Id = GUILayout. Toolbar(selected. Tool. Bar. Id, new string[]{“装备”, “经验 ”, “队友”}); 返回值为激活的按钮的序号。 复选框:is. Muted = GUILayout. Toggle(is. Muted, “静音”); 多行文本区: msg. Body = GUILayout. Text. Area(msg. Body, GUILayout. Width(300), GUILayo ut. Height(300));
游戏对象移动 l l l transform. Translate(vector 3)让对象沿着vector 3向量的方向移动,比如 transform. Translate(new Vector 3(0. 2 f, 0))就是z轴不动,向斜上方 45度运动,每次运动的分量是x、y都是 0. 2。 Vector 3类中内置了up、down、left、right、forward、back、 zero几个 简化的静态成员。 鼠标判断:Input. Get. Mouse. Button. Down(0)、Get. Mouse. Button. Up、 Get. Mouse. Button。 Get. Mouse. Button也是只要按下就一直返回true。案 例:键盘方向键控制元素移动。 键盘判断:Input. Get. Key. Down(Key. Code. Space), Input. Get. Key. Up(Key. Code. Left. Arrow),Input. Get. Key(Key. Code. A), Get. Key像Repeat. Button一样只要按下保持住就一直返回true。 案例点鼠标摄像头产生后坐力,按下左键摄像头back移动,松开左键摄 像头forward移动。
给“力” l l l 可以给游戏对象一个力,这样对象可以响应,比如愤怒的小鸟。 注意添加了刚体组件才能给力,否则rigidbody为null rigidbody. Add. Force(Vector 3. up*10, Force. Mode. Impulse); 给一 个向上的为 10的力,Impulse表示是冲击力 rigidbody. Add. Force(new Vector 3(3, 3, 0), Force. Mode. Impulse); 给 一个x为 3、y为 3的力,抛物线出去 案例:向对象施加一个从游戏对象指向摄像机的脉冲力 Vector 3 vector = main. Cam. transform. position cube 1. transform. position; //v 1 -v 2为从v 2指向v 1的向量 cube 1. rigidbody. Add. Force(vector*20); 练习:开发打鸭子、水果忍者游戏; 32
给“力” 2(*) l l Add. Force. At. Position (Vector 3 force, Vector 3 position),则 是在position这个点施加一个force方向的力。 Add. Torque是增加一扭矩力,第一个参数是设定围绕旋转 的中心点以及向量大小,如果Cube放到(0, 0, 0)这个位置, 则cube 1. rigidbody. Add. Torque(new Vector 3(0, 0. 5 f, 0), Force. Mode. Impulse); 就是让Cube围绕着 Y轴中心旋转。
动态创建游戏对象 l 使用Create. Primitive方法创建对象,创建出的对象不需要Add之类的就 可以显示出来: • • l l Game. Object cube = Game. Object. Create. Primitive(Primitive. Type. Cube); cube. Add. Component(typeof(Rigidbody)); cube. name = "cube 1"; //设定名字 cube. renderer. material. color = Color. red; 动态创建出来的对象运行时在Hierarchy中可以看到,可以帮助检查内存 泄露。 克隆游戏对象产生复制对象的效率高,比如游戏中产生大量子弹。调用 Instantiate来生成对象,Destroy(obj)是立即销毁游戏对象, Destroy(obj, 1)是延迟一秒销毁游戏对象: • • Game. Object obj = (Game. Object)Instantiate(cube); Destroy(obj, 1);
自定义鼠标指针 • • 屏幕坐标系(Screen. Point)是以 屏幕 左下角为(0, 0),右上角 为(Screen. Width, Screen. Height),向上向右正方向,鼠标的位置 Input. mouse. Position 是屏幕坐标系; GUI则是常规的以右上角为(0, 0),向下向右为正方向。 Screen. Width, Screen. Height是游戏屏幕的大小,不是电脑屏幕的大 小; Screen. full. Screen读写游戏全屏状态(模拟器中不起作用); Screen. show. Cursor读写是否显示鼠标光标状态。 自定义游戏光标:Start中隐藏光标 Screen. show. Cursor = false; 声 明属性 public Texture Cursor. Texture; 找一个png格式鼠标图片放到 Project中,然后拖到Cursor. Texture属性上;On. GUI中: • • Vector 3 mouse. Pos = Input. mouse. Position; GUI. Draw. Texture(new Rect(mouse. Pos. x, Screen. heightmouse. Pos. y, Cursor. Texture. width, Cursor. Texture. height), Cursor. Texture);
角色控制 if(Mathf. Abs(Vector 3. Distance(transform. position, target. Position))>1) l { l Character. Controller char. Ctrl = game. Object. Get. Component<Character. Controller>(); l transform. Look. At(new Vector 3(target. Position. x, transform. position. y, target. Position. z)); l float speed = 0. 1 f; l Vector 3 next. Pos = Vector 3. Clamp. Magnitude(target. Positiontransform. position, speed); l char. Ctrl. Move(next. Pos); } 选中地形则在地形的当前位置创建对象,选中其他对象则在它位置产生一个 l
Nav. Mesh寻找路径 l l l 对于NPC可以采用Nav. Mesh进行控制。 打开主菜单Windows->Navigation。在Hierarchy中将所有障碍物选上, 在Navigation窗口,将Navigation Static打上勾,Navigation Layer 设置 为not walkable; Component-> Navigation ->Nav. Mesh. Agent给角色添加Nav. Mesh. Agent 组件。 在Navigation窗口中,点击【Bake】烘焙生成路径数据。 脚本: • navmeshagent = game. Object. Get. Component<Nav. Mesh. Agent>(); 拿到组件对象 • 在Update中navmeshagent. Set. Destination(position); 刷新显示向 position位置走。 41
声音的3 D特性 l l l Audio Listener和Audio Source的空间距离决定了听到的声音的 效果,比如第二人生或者浪漫庄园中离人物越远听到的声音越小 就是这个原因 向右前方越来越远的声音:把音乐组件放到cube上, Main. Camera为Audio. Listener,给cube添加如下脚本: • void Update () { • transform. Translate(new Vector 3(1, 0, 1)*Time. delta. Time); • } 环绕声音,把上面的Update代码改成: transform. Rotate. Around(Camera. main. transform. position, Vecto r 3. up, 1);
模型动画 2 l l l 3)片段切割完毕要把片段授权,否则运行的时候会提示没有 legacy或者gameobject中没有animation组件。切换到Rig, Animation Type选择“legacy”,Generation选择“Store in Root”, 点击【apply】按钮。 4)把fbx拖到Hierarchy或者Scene中这样就成为Game. Object了 5)播放动画:game. Object. animation. Play("walk");
Coroutine l l l l l Unity中使用Start. Coroutine实现异步操作的效果,类似于Win 8中 的async。Yield原理见备注。 一个方法如果是异步的则需要返回IEnumerator类型的,必须有 至少一个yield return,使用Start. Coroutine获得方法返回值即可。 例如: Start. Coroutine(My. Start()); IEnumerator My. Start() { hero. transform. Rotate(Vector 3. up, 30); yield return new Wait. For. Seconds(2); hero. transform. Rotate(Vector 3. down, 30); } 游戏中敌人的AI可以使用Wait. For. Seconds降低资源占用。 50
- Slides: 57