首页 > 其他分享 >unity3d异步加载场景

unity3d异步加载场景

时间:2023-01-05 14:33:23浏览次数:69  
标签:unity3d 场景 异步 MoveNext Person 枚举 集合 public 加载




​​unity3d​​​​loading界面​​​​异步加载​​​​进度条​​

根据宣雨松前辈的教程来做的,因为我用到的场景不是在游戏里的那种(本人做增强现实的,完全把unity拿来做应用了=。=),所以这里的方法不是很全面​

异步加载流程:

  lovdlevel                  异步读取
A---------------> B ------------------------>C
                                 播放加载动画

示例背景介绍:A场景是一个菜单,鼠标选中其中一项,则跳转到相应场景(C场景),B场景为加载动画播放场景

A场景:摄像机添加menu.cs
B场景:绑定loading.cs,把loading图片附到loading.cs

menu.cs:
[csharp]​​view plain​​​​copy​​


1. usingUnityEngine;
2. usingSystem.Collections;
3.
4. publicclassGlobe{
5. //在这里记录当前切换场景的名称
6. publicstaticstringloadName;
7. }
8. publicclassmenu : MonoBehaviour {
9.
10. // Use this for initialization
11. voidStart ()
12. {
13.
14. }
15.
16. // Update is called once per frame
17. voidUpdate ()
18. {
19. if(Input.GetKey(KeyCode.Escape))
20. Application.Quit();
21. Camera cam = Camera.mainCamera;
22. if(Input.GetMouseButtonDown(0))
23. {
24. Ray ray = cam.ScreenPointToRay(Input.mousePosition);
25. RaycastHit hit;
26. if(Physics.Raycast(ray, outhit) )
27. {
28. switch(hit.collider.name)
29. {
30.
31. case"***":
32. Globe.loadName = "C";
33. Application.LoadLevel ("B");
34. break;
35. case"***":
36. Globe.loadName = "CCC";
37. Application.LoadLevel ("B");
38. break;
39.
40. }
41. }
42. }
43. }
44.}


loading.cs
[csharp]​​view plain​​​​copy​​


