文档章节

协同程序(Coroutines)

LIndieGS
 LIndieGS
发布于 2017/06/05 14:35
字数 804
阅读 0
收藏 0
点赞 0
评论 0

原文链接:https://docs.unity3d.com/Manual/Coroutines.html

    当你调用一个函数,它先与返回运行结束。这意味着,任何一个发生在函数里的动作必须发生在一个单独的帧刷新里;函数的调用不能被用来包含一个程序化的动画或一个持续一段时间的一系列事件。例如,考虑这样的情况,不断减少一个物体的初值(不透明度)知道它变得完全不可见。

void Fade() {
    for (float f = 1f; f >= 0; f -= 0.1f) {
        Color c = renderer.material.color;
        c.a = f;
        renderer.material.color = c;
    }
}

    实际上,这个函数不会像你希望那样执行。为了使这个淡出效果可视化,初值必须在连续的几帧内不断减少,去显示不断被渲染的中间值。可是,函数会在一帧刷新内就执行结束,这些中间值就不能显示出来,物体也会立即消失。

    解决方案就是在Update函数里加一些代码,这些代码能使淡出效果逐帧显示。但是,更常用的方法是使用coroutine。

    coroutine就像一个函数,它具有暂停函数执行并把控制权交给Unity的能力,同时,能在下一帧里,让函数从暂停的地方继续执行。在C#中,coroutine是这样声明的:

IEnumerator Fade() {
    for (float f = 1f; f >= 0; f -= 0.1f) {
        Color c = renderer.material.color;
        c.a = f;
        renderer.material.color = c;
        yield return null;
    }
}

    它本质上是一个函数,返回值类型是IEnumerator。它还有一个yield return语句,这是实现coroutine功能的关键,也就是暂停程序,在下一帧继续着个功能。为了能使coroutine运行起来,你需要使用StartCoroutine函数:

void Update() {
    if (Input.GetKeyDown("f")) {
        StartCoroutine("Fade");
    }
}

    你需要注意这个Fade函数中的这循环语句,它是保证在coroutine的生命期里,值的正确性。事实上,任何变量或参数都能准确的保存在yield里。

    一帧画面里,coroutine默认在它yield之后继续执行,但也可以使它延迟一段时间执行。这就要用到WaitForSecond:

IEnumerator Fade() {
    for (float f = 1f; f >= 0; f -= 0.1f) {
        Color c = renderer.material.color;
        c.a = f;
        renderer.material.color = c;
        yield return new WaitForSeconds(.1f);
    }
}

    它被常用于扩散一个效果并持续一段时间,它也是一种有用的优化手段。游戏中许多任务需要被定期执行,最好的方法就是把它们写进Update函数里。可是,一个函数通常在一秒中被调用很多次。当一个任务不需要被如此频繁地反复执行时,你能把它放进coroutine里,使它有规律地执行,而不是在每一帧中都执行。比如在游戏中,当敌人出现在玩家附近是,警报就会响起,代码可以这样写:

function ProximityCheck() {
    for (int i = 0; i < enemies.Length; i++) {
        if (Vector3.Distance(transform.position, enemies[i].transform.position) < dangerDistance) {
                return true;
        }
    }
    
    return false;
}

    如果附近有很多敌人,调用这个函数就会对硬件产生巨大的开销。这时,你就可以使用coroutine,让它每秒钟调用十次:

IEnumerator DoCheck() {
    for(;;) {
        ProximityCheck;
        yield return new WaitForSeconds(.1f);
    }
}

    这将大大减少执行检查的数量,而不会对游戏产生任何明显的影响。

© 著作权归作者所有

共有 人打赏支持
LIndieGS
粉丝 0
博文 9
码字总数 6421
作品 0
程序员
Java也可以有协同程序!

Java也能够像Lua一样拥有协同程序。你觉得不可能?其实可以用JavaX(一种Java源代码编译的Java方言)中实现! 目前,将一个函数转换为协同程序需要一点(直接的)源代码转换——当然这些转换...

鸟栖沙岩 ⋅ 2016/08/26 ⋅ 0

Coroutines & Yield 协同程序 & 中断

