【Unity】使用JSONObject解析Json


為何要用JSONObject

之前已經用過JsonUtility和Newton.Json來解析Json了,為什么現在又要用一個新的JSONObject來解析Json?

在Unity游戲開發中,使用Newton.Json來反序列化時,需要指定確定的類型,這會帶來什么問題?

在游戲的道具系統中,有一個父類Item類,包含屬性ID和Name,有一個子類Consumable消耗品類,包含屬性HP和MP,UML如下:

后端返回的物品信息Json如下:

[
    {
        "id": 1,
        "name": "血瓶",
        "type": "Consumable",
        "hp": 10,
        "mp": 0,
    },
    {
        "id": 2,
        "name": "藍瓶",
        "type": "Consumable",
        "hp": 0,
        "mp": 10,
    }
]

 

使用Newton.Json時,代碼如下:

// itemsJson是包含了物品信息的Json字符串
public void ParseItemJson(string itemsJson)
{
    List<Item> itemList = Newtonsoft.Json.JsonConvert.DeserializeObject<List<Item>>(itemsJson);

    foreach (Item temp in itemList)
    {
        int id = temp.ID;
        string name = temp.Name;
        Item.ItemType type = temp.Type;

        Item item = null;
        switch (type)
        {
            case Item.ItemType.Consumable:
                Consumable consumable = temp as Consumable;
                int hp = consumable.HP;
                int mp = consumable.MP;
                item = new Consumable(id, name, type, hp, mp);
                break;
            // 其他類型省略。。。
            default:
                break;
        }

itemList.Add(temp); } }

按照以上思路,先以Item類型來反序列化,然后根據Item.Type來判斷物品類的具體子類型,如果為Consumable消耗品類型,就獲取該類型的HP和MP屬性,再按消耗品類型來實例化對象。

但是由於反序列化時指定為Item類型,所以即便Json字符串中包含了HP和MP的內容,也不會被解析到Item對象身上。

所以問題是:解析為父類時,再想根據父類中的屬性來轉型為子類,會導致轉型失敗!


 

JSONObject怎么用

現在改用JSONObject,可以解決該問題。

首先在AssetStore中下載JSONObject並導入到Unity項目中。

根據它的ReadMe以及里面自帶的Demo,可以快速學習使用該插件。代碼修改為如下:

    private List<Item> itemList = new List<Item>();
   
    /// <summary>
    /// 解析物品Json
    /// </summary>
    public void ParseItemJson(string itemsJson)
    {
        JSONObject j = new JSONObject(itemsJson);

        foreach (JSONObject temp in j.list)
        {
            int id = (int)temp["id"].n;
            string name = temp["name"].str;
            Item.ItemType type = (Item.ItemType)System.Enum.Parse(typeof(Item.ItemType), temp["type"].str);

            Item item = null;
            switch (type)
            {
                case Item.ItemType.Consumable:
                    int hp = (int)temp["hp"].n;
                    int mp = (int)temp["mp"].n;
                    item = new Consumable(id, name, type, hp, mp);
                    break;
                // 其他類型省略
                default:
                    break;
            }

            Debug.Log("item.id = " + item.ID + " , consumable.hp = " + ((Consumable)item).HP); itemList.Add(item); } }

運行后可以正確解析Json,拿到父類和子類的屬性值。


學習資料:

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM