近期热门
粉丝5
关注 0
获赞 13
基于AssetBundle的无缝地图实现

[U3D] 基于AssetBundle的无缝地图实现

 !heats_icon! [复制链接]
5717 4 0 2 12年前 举报
本帖最后由 A你 于 2012-5-8 17:00 编辑

此代码是最终调试后可行的代码,前面已经试过了很多次别的策略,遇到很多很多棘手的问题,通过下面的制作过程和代码来逐步解释。

脚本:
Script_Cube_Trigger_Terrain1.cs
Script_Cube_Trigger_Terrain3.cs

Objects:
1、人物资源,需要有CharactorController,不然无法做object的Trigger碰撞响应。
2、两个Cube,在其Inspector面板中,将BoxCollider下的IsTrigger属性勾选上,调整该Cube的形状,作为加载地形的触发点,我把它们放在地形交界点处,玩家碰触后加载对面的地形。
如下图:
12.jpg
3、将脚本绑定在两个cube上。
4、把各个地形块都制作好后,将地形上的Object作为地形对象的子节点。在Project视图里,创建几个prefab文件,将地形文件分别拖入其中,然后制作成AssetBundle。
5、制作过程中发现一个重大的问题,客户端模式Build出来的文件或者在编辑器中直观看到的结果,和Build成Web格式后的结果有些不一样。可能是WebPlayer的数据要依据固定的stream来源---WWW对象。而在CS脚本里所定义的成员或静态成员Object对象均无法保存当前WWW对象刚下载后的资源,造成下载部分和加载部分代码不能分开写,否则会因为丢失对象而加载失败,更糟糕的是在Web模式下,是不会报告什么错误的。所以这里解释下,两个脚本分别对应两个Cube的原因,就是各自保存了一份WWW对象,分别记录着自己所下载过的资源。注意不要用AssetBundleRequest对象来保存WWW对象中的asset,虽然手册上例子是这样写,但我们的问题也出现在这里,在经验和资料还不充分的情况下先做备案。

脚本代码:

  1. using UnityEngine;
  2. using System.Collections;

  3. public class Script_Cube_Trigger_Terrain1 : MonoBehaviour {

  4. int Flag = 0; //记录是否已经加载过该资源,避免多次加载
  5. //AssetBundleRequest abr; string debugstr = ""; //调试信息
  6. static WWW wwwObj; //每个场景中一个单独的对象

  7. void Start ()
  8. {
  9. if(Flag == 0)
  10. {
  11. //判断平台信息,如果是webPlayer就从网络上加载,如果是本地,就从本地资源目录中加载。
  12. if( Application.platform == RuntimePlatform.OSXWebPlayer || Application.platform == RuntimePlatform.WindowsWebPlayer )
  13. {
  14. //实例WWW对象,相当于从参数代表的网络地址上下载资源过程。
  15. //GlobalConfig.GetConnectIP()方法可以取得当前机器的全局IP地址(这个例子中,服务器端和客户端在同一台机器上)
  16. wwwObj = new WWW("http://"+GlobalConfig.GetConnectIP()+"/AB/Terrain/Terrain1.unity3d");
  17. }
  18. else
  19. {
  20. // 因为玩家是玩Web形式发布的游戏,所以本地没有资源,所以这里可以省略了,本地调试的时候可以打开用。
  21. // wwwObj = new WWW("file:///E:/123/Terrain1.unity3d");
  22. }
  23. }
  24. }

  25. void Update () {
  26. }

  27. // 当前对象(此例中就是那俩Cube)如果Collier的IsTrigger属性被勾选上了,那么当另一个Collier碰撞到此对象上,就会触发这个函数。
  28. void OnTriggerEnter(Collider other)
  29. {
  30. // this if-type hierarchy is just for simple debug, we can put debug message in each curly braces
  31. if(Flag == 0)
  32. {
  33. if(wwwObj!=null)
  34. {
  35. print(wwwObj.isDone.ToString()); //判断是否WWW对象已经下载完了
  36. if(wwwObj.assetBundle!=null)
  37. {
  38. if(wwwObj.assetBundle.mainAsset !=null)
  39. {
  40. //load resouce into the assetbundle of wwwObject
  41. wwwObj.assetBundle.LoadAsync("Terrain1", typeof(GameObject));

  42. //创建地形实例
  43. if(Instantiate(wwwObj.assetBundle.mainAsset ) != null)
  44. Flag = 1;
  45. }
  46. }
  47. }
  48. }
  49. }

  50. // 调试用的,通过GUI来调试,可视化,蛮方便的
  51. void OnGUI()
  52. {
  53. GUI.Label(new Rect(0,0,200,200),debugstr);
  54. }
  55. }
复制代码
后期期望:
能实现本地缓存办法,让玩家下次登陆游戏时不用再去下载上次已经下载过的资源。
能实现真正的后台下载,玩家登陆后再进行异步下载,在不影响玩家正常游戏的情况下按照指定的方案去下载。

0
点赞
0
打赏
2
添加到收藏夹

0

点击复制链接

使用微信扫码分享
一次扣10个券
全部评论4
您需要登录后才可以回帖 登录

多谢分享
10年前
回复

使用道具 举报

楼主好淫啊,{:7_268:}感谢楼主拿出来分享,希望楼主人品爆棚
10年前
回复

使用道具 举报

一点点地学一点点地靠近
12年前
回复

使用道具 举报

{:soso_e102:}有案例下载就好了。。。
12年前
回复

使用道具 举报

您当前使用的浏览器IE内核版本过低会导致网站显示错误

请使用高速内核浏览器或其他浏览器