安卓動(dòng)態(tài)加載StreamingAssets路徑下的資源

最近負(fù)責(zé)把一個(gè)低模的HTC VR項(xiàng)目打包到一體機(jī),一體機(jī)其實(shí)就可以看成一個(gè)安卓機(jī),遇到的問題就是原來項(xiàng)目打包到安卓后跑步起來,網(wǎng)上查找資料才知道是因?yàn)镾treamingAssets路徑下的資源加載路徑不同,安卓和pc平臺(tái)的加載路徑不一樣,可以參考http://zhaolongchn.blog.163.com/blog/static/1906585042013624115926451/
得出結(jié)論,在安卓平臺(tái)StreamingAssets文件下的資源加載必須通過www的方式異步加載,而且要注意加載路徑。下面通過一個(gè)小demo來測(cè)試一下:

首先搭建一個(gè)場(chǎng)景

Paste_Image.png

然后在StreamingAssets文件下創(chuàng)建一個(gè)xml文件

Paste_Image.png
<?xml version="1.0" encoding="utf-8"?>
<npcData>
  <value>
    <ID>2017</ID>
    <Name>LuNa</Name>
    <Sex>woman</Sex>
  </value>
  

</npcData>

切記必須是utf-8的格式。該xml文件就用來后續(xù)我們用來測(cè)試資源加載,把xml文件當(dāng)成資源,就不再實(shí)例出怪物之類的物體了。

創(chuàng)建儲(chǔ)存xml文件數(shù)據(jù)信息的腳本

Paste_Image.png
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class XmlData  {
    public int id_;
    public int mID
    {
        get { return id_; }
        set { id_ = value; }
    }

    public string name_;
    public string mName
    {
        get { return name_; }
        set { name_ = value; }
    }

    public string sex_;
    public string mSex
    {
        get { return sex_; }
        set { sex_ = value; }
    }
}

創(chuàng)建一個(gè)解析xml文件的腳本類

Paste_Image.png
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.Xml;
using System.IO;

public class JXXml
{

    public static XmlData ReadXML(string xmlfile)//讀取xml信息
    {
        XmlData npcdata = new XmlData();
        if (xmlfile != string.Empty)
        {
            //去除utf-8格式的bom,這樣才能讀取xml內(nèi)容
            StringReader stringReader = new StringReader(xmlfile);
            stringReader.Read(); // skip BOM
            string result = stringReader.ReadToEnd();
            stringReader.Close();

            XmlDocument xmlDoc = new XmlDocument();
            xmlDoc.LoadXml(result);
            XmlNode npcNode = xmlDoc.DocumentElement;
            foreach (XmlNode npcSonNode in npcNode.ChildNodes)
            {
                if (npcSonNode.Name == "value")
                {
                    npcdata.mID = int.Parse(npcSonNode.ChildNodes.Item(0).InnerText);
                    npcdata.mName = npcSonNode.ChildNodes.Item(1).InnerText;
                    npcdata.mSex = npcSonNode.ChildNodes.Item(2).InnerText;
                }
            }
        }
            return npcdata;
        
    }
}

最后創(chuàng)建一個(gè)腳本觸發(fā)加載

Paste_Image.png
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class LoadXmlTest : MonoBehaviour {
    private TextMesh textmesh;
    private string path;
    private string result;

    void Start () {
        textmesh = GetComponent<TextMesh>();
        path = Application.streamingAssetsPath + "/TestXml.xml";
        StartCoroutine(LoadXml());
    }
    

    void Update () {
        
    }

    private void OnGUI()
    {
        GUIStyle titleStyle = new GUIStyle();
        titleStyle.fontSize = 40;
        titleStyle.normal.textColor = new Color(46f / 256f, 163f / 256f, 256f / 256f, 256f / 256f);
        GUI.Label(new Rect(100, 40, 500, 200),result, titleStyle);
    }

    IEnumerator  LoadXml()
    {
        WWW www = new WWW("file://" + Application.streamingAssetsPath+ "/TestXml.xml");
        yield return www;
        textmesh.text = www.text;
        
        XmlData npcdata = JXXml.ReadXML(www.text);
        result = npcdata.name_; 
    }
}

在unity運(yùn)行?。?!注意是在unity,不是打包后在安卓平臺(tái)

Paste_Image.png

看到game視圖我們就能確定我們已經(jīng)成功的用www實(shí)現(xiàn)了StreamingAssets路徑下的資源加載,但是需要注意,我們此時(shí)是在unity里面運(yùn)行的,如果我們要打包到安卓,就需要改一下加載路徑,改成:

WWW www = new WWW( Application.streamingAssetsPath+ "/TestXml.xml");

也就是把"file://" +去掉了。此時(shí)打包到安卓就可以運(yùn)行出正確結(jié)果了。

總結(jié)

1、安卓讀取StreamingAssets路徑下的文件不能用DirectoryInfo類(切記!?。。?,只能通過www異步加載,然后就是注意各個(gè)平臺(tái)的訪問路徑不一樣;
2、讀取xml文件時(shí)遇到的坑,就是如果把解析xml代碼改成:

public static XmlData ReadXML(string xmlfile)//讀取xml信息
    {
        XmlData npcdata = new XmlData();
        if (xmlfile != string.Empty)
        {
            //去除utf-8格式的bom,這樣才能讀取xml內(nèi)容
            //StringReader stringReader = new StringReader(xmlfile);
            //stringReader.Read(); // skip BOM
            //string result = stringReader.ReadToEnd();
            //stringReader.Close();

            XmlDocument xmlDoc = new XmlDocument();

            xmlDoc.LoadXml(xmlfile);   //注釋的時(shí)候記得把參數(shù)改成傳入的參數(shù)

            XmlNode npcNode = xmlDoc.DocumentElement;
            foreach (XmlNode npcSonNode in npcNode.ChildNodes)
            {
                if (npcSonNode.Name == "value")
                {
                    npcdata.mID = int.Parse(npcSonNode.ChildNodes.Item(0).InnerText);
                    npcdata.mName = npcSonNode.ChildNodes.Item(1).InnerText;
                    npcdata.mSex = npcSonNode.ChildNodes.Item(2).InnerText;
                }
            }
        }
            return npcdata;
        
    }

這樣再運(yùn)行就會(huì)報(bào)錯(cuò):

Paste_Image.png

出現(xiàn)這個(gè)錯(cuò)誤的原因是因?yàn)閁nity3D加載XML文件的時(shí)候,XML文件必須保存為UTF-8編碼的格式,同時(shí)還必須去掉開頭的兩個(gè)字節(jié)(BOM)用來標(biāo)識(shí)UTF-8用的。如何去掉bom標(biāo)示就用剛才注釋掉的代碼就行了,分享鏈接http://answers.unity3d.com/questions/10904/xmlexception-text-node-canot-appear-in-this-state.html

去掉bom標(biāo)示后就可以正常解析了,很神奇,明明前后打印出來字符串都一樣。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容