split CKContext work
This commit is contained in:
parent
5c1af5be24
commit
ab8a9da526
|
@ -14,7 +14,7 @@ namespace LibCmo::CK2 {
|
||||||
#pragma region Ctor Dtor
|
#pragma region Ctor Dtor
|
||||||
|
|
||||||
CKContext::CKContext() :
|
CKContext::CKContext() :
|
||||||
m_ObjectsList(), m_ReturnedObjectIds(),
|
m_ObjectsList(), m_ReturnedObjectOffsets(),
|
||||||
m_GroupGlobalIndex(), m_SceneGlobalIndex(),
|
m_GroupGlobalIndex(), m_SceneGlobalIndex(),
|
||||||
m_CompressionLevel(5), m_FileWriteMode(CK_FILE_WRITEMODE::CKFILE_UNCOMPRESSED),
|
m_CompressionLevel(5), m_FileWriteMode(CK_FILE_WRITEMODE::CKFILE_UNCOMPRESSED),
|
||||||
m_NameEncoding(), m_TempFolder(),
|
m_NameEncoding(), m_TempFolder(),
|
||||||
|
@ -29,147 +29,28 @@ namespace LibCmo::CK2 {
|
||||||
}
|
}
|
||||||
|
|
||||||
CKContext::~CKContext() {
|
CKContext::~CKContext() {
|
||||||
DestroyAllCKObjects();
|
ClearAll();
|
||||||
}
|
}
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region Objects Management
|
#pragma region Objects Management
|
||||||
|
|
||||||
ObjImpls::CKObject* CKContext::CreateObject(CK_CLASSID cls, CKSTRING name,
|
void CKContext::ClearAll() {
|
||||||
CK_OBJECTCREATION_OPTIONS options, CK_CREATIONMODE* res) {
|
|
||||||
// todo: Process paramter options and res
|
|
||||||
|
|
||||||
// get description first
|
|
||||||
const CKClassDesc* desc = CKGetClassDesc(cls);
|
|
||||||
if (desc == nullptr) return nullptr;
|
|
||||||
|
|
||||||
// allocate a CK_ID first
|
|
||||||
CK_ID decided_id;
|
|
||||||
if (this->m_ReturnedObjectIds.empty()) {
|
|
||||||
// create new CK_ID.
|
|
||||||
decided_id = static_cast<CK_ID>(m_ObjectsList.size());
|
|
||||||
m_ObjectsList.resize(decided_id + 1);
|
|
||||||
} else {
|
|
||||||
// use returned CK_ID.
|
|
||||||
decided_id = m_ReturnedObjectIds.back();
|
|
||||||
m_ReturnedObjectIds.pop_back();
|
|
||||||
}
|
|
||||||
|
|
||||||
// create one
|
|
||||||
ObjImpls::CKObject* obj = desc->CreationFct(this, decided_id + c_ObjectIdOffset, name);
|
|
||||||
|
|
||||||
// put into slot
|
|
||||||
m_ObjectsList[decided_id] = obj;
|
|
||||||
|
|
||||||
// set out variable
|
|
||||||
return obj;
|
|
||||||
}
|
|
||||||
|
|
||||||
ObjImpls::CKObject* CKContext::GetObject(CK_ID id) {
|
|
||||||
id -= c_ObjectIdOffset;
|
|
||||||
if (id >= m_ObjectsList.size()) return nullptr;
|
|
||||||
return m_ObjectsList[id];
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief The real CKObject destroy worker shared by CKContext::DestroyObject and CKContext::~CKContext
|
|
||||||
* @param[in] ctx The CKContext
|
|
||||||
* @param[in] obj The CKObject need to be free.
|
|
||||||
*/
|
|
||||||
static void InternalDestroy(CKContext* ctx, ObjImpls::CKObject* obj) {
|
|
||||||
// find desc by classid
|
|
||||||
// if really we can not find it, we only can delete it directly.
|
|
||||||
const CKClassDesc* desc = CKGetClassDesc(obj->GetClassID());
|
|
||||||
if (desc == nullptr) {
|
|
||||||
delete obj;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// free it and return its value
|
|
||||||
desc->ReleaseFct(ctx, obj);
|
|
||||||
}
|
|
||||||
void CKContext::DestroyObject(CK_ID id) {
|
|
||||||
id -= c_ObjectIdOffset;
|
|
||||||
if (id >= m_ObjectsList.size()) return;
|
|
||||||
|
|
||||||
// get object and free it
|
|
||||||
ObjImpls::CKObject* obj = m_ObjectsList[id];
|
|
||||||
if (obj == nullptr) return;
|
|
||||||
InternalDestroy(this, obj);
|
|
||||||
|
|
||||||
// return its allocated id.
|
|
||||||
m_ObjectsList[id] = nullptr;
|
|
||||||
m_ReturnedObjectIds.emplace_back(id);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
CKDWORD CKContext::AllocateGroupGlobalIndex() {
|
|
||||||
// try find first non-true position
|
|
||||||
CKDWORD index;
|
|
||||||
if (!XContainer::XBitArrayPatch::GetSetBitPosition(m_GroupGlobalIndex, 0, index)) {
|
|
||||||
// failed. distribute new one
|
|
||||||
index = static_cast<CKDWORD>(m_GroupGlobalIndex.size());
|
|
||||||
m_GroupGlobalIndex.resize(m_GroupGlobalIndex.size() + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// set to occupy
|
|
||||||
m_GroupGlobalIndex[index] = true;
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
|
|
||||||
CKDWORD CKContext::AllocateSceneGlobalIndex() {
|
|
||||||
// same as group
|
|
||||||
CKDWORD index;
|
|
||||||
if (!XContainer::XBitArrayPatch::GetSetBitPosition(m_SceneGlobalIndex, 0, index)) {
|
|
||||||
index = static_cast<CKDWORD>(m_SceneGlobalIndex.size());
|
|
||||||
m_SceneGlobalIndex.resize(m_SceneGlobalIndex.size() + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_SceneGlobalIndex[index] = true;
|
|
||||||
return index;
|
|
||||||
}
|
|
||||||
|
|
||||||
void CKContext::FreeGroupGlobalIndex(CKDWORD id) {
|
|
||||||
// check position
|
|
||||||
if (id >= m_GroupGlobalIndex.size()) return;
|
|
||||||
// set value
|
|
||||||
m_GroupGlobalIndex[id] = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void CKContext::FreeSceneGlobalIndex(CKDWORD id) {
|
|
||||||
// same as group
|
|
||||||
if (id >= m_SceneGlobalIndex.size()) return;
|
|
||||||
m_SceneGlobalIndex[id] = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void CKContext::DestroyAllCKObjects() {
|
|
||||||
// free all created objects
|
|
||||||
for (auto& ptr : m_ObjectsList) {
|
|
||||||
if (ptr != nullptr) {
|
|
||||||
InternalDestroy(this, ptr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// restore returned object list
|
|
||||||
m_ReturnedObjectIds.clear();
|
|
||||||
// empty object list
|
|
||||||
m_ObjectsList.clear();
|
|
||||||
|
|
||||||
// clear group and scene global index at the same time
|
|
||||||
m_SceneGlobalIndex.clear();
|
|
||||||
m_GroupGlobalIndex.clear();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region Common Manager Functions
|
#pragma region Common Manager Functions
|
||||||
|
|
||||||
CKINT CKContext::GetManagerCount() {
|
CKDWORD CKContext::GetManagerCount() {
|
||||||
return 0;
|
return m_ManagerList.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
MgrImpls::CKBaseManager* CKContext::GetManager(CKINT index) {
|
MgrImpls::CKBaseManager* CKContext::GetManager(CKDWORD index) {
|
||||||
return nullptr;
|
if (index >= m_ManagerList.size()) return nullptr;
|
||||||
|
return m_ManagerList[index];
|
||||||
}
|
}
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
|
@ -21,52 +21,26 @@ namespace LibCmo::CK2 {
|
||||||
class CKContext {
|
class CKContext {
|
||||||
public:
|
public:
|
||||||
CKContext();
|
CKContext();
|
||||||
CKContext(const CKContext&) = delete;
|
|
||||||
CKContext& operator=(const CKContext&) = delete;
|
|
||||||
~CKContext();
|
~CKContext();
|
||||||
|
LIBCMO_DISABLE_COPY_MOVE(CKContext);
|
||||||
// ========== Objects Management ==========
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Creates a CKObject or derived class instance.
|
* @brief Simply clear all CKContext to restore its status.
|
||||||
* @param[in] cls Class Identifier (CK_CLASSID) of the object to create.
|
|
||||||
* @param[in] name The name of this object.
|
|
||||||
* @param[in] options Tell CKContext how to create this object when conflict happended.
|
|
||||||
* @param[out] res The value indicate the real method how this object created.
|
|
||||||
* @return A pointer to the newly created object.
|
|
||||||
* @remark CKObjects must be destroy with the DestroyObject method.
|
|
||||||
* @see CKObject, DestroyObject
|
|
||||||
*/
|
*/
|
||||||
ObjImpls::CKObject* CreateObject(CK_CLASSID cls, CKSTRING name,
|
void ClearAll();
|
||||||
CK_OBJECTCREATION_OPTIONS options = CK_OBJECTCREATION_OPTIONS::CK_OBJECTCREATION_NONAMECHECK,
|
|
||||||
CK_CREATIONMODE* res = nullptr);
|
|
||||||
ObjImpls::CKObject* GetObject(CK_ID id);
|
|
||||||
void DestroyObject(CK_ID id);
|
|
||||||
|
|
||||||
CKDWORD AllocateGroupGlobalIndex();
|
// ========== Common Managers ==========
|
||||||
CKDWORD AllocateSceneGlobalIndex();
|
|
||||||
void FreeGroupGlobalIndex(CKDWORD id);
|
|
||||||
void FreeSceneGlobalIndex(CKDWORD id);
|
|
||||||
|
|
||||||
void DestroyAllCKObjects();
|
MgrImpls::CKObjectManager* GetObjectManager();
|
||||||
|
MgrImpls::CKPathManager* GetPathManager();
|
||||||
|
|
||||||
// ========== Object Access ==========
|
CKDWORD GetManagerCount();
|
||||||
|
MgrImpls::CKBaseManager* GetManager(CKDWORD index);
|
||||||
|
|
||||||
//CKManagerImplements::CKBaseManager* CreateCKManager(CKGUID guid);
|
void ExecuteManagersOnPreClearAll();
|
||||||
//CKManagerImplements::CKBaseManager* GetCKManager(CK_ID guid);
|
void ExecuteManagersOnPostClearAll();
|
||||||
//void DestroyCKManager(CKManagerImplements::CKBaseManager* mgr);
|
void ExecuteManagersSequenceToBeDeleted();
|
||||||
|
void ExecuteManagersSequenceDeleted();
|
||||||
//CKObject* GetObjectByName(CKSTRING name, CKObject* previous = NULL);
|
|
||||||
//CKObject* GetObjectByNameAndClass(CKSTRING name, CK_CLASSID cid, CKObject* previous = NULL);
|
|
||||||
//CKObject* GetObjectByNameAndParentClass(CKSTRING name, CK_CLASSID pcid, CKObject* previous);
|
|
||||||
//const XContainer::XObjectPointerArray GetObjectListByType(CK_CLASSID cid, CKBOOL derived);
|
|
||||||
//CKINT GetObjectsCountByClassID(CK_CLASSID cid);
|
|
||||||
//CK_ID* GetObjectsListByClassID(CK_CLASSID cid);
|
|
||||||
|
|
||||||
// ========== Common Managers Functions ==========
|
|
||||||
|
|
||||||
CKINT GetManagerCount();
|
|
||||||
MgrImpls::CKBaseManager* GetManager(CKINT index);
|
|
||||||
|
|
||||||
// ========== File Save/Load Options ==========
|
// ========== File Save/Load Options ==========
|
||||||
|
|
||||||
|
@ -76,6 +50,15 @@ namespace LibCmo::CK2 {
|
||||||
void SetFileWriteMode(CK_FILE_WRITEMODE mode);
|
void SetFileWriteMode(CK_FILE_WRITEMODE mode);
|
||||||
CK_FILE_WRITEMODE GetFileWriteMode();
|
CK_FILE_WRITEMODE GetFileWriteMode();
|
||||||
|
|
||||||
|
CK_TEXTURE_SAVEOPTIONS GetGlobalImagesSaveOptions();
|
||||||
|
void SetGlobalImagesSaveOptions(CK_TEXTURE_SAVEOPTIONS Options);
|
||||||
|
|
||||||
|
CKBitmapProperties* GetGlobalImagesSaveFormat();
|
||||||
|
void SetGlobalImagesSaveFormat(CKBitmapProperties* Format);
|
||||||
|
|
||||||
|
CK_SOUND_SAVEOPTIONS GetGlobalSoundsSaveOptions();
|
||||||
|
void SetGlobalSoundsSaveOptions(CK_SOUND_SAVEOPTIONS Options);
|
||||||
|
|
||||||
// ========== Encoding utilities ==========
|
// ========== Encoding utilities ==========
|
||||||
|
|
||||||
void GetUtf8String(const std::string& native_name, std::string& u8_name);
|
void GetUtf8String(const std::string& native_name, std::string& u8_name);
|
||||||
|
@ -95,24 +78,16 @@ namespace LibCmo::CK2 {
|
||||||
void SetOutputCallback(OutputCallback cb);
|
void SetOutputCallback(OutputCallback cb);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// ========== Objects Management ==========
|
// ========== Common Managers ==========
|
||||||
|
void ExecuteManagersGeneral(std::function<void(MgrImpls::CKBaseManager*)> fct);
|
||||||
/**
|
XContainer::XArray<MgrImpls::CKBaseManager*> m_ManagerList;
|
||||||
* The global offset of created CK_ID.
|
|
||||||
* The value close to zero may cause some issue.
|
|
||||||
* So we add a static offset to every created CK_ID.
|
|
||||||
*/
|
|
||||||
const CK_ID c_ObjectIdOffset = 61u;
|
|
||||||
|
|
||||||
XContainer::XArray<ObjImpls::CKObject*> m_ObjectsList;
|
|
||||||
std::deque<CK_ID> m_ReturnedObjectIds;
|
|
||||||
|
|
||||||
XContainer::XBitArray m_GroupGlobalIndex;
|
|
||||||
XContainer::XBitArray m_SceneGlobalIndex;
|
|
||||||
|
|
||||||
// ========== File Save/Load Options ==========
|
// ========== File Save/Load Options ==========
|
||||||
CKINT m_CompressionLevel;
|
CKINT m_CompressionLevel;
|
||||||
CK_FILE_WRITEMODE m_FileWriteMode;
|
CK_FILE_WRITEMODE m_FileWriteMode;
|
||||||
|
CK_TEXTURE_SAVEOPTIONS m_GlobalImagesSaveOptions;
|
||||||
|
CK_SOUND_SAVEOPTIONS m_GlobalSoundsSaveOptions;
|
||||||
|
CKBitmapProperties* m_GlobalImagesSaveFormat;
|
||||||
|
|
||||||
// ========== Encoding utilities ==========
|
// ========== Encoding utilities ==========
|
||||||
|
|
||||||
|
|
|
@ -348,7 +348,7 @@ namespace LibCmo::CK2 {
|
||||||
if (obj.Data == nullptr) continue;
|
if (obj.Data == nullptr) continue;
|
||||||
|
|
||||||
// create object and assign created obj ckid
|
// create object and assign created obj ckid
|
||||||
obj.ObjPtr = m_Ctx->CreateObject(obj.ObjectCid, obj.Name.c_str());
|
obj.ObjPtr = m_Ctx->CreateObject(obj.ObjectCid, obj.Name.toCKSTRING());
|
||||||
if (obj.ObjPtr == nullptr) {
|
if (obj.ObjPtr == nullptr) {
|
||||||
obj.CreatedObjectId = 0u;
|
obj.CreatedObjectId = 0u;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -89,9 +89,9 @@ namespace LibCmo::CK2 {
|
||||||
for (auto& obj : m_FileObjects) {
|
for (auto& obj : m_FileObjects) {
|
||||||
// += 4DWORD(ObjId, ObjCid, FileIndex, NameLen)
|
// += 4DWORD(ObjId, ObjCid, FileIndex, NameLen)
|
||||||
sumHdrObjSize += 4 * CKSizeof(CKDWORD);
|
sumHdrObjSize += 4 * CKSizeof(CKDWORD);
|
||||||
if (obj.Name.c_str() != nullptr) {
|
if (obj.Name.toCKSTRING() != nullptr) {
|
||||||
// += Name size
|
// += Name size
|
||||||
m_Ctx->GetNativeString(obj.Name.string(), name_conv);
|
m_Ctx->GetNativeString(obj.Name.toString(), name_conv);
|
||||||
sumHdrObjSize += static_cast<CKDWORD>(name_conv.size());
|
sumHdrObjSize += static_cast<CKDWORD>(name_conv.size());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -176,8 +176,8 @@ namespace LibCmo::CK2 {
|
||||||
hdrparser->Write(&obj.ObjectCid, sizeof(CK_CLASSID));
|
hdrparser->Write(&obj.ObjectCid, sizeof(CK_CLASSID));
|
||||||
hdrparser->Write(&obj.FileIndex, sizeof(CKDWORD));
|
hdrparser->Write(&obj.FileIndex, sizeof(CKDWORD));
|
||||||
|
|
||||||
if (obj.Name.c_str() != nullptr) {
|
if (obj.Name.toCKSTRING() != nullptr) {
|
||||||
m_Ctx->GetNativeString(obj.Name.string(), name_conv);
|
m_Ctx->GetNativeString(obj.Name.toString(), name_conv);
|
||||||
CKDWORD namelen = static_cast<CKDWORD>(name_conv.size());
|
CKDWORD namelen = static_cast<CKDWORD>(name_conv.size());
|
||||||
hdrparser->Write(&namelen, sizeof(CKDWORD));
|
hdrparser->Write(&namelen, sizeof(CKDWORD));
|
||||||
hdrparser->Write(name_conv.data(), namelen);
|
hdrparser->Write(name_conv.data(), namelen);
|
||||||
|
|
|
@ -64,6 +64,22 @@ namespace LibCmo::CK2 {
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
|
#pragma region String Utilities
|
||||||
|
|
||||||
|
bool CKStrEqual(CKSTRING str1, CKSTRING str2) {
|
||||||
|
if (str1 == nullptr) {
|
||||||
|
if (str2 == nullptr) return true;
|
||||||
|
else return false;
|
||||||
|
} else {
|
||||||
|
if (str2 == nullptr) return false;
|
||||||
|
else {
|
||||||
|
return std::strcmp(str1, str2) == 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region CKClass Registration
|
#pragma region CKClass Registration
|
||||||
|
|
||||||
static XContainer::XArray<CKClassDesc> g_CKClassInfo;
|
static XContainer::XArray<CKClassDesc> g_CKClassInfo;
|
||||||
|
|
|
@ -45,6 +45,10 @@ namespace LibCmo::CK2 {
|
||||||
*/
|
*/
|
||||||
CKDWORD CKComputeDataCRC(const void* data, CKDWORD size, CKDWORD PreviousCRC = 0);
|
CKDWORD CKComputeDataCRC(const void* data, CKDWORD size, CKDWORD PreviousCRC = 0);
|
||||||
|
|
||||||
|
// ========== String Utilities ==========
|
||||||
|
|
||||||
|
bool CKStrEqual(CKSTRING str1, CKSTRING str2);
|
||||||
|
|
||||||
// ========== Numberic Utilities ==========
|
// ========== Numberic Utilities ==========
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -272,6 +272,7 @@ namespace LibCmo::CK2 {
|
||||||
//--- Managers
|
//--- Managers
|
||||||
namespace MgrImpls {
|
namespace MgrImpls {
|
||||||
class CKBaseManager;
|
class CKBaseManager;
|
||||||
|
class CKObjectManager;
|
||||||
class CKSoundManager;
|
class CKSoundManager;
|
||||||
class CKTimeManager;
|
class CKTimeManager;
|
||||||
class CKRenderManager;
|
class CKRenderManager;
|
||||||
|
|
|
@ -2,6 +2,28 @@
|
||||||
|
|
||||||
#include "../../VTAll.hpp"
|
#include "../../VTAll.hpp"
|
||||||
|
|
||||||
|
/**
|
||||||
|
CKBaseManager virtual functions implementations help
|
||||||
|
All virtual functions is not supported except we implemented.
|
||||||
|
|
||||||
|
Read/Write functions:
|
||||||
|
- SaveData()
|
||||||
|
- LoadData()
|
||||||
|
|
||||||
|
Clear functions:
|
||||||
|
- PreClearAll()
|
||||||
|
- PostClearAll()
|
||||||
|
|
||||||
|
Delete functions:
|
||||||
|
- SequenceToBeDeleted()
|
||||||
|
- SequenceDeleted()
|
||||||
|
|
||||||
|
Moved functions
|
||||||
|
- OnCKInit(): Implement in ctor
|
||||||
|
- OnCKEnd(): Implement in dtor
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
namespace LibCmo::CK2::MgrImpls {
|
namespace LibCmo::CK2::MgrImpls {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -16,8 +38,7 @@ namespace LibCmo::CK2::MgrImpls {
|
||||||
CKBaseManager(CKContext* ctx, CKGUID guid, CKSTRING name) :
|
CKBaseManager(CKContext* ctx, CKGUID guid, CKSTRING name) :
|
||||||
m_ManagerGuid(guid),
|
m_ManagerGuid(guid),
|
||||||
m_ManagerName(name),
|
m_ManagerName(name),
|
||||||
m_Context(ctx)
|
m_Context(ctx) {}
|
||||||
{}
|
|
||||||
virtual ~CKBaseManager() {}
|
virtual ~CKBaseManager() {}
|
||||||
LIBCMO_DISABLE_COPY_MOVE(CKBaseManager);
|
LIBCMO_DISABLE_COPY_MOVE(CKBaseManager);
|
||||||
|
|
||||||
|
@ -56,13 +77,13 @@ namespace LibCmo::CK2::MgrImpls {
|
||||||
```
|
```
|
||||||
*/
|
*/
|
||||||
CKSTRING GetName() {
|
CKSTRING GetName() {
|
||||||
return m_ManagerName.c_str();
|
return m_ManagerName.toCKSTRING();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@brief Called to save manager data.
|
@brief Called to save manager data.
|
||||||
@param SavedFile A pointer to the CKFile being saved.
|
@param SavedFile A pointer to the CKFile being saved.
|
||||||
@return This function should return a valid CKStateChunk that contain data to save or NULL if there is nothing to save.
|
@return This function should return true or false if there is nothing to save.
|
||||||
@remark
|
@remark
|
||||||
+ During a save operation, each manager is given the opportunity to save its data in the file.
|
+ During a save operation, each manager is given the opportunity to save its data in the file.
|
||||||
+ The file being saved is given for information only and must not be modified. It can be used to decide whether it is worth saving
|
+ The file being saved is given for information only and must not be modified. It can be used to decide whether it is worth saving
|
||||||
|
@ -70,13 +91,13 @@ namespace LibCmo::CK2::MgrImpls {
|
||||||
@see CKStateChunk, LoadData
|
@see CKStateChunk, LoadData
|
||||||
*/
|
*/
|
||||||
virtual bool SaveData(CKStateChunk* chunk, CKFileVisitor* SavedFile) {
|
virtual bool SaveData(CKStateChunk* chunk, CKFileVisitor* SavedFile) {
|
||||||
return true;
|
return false; // default value is false to indicate this manager do not need save any data.
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
@brief Called to load manager data.
|
@brief Called to load manager data.
|
||||||
@param chunk A pointer to a CKStateChunk that was saved in the file.
|
@param chunk A pointer to a CKStateChunk that was saved in the file.
|
||||||
@param LoadedFile A pointer to the CKFile being loaded.
|
@param LoadedFile A pointer to the CKFile being loaded.
|
||||||
@return CK_OK if successful or an error code otherwise.
|
@return CKERR_OK if successful or an error code otherwise.
|
||||||
@remark
|
@remark
|
||||||
+ During a load operation, each manager is automatically called if there was a chunk saved in the file with SaveData.
|
+ During a load operation, each manager is automatically called if there was a chunk saved in the file with SaveData.
|
||||||
@see CKStateChunk, SaveData
|
@see CKStateChunk, SaveData
|
||||||
|
@ -85,6 +106,53 @@ namespace LibCmo::CK2::MgrImpls {
|
||||||
return CKERROR::CKERR_OK;
|
return CKERROR::CKERR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
@brief Called at the beginning of a CKContext::ClearAll operation.
|
||||||
|
@return CK_OK if successful or an error code otherwise.
|
||||||
|
@remark
|
||||||
|
+ You can override this function to add specific processing at the beginning of a CKContext::ClearAll operation.
|
||||||
|
+ You must override GetValidFunctionsMask and return a value including
|
||||||
|
CKMANAGER_FUNC_PreClearAll for this function to get called.
|
||||||
|
@see Main Virtools Events, PostClearAll, CKContext::ClearAll
|
||||||
|
*/
|
||||||
|
virtual CKERROR PreClearAll() { return CKERROR::CKERR_OK; }
|
||||||
|
/**
|
||||||
|
@brief Called at the end of a CKContext::ClearAll operation.
|
||||||
|
@return CKERR_OK if successful or an error code otherwise.
|
||||||
|
@remark
|
||||||
|
+ You can override this function to add specific processing at the end of a CKContext::ClearAll operation.
|
||||||
|
+ You must override GetValidFunctionsMask and return a value including
|
||||||
|
CKMANAGER_FUNC_PostClearAll for this function to get called.
|
||||||
|
@see Main Virtools Events, PreClearAll, CKContext::ClearAll
|
||||||
|
*/
|
||||||
|
virtual CKERROR PostClearAll() { return CKERROR::CKERR_OK; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
@brief Called just before objects are deleted.
|
||||||
|
@return CK_OK if successful or an error code otherwise.
|
||||||
|
@param objids[in] A pointer to a list of CK_ID of the objects being deleted.
|
||||||
|
@param count[in] number of objects in objids list.
|
||||||
|
@remark
|
||||||
|
+ You can override this function if you need to add specific processing before objects are deleted.
|
||||||
|
+ You must override GetValidFunctionsMask and return a value including
|
||||||
|
CKMANAGER_FUNC_OnSequenceToBeDeleted for this function to get called.
|
||||||
|
@see Main Virtools Events, CKContext::DestroyObjects, SequenceDeleted
|
||||||
|
*/
|
||||||
|
virtual CKERROR SequenceToBeDeleted(const CK_ID* objids, CKDWORD count) { return CKERROR::CKERR_OK; }
|
||||||
|
/**
|
||||||
|
@brief Called after objects have been deleted.
|
||||||
|
@return CK_OK if successful or an error code otherwise.
|
||||||
|
@param objids[in] A pointer to a list of CK_ID of the objects being deleted.
|
||||||
|
@param count[in] number of objects in objids list.
|
||||||
|
@remark
|
||||||
|
+ You can override this function if you need to add specific processing after objects have been deleted.
|
||||||
|
+ You must override GetValidFunctionsMask and return a value including
|
||||||
|
CKMANAGER_FUNC_OnSequenceDeleted for this function to get called.
|
||||||
|
@see Main Virtools Events, CKContext::DestroyObjects, SequenceToBeDeleted
|
||||||
|
*/
|
||||||
|
virtual CKERROR SequenceDeleted(const CK_ID* objids, CKDWORD count) { return CKERROR::CKERR_OK; }
|
||||||
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
CKGUID m_ManagerGuid; ///> Manager GUID
|
CKGUID m_ManagerGuid; ///> Manager GUID
|
||||||
TypeHelper::MKString m_ManagerName; ///> Manager Name
|
TypeHelper::MKString m_ManagerName; ///> Manager Name
|
||||||
|
|
196
LibCmo/CK2/MgrImpls/CKObjectManager.cpp
Normal file
196
LibCmo/CK2/MgrImpls/CKObjectManager.cpp
Normal file
|
@ -0,0 +1,196 @@
|
||||||
|
#include "CKObjectManager.hpp"
|
||||||
|
#include "../ObjImpls/CKObject.hpp"
|
||||||
|
|
||||||
|
namespace LibCmo::CK2::MgrImpls {
|
||||||
|
|
||||||
|
CKObjectManager::CKObjectManager(CKContext* ctx) :
|
||||||
|
CKBaseManager(ctx, OBJECT_MANAGER_GUID, "Object Manager"),
|
||||||
|
m_ObjectsList(), m_ReturnedObjectOffsets(), m_ObjectCount(0),
|
||||||
|
m_GroupGlobalIndex(), m_SceneGlobalIndex(),
|
||||||
|
m_ObjectsListByClass(CKGetClassCount()) {}
|
||||||
|
|
||||||
|
CKObjectManager::~CKObjectManager() {
|
||||||
|
DestroyAllObjects();
|
||||||
|
}
|
||||||
|
|
||||||
|
ObjImpls::CKObject* CKObjectManager::CreateObject(CK_CLASSID cls, CKSTRING name,
|
||||||
|
CK_OBJECTCREATION_OPTIONS options, CK_CREATIONMODE* res) {
|
||||||
|
// todo: Process paramter options and res
|
||||||
|
|
||||||
|
// get description first
|
||||||
|
const CKClassDesc* desc = CKGetClassDesc(cls);
|
||||||
|
if (desc == nullptr) return nullptr;
|
||||||
|
|
||||||
|
// allocate a CK_ID first
|
||||||
|
CKDWORD decided_off;
|
||||||
|
if (this->m_ReturnedObjectOffsets.empty()) {
|
||||||
|
// create new CK_ID.
|
||||||
|
decided_off = static_cast<CKDWORD>(m_ObjectsList.size());
|
||||||
|
m_ObjectsList.resize(decided_off + 1);
|
||||||
|
} else {
|
||||||
|
// use returned CK_ID.
|
||||||
|
decided_off = m_ReturnedObjectOffsets.back();
|
||||||
|
m_ReturnedObjectOffsets.pop_back();
|
||||||
|
}
|
||||||
|
|
||||||
|
// create one
|
||||||
|
ObjImpls::CKObject* obj = desc->CreationFct(m_Context, Offset2Id(decided_off), name);
|
||||||
|
|
||||||
|
// put into slot and inc count
|
||||||
|
m_ObjectsList[decided_off] = obj;
|
||||||
|
++m_ObjectCount;
|
||||||
|
|
||||||
|
// set out variable
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
ObjImpls::CKObject* CKObjectManager::GetObject(CK_ID id) {
|
||||||
|
CKDWORD off = Id2Offset(id);
|
||||||
|
if (off >= m_ObjectsList.size()) return nullptr;
|
||||||
|
return m_ObjectsList[off];
|
||||||
|
}
|
||||||
|
|
||||||
|
CKDWORD CKObjectManager::GetObjectCount() {
|
||||||
|
return m_ObjectCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CKObjectManager::InternalDestroy(ObjImpls::CKObject* obj) {
|
||||||
|
// find desc by classid
|
||||||
|
// if really we can not find it, we only can delete it directly.
|
||||||
|
const CKClassDesc* desc = CKGetClassDesc(obj->GetClassID());
|
||||||
|
if (desc == nullptr) {
|
||||||
|
delete obj;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// free it
|
||||||
|
desc->ReleaseFct(m_Context, obj);
|
||||||
|
}
|
||||||
|
|
||||||
|
void CKObjectManager::DestroyObject(CK_ID id) {
|
||||||
|
CKDWORD off = Id2Offset(id);
|
||||||
|
if (off >= m_ObjectsList.size()) return;
|
||||||
|
|
||||||
|
// get object and free it
|
||||||
|
ObjImpls::CKObject* obj = m_ObjectsList[off];
|
||||||
|
if (obj == nullptr) return;
|
||||||
|
InternalDestroy(obj);
|
||||||
|
|
||||||
|
// return its allocated id.
|
||||||
|
// and dec count
|
||||||
|
m_ObjectsList[off] = nullptr;
|
||||||
|
m_ReturnedObjectOffsets.emplace_back(off);
|
||||||
|
--m_ObjectCount;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void CKObjectManager::DestroyAllObjects() {
|
||||||
|
// free all created objects
|
||||||
|
for (auto& ptr : m_ObjectsList) {
|
||||||
|
if (ptr != nullptr) {
|
||||||
|
InternalDestroy(ptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// restore returned object list
|
||||||
|
m_ReturnedObjectOffsets.clear();
|
||||||
|
// empty object list
|
||||||
|
m_ObjectsList.clear();
|
||||||
|
// reset count
|
||||||
|
m_ObjectCount = 0;
|
||||||
|
|
||||||
|
// clear obj by class list
|
||||||
|
for (auto& ls : m_ObjectsListByClass) {
|
||||||
|
ls.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
// clear group and scene global index at the same time
|
||||||
|
m_SceneGlobalIndex.clear();
|
||||||
|
m_GroupGlobalIndex.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
XContainer::XObjectPointerArray CKObjectManager::GetObjectByNameAndClass(CKSTRING name, CK_CLASSID cid, bool derived) {
|
||||||
|
XContainer::XObjectPointerArray result;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < m_ObjectsListByClass.size(); ++i) {
|
||||||
|
// check class id first
|
||||||
|
if (derived) {
|
||||||
|
if (!CKIsChildClassOf(static_cast<CK_CLASSID>(i), cid)) continue;
|
||||||
|
} else {
|
||||||
|
if (static_cast<CK_CLASSID>(i) != cid) continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// iterate all sub object and check name
|
||||||
|
for (const auto& objoff : m_ObjectsListByClass[i]) {
|
||||||
|
ObjImpls::CKObject* obj = m_ObjectsList[objoff];
|
||||||
|
|
||||||
|
if (name == nullptr) {
|
||||||
|
// directly add
|
||||||
|
result.emplace_back(obj);
|
||||||
|
} else {
|
||||||
|
// check name
|
||||||
|
if (CKStrEqual(name, obj->GetName())) {
|
||||||
|
result.emplace_back(obj);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
CKDWORD CKObjectManager::AllocateGroupGlobalIndex(ObjImpls::CKObject* group) {
|
||||||
|
// try find first nullptr position
|
||||||
|
CKDWORD index = 0;
|
||||||
|
for (const auto& ptr : m_GroupGlobalIndex) {
|
||||||
|
if (ptr == nullptr) break;
|
||||||
|
++index;
|
||||||
|
}
|
||||||
|
// resize array for new position
|
||||||
|
if (index == m_GroupGlobalIndex.size()) {
|
||||||
|
m_GroupGlobalIndex.resize(m_GroupGlobalIndex.size() + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set to occupy
|
||||||
|
m_GroupGlobalIndex[index] = group;
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
|
||||||
|
CKDWORD CKObjectManager::AllocateSceneGlobalIndex(ObjImpls::CKObject* scene) {
|
||||||
|
// same as group
|
||||||
|
CKDWORD index = 0;
|
||||||
|
for (const auto& ptr : m_SceneGlobalIndex) {
|
||||||
|
if (ptr == nullptr) break;
|
||||||
|
++index;
|
||||||
|
}
|
||||||
|
// resize array for new position
|
||||||
|
if (index == m_SceneGlobalIndex.size()) {
|
||||||
|
m_SceneGlobalIndex.resize(m_SceneGlobalIndex.size() + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set to occupy
|
||||||
|
m_SceneGlobalIndex[index] = scene;
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
|
||||||
|
ObjImpls::CKObject* CKObjectManager::GetGroupByGlobalIndex(CKDWORD index) {
|
||||||
|
if (index >= m_GroupGlobalIndex.size()) return nullptr;
|
||||||
|
else return m_GroupGlobalIndex[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
ObjImpls::CKObject* CKObjectManager::GetSceneByGlobalIndex(CKDWORD index) {
|
||||||
|
if (index >= m_SceneGlobalIndex.size()) return nullptr;
|
||||||
|
else return m_SceneGlobalIndex[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
void CKObjectManager::FreeGroupGlobalIndex(CKDWORD id) {
|
||||||
|
// check position
|
||||||
|
if (id >= m_GroupGlobalIndex.size()) return;
|
||||||
|
// set value
|
||||||
|
m_GroupGlobalIndex[id] = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CKObjectManager::FreeSceneGlobalIndex(CKDWORD id) {
|
||||||
|
// same as group
|
||||||
|
if (id >= m_SceneGlobalIndex.size()) return;
|
||||||
|
m_SceneGlobalIndex[id] = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
81
LibCmo/CK2/MgrImpls/CKObjectManager.hpp
Normal file
81
LibCmo/CK2/MgrImpls/CKObjectManager.hpp
Normal file
|
@ -0,0 +1,81 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "../../VTAll.hpp"
|
||||||
|
#include "CKBaseManager.hpp"
|
||||||
|
#include <deque>
|
||||||
|
|
||||||
|
namespace LibCmo::CK2::MgrImpls {
|
||||||
|
|
||||||
|
class CKObjectManager : public CKBaseManager {
|
||||||
|
public:
|
||||||
|
CKObjectManager(CKContext* ctx);
|
||||||
|
virtual ~CKObjectManager();
|
||||||
|
LIBCMO_DISABLE_COPY_MOVE(CKObjectManager);
|
||||||
|
|
||||||
|
// ========== Objects Management ==========
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Creates a CKObject or derived class instance.
|
||||||
|
* @param[in] cls Class Identifier (CK_CLASSID) of the object to create.
|
||||||
|
* @param[in] name The name of this object.
|
||||||
|
* @param[in] options Tell CKContext how to create this object when conflict happended.
|
||||||
|
* @param[out] res The value indicate the real method how this object created.
|
||||||
|
* @return A pointer to the newly created object.
|
||||||
|
* @remark CKObjects must be destroy with the DestroyObject method.
|
||||||
|
* @see CKObject, DestroyObject
|
||||||
|
*/
|
||||||
|
ObjImpls::CKObject* CreateObject(CK_CLASSID cls, CKSTRING name,
|
||||||
|
CK_OBJECTCREATION_OPTIONS options = CK_OBJECTCREATION_OPTIONS::CK_OBJECTCREATION_NONAMECHECK,
|
||||||
|
CK_CREATIONMODE* res = nullptr);
|
||||||
|
// todo: implement CopyObject by CKClassDesc
|
||||||
|
//ObjImpls::CKObject* CopyObject(ObjImpls::CKObject *src,
|
||||||
|
// CKDependencies* Dependencies = nullptr,
|
||||||
|
// CKSTRING AppendName = nullptr,
|
||||||
|
// CK_OBJECTCREATION_OPTIONS Options = CK_OBJECTCREATION_OPTIONS::CK_OBJECTCREATION_NONAMECHECK);
|
||||||
|
|
||||||
|
ObjImpls::CKObject* GetObject(CK_ID id);
|
||||||
|
CKDWORD GetObjectCount();
|
||||||
|
void DestroyObject(CK_ID id);
|
||||||
|
void DestroyAllObjects();
|
||||||
|
|
||||||
|
// ========== Objects Access ==========
|
||||||
|
|
||||||
|
XContainer::XObjectPointerArray GetObjectByNameAndClass(
|
||||||
|
CKSTRING name, CK_CLASSID cid, bool derived);
|
||||||
|
|
||||||
|
// ========== Special Functions ==========
|
||||||
|
|
||||||
|
CKDWORD AllocateGroupGlobalIndex(ObjImpls::CKObject* group);
|
||||||
|
CKDWORD AllocateSceneGlobalIndex(ObjImpls::CKObject* scene);
|
||||||
|
ObjImpls::CKObject* GetGroupByGlobalIndex(CKDWORD index);
|
||||||
|
ObjImpls::CKObject* GetSceneByGlobalIndex(CKDWORD index);
|
||||||
|
void FreeGroupGlobalIndex(CKDWORD id);
|
||||||
|
void FreeSceneGlobalIndex(CKDWORD id);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
/**
|
||||||
|
* The global offset of created CK_ID.
|
||||||
|
* The value close to zero may cause some issue.
|
||||||
|
* So we add a static offset to every created CK_ID.
|
||||||
|
*/
|
||||||
|
const CK_ID c_ObjectIdOffset = 61u;
|
||||||
|
CKDWORD Id2Offset(CK_ID id) { return static_cast<CKDWORD>(id - c_ObjectIdOffset); }
|
||||||
|
CK_ID Offset2Id(CKDWORD off) { return static_cast<CK_ID>(off + c_ObjectIdOffset); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief The real CKObject destroy worker shared by CKObjectManager::DestroyObject and CKObjectManager::~CKObjectManager
|
||||||
|
* @param[in] obj The CKObject need to be free.
|
||||||
|
*/
|
||||||
|
void InternalDestroy(ObjImpls::CKObject* obj);
|
||||||
|
|
||||||
|
CKDWORD m_ObjectCount;
|
||||||
|
XContainer::XObjectPointerArray m_ObjectsList;
|
||||||
|
XContainer::XArray<XContainer::XArray<CKDWORD>> m_ObjectsListByClass;
|
||||||
|
std::deque<CKDWORD> m_ReturnedObjectOffsets;
|
||||||
|
|
||||||
|
XContainer::XObjectPointerArray m_GroupGlobalIndex;
|
||||||
|
XContainer::XObjectPointerArray m_SceneGlobalIndex;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
6
LibCmo/CK2/MgrImpls/CKPathManager.cpp
Normal file
6
LibCmo/CK2/MgrImpls/CKPathManager.cpp
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
#include "CKPathManager.hpp"
|
||||||
|
|
||||||
|
namespace LibCmo::CK2::MgrImpls {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
19
LibCmo/CK2/MgrImpls/CKPathManager.hpp
Normal file
19
LibCmo/CK2/MgrImpls/CKPathManager.hpp
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "../../VTAll.hpp"
|
||||||
|
#include "CKBaseManager.hpp"
|
||||||
|
|
||||||
|
namespace LibCmo::CK2::MgrImpls {
|
||||||
|
|
||||||
|
class CKPathManager : public CKBaseManager {
|
||||||
|
public:
|
||||||
|
CKPathManager(CKContext* ctx) :
|
||||||
|
CKBaseManager(ctx, PATH_MANAGER_GUID, "Path Manager") {}
|
||||||
|
virtual ~CKPathManager() {}
|
||||||
|
LIBCMO_DISABLE_COPY_MOVE(CKPathManager);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
|
@ -2,6 +2,37 @@
|
||||||
|
|
||||||
#include "../../VTAll.hpp"
|
#include "../../VTAll.hpp"
|
||||||
|
|
||||||
|
/**
|
||||||
|
CKObject virtual functions implementations help
|
||||||
|
|
||||||
|
Implement as original meaning:
|
||||||
|
- PreSave()
|
||||||
|
- Save()
|
||||||
|
- Load()
|
||||||
|
- PostLoad()
|
||||||
|
|
||||||
|
- GetClassID()
|
||||||
|
|
||||||
|
- Show()
|
||||||
|
- IsHiddenByParent()
|
||||||
|
- CanBeHide()
|
||||||
|
- IsVisible()
|
||||||
|
|
||||||
|
No implement because don't care:
|
||||||
|
- GetMemoryOccupation()
|
||||||
|
- IsObjectUsed()
|
||||||
|
- PrepareDependencies()
|
||||||
|
- RemapDependencies()
|
||||||
|
|
||||||
|
- CheckPreDeletion()
|
||||||
|
- CheckPostDeletion()
|
||||||
|
|
||||||
|
Implement moved into other location:
|
||||||
|
- Copy(): Use CKObject::CKObject(CK_ID newid, const CKObject* obj) ctor and CKClassDesc to implement.
|
||||||
|
- PreDelete(): Write in dtor.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
namespace LibCmo::CK2::ObjImpls {
|
namespace LibCmo::CK2::ObjImpls {
|
||||||
|
|
||||||
class CKObject {
|
class CKObject {
|
||||||
|
@ -19,7 +50,7 @@ namespace LibCmo::CK2::ObjImpls {
|
||||||
return m_ID;
|
return m_ID;
|
||||||
}
|
}
|
||||||
CKSTRING GetName(void) {
|
CKSTRING GetName(void) {
|
||||||
return m_Name.c_str();
|
return m_Name.toCKSTRING();
|
||||||
}
|
}
|
||||||
void SetName(CKSTRING u8_name) {
|
void SetName(CKSTRING u8_name) {
|
||||||
m_Name = u8_name;
|
m_Name = u8_name;
|
||||||
|
|
|
@ -180,6 +180,8 @@
|
||||||
<ClCompile Include="CK2\CKGlobals.cpp" />
|
<ClCompile Include="CK2\CKGlobals.cpp" />
|
||||||
<ClCompile Include="CK2\MgrImpls\CKBaseManager.cpp" />
|
<ClCompile Include="CK2\MgrImpls\CKBaseManager.cpp" />
|
||||||
<ClCompile Include="CK2\CKContext.cpp" />
|
<ClCompile Include="CK2\CKContext.cpp" />
|
||||||
|
<ClCompile Include="CK2\MgrImpls\CKObjectManager.cpp" />
|
||||||
|
<ClCompile Include="CK2\MgrImpls\CKPathManager.cpp" />
|
||||||
<ClCompile Include="CK2\ObjImpls\CK3dEntity.cpp" />
|
<ClCompile Include="CK2\ObjImpls\CK3dEntity.cpp" />
|
||||||
<ClCompile Include="CK2\ObjImpls\CKBeObject.cpp" />
|
<ClCompile Include="CK2\ObjImpls\CKBeObject.cpp" />
|
||||||
<ClCompile Include="CK2\ObjImpls\CKGroup.cpp" />
|
<ClCompile Include="CK2\ObjImpls\CKGroup.cpp" />
|
||||||
|
@ -203,6 +205,8 @@
|
||||||
<ClInclude Include="CK2\CKContext.hpp" />
|
<ClInclude Include="CK2\CKContext.hpp" />
|
||||||
<ClInclude Include="CK2\CKStateChunk.hpp" />
|
<ClInclude Include="CK2\CKStateChunk.hpp" />
|
||||||
<ClInclude Include="CK2\CKTypes.hpp" />
|
<ClInclude Include="CK2\CKTypes.hpp" />
|
||||||
|
<ClInclude Include="CK2\MgrImpls\CKObjectManager.hpp" />
|
||||||
|
<ClInclude Include="CK2\MgrImpls\CKPathManager.hpp" />
|
||||||
<ClInclude Include="CK2\ObjImpls\CK3dEntity.hpp" />
|
<ClInclude Include="CK2\ObjImpls\CK3dEntity.hpp" />
|
||||||
<ClInclude Include="CK2\ObjImpls\CK3dObject.hpp" />
|
<ClInclude Include="CK2\ObjImpls\CK3dObject.hpp" />
|
||||||
<ClInclude Include="CK2\ObjImpls\CKBeObject.hpp" />
|
<ClInclude Include="CK2\ObjImpls\CKBeObject.hpp" />
|
||||||
|
|
|
@ -96,6 +96,12 @@
|
||||||
<ClCompile Include="CK2\ObjImpls\CK3dEntity.cpp">
|
<ClCompile Include="CK2\ObjImpls\CK3dEntity.cpp">
|
||||||
<Filter>Sources\CK2\ObjImpls</Filter>
|
<Filter>Sources\CK2\ObjImpls</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="CK2\MgrImpls\CKObjectManager.cpp">
|
||||||
|
<Filter>Sources\CK2\MgrImpls</Filter>
|
||||||
|
</ClCompile>
|
||||||
|
<ClCompile Include="CK2\MgrImpls\CKPathManager.cpp">
|
||||||
|
<Filter>Sources\CK2\MgrImpls</Filter>
|
||||||
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClInclude Include="VTUtils.hpp">
|
<ClInclude Include="VTUtils.hpp">
|
||||||
|
@ -167,5 +173,11 @@
|
||||||
<ClInclude Include="CK2\ObjImpls\CK3dObject.hpp">
|
<ClInclude Include="CK2\ObjImpls\CK3dObject.hpp">
|
||||||
<Filter>Headers\CK2\ObjImpls</Filter>
|
<Filter>Headers\CK2\ObjImpls</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
<ClInclude Include="CK2\MgrImpls\CKObjectManager.hpp">
|
||||||
|
<Filter>Headers\CK2\MgrImpls</Filter>
|
||||||
|
</ClInclude>
|
||||||
|
<ClInclude Include="CK2\MgrImpls\CKPathManager.hpp">
|
||||||
|
<Filter>Headers\CK2\MgrImpls</Filter>
|
||||||
|
</ClInclude>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
|
@ -94,12 +94,26 @@ namespace LibCmo {
|
||||||
m_Str = m_HasStr ? cstr : "";
|
m_Str = m_HasStr ? cstr : "";
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
bool operator==(const char* rhs) const {
|
||||||
|
if (m_HasStr) {
|
||||||
|
return m_Str == rhs;
|
||||||
|
} else {
|
||||||
|
return rhs == nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
MKString(const std::string& cstr) : m_HasStr(true), m_Str(cstr) {}
|
MKString(const std::string& cstr) : m_HasStr(true), m_Str(cstr) {}
|
||||||
MKString& operator=(const std::string& cstr) {
|
MKString& operator=(const std::string& cstr) {
|
||||||
m_HasStr = true;
|
m_HasStr = true;
|
||||||
m_Str = cstr;
|
m_Str = cstr;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
bool operator==(const std::string& rhs) const {
|
||||||
|
if (m_HasStr) {
|
||||||
|
return m_Str == rhs;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
MKString(const MKString& rhs) : m_HasStr(rhs.m_HasStr), m_Str(rhs.m_Str) {}
|
MKString(const MKString& rhs) : m_HasStr(rhs.m_HasStr), m_Str(rhs.m_Str) {}
|
||||||
MKString(MKString&& rhs) noexcept : m_HasStr(rhs.m_HasStr), m_Str(std::move(rhs.m_Str)) {
|
MKString(MKString&& rhs) noexcept : m_HasStr(rhs.m_HasStr), m_Str(std::move(rhs.m_Str)) {
|
||||||
|
@ -116,13 +130,26 @@ namespace LibCmo {
|
||||||
rhs.m_HasStr = false;
|
rhs.m_HasStr = false;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
bool operator==(const MKString& rhs) const {
|
||||||
|
return (m_HasStr == rhs.m_HasStr && m_Str == rhs.m_Str);
|
||||||
|
}
|
||||||
|
|
||||||
const char* c_str() const {
|
const char* toCKSTRING() const {
|
||||||
return m_HasStr ? m_Str.c_str() : nullptr;
|
return m_HasStr ? m_Str.c_str() : nullptr;
|
||||||
}
|
}
|
||||||
const std::string& string() const {
|
/**
|
||||||
|
* @brief Return the std::string format of this string.
|
||||||
|
* @remark nullptr string will return blank string.
|
||||||
|
* @return The std::string format of this string.
|
||||||
|
*/
|
||||||
|
const std::string& toString() const {
|
||||||
return m_Str;
|
return m_Str;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* @brief The size of this string.
|
||||||
|
* @remark Both empty string and nullptr will return 0
|
||||||
|
* @return The size of this string
|
||||||
|
*/
|
||||||
const size_t size() const {
|
const size_t size() const {
|
||||||
return m_HasStr ? m_Str.size() : 0u;
|
return m_HasStr ? m_Str.size() : 0u;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user