1. usingUnityEngine;
2. usingSystem.Collections;
3.
4. publicclassloading : MonoBehaviour {
5.
6. privatefloatfps = 1000.0f;
7. privatefloattime;
8. //一组动画的贴图,在编辑器中赋值。
9. publicTexture2D[] animations;
10. privateintnowFram;
11. //异步对象
12. AsyncOperation async;
13.
14. //读取场景的进度,它的取值范围在0 - 1 之间。
15. intprogress = 1;
16.
17. voidStart()
18. {
19. //在这里开启一个异步任务,
20. //进入loadScene方法。
21. StartCoroutine(loadScene());
22. }
23.
24. //注意这里返回值一定是IEnumerator
25. IEnumerator loadScene()
26. {
27. //异步读取场景。
28. //Globe.loadName 就是A场景中需要读取的C场景名称。
29. async = Application.LoadLevelAsync(Globe.loadName);
30.
31. //读取完毕后返回,系统会自动进入C场景
32. yield returnasync;
33.
34. }
35.
36. voidOnGUI()
37. {
38. //因为在异步读取场景,
39. //所以这里我们可以刷新UI
40. DrawAnimation(animations);
41.
42. }
43.
44. voidUpdate()
45. {
46.
47. //在这里计算读取的进度,
48. //progress 的取值范围在0.1 - 1之间,但是它不会等于1
49. //也就是说progress可能是0.9的时候就直接进入新场景了
50. //所以在写进度条的时候需要注意一下。
51. //为了计算百分比所以直接乘以100即可
52. progress = (int)(async.progress *100);
53.
54. //有了读取进度的数值,大家可以自行制作进度条啦。
55. Debug.Log(progress);
56.
57. }
58. //简单绘制2D动画
59. void DrawAnimation(Texture2D[] tex)
60. {
61.
62. time += Time.deltaTime;
63.
64. if(time >= 1.0 / fps){
65.
66. nowFram++;
67.
68. time = 0;
69.
70. if(nowFram >= tex.Length)
71. {
72. nowFram = 0;
73. }
74. }
75.
76. GUI.DrawTexture(newRect( (Screen.width-60)*0.5f,(Screen.height-60)*0.5f,60,60) ,tex[nowFram] );
77. //在这里显示读取的进度。
78. GUI.Label(newRect( (Screen.width-100)*0.5f,(Screen.height-60)*0.5f+100,100,60), "LOADING..."+ progress+"%");
79.
80. }



IEnumerator 接口

语法


C#

C++

VB


IEnumerator

有关此接口的泛形版本,请参见 ​​IEnumerator​​。

C# 语言的 foreach 语句(在 Visual Basic 中为 for each)隐藏了枚举数的复杂性。因此,建议使用 foreach,而不直接操作枚举数。

枚举数可用于读取集合中的数据,但不能用于修改基础集合。

最初,枚举数定位在集合中第一个元素前。​​Reset​​​ 方法还会将枚举数返回到此位置。在此位置,调用 ​​ Current​​ 属性会引发异常。因此,在读取 Current 的值之前,必须调用 ​​ MoveNext​​ 方法将枚举数提前到集合的第一个元素。

在调用 MoveNextReset 之前,Current 返回同一对象。MoveNextCurrent

如果 MoveNext 越过集合的末尾,则枚举数将被放置在此集合中最后一个元素的后面,而且 MoveNext 返回 false。当枚举数位于此位置时,对 MoveNext 的后续调用也返回 false。如果最后一次调用 MoveNext 返回 false,则调用 Current 会引发异常。若要再次将 Current 设置为集合的第一个元素,可以调用 Reset,然后再调用 MoveNext

只要集合保持不变,枚举数就保持有效。如果对集合进行了更改(如添加、修改或删除元素),则枚举数将失效且不可恢复,并且下一次对 MoveNextReset 的调用将引发 ​​n​​。如果在 MoveNextCurrent 之间修改集合,那么即使枚举数已经无效,Current

枚举数没有对集合的独占访问权;因此,枚举通过集合在本质上不是一个线程安全的过程。即使一个集合已进行同步,其他线程仍可以修改该集合,这将导致枚举数引发异常。若要在枚举过程中保证线程安全,可以在整个枚举过程中锁定集合,或者捕捉由于其他线程进行的更改而引发的异常。

示例


下面的代码示例演示如何实现自定义集合的 ​​ IEnumerable​​ 和 IEnumerator 接口。在此示例中,没有显式调用这些接口的成员,但实现了它们,以便支持使用 foreach(在 Visual Basic 中为 for each)循环访问该集合。

C#

​VB​

复制

using System;
using System.Collections;

public class Person
{
public Person(string fName, string lName)
{
this.firstName = fName;
this.lastName = lName;
}

public string firstName;
public string lastName;
}

public class People : IEnumerable
{
private Person[] _people;
public People(Person[] pArray)
{
_people = new Person[pArray.Length];

for (int i = 0; i < pArray.Length; i++)
{
_people[i] = pArray[i];
}
}

public IEnumerator GetEnumerator()
{
return new PeopleEnum(_people);
}
}

public class PeopleEnum : IEnumerator
{
public Person[] _people;

// Enumerators are positioned before the first element
// until the first MoveNext() call.
int position = -1;

public PeopleEnum(Person[] list)
{
_people = list;
}

public bool MoveNext()
{
position++;
return (position < _people.Length);
}

public void Reset()
{
position = -1;
}

public object Current
{
get
{
try
{
return _people[position];
}
catch (IndexOutOfRangeException)
{
throw new InvalidOperationException();
}
}
}
}

class App
{
static void Main()
{
Person[] peopleArray = new Person[3]
{
new Person("John", "Smith"),
new Person("Jim", "Johnson"),
new Person("Sue", "Rabon"),
};

People peopleList = new People(peopleArray);
foreach (Person p in peopleList)
Console.WriteLine(p.firstName + " " + p.lastName);

}
}


标签:unity3d,场景,异步,MoveNext,Person,枚举,集合,public,加载
From: https://blog.51cto.com/u_8378185/5991068

相关文章

  • 获取某地模型并用Cesium加载
     2023-01-04最近想用Cesium给学校做一个类似智慧校园的东西,要做的东西很多,首先是获取学校模型的问题,然后怎么用Cesium加载3Dtile 1.获取学校模型想到之前被老师抓苦......
  • [unity3D插件]Unity界面插件NGUI核…
    本文转载于互联网,是一个比较经典帖子,特来分享:UICamera-可以添加到任何相机,包含事件系统.UICamera是每个UI的重要组成部分.它负责发送Camera中所有NGUI的活动.如果场景中......
  • android基础02 - 多媒体、多线程与异步任务、Service、网络
    多媒体通知通知渠道:程序对自己发出的通知进行分类,用户可根据渠道对消息进行屏蔽或设置响铃振动。一个应用的通知渠道一旦创建就无法再修改,只能再创建新的可在Activity、......
  • unity3D实现镜头拉近拉远及视角旋转
    镜头拉近拉远的代码(无限拉远拉近) 代码如下: if(Input.GetAxis("MouseScrollWheel")!=0){this.gameObject.transform.Translate(newVector3(0,0,Input.GetAxis("Mouse......
  • Unity3D之数据持久化储存
        首先我们来看两段Unity3D中实现数据读写的简单代码吧://保存数据PlayerPrefs.SetString("Name",mName);PlayerPrefs.SetInt("Age",mAge);PlayerPref......
  • Unity3D常用函数说明
    Unity3D中所有控制脚本的基类MonoBehaviour有一些虚函数用于绘制中事件的回调,也可以直接理解为事件函数,例如大家都很清楚的Start,Update等函数,以下做个总结。 Awake当前控......
  • Unity利用协同实现场景异步加载
    1.usingUnityEngine;2.usingSystem.Collections;3.4.publicclassFightTriggle:MonoBehaviour{5.privateAsyncOperationasync;6.i=0;7.......
  • Unity3D中Resources动态加载NGUI图片
    在NGUI中有些图片我需要动态进行变更或者加载,怎么办?首先在项目中创建一个Resources目录,接着把需要的图片放在这里面,可以有子文件夹么?当然可以,文件结构很重要哦~NGUI加载图片......
  • Assetbundle打包及加载入门详解(三)
                 主要讲Assetbundle的网络加载方式之前所讲的都是AssetBundle.LoadFromFile的方法,这是直接从硬盘上加载,而且属于同步加载。WWW.LoadF......
  • Assetbundle打包及加载入门详解(二)
    接着上篇,本节写如何更加科学的打包,以及打包中的一些依赖关系。科学打包:一般来说会把物体打成一个assetbundle包,把材质打成另个包,然后在加载的时候都加载出来。当然如果是有......