summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ZAPD/HighLevel/HLModelIntermediette.cpp2
-rw-r--r--ZAPD/ZFile.cpp5
-rw-r--r--ZAPD/ZLimb.cpp572
-rw-r--r--ZAPD/ZLimb.h166
-rw-r--r--ZAPD/ZSkeleton.cpp359
-rw-r--r--ZAPD/ZSkeleton.h64
6 files changed, 891 insertions, 277 deletions
diff --git a/ZAPD/HighLevel/HLModelIntermediette.cpp b/ZAPD/HighLevel/HLModelIntermediette.cpp
index 037172e..bd8ec78 100644
--- a/ZAPD/HighLevel/HLModelIntermediette.cpp
+++ b/ZAPD/HighLevel/HLModelIntermediette.cpp
@@ -259,7 +259,7 @@ void HLModelIntermediette::FromZSkeleton(HLModelIntermediette* model, ZSkeleton*
for (int i = 0; i < zSkeleton->limbs.size(); i++)
{
- ZLimbStandard* limb = zSkeleton->limbs[i];
+ ZLimb* limb = zSkeleton->limbs[i];
for (int j = 0; j < model->blocks.size(); j++)
{
diff --git a/ZAPD/ZFile.cpp b/ZAPD/ZFile.cpp
index 220ba11..5046ed1 100644
--- a/ZAPD/ZFile.cpp
+++ b/ZAPD/ZFile.cpp
@@ -4,6 +4,7 @@
#include "ZRoom/ZRoom.h"
#include "ZTexture.h"
#include "ZAnimation.h"
+#include "ZLimb.h"
#include "ZSkeleton.h"
#include "ZCollision.h"
#include "ZScalar.h"
@@ -237,10 +238,10 @@ void ZFile::ParseXML(ZFileMode mode, XMLElement* reader, std::string filename, b
}
else if (string(child->Name()) == "Limb")
{
- ZLimbStandard* limb = nullptr;
+ ZLimb* limb = nullptr;
if (mode == ZFileMode::Extract)
- limb = ZLimbStandard::FromXML(child, rawData, rawDataIndex, folderName, this);
+ limb = ZLimb::FromXML(child, rawData, rawDataIndex, folderName, this);
resources.push_back(limb);
diff --git a/ZAPD/ZLimb.cpp b/ZAPD/ZLimb.cpp
new file mode 100644
index 0000000..b7e6398
--- /dev/null
+++ b/ZAPD/ZLimb.cpp
@@ -0,0 +1,572 @@
+#include "ZLimb.h"
+#include "BitConverter.h"
+#include "StringHelper.h"
+#include "Globals.h"
+#include <cassert>
+
+using namespace std;
+
+
+Struct_800A57C0::Struct_800A57C0(const std::vector<uint8_t>& rawData, uint32_t fileOffset)
+{
+ unk_0 = BitConverter::ToUInt16BE(rawData, fileOffset + 0x00);
+ unk_2 = BitConverter::ToInt16BE(rawData, fileOffset + 0x02);
+ unk_4 = BitConverter::ToInt16BE(rawData, fileOffset + 0x04);
+ unk_6 = BitConverter::ToInt8BE(rawData, fileOffset + 0x06);
+ unk_7 = BitConverter::ToInt8BE(rawData, fileOffset + 0x07);
+ unk_8 = BitConverter::ToInt8BE(rawData, fileOffset + 0x08);
+ unk_9 = BitConverter::ToUInt8BE(rawData, fileOffset + 0x09);
+}
+Struct_800A57C0::Struct_800A57C0(const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index)
+ : Struct_800A57C0(rawData, fileOffset + index * GetRawDataSize())
+{
+}
+
+std::string Struct_800A57C0::GetSourceOutputCode() const
+{
+ return StringHelper::Sprintf("0x%02X, %i, %i, %i, %i, %i, 0x%02X",
+ unk_0, unk_2, unk_4, unk_6, unk_7, unk_8, unk_9);
+}
+
+size_t Struct_800A57C0::GetRawDataSize()
+{
+ return 0x0A;
+}
+
+std::string Struct_800A57C0::GetSourceTypeName()
+{
+ return "Struct_800A57C0";
+}
+
+
+Struct_800A598C_2::Struct_800A598C_2(const std::vector<uint8_t>& rawData, uint32_t fileOffset)
+{
+ unk_0 = BitConverter::ToUInt8BE(rawData, fileOffset + 0x00);
+ x = BitConverter::ToInt16BE(rawData, fileOffset + 0x02);
+ y = BitConverter::ToInt16BE(rawData, fileOffset + 0x04);
+ z = BitConverter::ToInt16BE(rawData, fileOffset + 0x06);
+ unk_8 = BitConverter::ToUInt8BE(rawData, fileOffset + 0x08);
+}
+Struct_800A598C_2::Struct_800A598C_2(const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index)
+ : Struct_800A598C_2(rawData, fileOffset + index * GetRawDataSize())
+{
+}
+
+std::string Struct_800A598C_2::GetSourceOutputCode() const
+{
+ return StringHelper::Sprintf("0x%02X, %i, %i, %i, 0x%02X",
+ unk_0, x, y, z, unk_8);
+}
+
+size_t Struct_800A598C_2::GetRawDataSize()
+{
+ return 0x0A;
+}
+
+std::string Struct_800A598C_2::GetSourceTypeName()
+{
+ return "Struct_800A598C_2";
+}
+
+
+Struct_800A598C::Struct_800A598C(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset)
+ : parent(parent)
+{
+ unk_0 = BitConverter::ToUInt16BE(rawData, fileOffset + 0x00);
+ unk_2 = BitConverter::ToUInt16BE(rawData, fileOffset + 0x02);
+ unk_4 = BitConverter::ToUInt16BE(rawData, fileOffset + 0x04);
+ unk_8 = BitConverter::ToUInt32BE(rawData, fileOffset + 0x08);
+ unk_C = BitConverter::ToUInt32BE(rawData, fileOffset + 0x0C);
+
+ if (unk_8 != 0) {
+ uint32_t unk_8_Offset = Seg2Filespace(unk_8, parent->baseAddress);
+ for (size_t i = 0; i < unk_0; i++) {
+ unk_8_arr.emplace_back(rawData, unk_8_Offset, i);
+ }
+ }
+
+ if (unk_C != 0) {
+ uint32_t unk_C_Offset = Seg2Filespace(unk_C, parent->baseAddress);
+ for (size_t i = 0; i < unk_2; i++) {
+ unk_C_arr.emplace_back(rawData, unk_C_Offset, i);
+ }
+ }
+}
+Struct_800A598C::Struct_800A598C(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index)
+ : Struct_800A598C(parent, rawData, fileOffset + index * GetRawDataSize())
+{
+}
+
+void Struct_800A598C::PreGenSourceFiles(const std::string& prefix)
+{
+ string entryStr;
+
+ if (unk_8 != 0) {
+ uint32_t unk_8_Offset = Seg2Filespace(unk_8, parent->baseAddress);
+ string unk_8_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A57C0::GetSourceTypeName().c_str(), unk_8_Offset);
+
+ size_t arrayItemCnt = unk_8_arr.size();
+ entryStr = "";
+ size_t i = 0;
+ for (auto& child: unk_8_arr) {
+ entryStr += StringHelper::Sprintf(" { %s },%s",
+ child.GetSourceOutputCode().c_str(),
+ (++i < arrayItemCnt) ? "\n" : "");
+ }
+
+ Declaration* decl = parent->GetDeclaration(unk_8_Offset);
+ if (decl == nullptr) {
+ parent->AddDeclarationArray(
+ unk_8_Offset, DeclarationAlignment::None,
+ arrayItemCnt * Struct_800A57C0::GetRawDataSize(), Struct_800A57C0::GetSourceTypeName(),
+ unk_8_Str, arrayItemCnt, entryStr);
+ }
+ else {
+ decl->text = entryStr;
+ }
+ }
+
+ if (unk_C != 0) {
+ uint32_t unk_C_Offset = Seg2Filespace(unk_C, parent->baseAddress);
+ string unk_C_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A598C_2::GetSourceTypeName().c_str(), unk_C_Offset);
+
+ size_t arrayItemCnt = unk_C_arr.size();
+ entryStr = "";
+ size_t i = 0;
+ for (auto& child: unk_C_arr) {
+ entryStr += StringHelper::Sprintf(" { %s },%s",
+ child.GetSourceOutputCode().c_str(),
+ (++i < arrayItemCnt) ? "\n" : "");
+ }
+
+ Declaration* decl = parent->GetDeclaration(unk_C_Offset);
+ if (decl == nullptr) {
+ parent->AddDeclarationArray(
+ unk_C_Offset, DeclarationAlignment::None,
+ arrayItemCnt * Struct_800A598C_2::GetRawDataSize(), Struct_800A598C_2::GetSourceTypeName(),
+ unk_C_Str, arrayItemCnt, entryStr);
+ }
+ else {
+ decl->text = entryStr;
+ }
+ }
+}
+
+std::string Struct_800A598C::GetSourceOutputCode(const std::string& prefix) const
+{
+ string entryStr;
+
+ string unk_8_Str = "NULL";
+ if (unk_8 != 0) {
+ uint32_t unk_8_Offset = Seg2Filespace(unk_8, parent->baseAddress);
+ unk_8_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A57C0::GetSourceTypeName().c_str(), unk_8_Offset);
+ }
+
+ string unk_C_Str = "NULL";
+ if (unk_C != 0) {
+ uint32_t unk_C_Offset = Seg2Filespace(unk_C, parent->baseAddress);
+ unk_C_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A598C_2::GetSourceTypeName().c_str(), unk_C_Offset);
+ }
+
+ entryStr = StringHelper::Sprintf("\n ARRAY_COUNTU(%s), ARRAY_COUNTU(%s),\n",
+ unk_8_Str.c_str(), unk_C_Str.c_str());
+ entryStr += StringHelper::Sprintf(" %i, %s, %s\n ", unk_4,
+ unk_8_Str.c_str(), unk_C_Str.c_str());
+
+ return entryStr;
+}
+
+size_t Struct_800A598C::GetRawDataSize()
+{
+ return 0x10;
+}
+
+std::string Struct_800A598C::GetSourceTypeName()
+{
+ return "Struct_800A598C";
+}
+
+
+Struct_800A5E28::Struct_800A5E28(ZFile* parent, const std::vector<uint8_t>& nRawData, uint32_t fileOffset)
+ : parent(parent), rawData(nRawData)
+{
+ unk_0 = BitConverter::ToUInt16BE(nRawData, fileOffset + 0x00);
+ unk_2 = BitConverter::ToUInt16BE(nRawData, fileOffset + 0x02);
+ unk_4 = BitConverter::ToUInt32BE(nRawData, fileOffset + 0x04);
+ unk_8 = BitConverter::ToUInt32BE(nRawData, fileOffset + 0x08);
+
+ if (unk_4 != 0) {
+ uint32_t unk_4_Offset = Seg2Filespace(unk_4, parent->baseAddress);
+ for (size_t i = 0; i < unk_2; i++) {
+ unk_4_arr.emplace_back(parent, nRawData, unk_4_Offset, i);
+ }
+ }
+}
+Struct_800A5E28::Struct_800A5E28(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index)
+ : Struct_800A5E28(parent, rawData, fileOffset + index * GetRawDataSize())
+{
+}
+
+Struct_800A5E28::~Struct_800A5E28()
+{
+ delete unk_8_dlist;
+}
+
+void Struct_800A5E28::PreGenSourceFiles(const std::string& prefix)
+{
+ if (unk_4 != 0) {
+ uint32_t unk_4_Offset = Seg2Filespace(unk_4, parent->baseAddress);
+ string unk_4_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A598C::GetSourceTypeName().c_str(), unk_4_Offset);
+
+ string entryStr = "";
+ uint16_t arrayItemCnt = unk_4_arr.size();
+
+ size_t i = 0;
+ for (auto& child: unk_4_arr) {
+ child.PreGenSourceFiles(prefix);
+
+ entryStr += StringHelper::Sprintf(" { %s },%s",
+ child.GetSourceOutputCode(prefix).c_str(),
+ (++i < arrayItemCnt) ? "\n" : "");
+ }
+
+ Declaration* decl = parent->GetDeclaration(unk_4_Offset);
+ if (decl == nullptr) {
+ parent->AddDeclarationArray(
+ unk_4_Offset, DeclarationAlignment::None,
+ arrayItemCnt * Struct_800A598C::GetRawDataSize(), Struct_800A598C::GetSourceTypeName(),
+ unk_4_Str, arrayItemCnt, entryStr);
+ }
+ else {
+ decl->text = entryStr;
+ }
+ }
+
+ if (unk_8 != 0) {
+ uint32_t unk_8_Offset = Seg2Filespace(unk_8, parent->baseAddress);
+
+ int dlistLength = ZDisplayList::GetDListLength(rawData, unk_8_Offset, Globals::Instance->game == ZGame::OOT_SW97 ? DListType::F3DEX : DListType::F3DZEX);
+ unk_8_dlist = new ZDisplayList(rawData, unk_8_Offset, dlistLength);
+ unk_8_dlist->parent = parent;
+
+ string dListStr = StringHelper::Sprintf("%sSkinLimbDL_%06X", prefix.c_str(), unk_8_Offset);
+ unk_8_dlist->SetName(dListStr);
+ unk_8_dlist->GetSourceOutputCode(prefix);
+ }
+}
+
+std::string Struct_800A5E28::GetSourceOutputCode(const std::string& prefix) const
+{
+ string entryStr = "";
+
+ string unk_4_Str = "NULL";
+ if (unk_4 != 0) {
+ uint32_t unk_4_Offset = Seg2Filespace(unk_4, parent->baseAddress);
+ Declaration* decl = parent->GetDeclaration(unk_4_Offset);
+ if (decl == nullptr) {
+ unk_4_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A598C::GetSourceTypeName().c_str(), unk_4_Offset);
+ }
+ else {
+ unk_4_Str = decl->varName;
+ }
+ }
+
+ string unk_8_Str = "NULL";
+ if (unk_8 != 0) {
+ uint32_t unk_8_Offset = Seg2Filespace(unk_8, parent->baseAddress);
+ Declaration* decl = parent->GetDeclaration(unk_8_Offset);
+ if (decl == nullptr) {
+ // Something went wrong...
+ unk_8_Str = StringHelper::Sprintf("0x%08X", unk_8);
+ }
+ else {
+ unk_8_Str = decl->varName;
+ }
+ }
+
+ return StringHelper::Sprintf("\n %i, ARRAY_COUNTU(%s),\n %s, %s\n",
+ unk_0, unk_4_Str.c_str(),
+ unk_4_Str.c_str(), unk_8_Str.c_str());
+}
+
+size_t Struct_800A5E28::GetRawDataSize()
+{
+ return 0x0C;
+}
+
+std::string Struct_800A5E28::GetSourceTypeName()
+{
+ return "Struct_800A5E28";
+}
+
+
+ZLimb::ZLimb(tinyxml2::XMLElement* reader, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent)
+{
+ rawData.assign(nRawData.begin(), nRawData.end());
+ rawDataIndex = nRawDataIndex;
+ parent = nParent;
+
+ segAddress = nRawDataIndex;
+
+ ParseXML(reader);
+ ParseRawData();
+
+ if (type == ZLimbType::Skin) {
+ if (skinSegmentType == ZLimbSkinType::SkinType_4 && skinSegment != 0) {
+ uint32_t skinSegmentOffset = Seg2Filespace(skinSegment, parent->baseAddress);
+ segmentStruct = Struct_800A5E28(parent, rawData, skinSegmentOffset);
+ }
+ }
+}
+
+ZLimb::ZLimb(ZLimbType limbType, const std::string& prefix, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent)
+{
+ rawData.assign(nRawData.begin(), nRawData.end());
+ rawDataIndex = nRawDataIndex;
+ parent = nParent;
+ type = limbType;
+
+ segAddress = nRawDataIndex;
+ name = StringHelper::Sprintf("%sLimb_%06X", prefix.c_str(), GetFileAddress());
+
+ ParseRawData();
+}
+
+void ZLimb::ParseXML(tinyxml2::XMLElement* reader)
+{
+ ZResource::ParseXML(reader);
+
+ // Reading from a <Skeleton/>
+ const char* limbType = reader->Attribute("LimbType");
+ if (limbType == nullptr) {
+ // Reading from a <Limb/>
+ limbType = reader->Attribute("Type");
+ }
+
+ if (limbType == nullptr) {
+ fprintf(stderr, "ZLimb::ParseXML: Warning in '%s'.\n\t Missing 'LimbType' attribute in xml. Defaulting to 'Standard'.\n", name.c_str());
+ type = ZLimbType::Standard;
+ }
+ else {
+ string limbTypeStr(limbType);
+ if (limbTypeStr == "Standard") {
+ type = ZLimbType::Standard;
+ }
+ else if(limbTypeStr == "LOD") {
+ type = ZLimbType::LOD;
+ }
+ else if(limbTypeStr == "Skin") {
+ type = ZLimbType::Skin;
+ }
+ else {
+ fprintf(stderr, "ZLimb::ParseXML: Warning in '%s'.\n\t Invalid LimbType found: '%s'. Defaulting to 'Standard'.\n", name.c_str(), limbType);
+ type = ZLimbType::Standard;
+ }
+ }
+}
+
+void ZLimb::ParseRawData()
+{
+ transX = BitConverter::ToInt16BE(rawData, rawDataIndex + 0);
+ transY = BitConverter::ToInt16BE(rawData, rawDataIndex + 2);
+ transZ = BitConverter::ToInt16BE(rawData, rawDataIndex + 4);
+
+ childIndex = rawData.at(rawDataIndex + 6);
+ siblingIndex = rawData.at(rawDataIndex + 7);
+
+ switch (type) {
+ case ZLimbType::LOD:
+ farDListPtr = BitConverter::ToUInt32BE(rawData, rawDataIndex + 12);
+ case ZLimbType::Standard:
+ dListPtr = BitConverter::ToUInt32BE(rawData, rawDataIndex + 8);
+ break;
+ case ZLimbType::Skin:
+ skinSegmentType = static_cast<ZLimbSkinType>(BitConverter::ToInt32BE(rawData, rawDataIndex + 8));
+ skinSegment = BitConverter::ToUInt32BE(rawData, rawDataIndex + 12);
+ break;
+ }
+}
+
+ZLimb* ZLimb::FromXML(tinyxml2::XMLElement* reader, vector<uint8_t> nRawData, int rawDataIndex, string nRelPath, ZFile* parent)
+{
+ ZLimb* limb = new ZLimb(reader, nRawData, rawDataIndex, parent);
+ limb->relativePath = std::move(nRelPath);
+
+ limb->parent->AddDeclaration(
+ limb->GetFileAddress(), DeclarationAlignment::None, limb->GetRawDataSize(),
+ limb->GetSourceTypeName(), limb->name, "");
+
+ return limb;
+}
+
+
+int ZLimb::GetRawDataSize()
+{
+ switch (type) {
+ case ZLimbType::Standard:
+ return 0x0C;
+ case ZLimbType::LOD:
+ case ZLimbType::Skin:
+ return 0x10;
+ }
+ return 0x0C;
+}
+
+string ZLimb::GetSourceOutputCode(const std::string& prefix)
+{
+ string dListStr = "NULL";
+ string dListStr2 = "NULL";
+
+ if (dListPtr != 0) {
+ dListStr = GetLimbDListSourceOutputCode(prefix, "", dListPtr);
+ }
+ if (farDListPtr != 0) {
+ dListStr2 = GetLimbDListSourceOutputCode(prefix, "Far", farDListPtr);
+ }
+
+ string entryStr = StringHelper::Sprintf("\n { %i, %i, %i },\n 0x%02X, 0x%02X,\n",
+ transX, transY, transZ, childIndex, siblingIndex);
+
+ switch (type) {
+ case ZLimbType::Standard:
+ entryStr += StringHelper::Sprintf(" %s\n", dListStr.c_str());
+ break;
+ case ZLimbType::LOD:
+ entryStr += StringHelper::Sprintf(" { %s, %s }\n",
+ dListStr.c_str(), dListStr2.c_str());
+ break;
+ case ZLimbType::Skin:
+ entryStr += GetSourceOutputCodeSkin(prefix);
+ break;
+ }
+
+ Declaration* decl = parent->GetDeclaration(GetFileAddress());
+ if (decl == nullptr) {
+ parent->AddDeclaration(GetFileAddress(), DeclarationAlignment::None, GetRawDataSize(), GetSourceTypeName(), name, entryStr);
+ }
+ else {
+ decl->text = entryStr;
+ }
+
+ return "";
+}
+
+std::string ZLimb::GetSourceTypeName()
+{
+ return GetSourceTypeName(type);
+}
+
+ZResourceType ZLimb::GetResourceType()
+{
+ return ZResourceType::Limb;
+}
+
+ZLimbType ZLimb::GetLimbType()
+{
+ return type;
+}
+
+const char* ZLimb::GetSourceTypeName(ZLimbType limbType)
+{
+ switch (limbType) {
+ case ZLimbType::Standard:
+ return "StandardLimb";
+ case ZLimbType::LOD:
+ return "LodLimb";
+ case ZLimbType::Skin:
+ return "SkinLimb";
+ }
+ return "StandardLimb";
+}
+
+uint32_t ZLimb::GetFileAddress()
+{
+ return Seg2Filespace(segAddress, parent->baseAddress);
+}
+
+std::string ZLimb::GetLimbDListSourceOutputCode(const std::string& prefix, const std::string& limbPrefix, segptr_t dListPtr)
+{
+ if (dListPtr == 0) {
+ return "NULL";
+ }
+
+ uint32_t dListOffset = Seg2Filespace(dListPtr, parent->baseAddress);
+
+ string dListStr;
+ Declaration* decl = parent->GetDeclaration(dListOffset);
+ if (decl == nullptr) {
+ dListStr = StringHelper::Sprintf("%s%sLimbDL_%06X", prefix.c_str(), limbPrefix.c_str(), dListOffset);
+
+ int dlistLength = ZDisplayList::GetDListLength(rawData, dListOffset, Globals::Instance->game == ZGame::OOT_SW97 ? DListType::F3DEX : DListType::F3DZEX);
+ auto& dList = dLists.emplace_back(rawData, dListOffset, dlistLength);
+ dList.parent = parent;
+ dList.SetName(dListStr);
+ dList.GetSourceOutputCode(prefix);
+ }
+ else {
+ dListStr = decl->varName;
+ }
+
+ return dListStr;
+}
+
+std::string ZLimb::GetSourceOutputCodeSkin_Type_4(const std::string& prefix)
+{
+ assert(type == ZLimbType::Skin);
+ assert(skinSegmentType == ZLimbSkinType::SkinType_4);
+
+ if (skinSegment == 0) {
+ return "NULL";
+ }
+
+ uint32_t skinSegmentOffset = Seg2Filespace(skinSegment, parent->baseAddress);
+
+ string struct_800A5E28_Str;
+ Declaration* decl = parent->GetDeclaration(skinSegmentOffset);
+ if (decl == nullptr) {
+ struct_800A5E28_Str = StringHelper::Sprintf("%sSkinLimb_%s_%06X", prefix.c_str(), Struct_800A5E28::GetSourceTypeName().c_str(), skinSegmentOffset);
+
+ segmentStruct.PreGenSourceFiles(prefix);
+ string entryStr = segmentStruct.GetSourceOutputCode(prefix);
+
+ parent->AddDeclaration(
+ skinSegmentOffset, DeclarationAlignment::None,
+ Struct_800A5E28::GetRawDataSize(), Struct_800A5E28::GetSourceTypeName(),
+ struct_800A5E28_Str, entryStr);
+ }
+ else {
+ struct_800A5E28_Str = decl->varName;
+ }
+
+ return struct_800A5E28_Str;
+}
+
+std::string ZLimb::GetSourceOutputCodeSkin(const std::string& prefix)
+{
+ assert(type == ZLimbType::Skin);
+
+ string skinSegmentStr = "NULL";
+
+ if (skinSegment != 0) {
+ switch (skinSegmentType) {
+ case ZLimbSkinType::SkinType_4:
+ skinSegmentStr = "&" + GetSourceOutputCodeSkin_Type_4(prefix);
+ break;
+ case ZLimbSkinType::SkinType_DList:
+ skinSegmentStr = GetLimbDListSourceOutputCode(prefix, "Skin", skinSegment);
+ break;
+ default:
+ fprintf(stderr, "ZLimb::GetSourceOutputCodeSkinType: Error in '%s'.\n\t Unknown segment type for SkinLimb: '%i'. \n\tPlease report this.\n", name.c_str(), static_cast<int32_t>(skinSegmentType));
+ case ZLimbSkinType::SkinType_0:
+ case ZLimbSkinType::SkinType_5:
+ fprintf(stderr, "ZLimb::GetSourceOutputCodeSkinType: Error in '%s'.\n\t Segment type for SkinLimb not implemented: '%i'.\n", name.c_str(), static_cast<int32_t>(skinSegmentType));
+ skinSegmentStr = StringHelper::Sprintf("0x%08X", skinSegment);
+ break;
+ }
+ }
+
+ string entryStr = StringHelper::Sprintf(" 0x%02X, %s\n",
+ skinSegmentType, skinSegmentStr.c_str());
+
+ return entryStr;
+}
diff --git a/ZAPD/ZLimb.h b/ZAPD/ZLimb.h
new file mode 100644
index 0000000..cc5e906
--- /dev/null
+++ b/ZAPD/ZLimb.h
@@ -0,0 +1,166 @@
+#pragma once
+
+#include <vector>
+#include <string>
+#include <cstdint>
+#include "ZFile.h"
+#include "ZDisplayList.h"
+
+
+enum class ZLimbType
+{
+ Standard,
+ LOD,
+ Skin
+};
+
+// TODO: check if more types exists
+enum class ZLimbSkinType
+{
+ SkinType_0, // Segment = 0
+ SkinType_4 = 4, // Segment = segmented address // Struct_800A5E28
+ SkinType_5 = 5, // Segment = 0
+ SkinType_DList = 11, // Segment = DList address
+};
+
+
+class Struct_800A57C0
+{
+protected:
+ uint16_t unk_0;
+ int16_t unk_2;
+ int16_t unk_4;
+ int8_t unk_6;
+ int8_t unk_7;
+ int8_t unk_8;
+ uint8_t unk_9;
+
+public:
+ Struct_800A57C0(const std::vector<uint8_t>& rawData, uint32_t fileOffset);
+ Struct_800A57C0(const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index);
+
+ [[nodiscard]]
+ std::string GetSourceOutputCode() const;
+
+ static size_t GetRawDataSize();
+ static std::string GetSourceTypeName();
+};
+
+
+class Struct_800A598C_2
+{
+protected:
+ uint8_t unk_0;
+ int16_t x;
+ int16_t y;
+ int16_t z;
+ uint8_t unk_8;
+
+public:
+ Struct_800A598C_2(const std::vector<uint8_t>& rawData, uint32_t fileOffset);
+ Struct_800A598C_2(const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index);
+
+ [[nodiscard]]
+ std::string GetSourceOutputCode() const;
+
+ static size_t GetRawDataSize();
+ static std::string GetSourceTypeName();
+};
+
+
+class Struct_800A598C
+{
+protected:
+ ZFile* parent;
+
+ uint16_t unk_0; // Length of unk_8
+ uint16_t unk_2; // Length of unk_C
+ uint16_t unk_4; // 0 or 1 // Used as an index for unk_C
+ segptr_t unk_8; // Struct_800A57C0*
+ segptr_t unk_C; // Struct_800A598C_2*
+
+ std::vector<Struct_800A57C0> unk_8_arr;
+ std::vector<Struct_800A598C_2> unk_C_arr;
+
+public:
+ Struct_800A598C(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset);
+ Struct_800A598C(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index);
+
+ void PreGenSourceFiles(const std::string& prefix);
+ [[nodiscard]]
+ std::string GetSourceOutputCode(const std::string& prefix) const;
+
+ static size_t GetRawDataSize();
+ static std::string GetSourceTypeName();
+};
+
+
+class Struct_800A5E28
+{
+protected:
+ ZFile* parent;
+ std::vector<uint8_t> rawData;
+
+ uint16_t unk_0; // Vtx count
+ uint16_t unk_2; // Length of unk_4
+ segptr_t unk_4; // Struct_800A598C*
+ segptr_t unk_8; // Gfx*
+
+ std::vector<Struct_800A598C> unk_4_arr;
+ ZDisplayList* unk_8_dlist = nullptr;
+
+public:
+ Struct_800A5E28() = default;
+ Struct_800A5E28(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset);
+ Struct_800A5E28(ZFile* parent, const std::vector<uint8_t>& rawData, uint32_t fileOffset, size_t index);
+ ~Struct_800A5E28();
+
+ void PreGenSourceFiles(const std::string& prefix);
+ [[nodiscard]]
+ std::string GetSourceOutputCode(const std::string& prefix) const;
+
+ static size_t GetRawDataSize();
+ static std::string GetSourceTypeName();
+};
+
+
+class ZLimb : public ZResource
+{
+protected:
+ segptr_t segAddress;
+ ZLimbType type = ZLimbType::Standard;
+
+ int16_t transX, transY, transZ;
+ uint8_t childIndex, siblingIndex;
+ segptr_t dListPtr = 0;
+
+ std::vector<ZDisplayList> dLists;
+
+ segptr_t farDListPtr = 0; // LOD only
+
+ ZLimbSkinType skinSegmentType = ZLimbSkinType::SkinType_0; // Skin only
+ segptr_t skinSegment = 0; // Skin only
+ Struct_800A5E28 segmentStruct; // Skin only
+
+ std::string GetLimbDListSourceOutputCode(const std::string& prefix, const std::string& limbPrefix, segptr_t dListPtr);
+
+ std::string GetSourceOutputCodeSkin(const std::string& prefix);
+ std::string GetSourceOutputCodeSkin_Type_4(const std::string& prefix);
+
+public:
+ ZLimb(tinyxml2::XMLElement* reader, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent);
+ ZLimb(ZLimbType limbType, const std::string& prefix, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent);
+
+ void ParseXML(tinyxml2::XMLElement* reader) override;
+ void ParseRawData() override;
+ static ZLimb* FromXML(tinyxml2::XMLElement* reader, std::vector<uint8_t> nRawData, int rawDataIndex, std::string nRelPath, ZFile* parent);
+ int GetRawDataSize() override;
+ std::string GetSourceOutputCode(const std::string& prefix) override;
+ std::string GetSourceTypeName() override;
+ ZResourceType GetResourceType() override;
+
+ ZLimbType GetLimbType();
+ static const char* GetSourceTypeName(ZLimbType limbType);
+
+ uint32_t GetFileAddress();
+};
diff --git a/ZAPD/ZSkeleton.cpp b/ZAPD/ZSkeleton.cpp
index 173570f..37d9f46 100644
--- a/ZAPD/ZSkeleton.cpp
+++ b/ZAPD/ZSkeleton.cpp
@@ -1,89 +1,108 @@
#include "ZSkeleton.h"
#include "BitConverter.h"
#include "StringHelper.h"
-#include "Globals.h"
#include "HighLevel/HLModelIntermediette.h"
-#include <typeinfo>
using namespace std;
-using namespace tinyxml2;
-ZLimbStandard::ZLimbStandard()
-{
- name = "";
- transX = 0;
- transY = 0;
- transZ = 0;
- childIndex = 0;
- siblingIndex = 0;
- dListPtr = 0;
- children = vector<ZLimbStandard*>();
-}
-ZLimbStandard* ZLimbStandard::FromXML(XMLElement* reader, vector<uint8_t> nRawData, int rawDataIndex, string nRelPath, ZFile* parent)
+ZSkeleton::ZSkeleton(tinyxml2::XMLElement* reader, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent)
{
- ZLimbType limbType = ZLimbType::Standard;
- string limbName = reader->Attribute("Name");
- int limbAddress = strtol(StringHelper::Split(reader->Attribute("Offset"), "0x")[1].c_str(), NULL, 16);
+ rawData.assign(nRawData.begin(), nRawData.end());
+ rawDataIndex = nRawDataIndex;
+ parent = nParent;
- if (string(reader->Attribute("Type")) == "LOD")
- limbType = ZLimbType::LOD;
+ ParseXML(reader);
+ ParseRawData();
- ZLimbStandard* limb = ZLimbStandard::FromRawData(nRawData, rawDataIndex);
- limb->ParseXML(reader);
- limb->parent = parent;
- limb->name = limbName;
- limb->address = limbAddress;
+ string defaultPrefix = name;
+ defaultPrefix.replace(0, 1, "s"); // replace g prefix with s for local variables
+ uint32_t ptr = Seg2Filespace(limbsArrayAddress, parent->baseAddress);
- string entryType = limbType == ZLimbType::LOD ? "LodLimb" : "StandardLimb";
+ for (size_t i = 0; i < limbCount; i++) {
+ uint32_t ptr2 = Seg2Filespace(BitConverter::ToUInt32BE(rawData, ptr), parent->baseAddress);
- limb->parent->AddDeclaration(limb->address, DeclarationAlignment::None, 12, entryType, StringHelper::Sprintf("%s", limbName.c_str(), limb->address), "");
+ ZLimb* limb = new ZLimb(reader, rawData, ptr2, parent);
+ limb->SetName(StringHelper::Sprintf("%sLimb_%06X", defaultPrefix.c_str(), limb->GetFileAddress()));
+ limbs.push_back(limb);
- return limb;
+ ptr += 4;
+ }
}
-ZLimbStandard* ZLimbStandard::FromRawData(std::vector<uint8_t> nRawData, int rawDataIndex)
+ZSkeleton::~ZSkeleton()
{
- ZLimbStandard* limb = new ZLimbStandard();
-
- limb->address = rawDataIndex;
-
- limb->transX = BitConverter::ToInt16BE(nRawData, rawDataIndex + 0);
- limb->transY = BitConverter::ToInt16BE(nRawData, rawDataIndex + 2);
- limb->transZ = BitConverter::ToInt16BE(nRawData, rawDataIndex + 4);
+ for (auto& limb: limbs) {
+ delete limb;
+ }
+}
- limb->childIndex = nRawData[rawDataIndex + 6];
- limb->siblingIndex = nRawData[rawDataIndex + 7];
+void ZSkeleton::ParseXML(tinyxml2::XMLElement* reader)
+{
+ ZResource::ParseXML(reader);
- limb->dListPtr = BitConverter::ToInt32BE(nRawData, rawDataIndex + 8) & 0x00FFFFFF;
+ const char* skelTypeXml = reader->Attribute("Type");
+ if (skelTypeXml == nullptr) {
+ fprintf(stderr, "ZSkeleton::ParseXML: Warning in '%s'.\n\t Type not found found. Defaulting to 'Normal'.\n", name.c_str());
+ type = ZSkeletonType::Normal;
+ }
+ else {
+ string skelTypeStr(skelTypeXml);
+ if (skelTypeStr == "Flex") {
+ type = ZSkeletonType::Flex;
+ }
+ else if (skelTypeStr != "Normal") {
+ fprintf(stderr, "ZSkeleton::ParseXML: Warning in '%s'.\n\t Invalid Type found: '%s'. Defaulting to 'Normal'.\n", name.c_str(), skelTypeXml);
+ type = ZSkeletonType::Normal;
+ }
+ }
- return limb;
+ const char* limbTypeXml = reader->Attribute("LimbType");
+ if (limbTypeXml == nullptr) {
+ fprintf(stderr, "ZSkeleton::ParseXML: Warning in '%s'.\n\t LimbType not found found. Defaulting to 'Standard'.\n", name.c_str());
+ limbType = ZLimbType::Standard;
+ }
+ else {
+ string limbTypeStr(limbTypeXml);
+ if (limbTypeStr == "Standard") {
+ limbType = ZLimbType::Standard;
+ }
+ else if (limbTypeStr == "LOD") {
+ limbType = ZLimbType::LOD;
+ }
+ else if (limbTypeStr == "Skin") {
+ limbType = ZLimbType::Skin;
+ }
+ else {
+ fprintf(stderr, "ZSkeleton::ParseXML: Warning in '%s'.\n\t Invalid LimbType found: '%s'. Defaulting to 'Standard'.\n", name.c_str(), limbTypeXml);
+ limbType = ZLimbType::Standard;
+ }
+ }
}
-string ZLimbStandard::GetSourceOutputCode(const std::string& prefix)
+void ZSkeleton::ParseRawData()
{
- string dListStr = dListPtr == 0 ? "NULL" : StringHelper::Sprintf("%s", parent->GetVarName(dListPtr).c_str());
-
- string entryStr = StringHelper::Sprintf("{ %i, %i, %i }, %i, %i, %s",
- transX, transY, transZ, childIndex, siblingIndex, dListStr.c_str());
-
- Declaration* decl = parent->GetDeclaration(address);
- decl->text = entryStr;
+ ZResource::ParseRawData();
- return "";
+ limbsArrayAddress = BitConverter::ToUInt32BE(rawData, rawDataIndex);
+ limbCount = BitConverter::ToUInt8BE(rawData, rawDataIndex + 4);
+ dListCount = BitConverter::ToUInt8BE(rawData, rawDataIndex + 8);
}
-int ZLimbStandard::GetRawDataSize()
+ZSkeleton* ZSkeleton::FromXML(tinyxml2::XMLElement* reader, vector<uint8_t> nRawData, int rawDataIndex, string nRelPath, ZFile* nParent)
{
- return 12;
+ ZSkeleton* skeleton = new ZSkeleton(reader, nRawData, rawDataIndex, nParent);
+ skeleton->relativePath = std::move(nRelPath);
+
+ skeleton->parent->AddDeclaration(
+ skeleton->rawDataIndex, DeclarationAlignment::Align16, skeleton->GetRawDataSize(),
+ skeleton->GetSourceTypeName(), skeleton->name, "");
+
+ return skeleton;
}
-ZSkeleton::ZSkeleton() : ZResource()
+void ZSkeleton::Save(const std::string& outFolder)
{
- type = ZSkeletonType::Normal;
- limbs = vector<ZLimbStandard*>();
- rootLimb = nullptr;
- dListCount = 0;
}
void ZSkeleton::GenerateHLIntermediette(HLFileIntermediette& hlFile)
@@ -93,176 +112,85 @@ void ZSkeleton::GenerateHLIntermediette(HLFileIntermediette& hlFile)
//mdl->blocks.push_back(new HLTerminator());
}
-ZSkeleton* ZSkeleton::FromXML(XMLElement* reader, vector<uint8_t> nRawData, int rawDataIndex, string nRelPath, ZFile* nParent)
+int ZSkeleton::GetRawDataSize()
{
- ZSkeleton* skeleton = new ZSkeleton();
- skeleton->name = reader->Attribute("Name");
- skeleton->parent = nParent;
- ZLimbType limbType = ZLimbType::Standard;
- ZSkeletonType skeletonType = ZSkeletonType::Normal;
- int limbCount = 0;
-
- skeleton->rawData = nRawData;
- skeleton->rawDataIndex = rawDataIndex;
-
- if (reader->Attribute("Type") != nullptr)
- {
- if (string(reader->Attribute("Type")) == "Flex")
- skeletonType = ZSkeletonType::Flex;
- else if (string(reader->Attribute("Type")) == "Skin")
- skeletonType = ZSkeletonType::Skin;
- else if (string(reader->Attribute("Type")) != "Normal")
- {
- // TODO: Print some error here...
- }
- }
-
- skeleton->type = skeletonType;
-
- if (reader->Attribute("LimbType") != nullptr)
- {
- //printf("C3\n");
-
- if (string(reader->Attribute("LimbType")) == "LOD")
- limbType = ZLimbType::LOD;
+ switch (type) {
+ case ZSkeletonType::Normal:
+ return 0x8;
+ case ZSkeletonType::Flex:
+ return 0xC;
+ default:
+ return 0x8;
}
-
- limbCount = nRawData[rawDataIndex + 4];
- skeleton->dListCount = nRawData[rawDataIndex + 8];
-
- ZLimbStandard* currentLimb = nullptr;
-
- uint32_t ptr = (uint32_t)BitConverter::ToInt32BE(nRawData, rawDataIndex) & 0x00FFFFFF;
-
- for (int i = 0; i < limbCount; i++)
- {
- uint32_t ptr2 = (uint32_t)BitConverter::ToInt32BE(nRawData, ptr) & 0x00FFFFFF;
-
- if (limbType == ZLimbType::Standard)
- {
- ZLimbStandard* limb = ZLimbStandard::FromRawData(nRawData, ptr2);
- skeleton->limbs.push_back(limb);
- }
- else
- {
- ZLimbLOD* limb = ZLimbLOD::FromRawData(nRawData, ptr2);
- skeleton->limbs.push_back(limb);
- }
-
- ptr += 4;
- }
-
- return skeleton;
}
std::string ZSkeleton::GetSourceOutputCode(const std::string& prefix)
{
- if (parent != nullptr)
- {
- string defaultPrefix = name.c_str();
- defaultPrefix.replace(0, 1, "s"); // replace g prefix with s for local variables
-
- for (int i = 0; i < limbs.size(); i++)
- {
- ZLimbStandard* limb = limbs[i];
-
- string defaultDLName = StringHelper::Sprintf("%sLimbDL_%06X", defaultPrefix.c_str(), limb->dListPtr);
- string dListStr = limb->dListPtr == 0 ? "NULL" : StringHelper::Sprintf("%s", parent->GetDeclarationName(limb->dListPtr, defaultDLName).c_str());
-
- if (limb->dListPtr != 0 && parent->GetDeclaration(limb->dListPtr) == nullptr)
- {
- ZDisplayList* dList = new ZDisplayList(rawData, limb->dListPtr, ZDisplayList::GetDListLength(rawData, limb->dListPtr, Globals::Instance->game == ZGame::OOT_SW97 ? DListType::F3DEX : DListType::F3DZEX));
- dList->parent = parent;
- dList->SetName(StringHelper::Sprintf("%sLimbDL_%06X", defaultPrefix.c_str(), limb->dListPtr));
- dList->GetSourceOutputCode(defaultPrefix);
- }
-
- string entryStr = "";
- string entryType = "";
-
- if (typeid(*limb) == typeid(ZLimbLOD))
- {
- ZLimbLOD* limbLOD = (ZLimbLOD*)limbs[i];
- string defaultFarDLName = StringHelper::Sprintf("%sFarLimbDL_%06X", defaultPrefix.c_str(), limbLOD->farDListPtr);
- string dListStr2 = limbLOD->farDListPtr == 0 ? "NULL" : StringHelper::Sprintf("%s", parent->GetDeclarationName(limbLOD->farDListPtr, defaultFarDLName).c_str());
-
- if (limbLOD->farDListPtr != 0 && parent->GetDeclaration(limbLOD->farDListPtr) == nullptr)
- {
- ZDisplayList* dList = new ZDisplayList(rawData, limbLOD->farDListPtr, ZDisplayList::GetDListLength(rawData, limbLOD->farDListPtr, Globals::Instance->game == ZGame::OOT_SW97 ? DListType::F3DEX : DListType::F3DZEX));
- dList->parent = parent;
- dList->SetName(StringHelper::Sprintf("%s_farLimbDL_%06X", defaultPrefix.c_str(), limbLOD->farDListPtr));
- dList->GetSourceOutputCode(defaultPrefix);
- }
-
- entryType = "LodLimb";
-
- entryStr = StringHelper::Sprintf("{ %i, %i, %i }, %i, %i, { %s, %s }",
- limbLOD->transX, limbLOD->transY, limbLOD->transZ, limbLOD->childIndex, limbLOD->siblingIndex, dListStr.c_str(), dListStr2.c_str());
- }
- else
- {
- entryType = "StandardLimb";
-
- entryStr = StringHelper::Sprintf("{ %i, %i, %i }, %i, %i, %s",
- limb->transX, limb->transY, limb->transZ, limb->childIndex, limb->siblingIndex, dListStr.c_str());
- }
-
- string limbName = StringHelper::Sprintf("%sLimb_%06X", defaultPrefix.c_str(), limb->address);
+ if (parent == nullptr) {
+ return "";
+ }
- if (parent->HasDeclaration(limb->address))
- limbName = parent->GetDeclarationName(limb->address);
+ string defaultPrefix = name.c_str();
+ defaultPrefix.replace(0, 1, "s"); // replace g prefix with s for local variables
- parent->AddDeclaration(limb->address, DeclarationAlignment::None, limb->GetRawDataSize(), entryType, limbName, entryStr);
- }
+ for (auto& limb: limbs) {
+ limb->GetSourceOutputCode(defaultPrefix);
+ }
+ uint32_t ptr = Seg2Filespace(limbsArrayAddress, parent->baseAddress);
+ if (!parent->HasDeclaration(ptr))
+ {
// Table
string tblStr = "";
- for (int i = 0; i < limbs.size(); i++)
+ for (size_t i = 0; i < limbs.size(); i++)
{
- ZLimbStandard* limb = limbs[i];
+ ZLimb* limb = limbs.at(i);
- //string decl = StringHelper::Sprintf(" &_%sLimb_%04X,\n", prefix.c_str(), limb->address);
- string decl = "";
-
- if (parent->HasDeclaration(limb->address)) {
- decl = StringHelper::Sprintf(" &%s,", parent->GetDeclarationName(limb->address).c_str());
- if (i != (limbs.size() - 1)) {
- decl += "\n";
- }
+ string decl = StringHelper::Sprintf(" &%s,", parent->GetDeclarationName(limb->GetFileAddress()).c_str());
+ if (i != (limbs.size() - 1)) {
+ decl += "\n";
}
tblStr += decl;
}
- uint32_t ptr = (uint32_t)BitConverter::ToInt32BE(rawData, rawDataIndex) & 0x00FFFFFF;
+ parent->AddDeclarationArray(ptr, DeclarationAlignment::None, 4 * limbCount,
+ StringHelper::Sprintf("static %s*", ZLimb::GetSourceTypeName(limbType)),
+ StringHelper::Sprintf("%sLimbs", defaultPrefix.c_str()), limbCount, tblStr);
+ }
- if (!parent->HasDeclaration(ptr))
- {
- parent->AddDeclarationArray(ptr, DeclarationAlignment::None, 4 * limbs.size(),
- "static void*", StringHelper::Sprintf("%sLimbs", defaultPrefix.c_str()), limbs.size(), tblStr);
- }
+ string headerStr;
+ switch (type) {
+ case ZSkeletonType::Normal:
+ headerStr = StringHelper::Sprintf("%sLimbs, %i", defaultPrefix.c_str(), limbCount);
+ break;
+ case ZSkeletonType::Flex:
+ headerStr = StringHelper::Sprintf("%sLimbs, %i, %i", defaultPrefix.c_str(), limbCount, dListCount);
+ break;
+ }
- if (type == ZSkeletonType::Normal)
- {
- string headerStr = StringHelper::Sprintf("%sLimbs, %i", defaultPrefix.c_str(), limbs.size());
- parent->AddDeclaration(rawDataIndex, DeclarationAlignment::Align16, 8,
- "SkeletonHeader", StringHelper::Sprintf("%s", name.c_str()), headerStr);
- }
- else
- {
- string headerStr = StringHelper::Sprintf("%sLimbs, %i, %i", defaultPrefix.c_str(), limbs.size(), dListCount);
- parent->AddDeclaration(rawDataIndex, DeclarationAlignment::Align16, 12,
- "FlexSkeletonHeader", StringHelper::Sprintf("%s", name.c_str()), headerStr);
- }
+ Declaration* decl = parent->GetDeclaration(GetAddress());
+ if (decl == nullptr) {
+ parent->AddDeclaration(GetAddress(), DeclarationAlignment::Align16,
+ GetRawDataSize(), GetSourceTypeName(), name, headerStr);
+ }
+ else {
+ decl->text = headerStr;
}
return "";
}
-void ZSkeleton::Save(const std::string& outFolder)
+std::string ZSkeleton::GetSourceTypeName()
{
-
+ switch (type) {
+ case ZSkeletonType::Normal:
+ return "SkeletonHeader";
+ case ZSkeletonType::Flex:
+ return "FlexSkeletonHeader";
+ }
+ return "SkeletonHeader";
}
ZResourceType ZSkeleton::GetResourceType()
@@ -270,36 +198,7 @@ ZResourceType ZSkeleton::GetResourceType()
return ZResourceType::Skeleton;
}
-ZLimbLOD::ZLimbLOD() : ZLimbStandard()
-{
- farDListPtr = 0;
-}
-
-ZLimbLOD* ZLimbLOD::FromRawData(vector<uint8_t> nRawData, int rawDataIndex)
-{
- ZLimbLOD* limb = new ZLimbLOD();
-
- limb->address = rawDataIndex;
-
- limb->transX = BitConverter::ToInt16BE(nRawData, rawDataIndex + 0);
- limb->transY = BitConverter::ToInt16BE(nRawData, rawDataIndex + 2);
- limb->transZ = BitConverter::ToInt16BE(nRawData, rawDataIndex + 4);
-
- limb->childIndex = nRawData[rawDataIndex + 6];
- limb->siblingIndex = nRawData[rawDataIndex + 7];
-
- limb->dListPtr = BitConverter::ToInt32BE(nRawData, rawDataIndex + 8) & 0x00FFFFFF;
- limb->farDListPtr = BitConverter::ToInt32BE(nRawData, rawDataIndex + 12) & 0x00FFFFFF;
-
- return limb;
-}
-
-string ZLimbLOD::GetSourceOutputCode(const std::string& prefix)
-{
- return std::string();
-}
-
-int ZLimbLOD::GetRawDataSize()
+segptr_t ZSkeleton::GetAddress()
{
- return 16;
+ return rawDataIndex;
}
diff --git a/ZAPD/ZSkeleton.h b/ZAPD/ZSkeleton.h
index 836251a..2cafd56 100644
--- a/ZAPD/ZSkeleton.h
+++ b/ZAPD/ZSkeleton.h
@@ -2,64 +2,40 @@
#include <vector>
#include <string>
-#include <stdint.h>
+#include <cstdint>
#include "ZFile.h"
-
-enum class ZLimbType
-{
- Standard,
- LOD
-};
-
-struct ZLimbStandard : public ZResource
-{
- uint32_t address;
- std::string name;
-
- int16_t transX, transY, transZ;
- uint8_t childIndex, siblingIndex;
- uint32_t dListPtr;
-
- std::vector<ZLimbStandard*> children;
-
- ZLimbStandard();
- static ZLimbStandard* FromXML(tinyxml2::XMLElement* reader, std::vector<uint8_t> nRawData, int rawDataIndex, std::string nRelPath, ZFile* parent);
- static ZLimbStandard* FromRawData(std::vector<uint8_t> nRawData, int rawDataIndex);
- std::string GetSourceOutputCode(const std::string& prefix) override;
- int GetRawDataSize() override;
-};
-
-struct ZLimbLOD : ZLimbStandard
-{
- uint32_t farDListPtr;
-
- ZLimbLOD();
- //static ZLimbLOD* FromXML(tinyxml2::XMLElement* reader, std::vector<uint8_t> nRawData, int rawDataIndex, std::string nRelPath, ZFile* parent);
- static ZLimbLOD* FromRawData(std::vector<uint8_t> nRawData, int rawDataIndex);
- std::string GetSourceOutputCode(const std::string& prefix) override;
- int GetRawDataSize() override;
-};
+#include "ZDisplayList.h"
+#include "ZLimb.h"
enum ZSkeletonType
{
Normal,
- Flex,
- Skin
+ Flex
};
class ZSkeleton : public ZResource
{
public:
- ZSkeletonType type;
- std::vector<ZLimbStandard*> limbs;
- ZLimbStandard* rootLimb;
+ ZSkeletonType type = ZSkeletonType::Normal;
+ ZLimbType limbType = ZLimbType::Standard;
+ std::vector<ZLimb*> limbs;
+ segptr_t limbsArrayAddress;
+ uint8_t limbCount;
uint8_t dListCount; // FLEX SKELETON ONLY
- ZSkeleton();
- virtual void GenerateHLIntermediette(HLFileIntermediette& hlFile);
+ ZSkeleton(tinyxml2::XMLElement* reader, const std::vector<uint8_t>& nRawData, int nRawDataIndex, ZFile* nParent);
+ ~ZSkeleton();
+ void ParseXML(tinyxml2::XMLElement* reader) override;
+ void ParseRawData() override;
static ZSkeleton* FromXML(tinyxml2::XMLElement* reader, std::vector<uint8_t> nRawData, int rawDataIndex, std::string nRelPath, ZFile* nParent);
void Save(const std::string& outFolder) override;
- ZResourceType GetResourceType() override;
+ void GenerateHLIntermediette(HLFileIntermediette& hlFile) override;
+ int GetRawDataSize() override;
std::string GetSourceOutputCode(const std::string& prefix) override;
+
+ std::string GetSourceTypeName() override;
+ ZResourceType GetResourceType() override;
+
+ segptr_t GetAddress();
};