untiy中常用的方法: Coroutines & Yield 协同程序 & 中断 他的作用是这样的: 写游戏代码,往往最终需要代码为连续的事件.结果会像这样:: public class example : MonoBehaviour {private ...

安世博 ⋅ 2016/02/04 ⋅ 0

Unity3D_c#脚本注意要点

Inherit from MonoBehaviour 继承自MonoBehaviour All behaviour scripts must inherit from MonoBehaviour (directly or indirectly). This happens automatically in Javascript, but mus......

Matrix4X4 ⋅ 2012/06/26 ⋅ 0

Kotlin/Native v0.2 发布,将 Kotlin 编译成机器码

Kotlin/Native v0.2 发布了,这是 Kotlin/Native 技术预览版的功能和修复程序更新。本次更新增加了对协同程序和跨模块内联函数的支持,以及错误修复和改进。 该版本包括以下内容: 如何为并发...

局长 ⋅ 2017/05/13 ⋅ 15

【Kotlin For Android】(三): Anko 库

一、简介 Github地址 是一个使 Android应用程序 开发更快,更容易的库。它使你的代码变得简洁易读,并让您忘记 的粗糙边缘。 Anko 由几部分组成: :一个轻量级的库,里面充满了,对话框,日...

Agnes2017 ⋅ 04/27 ⋅ 0

Tornado 4.0 发布,Web 服务器

Tornado 4.0 发布,此版本值得关注的特性如下: The tornado.web.streamrequestbody decorator allows large files to beuploaded with limited memory usage. Coroutines are now faster an......

oschina ⋅ 2014/07/16 ⋅ 18

Coroutines和Rxjava异步编程对比之二

原文地址:https://medium.com/@manuelvicnt/coroutines-and-rxjava-an-asynchronicity-comparison-part-2-cancelling-execution-199485cdf068 在Android开发中,取消RxJava或Coroutines的执......

小菜鸟程序媛 ⋅ 04/20 ⋅ 0

Unity3D中自带事件函数的执行顺序

在Unity3D脚本中,有几个Unity3D自带的事件函数按照预定的顺序执行作为脚本执行。其执行顺序如下: 编辑器(Editor) Reset:Reset函数被调用来初始化脚本属性当脚本第一次被附到对象上,并且...

qq_38150068 ⋅ 05/17 ⋅ 0

Coroutines和Rxjava异步编程对比

原文地址:https://medium.com/@manuelvicnt/coroutines-and-rxjava-an-asynchronicity-comparison-part-1-asynchronous-programming-e726a925342a 这一系列的文章将会用来进行Coroutines和R......

小菜鸟程序媛 ⋅ 04/09 ⋅ 0

Python 3.5的async和await特性(PEP492翻译)

原因: 1,coroutine容易与正常的generators弄混 2,一个function是否为coroutine由函数体内是否有yield 或者yield from 决定,这不科学。 3,如果在语法上允许yield的地方才能进行异步调用,...

junanhonglei ⋅ 2015/06/23 ⋅ 3

没有更多内容

加载失败,请刷新页面

加载更多

下一页

BS与CS的联系与区别【简】

C/S是Client/Server的缩写。服务器通常采用高性能的PC、工作站或小型机,并采用大型数据库系统,如Oracle、Sybase、InFORMix或 SQL Server。客户端需要安装专用的客户端软件。 B/S是Brower/...

anlve ⋅ 50分钟前 ⋅ 0

发生了什么?Linus 又发怒了?

在一个 Linux 内核 4.18-rc1 的 Pull Request 中,开发者 Andy Shevchenko 表示其在对设备属性框架进行更新时,移除了 union 别名,这引发了 Linus 的暴怒。 这一次 Linus Torvalds 发怒的原...

问题终结者 ⋅ 今天 ⋅ 0

在树莓派上搭建一个maven仓库

在树莓派上搭建一个maven仓库 20180618 lambo init 项目说明 家里有台树莓派性能太慢。想搭建一个maven私服, 使用nexus或者 jfrog-artifactory 运行的够呛。怎么办呢,手写一个吧.所在这个...

林小宝 ⋅ 今天 ⋅ 0

Spring发展历程总结

转自与 https://www.cnblogs.com/RunForLove/p/4641672.html 目前很多公司的架构,从Struts2迁移到了SpringMVC。你有想过为什么不使用Servlet+JSP来构建Java web项目,而是采用SpringMVC呢?...

onedotdot ⋅ 今天 ⋅ 0

Python模块/包/库安装(6种方法)

Python模块/包/库安装(6种方法) 冰颖机器人 2016-11-29 21:33:26 一、方法1: 单文件模块 直接把文件拷贝到 $python_dir/Lib 二、方法2: 多文件模块,带setup.py 下载模块包(压缩文件zip...

cswangyx ⋅ 今天 ⋅ 0

零基础学习大数据人工智能,学习路线篇!系统规划大数据之路?

大数据处理技术怎么学习呢?首先我们要学习Python语言和Linux操作系统,这两个是学习大数据的基础,学习的顺序不分前后。 Python:Python 的排名从去年开始就借助人工智能持续上升,现在它已经...

董黎明 ⋅ 今天 ⋅ 0

openJdk和sun jdk的区别

使用过LINUX的人都应该知道,在大多数LINUX发行版本里,内置或者通过软件源安装JDK的话,都是安装的OpenJDK, 那么到底什么是OpenJDK,它与SUN JDK有什么关系和区别呢? 历史上的原因是,Ope...

jason_kiss ⋅ 今天 ⋅ 0

梳理

Redux 是 JavaScript 状态容器,提供可预测化的状态管理。 它是JS的状态容器,是一种解决问题的方式,所以即可以用于 react 也可以用于 vue。 需要理解其思想及实现方式。 应用中所有的 stat...

分秒 ⋅ 今天 ⋅ 0

Java 后台判断是否为ajax请求

/** * 是否是Ajax请求 * @param request * @return */public static boolean isAjax(ServletRequest request){return "XMLHttpRequest".equalsIgnoreCase(((HttpServletReques......

JavaSon712 ⋅ 今天 ⋅ 0

Redis 单线程 为何却需要事务处理并发问题

Redis是单线程处理,也就是命令会顺序执行。那么为什么会存在并发问题呢? 个人理解是,虽然redis是单线程,但是可以同时有多个客户端访问,每个客户端会有 一个线程。客户端访问之间存在竞争...

码代码的小司机 ⋅ 今天 ⋅ 0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部