362 lines
11 KiB
C++
362 lines
11 KiB
C++
//
|
|
// /rageMayaGeoDataSet.h
|
|
//
|
|
// Copyright (C) 1999-2006 Rockstar Games. All Rights Reserved.
|
|
//
|
|
#ifndef _RAGEMAYAGEODATASET_H_
|
|
#define _RAGEMAYAGEODATASET_H_
|
|
|
|
#pragma warning(push)
|
|
#if _MSC_VER >= 1400
|
|
#pragma warning(disable: 4005) // warning C4005: 'strcasecmp' : macro redefinition
|
|
// rage\base\src\string\string.h declares strcasecmp, and so does MTypes.h
|
|
// but they are currently differenct
|
|
#endif
|
|
|
|
#define REQUIRE_IOSTREAM
|
|
#pragma warning(push)
|
|
#pragma warning(disable : 4668)
|
|
|
|
#include <windows.h>
|
|
|
|
#pragma warning(pop)
|
|
|
|
#pragma warning(disable : 4702) //Disable the 'unreachable code' warning
|
|
|
|
#include <algorithm>
|
|
#include <list>
|
|
#include <map>
|
|
#include <string>
|
|
#include <vector>
|
|
|
|
#include "atl/functor.h"
|
|
#include "atl/singleton.h"
|
|
#include "parsercore/attribute.h"
|
|
#include "parsercore/element.h"
|
|
#include "parsercore/stream.h"
|
|
#include "parser/manager.h"
|
|
#include "parser/tree.h"
|
|
#include "parser/treenode.h"
|
|
#include "vector/vector3.h"
|
|
|
|
using namespace std;
|
|
using namespace rage;
|
|
|
|
namespace rageGEO
|
|
{
|
|
|
|
//-----------------------------------------------------------------------------
|
|
|
|
enum GEOPARAMVALUE_TYPE
|
|
{
|
|
TYPE_INT,
|
|
TYPE_FLOAT,
|
|
TYPE_BOOL,
|
|
TYPE_STRING,
|
|
TYPE_VECTOR3,
|
|
TYPE_NULL
|
|
};
|
|
|
|
//-----------------------------------------------------------------------------
|
|
|
|
//PURPOSE : This class represents a value from a GEO type of template file
|
|
class GeoParamValueVariant
|
|
{
|
|
public:
|
|
GeoParamValueVariant()
|
|
: type(TYPE_NULL)
|
|
{};
|
|
|
|
GeoParamValueVariant(const GeoParamValueVariant& other)
|
|
{
|
|
*this = other;
|
|
}
|
|
|
|
void SetValue(int val) { type = TYPE_INT; iVal = val; }
|
|
void SetValue(float val) { type = TYPE_FLOAT; fVal = val; }
|
|
void SetValue(bool val) { type = TYPE_BOOL; bVal = val; }
|
|
void SetValue(const char* val) { type = TYPE_STRING; sVal = val; }
|
|
void SetValue(const Vector3& val) { type = TYPE_VECTOR3; v3Val = val; }
|
|
|
|
int GetIntValue() { Assert(type == TYPE_INT); return iVal; }
|
|
float GetFloatValue() { Assert(type == TYPE_FLOAT); return fVal; }
|
|
bool GetBoolValue() { Assert(type == TYPE_BOOL); return bVal; }
|
|
const char* GetStringValue() { Assert(type == TYPE_STRING); return sVal.c_str(); }
|
|
const Vector3& GetVector3Value() { Assert(type == TYPE_VECTOR3); return v3Val; }
|
|
|
|
GEOPARAMVALUE_TYPE GetType() const { return type; }
|
|
|
|
public:
|
|
static GeoParamValueVariant nullGeoParamValue;
|
|
|
|
private:
|
|
int iVal;
|
|
float fVal;
|
|
bool bVal;
|
|
string sVal;
|
|
Vector3 v3Val;
|
|
|
|
GEOPARAMVALUE_TYPE type;
|
|
};
|
|
|
|
//-----------------------------------------------------------------------------
|
|
|
|
//PURPOSE : This class represents a path to a node in the GEO Template/Type
|
|
//hierarchy.
|
|
//Paths can be specified in the following forms
|
|
//
|
|
// To reference a node at the root level of a GEO Type or Template:
|
|
// (Type Name)
|
|
//
|
|
// To reference a nested GEO type or template node
|
|
// (Type Name)/(Node)/(Node)
|
|
// i.e. Saloon/BarRoom/Bar
|
|
//
|
|
// To reference a particluar element in an array of contained GEOs
|
|
// (Type Name)/(Node)[index]
|
|
// i.e. Saloon/BarRoom/BarStool[3]
|
|
//
|
|
class GeoPath
|
|
{
|
|
private:
|
|
class GeoPathSection
|
|
{
|
|
public:
|
|
GeoPathSection()
|
|
: m_Index(-1)
|
|
{};
|
|
GeoPathSection(const char* name, int index)
|
|
: m_Name(name)
|
|
, m_Index(index)
|
|
{};
|
|
|
|
bool IsArraySection() const
|
|
{
|
|
if(m_Index == -1)
|
|
return false;
|
|
else
|
|
return true;
|
|
}
|
|
|
|
const char* GetName() const { return m_Name.c_str(); }
|
|
void SetName(const char* name) { m_Name = name; }
|
|
|
|
int GetArrayIndex() const { return m_Index; }
|
|
void SetArrayIndex(int idx) { m_Index = idx; }
|
|
private:
|
|
string m_Name;
|
|
int m_Index;
|
|
};
|
|
|
|
public:
|
|
GeoPath() {};
|
|
|
|
GeoPath(const GeoPath& other)
|
|
{
|
|
*this = other;
|
|
}
|
|
|
|
//PURPOSE: Initalize the GeoPath object, parsing the supplied path
|
|
bool Init(const char* path);
|
|
|
|
//PURPOSE: Returns the root type or template name the path references
|
|
const char* GetRootName() const { return m_RootName.c_str(); }
|
|
|
|
//PURPOSE: Returns the number of "sections" specified in the GEO Path
|
|
// i.e. Saloon/Rooms, would have the root type name, plus 1 "section"
|
|
int GetNumSections() const { return m_PathSections.size(); }
|
|
|
|
//PURPOSE: Returns the name of the specified section of the path
|
|
const char* GetSectionName(int idx) const { Assert(idx<(int)m_PathSections.size()); return m_PathSections[idx].GetName(); }
|
|
|
|
//PURPOSE: Returns the index of the specified section of the path
|
|
int GetSectionArrayIndex(int idx) const { Assert(idx<(int)m_PathSections.size()); return m_PathSections[idx].GetArrayIndex(); }
|
|
|
|
//PURPOSE: Returns a boolean value indicating whether the specified section is an array section or not.
|
|
bool IsSectionArray(int idx) const { Assert(idx<(int)m_PathSections.size()); return m_PathSections[idx].IsArraySection(); }
|
|
|
|
//PURPOSE: Returns the GEO path in the full string form
|
|
const char* GetPathAsString() const { return m_PathString.c_str(); };
|
|
|
|
inline bool operator==(const GeoPath& other);
|
|
inline void operator=(const GeoPath& other);
|
|
|
|
private:
|
|
string m_PathString;
|
|
string m_RootName;
|
|
vector<GeoPathSection> m_PathSections;
|
|
};
|
|
|
|
bool GeoPath::operator==(const GeoPath& other)
|
|
{
|
|
return (m_PathString == other.m_PathString);
|
|
}
|
|
|
|
void GeoPath::operator=(const GeoPath& other)
|
|
{
|
|
m_PathString = other.m_PathString;
|
|
m_RootName = other.m_RootName;
|
|
m_PathSections.clear();
|
|
std::copy(other.m_PathSections.begin(), other.m_PathSections.end(), m_PathSections.begin());
|
|
}
|
|
|
|
//-----------------------------------------------------------------------------
|
|
//PURPOSE: Represents a class used for caching parameter values that have been
|
|
//queried for through the GeoDataSet class
|
|
class GeoDataSetCache
|
|
{
|
|
public:
|
|
enum CACHEPATH
|
|
{
|
|
GEO_TYPE_DIR = 0,
|
|
GEO_TEMPLATE_DIR,
|
|
CACHE_PATH_COUNT
|
|
};
|
|
|
|
GeoDataSetCache()
|
|
{
|
|
m_CachPathChangeHandles[GEO_TYPE_DIR] = INVALID_HANDLE_VALUE;
|
|
m_CachPathChangeHandles[GEO_TEMPLATE_DIR] = INVALID_HANDLE_VALUE;
|
|
};
|
|
|
|
~GeoDataSetCache()
|
|
{
|
|
FlushCache();
|
|
}
|
|
|
|
bool InitializePaths(const char* typeFilePath, const char* templateFilePath);
|
|
|
|
GeoParamValueVariant FindNode(const GeoPath& gp, const char* paramName);
|
|
GeoParamValueVariant FindNode(const char* geoPath, const char* paramName);
|
|
|
|
void CacheNode(const GeoPath& gp, const char* paramName, GeoParamValueVariant& val);
|
|
void CacheNode(const char* geoPath, const char* paramName, GeoParamValueVariant& val);
|
|
|
|
private:
|
|
void FlushCache();
|
|
string BuildCacheKey(const char* geoPathStr, const char* paramName) const;
|
|
|
|
private:
|
|
HANDLE m_CachPathChangeHandles[CACHE_PATH_COUNT];
|
|
|
|
typedef std::map<std::string, GeoParamValueVariant> GEOPARAMCACHE;
|
|
GEOPARAMCACHE m_ParamCache;
|
|
};
|
|
|
|
//-----------------------------------------------------------------------------
|
|
//PURPOSE : This is a singleton class that is used to query data directly from GEO
|
|
//Template and GEO Type files.
|
|
class rageMayaGeoDataSet
|
|
{
|
|
friend class GeoDataSetCache;
|
|
|
|
public:
|
|
typedef rage::Functor1<const char*> rageGeoDataSetMsgFtor;
|
|
|
|
private:
|
|
struct GeoTypePathMember
|
|
{
|
|
GeoTypePathMember()
|
|
: m_Index(-1)
|
|
{};
|
|
GeoTypePathMember(const string& name, int index)
|
|
: m_Name(name)
|
|
, m_Index(index)
|
|
{};
|
|
|
|
string m_Name;
|
|
int m_Index;
|
|
};
|
|
|
|
struct searchItem
|
|
{
|
|
searchItem(string name, bool isTemplate)
|
|
: m_name(name)
|
|
, m_bIsTemplate(isTemplate)
|
|
{};
|
|
string m_name;
|
|
bool m_bIsTemplate;
|
|
};
|
|
|
|
public:
|
|
~rageMayaGeoDataSet();
|
|
|
|
//PURPOSE: Initializes the root GEO Type and GEO Template paths where the respective files are stored
|
|
void InitializePaths(const char* pTypePath, const char* pTemplatePath);
|
|
|
|
//PURPOSE: Returns the full path to the GEO type files.
|
|
const char* GetTypeRootPath() const { return m_TypeRootPath.c_str(); }
|
|
|
|
//PURPOSE: Returns the full path to the GEO template files.
|
|
const char* GetTemplateRootPath() const { return m_TemplateRootPath.c_str(); }
|
|
|
|
//PURPOSE: Returns a boolean value indicating whether the supplied parameter can be found in the specified type
|
|
bool IsGEOParamAvailable(const char* typeName, const char* paramName, GEOPARAMVALUE_TYPE paramType);
|
|
|
|
//PURPOSE: The following methods retrieve the specified parameter value as the data type indicated by the method name.
|
|
bool GetGEOParamValueAsInt(const char* typeName, const char* paramName, int& retVal);
|
|
bool GetGEOParamValueAsFloat(const char* typeName, const char* paramName, float& retVal);
|
|
bool GetGEOParamValueAsBool(const char* typeName, const char* paramName, bool& retVal);
|
|
bool GetGEOParamValueAsVec3(const char* typeName, const char* paramName, Vector3& retVal);
|
|
bool GetGEOParamValueAsString(const char* typeName, const char* paramName, string& retVal);
|
|
|
|
//PURPOSE: The following methods allow the client of the GEODataSet object to specify callbacks that can be used
|
|
// to display info, warning, or error messages.
|
|
void SetInfoMsgFtor( rageGeoDataSetMsgFtor fn ) { m_InfoMsgFtor = fn; }
|
|
void SetWarnMsgFtor( rageGeoDataSetMsgFtor fn ) { m_WarnMsgFtor = fn; }
|
|
void SetErrorMsgFtor( rageGeoDataSetMsgFtor fn ) { m_ErrorMsgFtor = fn; }
|
|
|
|
protected:
|
|
rageMayaGeoDataSet();
|
|
|
|
private:
|
|
bool ParseGEOTypeName(const char* typeName, vector<GeoTypePathMember>& pathMembers);
|
|
|
|
GeoParamValueVariant TreeNodeToVariant(parTreeNode *pNode, bool bIsTemplateNode, GEOPARAMVALUE_TYPE paramType);
|
|
GeoParamValueVariant GetGEOParamValue(const char* typeName, const char* paramName, GEOPARAMVALUE_TYPE paramType);
|
|
|
|
GeoParamValueVariant FindGEOParamNodeInType(GeoPath& geoTypePath,
|
|
const char* paramName,
|
|
GEOPARAMVALUE_TYPE paramType,
|
|
searchItem& curItem,
|
|
list<searchItem>& searchQueue);
|
|
|
|
GeoParamValueVariant FindGEOParamNodeInTemplate(const char* paramName,
|
|
GEOPARAMVALUE_TYPE paramType,
|
|
searchItem& curItem,
|
|
list<searchItem>& searchQueue);
|
|
|
|
bool FindGeoParameterNode(parTreeNode *pRootNode,
|
|
const char *paramPath,
|
|
GEOPARAMVALUE_TYPE paramType,
|
|
bool bIsTemplate,
|
|
GeoParamValueVariant &retVal);
|
|
|
|
void DisplayInfoMsg(const char* format, ...);
|
|
void DisplayWarnMsg(const char* format, ...);
|
|
void DisplayErrorMsg(const char* format, ...);
|
|
|
|
private:
|
|
string m_TypeRootPath;
|
|
string m_TemplateRootPath;
|
|
GeoDataSetCache m_ParamCache;
|
|
|
|
rageGeoDataSetMsgFtor m_InfoMsgFtor;
|
|
rageGeoDataSetMsgFtor m_WarnMsgFtor;
|
|
rageGeoDataSetMsgFtor m_ErrorMsgFtor;
|
|
};
|
|
|
|
//-----------------------------------------------------------------------------
|
|
|
|
typedef atSingleton<rageMayaGeoDataSet> rageMayaGeoDataSetSingleton;
|
|
|
|
#define GEODATASET ::rageGEO::rageMayaGeoDataSetSingleton::InstanceRef()
|
|
#define INIT_GEODATASET ::rageGEO::rageMayaGeoDataSetSingleton::Instantiate()
|
|
#define SHUTDOWN_GEODATASET ::rageGEO::rageMayaGeoDataSetSingleton::Destroy()
|
|
|
|
//-----------------------------------------------------------------------------
|
|
|
|
} //End namespace rageGEO
|
|
|
|
#endif //_RAGEMAYAGEODATASET_H_
|