I have written a simple wrapper around rapidjson for parsing json file in Cocos2dx-2.3.3. You can not use this wrapper in lower versions of Cocos2dx because they don't have included rapidjon library by default, therefore you have to add rapidjson externally for use.
JsonReader.h
#ifndef __JSON_READER__
#define __JSON_READER__
#include "cocos2d.h"
#include "cocos-ext.h"
#include <string>
USING_NS_CC;
USING_NS_CC_EXT;
using namespace std;
using namespace rapidjson;
class JsonReader
{
public:
static JsonReader* getInstance();
void read(const char *fileName);
void purge(void);
void destroyInstance(void);
void moveNext(void);
int getRowCount(void);
int getInt(const char* key, int def = 0);
float getFloat(const char* key, float def = 0.0f);
string getString(const char* key, const char* def = "");
bool getBool(const char* key, bool def = false);
private:
JsonReader();
~JsonReader();
const Value& getSubDict(void);
static JsonReader* m_pJsonReader;
Document doc;
unsigned char* m_pBytes;
string m_sFileName;
int m_nRowId;
};
#endif
JsonReader.cpp
#include "JsonReader.h"
JsonReader* JsonReader::m_pJsonReader = NULL;
JsonReader::JsonReader() {
m_pBytes = NULL;
m_nRowId = -1;
}
JsonReader::~JsonReader() {
purge();
}
JsonReader* JsonReader::getInstance() {
if (m_pJsonReader == NULL) {
m_pJsonReader = new JsonReader();
}
return m_pJsonReader;
}
void JsonReader::read(const char *fileName) {
unsigned long size = 0;
m_sFileName = fileName;
string jsonFile = m_sFileName + ".json";
string jsonpath = CCFileUtils::sharedFileUtils()->fullPathForFilename(jsonFile.c_str());
m_pBytes = CCFileUtils::sharedFileUtils()->getFileData(jsonpath.c_str(), "r", &size);
CCAssert( m_pBytes!= NULL, "JSON file not found");
CCAssert( strcmp((char*)m_pBytes, "") != 0, "JSON file is empty");
string load_str((const char*)m_pBytes, size);
doc.Parse<0>(load_str.c_str());
if(doc.HasParseError()) {
CCLog("Parsing for JSON file failed : %s", jsonFile.c_str());
}
CCAssert(!doc.HasParseError(), doc.GetParseError());
}
void JsonReader::purge(void) {
if(m_pBytes) {
delete m_pBytes;
m_pBytes = NULL;
m_nRowId = -1;
}
}
void JsonReader::destroyInstance(void) {
DictionaryHelper::shareHelper()->purgeDictionaryHelper();
if(m_pJsonReader) {
purge();
delete m_pJsonReader;
m_pJsonReader = NULL;
}
}
void JsonReader::moveNext(void) {
m_nRowId++;
}
const Value& JsonReader::getSubDict(void) {
return DICTOOL->getSubDictionary_json(doc, m_sFileName.c_str(), m_nRowId);
}
int JsonReader::getRowCount(void) {
return DICTOOL->getArrayCount_json(doc, m_sFileName.c_str());
}
int JsonReader::getInt(const char* key, int def /* = 0 */) {
return DICTOOL->getIntValue_json(getSubDict(), key, def);
}
float JsonReader::getFloat(const char* key, float def /* = 0.0f */) {
return DICTOOL->getFloatValue_json(getSubDict(), key, def);
}
string JsonReader::getString(const char* key, const char* def /* = "" */) {
return DICTOOL->getStringValue_json(getSubDict(), key, def );
}
bool JsonReader::getBool(const char* key, bool def /* = false */) {
return DICTOOL->getBooleanValue_json(getSubDict(), key, def);
}
Sample JSON file: LEVELS.json
{ "LEVELS" : [ {
"ID" : 0,
"LOCK" : false,
"NAME" : "LEVEL0",
"SCORE" : 100,
"SPEED" : 10
},
{ "ID" : 1,
"LOCK" : true,
"NAME" : "LEVEL1",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 2,
"LOCK" : true,
"NAME" : "LEVEL2",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 3,
"LOCK" : true,
"NAME" : "LEVEL3",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 4,
"LOCK" : true,
"NAME" : "LEVEL4",
"SCORE" : 100,
"SPEED" : 10
}
] }
Sample function to parse JSON file using JsonReader wrapper class.
void parseJsonFile(void) {
struct LevelItem {
int id;
bool lock;
int score;
int velocity;
std::string name;
void Print() {
CCLOG("ID: %d", id);
CCLOG("LOCK: %s", lock ? "true" : "false");
CCLOG("SCORE: %d", score);
CCLOG("VELOCITY: %d", velocity);
CCLOG("NAME: %s", name.c_str());
}
};
JsonReader* pReader = JsonReader::getInstance();
pReader->read("LEVELS");
int rows = pReader->getRowCount();
for (int i = 0; i < rows; i++) {
pReader->moveNext();
LevelItem* pLevelItem = new LevelItem();
pLevelItem->id = pReader->getInt("ID");
pLevelItem->lock = pReader->getBool("LOCK");
pLevelItem->score = pReader->getInt("SCORE");
pLevelItem->velocity = pReader->getInt("VELOCITY");
pLevelItem->name = pReader->getString("NAME");
pLevelItem->Print();
}
pReader->purge();
}
JsonReader.h
#ifndef __JSON_READER__
#define __JSON_READER__
#include "cocos2d.h"
#include "cocos-ext.h"
#include <string>
USING_NS_CC;
USING_NS_CC_EXT;
using namespace std;
using namespace rapidjson;
class JsonReader
{
public:
static JsonReader* getInstance();
void read(const char *fileName);
void purge(void);
void destroyInstance(void);
void moveNext(void);
int getRowCount(void);
int getInt(const char* key, int def = 0);
float getFloat(const char* key, float def = 0.0f);
string getString(const char* key, const char* def = "");
bool getBool(const char* key, bool def = false);
private:
JsonReader();
~JsonReader();
const Value& getSubDict(void);
static JsonReader* m_pJsonReader;
Document doc;
unsigned char* m_pBytes;
string m_sFileName;
int m_nRowId;
};
#endif
JsonReader.cpp
#include "JsonReader.h"
JsonReader* JsonReader::m_pJsonReader = NULL;
JsonReader::JsonReader() {
m_pBytes = NULL;
m_nRowId = -1;
}
JsonReader::~JsonReader() {
purge();
}
JsonReader* JsonReader::getInstance() {
if (m_pJsonReader == NULL) {
m_pJsonReader = new JsonReader();
}
return m_pJsonReader;
}
void JsonReader::read(const char *fileName) {
unsigned long size = 0;
m_sFileName = fileName;
string jsonFile = m_sFileName + ".json";
string jsonpath = CCFileUtils::sharedFileUtils()->fullPathForFilename(jsonFile.c_str());
m_pBytes = CCFileUtils::sharedFileUtils()->getFileData(jsonpath.c_str(), "r", &size);
CCAssert( m_pBytes!= NULL, "JSON file not found");
CCAssert( strcmp((char*)m_pBytes, "") != 0, "JSON file is empty");
string load_str((const char*)m_pBytes, size);
doc.Parse<0>(load_str.c_str());
if(doc.HasParseError()) {
CCLog("Parsing for JSON file failed : %s", jsonFile.c_str());
}
CCAssert(!doc.HasParseError(), doc.GetParseError());
}
void JsonReader::purge(void) {
if(m_pBytes) {
delete m_pBytes;
m_pBytes = NULL;
m_nRowId = -1;
}
}
void JsonReader::destroyInstance(void) {
DictionaryHelper::shareHelper()->purgeDictionaryHelper();
if(m_pJsonReader) {
purge();
delete m_pJsonReader;
m_pJsonReader = NULL;
}
}
void JsonReader::moveNext(void) {
m_nRowId++;
}
const Value& JsonReader::getSubDict(void) {
return DICTOOL->getSubDictionary_json(doc, m_sFileName.c_str(), m_nRowId);
}
int JsonReader::getRowCount(void) {
return DICTOOL->getArrayCount_json(doc, m_sFileName.c_str());
}
int JsonReader::getInt(const char* key, int def /* = 0 */) {
return DICTOOL->getIntValue_json(getSubDict(), key, def);
}
float JsonReader::getFloat(const char* key, float def /* = 0.0f */) {
return DICTOOL->getFloatValue_json(getSubDict(), key, def);
}
string JsonReader::getString(const char* key, const char* def /* = "" */) {
return DICTOOL->getStringValue_json(getSubDict(), key, def );
}
bool JsonReader::getBool(const char* key, bool def /* = false */) {
return DICTOOL->getBooleanValue_json(getSubDict(), key, def);
}
Sample JSON file: LEVELS.json
{ "LEVELS" : [ {
"ID" : 0,
"LOCK" : false,
"NAME" : "LEVEL0",
"SCORE" : 100,
"SPEED" : 10
},
{ "ID" : 1,
"LOCK" : true,
"NAME" : "LEVEL1",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 2,
"LOCK" : true,
"NAME" : "LEVEL2",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 3,
"LOCK" : true,
"NAME" : "LEVEL3",
"SCORE" : 100,
"SPEED" : 10
},
{"ID" : 4,
"LOCK" : true,
"NAME" : "LEVEL4",
"SCORE" : 100,
"SPEED" : 10
}
] }
Sample function to parse JSON file using JsonReader wrapper class.
void parseJsonFile(void) {
struct LevelItem {
int id;
bool lock;
int score;
int velocity;
std::string name;
void Print() {
CCLOG("ID: %d", id);
CCLOG("LOCK: %s", lock ? "true" : "false");
CCLOG("SCORE: %d", score);
CCLOG("VELOCITY: %d", velocity);
CCLOG("NAME: %s", name.c_str());
}
};
JsonReader* pReader = JsonReader::getInstance();
pReader->read("LEVELS");
int rows = pReader->getRowCount();
for (int i = 0; i < rows; i++) {
pReader->moveNext();
LevelItem* pLevelItem = new LevelItem();
pLevelItem->id = pReader->getInt("ID");
pLevelItem->lock = pReader->getBool("LOCK");
pLevelItem->score = pReader->getInt("SCORE");
pLevelItem->velocity = pReader->getInt("VELOCITY");
pLevelItem->name = pReader->getString("NAME");
pLevelItem->Print();
}
pReader->purge();
}