Unity离散仿真引擎基础

Unity离散仿真引擎基础

前言

这是中山大学2020年3D游戏设计的第二次作业,如有错误,请指正,感谢您的阅读。

简答题

1、游戏对象(GameObjects) 和 资源(Assets)的区别与联系。

首先来看看官网给出的定义

GameObjects: The fundamental object in Unity scenes. A Scene contains the environments and menus of your game. Think of each unique Scene file as a unique level. In each Scene, you place your environments, obstacles, and decorations, essentially designing and building your game in pieces.

Assets: Any media or data that can be used in your game or Project. An Asset may come from a file created outside of Unity, such as a 3D model, an audio file or an image. You can also create some asset types in Unity, such as an Animator Controller Controls animation through Animation Layers with Animation State Machines and Animation Blend Trees, controlled by Animation Parameters. The same Animator Controller can be referenced by multiple models with Animator components.

简单来说,两者的区别为游戏对象是所有其他组件的容器。游戏中的所有对象本质上都是游戏对象 。除了作为组件的容器之外,游戏对象还具有标记、层和名称。
资源是游戏项目中的素材,可以包括建模、音频、脚本等。
两者的联系为游戏对象可以保存为资源,资源可以实例化为游戏对象。当然,多个游戏对象也可以保存为一个资源,而一个游戏对象也可以有很多资源。

2、下载几个游戏案例,分别总结资源、对象组织的结构(指资源的目录组织结构与游戏对象树的层次结构)

我们在Unity Hub上下载一个游戏案例,如下所示:
游戏案例
以这个游戏为案例,资源文件夹采用树形结构,如下所示。(由于展开文件实在太多,这里就不展开到最后了)
文件夹
通过观察我发现,资源文件夹将作用相似的资源放在同一个文件夹中,这样会让调用显得更加清晰明了,无论是增添新对象还是修改对象都可以很快找到自己想调用的资源。
游戏对象树的层次结构十分相似,如下图:
游戏对象树
作者很巧妙的用一些空对象的名字作为分类,同时将相似功能的写为一个对象,通过父对象和子对象的嵌套来完成对应的目标。

3、编写一个代码,使用 debug 语句来验证 MonoBehaviour 基本行为或事件触发的条件。

  • 基本行为包括 Awake() Start() Update() FixedUpdate() LateUpdate()

  • 常用事件包括 OnGUI() OnDisable() OnEnable()

测试的代码如下

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class test : MonoBehaviour
{
    void Awake()
    {
        Debug.Log("TestAwake");
    }

    void Start()
    {
        Debug.Log("TestStart");
    }

    void Update()
    {
        Debug.Log("TestUpdate");
    }

    void FixedUpdate()
    {
        Debug.Log("TestFixedUpdate");
    }

    void LateUpdate()
    {
        Debug.Log("TestLateUpdate");
    }

    void OnGUI()
    {
        Debug.Log("TestOnGUI");
    }

    void OnDisable()
    {
        Debug.Log("TestOnDisable");
    }

    void OnEnable()
    {
        Debug.Log("TestOnEnable");
    }

}

运行后结果如下:
运行结果
经实验和网上资料结合可以知道:

  • Awake:用于在游戏开始之前初始化。在脚本整个生命周期内它仅被调用一次。

  • Start:仅在Update函数第一次被调用前调用。Start在behaviour的生命周期中只被调用一次。

  • FixedUpdate:固定帧更新,更新频率默认为0.02s。

  • Update:正常帧更新,用于更新逻辑。

  • LateUpdate:在所有Update函数调用后被调用,和fixedupdate一样都是每一帧都被调用执行,这可用于调整脚本执行顺序。

  • OnGUI:在渲染和处理GUI事件时调用。

  • Reset:在用户点击检视面板的Reset按钮或者首次添加该组件时被调用。

  • OnDisable:当物体被销毁时 OnDisable将被调用,可用于任意清理代码。

  • OnEnable:在脚本被载入后调用。

  • OnDestroy:当MonoBehaviour将被销毁时,这个函数被调用。

4、查找脚本手册,了解 GameObject,Transform,Component 对象

  • 三个对象的描述

GameObject: Base class for all entities in Unity Scenes.

Transform: Position, rotation and scale of an object.

Component: Base class for everything attached to GameObjects.

  • 分别翻译官方对三个对象的描述(Description)
  1. GameObject:Unity场景中所有实体的基类。
  2. Transform:对象的位置,旋转和比例。
  3. Component:所有附加到GameObject的基类。
  • 描述下图中 chair对象(实体)的属性、chair的 Transform 的属性、 chair的部件。本题目要求是把可视化图形编程界面与 Unity API 对应起来,当你在 Inspector 面板上每一个内容,应该知道对应 API。例如:chair的对象是 GameObject,第一个选择框是 activeSelf 属性。
    table

