本部分介绍了使用 Unity 时可能出现的常见问题。按照平台分别在下方列出。
对象的渲染必须启用接受阴影 (Receive Shadows) 才能在物体表面渲染阴影。同时,对象必须启用投射阴影 (Cast Shadows) 以便在其他对象上投射阴影(默认为启用这两种功能)。
只有不透明的对象才能投射和接受阴影。这意味着使用内置透明或颗粒阴影的对象将不会投射阴影。大部分情况下,可以使用透明抠图 (Transparent Cutout) 着色器处理围栏、植被等对象。如使用自定义编写的几何渲染队列。使用顶点光照 (VertexLit) 着色器的对象不接受阴影,但可以投射阴影。
只有像素发光 (Pixel lights) 能投射阴影。如果需要确定无论在场景中使用多少种其他灯光,灯光始终投射阴影,可以将其设置为 Force Pixel 渲染模式(请参阅灯光 (Light) 参考页)。
对于 iOS 来说,在某些情况下,游戏可以在 Unity 编辑器中完美运行,但在实际设备上却无法运行甚至不能启动。这些问题通常是由代码或内容质量引起的。本部分将介绍最常见的几种情况。
导致这一现象有多种原因,主要原因包括:
XCode 调试控制台的信息有助于检测此类故障(Xcode 菜单:查看 (View) > 调试区 (Debug Area) > 激活控制台 (Activate Console))。
此消息通常在应用程序收到 NullReferenceException 时出现在 iOS 设备。有两种方式找出发生错误的位置:
从 3.4 版开始 Unity 包含基于软件的空引用 (NullReferenceException) 处理。AOT 编译器包含每次访问对象的一种方法或变量时,快速查看所有空引用。这一功能影响了脚本的性能,这也是为什么只在开发构建中启用该功能的原因(在基础版许可证书中,用户可以在构建设置 (Build Setting) 对话框中打开“开发构建 (development build)” 选项,但 iOS 专业版许可证书用户需要另外启用“脚本调试 (script debugging)” 选项)。 如果上述内容都正确,而错误实际出现在 .NET 代码中,那么您将不会再看到 EXC_BAD_ACCESS, 相反,.NET 异常文本将要 Xcode 控制台中显示(或者代码在 "catch" 语句处理)。典型的输出可能是:
Unhandled Exception: System.NullReferenceException: A null value was found where an object instance was required. at DayController+$handleTimeOfDay$121+$.MoveNext () [0x0035a] in DayController.js:122
这表明错误发生在 DayController 类的 handleTimeOfDay 方法中,是一个协同程序。 此外,如果它是脚本代码,就会提示出错误所在的行号(例如:"DayController.js:122 ")。问题语句可能如下:
Instantiate(_imgwww.assetBundle.mainAsset);
如果脚本在没有首先检查下载是否正确的前提下访问资源包,可能发生这种错误。
本机堆栈跟踪对于故障调查是一项更为强大的工具,但是,使用它需要一些专业技术。通常在发生此类本机(硬件内存访问)故障之后通常不能继续。要进行本机堆栈跟踪需要在 Xcode 调试控制台输入 bt all。仔细检查显示的堆栈跟踪,它们可能包括了错误来源信息。您可能会看到这样的信息:
... Thread 1 (thread 11523): #0 0x006267d0 in m_OptionsMenu_Start () #1 0x002e4160 in wrapper_runtime_invoke_object_runtime_invoke_void__this___object_intptr_intptr_intptr () #2 0x00a1dd64 in mono_jit_runtime_invoke (method=0x18b63bc, obj=0x5d10cb0, params=0x0, exc=0x2fffdd34) at /Users/mantasp/work/unity/unity-mono/External/Mono/mono/mono/mini/mini.c:4487 #3 0x0088481c in MonoBehaviour::InvokeMethodOrCoroutineChecked () ...
首先应该找到 "Thread 1" 的堆栈跟踪,这是主线程。堆栈跟踪的第一行将指向发生错误的位置。在这个示例中,跟踪显示 NullReferenceException 发生在 "OptionsMenu" 脚本中的 "Start" 方法。仔细查看这一方法实现便可发现故障的原因。很明显,NullReferenceExceptions 发生在 Start 方法,对初始化顺序做出了错误的假设。 在某些情况下,调试控制台中只可以看到一小部分堆栈跟踪:
Thread 1 (thread 11523): #0 0x0062564c in start ()
这表明在应用程序发布期间,已经去除本地符号。通过以下步骤可获得完整的堆栈跟踪信息:
这通常在外部库由ARM Thumb 指令集编译时发生。目前这种库不兼容 Unity。不用 Thumb 指令重新编译库,即可轻松解决这一问题。库的 Xcode 工程重新编译可使用以下步骤:
如果该库的源不可用,应联络提供 商,取得库的 non-thumb 版本。
(有时会看到 Program received signal: