JSON文件使用
Cocos2d-x 3.x 加入了 rapidjson库,用于Json解析。位于external/json下。
Json文件格式必须为UTF8无BOM格式编码,不然游戏中会出现乱码。
只支持标准的Json格式,一些非标准的Json格式不支持。一些常用的解析方法需要自己封装。注意判断解析节点是否存在。
PS:解析的Json文件,根节点必须为对象、或数组。不然无法解析。
只支持标准的Json格式,一些非标准的Json格式不支持。一些常用的解析方法需要自己封装。注意判断解析节点是否存在。
PS:解析的Json文件,根节点必须为对象、或数组。不然无法解析。
1、添加头文件
如果只用于解析Json文件,只要前2行的头文件即可。
Json对象解析使用:

如果只用于解析Json文件,只要前2行的头文件即可。
//
#include "json/rapidjson.h"
#include "json/document.h"
#include "json/writer.h"
#include "json/stringbuffer.h"
//#include "json/filestream.h"
//#include "json/prettywriter.h"
using namespace rapidjson; // 命名空间
//<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);"> </span>
2、Json数据解析
Cocos封装的 rapidjson库,只能解析对象格式、或数组格式的Json文件。
2.1、解析对象格式的Json
Json文件中的数据,根节点为一个对象,所有属性在大花括号 { } 中。
对象中的数据,通过 名称/值 的形式进行访问。
Json文件内容如下:
//
{
"hello" : "world",
"t" : true,
"f" : false,
"n" : null,
"i" : 123,
"pi" : 3.1416,
"array" : [1, 2, 3, 4],
"object": {
"name" : "alice",
"age" : 23
}
}
//
Json对象解析使用:
//
//[1] 读取json文件内容
std::string str = FileUtils::getInstance()->getStringFromFile("testJson.json");
CCLOG("%s", str.c_str());
//[2] 创建用于处理json代码的类
// 创建rapidjson::Document类:用于操作json代码
rapidjson::Document d;
//[3] 解析json文件内容
// 其中 rapidjson::kParseDefaultFlags = 0,默认方式
d.Parse<rapidjson::kParseDefaultFlags>(str.c_str());
// d.Parse<0>(str.c_str()); // 也可以直接写<0>
//[4] 判断解析是否出错
if (d.HasParseError()) {
CCLOG("GetParseError %s\n",d.GetParseError());
return;
}
//[5] 获取json中的数据
// 判断json文件是否为对象格式
if (d.IsObject()) {
// 是否有 "hello" 属性
if (d.HasMember("hello")) {
CCLOG("%s", d["hello"].GetString()); // 方式一:直接获取
}
// 是否有 "i" 属性
if (d.HasMember("i")) {
rapidjson::Value& i = d["i"]; // 方式二:保存为rapidjson::Value&
CCLOG("%d", i.GetInt());
}
// 数组
if (d.HasMember("array")) {
// 获取数组中的元素:d["array"][i]
for (int i = 0; i < d["array"].Size(); i++) {
CCLOG("%d : %d", i, d["array"][i].GetInt());
}
// // 也可以这么写
// rapidjson::Value& array = d["array"];
// for (int i = 0; i < array.Size(); i++) {
// CCLOG("%d : %d", i, array[i].GetInt());
// }
}
// 对象
if (d.HasMember("object")) {
// 判断 "object" 属性对应的值,是否为一个对象
if (d["object"].IsObject()) {
// 转化为 rapidjson::Value&
rapidjson::Value& object = d["object"];
CCLOG("%s", d["object"]["name"].GetString());
CCLOG("%d", object["age"].GetInt());
}
}
}
//
输出结果:
2.2、解析数组格式的Json
Json文件中的数据,根节点为一个数组,所有元素在一个大方括号 [ ] 中。
数组中的数据,通过下标的形式访问元素值(下标从0开始)。
Json文件内容如下:
//
[
true,
123,
"888",
"hello world",
{"name" : "alice", "age" : 23},
[1,2,3,4]
]
//
Json数组解析使用:
//
//[1] 读取json文件内容
std::string str = FileUtils::getInstance()->getStringFromFile("testJson.json");
CCLOG("%s", str.c_str());
//[2] 创建用于处理json代码的类
// 创建rapidjson::Document类:用于操作json代码
rapidjson::Document d;
//[3] 解析json文件内容
// 其中 rapidjson::kParseDefaultFlags = 0,默认方式
d.Parse<rapidjson::kParseDefaultFlags>(str.c_str());
// d.Parse<0>(str.c_str()); // 也可以直接写<0>
//[4] 判断解析是否出错
if (d.HasParseError()) {
CCLOG("GetParseError %s\n",d.GetParseError());
return;
}
//[5] 获取json中的数据
// 判断json文件是否为数组格式
if (d.IsArray()) {
rapidjson::Value& array = d;
for (int i = 0; i < array.Size(); i++) {
if (d[i].IsBool()) { // 逻辑值
CCLOG("%d is Bool : %d", i, array[i].GetBool());
}
if (d[i].IsNumber()) { // 数字
CCLOG("%d is Number : %d", i, array[i].GetInt());
}
if (d[i].IsString()) { // 字符串
CCLOG("%d is String : %s", i, array[i].GetString());
}
if (d[i].IsObject()) { // 对象
rapidjson::Value& object = d[i];
CCLOG("%d is Object : %s", i, array[i]["name"].GetString());
CCLOG("%d is Object : %d", i, object["age"].GetInt());
}
if (d[i].IsArray()) { // 数组
for (int j = 0; j < array[i].Size(); j++) {
CCLOG("[%d,%d] is Array : %d", i, j, array[i][j].GetInt());
}
}
}
}
//
输出结果:
其实用起来可不必这么麻烦,如果对自己的Json文件相当熟悉,可以不需要那么多判断 直接使用就好。
下面是我写RPG游戏时的Json数据加载,因为这个Json是我自己设计的,相当的熟悉,所以我也就直接拿来用了:
void DataLoad::getNpc()
{
//[1] 读取json文件内容
std::string str = FileUtils::getInstance()->getStringFromFile("Npc.json");
//CCLOG("%s", str.c_str());
//[2] 创建用于处理json代码的类
rapidjson::Document d;
//[3] 解析json文件内容
d.Parse<rapidjson::kParseDefaultFlags>(str.c_str());
//数组内容加载
int len = d.Size();
for (int i = 0; i < len; i++) {
NpcObject* Npc = new NpcObject();
Npc->NpcID = d[i]["id"].GetInt();
Npc->NpcPic = d[i]["NpcURL"].GetString();
Npc->NpcName = d[i]["NpcName"].GetString();
Npc->setNpcX = d[i]["X"].GetInt();
Npc->setNpcY = d[i]["Y"].GetInt();
Npc->NpcLines = d[i]["dialogue"].GetString();
Npc->type = d[i]["type"].GetInt();
npcVec.push_back(Npc);
}
}
上面就是一个把Json数据加载成内存数据的过程。