chair的对象是 GameObject,第一个选择框是 activeSelf 属性,后面下拉栏是Static属性(动静态),接下来是Layer、Tag、Prefab属性。

chair的Transform属性,Position上的三个值分别为X=-2,Y=0,Z=0;Rotation在XYZ三个轴上的值均为0,Scale在XYZ三个轴上的值均为X=1,Y=0.2,Z=1。

chair的组件除了Transform,还有Mesh Filter、Box Colider、Mesh Renderer。它们分别可以调整网格形状,调整坐标系的位置、大小以及渲染网格

  • 用 UML 图描述 三者的关系(使用 UMLet 14.1.1 stand-alone版本出图)
    uml

5、资源预设(Prefabs)与 对象克隆 (clone)

  • 预设(Prefabs)有什么好处?

Unity’s Prefab system allows you to create, configure, and store a GameObject complete with all its components, property values, and child GameObjectsThe fundamental object in Unity scenes, which can represent characters, props, scenery, cameras, waypoints, and more. A GameObject’s functionality is defined by the Components attached to it.

根据unity的官方文档,预设有利于资源的重用,使用预设能够避免多次重复地构建对象。如果你想使用你制作好的建模,无需多次重构,只需要将其预设后就可以重复使用。

  • 预设与对象克隆 (clone or copy or Instantiate of Unity Object) 关系?
    当利用预设来创建一个新的对象时,这个对象相当于是从预设克隆而来的。预设和对象克隆的不同点在于,当修改预设时,由它实例化产生的多个对象也会跟着变化;而克隆得到的对象是相互独立的,因此修改克隆的对象时则不会发生这种变化。
  • 制作 table 预制,写一段代码将 table 预制资源实例化成游戏对象
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class tables: MonoBehaviour {
    public Transform table;
    void Start () {
        table = gameObject.GetComponent<Transform>();
        GameObject table2 = (GameObject)Instantiate(Resources.Load("table"));
        table2.transform.position = new Vector3(0, 0, 0);
        table2.transform.parent = this.transform;
    }
    void Update() {}
}

代码题

实现井字棋

详细请看文章:井字棋的实现

思考题【选做】

微软 XNA 引擎的 Game 对象屏蔽了游戏循环的细节,并使用一组虚方法让继承者完成它们,我们称这种设计为“模板方法模式”。为什么是“模板方法”模式而不是“策略模式”呢?

  • 策略模式则是指对象具备某个行为,但是在不同的场景中,该行为有不同的实现算法。
  • 在模板模式(Template Pattern)中,一个抽象类公开定义了执行它的方法的方式/模板。它的子类可以按需要重写方法实现,但调用将以抽象类中定义的方式进行。
  • 对于微软的XNA引擎,其屏蔽了游戏循环的细节,并使用一组虚方法由继承者完成,目的就是使得可以在不改变代码基本结构的情况下将一些具体模块交由继承者具体实现,这更符合“模板方法”。

将游戏对象组成树型结构,每个节点都是游戏对象(或数)。

  1. 尝试解释组合模式(Composite Pattern / 一种设计模式)。

组合模式(Composite Pattern),又叫部分整体模式,是用于把一组相似的对象当作一个单一的对象。组合模式依据树形结构来组合对象,用来表示部分以及整体层次。这种类型的设计模式属于结构型模式,它创建了对象组的树形结构。

简单来说,组合模式就是将对象组合成树形结构以表示“部分整体”的层次结构。

  1. 使用 BroadcastMessage() 方法,向子对象发送消息。你能写出 BroadcastMessage() 的伪代码吗?
public class father : MonoBehaviour {
	void Update () {
		var test = GameObject.Find ("test");
		object.BroadcastMessage ("tested", 5.0);
	}
}

BroadcastMessage() 大概实现思路:

遍历所有对象
	如果是子对象
		发送信息
	否则
		跳过

一个游戏对象用许多部件描述不同方面的特征。我们设计坦克(Tank)游戏对象不是继承于GameObject对象,而是 GameObject 添加一组行为部件(Component)。

  1. 这是什么设计模式?
  • 装饰器模式

装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构。这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装。
这种模式创建了一个装饰类,用来包装原有的类,并在保持类方法签名完整性的前提下,提供了额外的功能。
我们通过下面的实例来演示装饰器模式的用法。其中,我们将把一个形状装饰上不同的颜色,同时又不改变形状类。

  1. 为什么不用继承设计特殊的游戏对象?
  • 装饰器模式不需要改变其结构就可以向现有对象添加新的功能,而继承会有可能出现未知的错误,并且容易使代码显得更加晦涩难懂。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值