summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ExporterTest/RoomExporter.cpp2
-rw-r--r--ZAPD/ZAPD.vcxproj2
-rw-r--r--ZAPD/ZActorList.cpp194
-rw-r--r--ZAPD/ZActorList.h52
-rw-r--r--ZAPD/ZResource.h1
-rw-r--r--ZAPD/ZRoom/Commands/SetActorList.cpp158
-rw-r--r--ZAPD/ZRoom/Commands/SetActorList.h32
7 files changed, 275 insertions, 166 deletions
diff --git a/ExporterTest/RoomExporter.cpp b/ExporterTest/RoomExporter.cpp
index 6c5552d..9a5ea19 100644
--- a/ExporterTest/RoomExporter.cpp
+++ b/ExporterTest/RoomExporter.cpp
@@ -334,7 +334,7 @@ void ExporterExample_Room::Save(ZResource* res, fs::path outPath, BinaryWriter*
writer->Write(entry.rotX);
writer->Write(entry.rotY);
writer->Write(entry.rotZ);
- writer->Write(entry.initVar);
+ writer->Write(entry.params);
}
writer->Seek(oldOffset, SeekOffsetType::Start);
diff --git a/ZAPD/ZAPD.vcxproj b/ZAPD/ZAPD.vcxproj
index da3328e..505e411 100644
--- a/ZAPD/ZAPD.vcxproj
+++ b/ZAPD/ZAPD.vcxproj
@@ -190,6 +190,7 @@ mkdir build\ZAPD
<ClCompile Include="OtherStructs\SkinLimbStructs.cpp" />
<ClCompile Include="OutputFormatter.cpp" />
<ClCompile Include="WarningHandler.cpp" />
+ <ClCompile Include="ZActorList.cpp" />
<ClCompile Include="ZArray.cpp" />
<ClCompile Include="ZBackground.cpp" />
<ClCompile Include="ZCollisionPoly.cpp" />
@@ -279,6 +280,7 @@ mkdir build\ZAPD
<ClInclude Include="OtherStructs\SkinLimbStructs.h" />
<ClInclude Include="OutputFormatter.h" />
<ClInclude Include="WarningHandler.h" />
+ <ClInclude Include="ZActorList.h" />
<ClInclude Include="ZAnimation.h" />
<ClInclude Include="ZArray.h" />
<ClInclude Include="ZBackground.h" />
diff --git a/ZAPD/ZActorList.cpp b/ZAPD/ZActorList.cpp
new file mode 100644
index 0000000..ee5cb4d
--- /dev/null
+++ b/ZAPD/ZActorList.cpp
@@ -0,0 +1,194 @@
+#include "ZActorList.h"
+
+#include "Globals.h"
+#include "Utils/BitConverter.h"
+#include "WarningHandler.h"
+#include "ZFile.h"
+#include "ZRoom/ZNames.h"
+
+REGISTER_ZFILENODE(ActorList, ZActorList);
+
+ZActorList::ZActorList(ZFile* nParent) : ZResource(nParent)
+{
+ RegisterRequiredAttribute("Count");
+}
+
+void ZActorList::ExtractFromBinary(uint32_t nRawDataIndex, uint8_t nNumActors)
+{
+ rawDataIndex = nRawDataIndex;
+ numActors = nNumActors;
+
+ // Don't parse raw data of external files
+ if (parent->GetMode() == ZFileMode::ExternalFile)
+ return;
+
+ ParseRawData();
+}
+
+void ZActorList::ParseXML(tinyxml2::XMLElement* reader)
+{
+ ZResource::ParseXML(reader);
+
+ numActors = StringHelper::StrToL(registeredAttributes.at("Count").value);
+
+ if (numActors < 1)
+ {
+ HANDLE_ERROR_RESOURCE(
+ WarningType::InvalidAttributeValue, parent, this, rawDataIndex,
+ StringHelper::Sprintf("invalid value '%d' found for 'NumPaths' attribute", numActors),
+ "Should be at least '1'");
+ }
+}
+
+void ZActorList::ParseRawData()
+{
+ ZResource::ParseRawData();
+
+ offset_t currentPtr = rawDataIndex;
+ size_t largestlength = 0;
+
+ for (size_t i = 0; i < numActors; i++)
+ {
+ ActorSpawnEntry entry(parent->GetRawData(), currentPtr);
+
+ currentPtr += entry.GetRawDataSize();
+ actors.push_back(entry);
+
+ size_t actorNameLength = ZNames::GetActorName(entry.GetActorId()).size();
+ if (actorNameLength > largestlength)
+ largestlength = actorNameLength;
+ }
+
+ for (auto& entry : actors)
+ {
+ entry.SetLargestActorName(largestlength);
+ }
+}
+
+Declaration* ZActorList::DeclareVar(const std::string& prefix, const std::string& bodyStr)
+{
+ std::string auxName = name;
+
+ if (name == "")
+ auxName = GetDefaultName(prefix);
+
+ Declaration* decl =
+ parent->AddDeclarationArray(rawDataIndex, GetDeclarationAlignment(), GetRawDataSize(),
+ GetSourceTypeName(), name, GetActorListArraySize(), bodyStr);
+ decl->staticConf = staticConf;
+
+ return decl;
+}
+
+std::string ZActorList::GetBodySourceCode() const
+{
+ std::string declaration;
+
+ size_t index = 0;
+ for (auto& entry : actors)
+ {
+ declaration += StringHelper::Sprintf("\t{ %s },", entry.GetBodySourceCode().c_str());
+
+ if (index < actors.size() - 1)
+ declaration += "\n";
+
+ index++;
+ }
+
+ return declaration;
+}
+
+std::string ZActorList::GetSourceTypeName() const
+{
+ return actors.front().GetSourceTypeName();
+}
+
+ZResourceType ZActorList::GetResourceType() const
+{
+ return ZResourceType::ActorList;
+}
+
+size_t ZActorList::GetRawDataSize() const
+{
+ return actors.size() * actors.front().GetRawDataSize();
+}
+
+size_t ZActorList::GetActorListArraySize() const
+{
+ size_t actorCount = 0;
+
+ // Doing an else-if here so we only do the loop when the game is SW97.
+ // Actor 0x22 is removed from SW97, so we need to ensure that we don't increment the actor count
+ // for it.
+ if (Globals::Instance->game == ZGame::OOT_SW97)
+ {
+ actorCount = 0;
+
+ for (const auto& entry : actors)
+ if (entry.GetActorId() != 0x22)
+ actorCount++;
+ }
+ else
+ {
+ actorCount = actors.size();
+ }
+
+ return actorCount;
+}
+
+/* ActorSpawnEntry */
+
+ActorSpawnEntry::ActorSpawnEntry(const std::vector<uint8_t>& rawData, uint32_t rawDataIndex)
+{
+ actorNum = BitConverter::ToInt16BE(rawData, rawDataIndex + 0);
+ posX = BitConverter::ToInt16BE(rawData, rawDataIndex + 2);
+ posY = BitConverter::ToInt16BE(rawData, rawDataIndex + 4);
+ posZ = BitConverter::ToInt16BE(rawData, rawDataIndex + 6);
+ rotX = BitConverter::ToUInt16BE(rawData, rawDataIndex + 8);
+ rotY = BitConverter::ToUInt16BE(rawData, rawDataIndex + 10);
+ rotZ = BitConverter::ToUInt16BE(rawData, rawDataIndex + 12);
+ params = BitConverter::ToInt16BE(rawData, rawDataIndex + 14);
+}
+
+std::string ActorSpawnEntry::GetBodySourceCode() const
+{
+ std::string body;
+
+ std::string actorNameFmt = StringHelper::Sprintf("%%-%zus ", largestActorName + 1);
+ body =
+ StringHelper::Sprintf(actorNameFmt.c_str(), (ZNames::GetActorName(actorNum) + ",").c_str());
+
+ body += StringHelper::Sprintf("{ %6i, %6i, %6i }, ", posX, posY, posZ);
+ if (Globals::Instance->game == ZGame::MM_RETAIL)
+ body += StringHelper::Sprintf("{ SPAWN_ROT_FLAGS(%#5hX, 0x%04X)"
+ ", SPAWN_ROT_FLAGS(%#5hX, 0x%04X)"
+ ", SPAWN_ROT_FLAGS(%#5hX, 0x%04X) }, ",
+ (rotX >> 7) & 0b111111111, rotX & 0b1111111,
+ (rotY >> 7) & 0b111111111, rotY & 0b1111111,
+ (rotZ >> 7) & 0b111111111, rotZ & 0b1111111);
+ else
+ body += StringHelper::Sprintf("{ %#6hX, %#6hX, %#6hX }, ", rotX, rotY, rotZ);
+ body += StringHelper::Sprintf("0x%04X", params);
+
+ return body;
+}
+
+std::string ActorSpawnEntry::GetSourceTypeName() const
+{
+ return "ActorEntry";
+}
+
+size_t ActorSpawnEntry::GetRawDataSize() const
+{
+ return 16;
+}
+
+uint16_t ActorSpawnEntry::GetActorId() const
+{
+ return actorNum;
+}
+
+void ActorSpawnEntry::SetLargestActorName(size_t nameSize)
+{
+ largestActorName = nameSize;
+}
diff --git a/ZAPD/ZActorList.h b/ZAPD/ZActorList.h
new file mode 100644
index 0000000..7cc63da
--- /dev/null
+++ b/ZAPD/ZActorList.h
@@ -0,0 +1,52 @@
+#pragma once
+
+#include "ZResource.h"
+
+class ActorSpawnEntry
+{
+public:
+ uint16_t actorNum;
+ int16_t posX;
+ int16_t posY;
+ int16_t posZ;
+ uint16_t rotX;
+ uint16_t rotY;
+ uint16_t rotZ;
+ uint16_t params;
+ size_t largestActorName = 16;
+
+ ActorSpawnEntry(const std::vector<uint8_t>& rawData, uint32_t rawDataIndex);
+
+ std::string GetBodySourceCode() const;
+
+ std::string GetSourceTypeName() const;
+ size_t GetRawDataSize() const;
+
+ uint16_t GetActorId() const;
+ void SetLargestActorName(size_t nameSize);
+};
+
+class ZActorList : public ZResource
+{
+public:
+ std::vector<ActorSpawnEntry> actors;
+ uint32_t numActors = 0;
+
+ ZActorList(ZFile* nParent);
+
+ void ExtractFromBinary(offset_t nRawDataIndex, uint8_t nNumActors);
+
+ void ParseXML(tinyxml2::XMLElement* reader) override;
+ void ParseRawData() override;
+
+ Declaration* DeclareVar(const std::string& prefix, const std::string& bodyStr) override;
+ std::string GetBodySourceCode() const override;
+
+ std::string GetSourceTypeName() const override;
+ ZResourceType GetResourceType() const override;
+
+ size_t GetRawDataSize() const override;
+
+protected:
+ size_t GetActorListArraySize() const;
+};
diff --git a/ZAPD/ZResource.h b/ZAPD/ZResource.h
index 3bb2012..f97b259 100644
--- a/ZAPD/ZResource.h
+++ b/ZAPD/ZResource.h
@@ -25,6 +25,7 @@ class ZFile;
enum class ZResourceType
{
Error,
+ ActorList,
Animation,
Array,
AltHeader,
diff --git a/ZAPD/ZRoom/Commands/SetActorList.cpp b/ZAPD/ZRoom/Commands/SetActorList.cpp
index 719b336..b3c186f 100644
--- a/ZAPD/ZRoom/Commands/SetActorList.cpp
+++ b/ZAPD/ZRoom/Commands/SetActorList.cpp
@@ -1,117 +1,56 @@
#include "SetActorList.h"
+#include <cassert>
+
#include "Globals.h"
#include "Utils/BitConverter.h"
#include "Utils/StringHelper.h"
-#include "ZFile.h"
-#include "ZRoom/ZNames.h"
#include "ZRoom/ZRoom.h"
SetActorList::SetActorList(ZFile* nParent) : ZRoomCommand(nParent)
{
}
+SetActorList::~SetActorList()
+{
+ if (actorList != nullptr)
+ delete actorList;
+}
+
void SetActorList::ParseRawData()
{
ZRoomCommand::ParseRawData();
numActors = cmdArg1;
-}
-void SetActorList::DeclareReferences(const std::string& prefix)
-{
- if (numActors != 0 && cmdArg2 != 0)
- {
- std::string varName =
- StringHelper::Sprintf("%sActorList_%06X", prefix.c_str(), segmentOffset);
- parent->AddDeclarationPlaceholder(segmentOffset, varName);
- }
+ actorList = new ZActorList(parent);
+ actorList->ExtractFromBinary(segmentOffset, numActors);
}
-void SetActorList::ParseRawDataLate()
+void SetActorList::DeclareReferences(const std::string& prefix)
{
- ZRoomCommand::ParseRawDataLate();
- size_t actorsAmount = zRoom->GetDeclarationSizeFromNeighbor(segmentOffset) / 0x10;
-
- uint32_t currentPtr = segmentOffset;
-
- actors.reserve(actorsAmount);
- for (size_t i = 0; i < actorsAmount; i++)
+ if (parent->HasDeclaration(segmentOffset))
{
- ActorSpawnEntry entry(parent->GetRawData(), currentPtr);
-
- currentPtr += entry.GetRawDataSize();
- actors.push_back(entry);
- }
-}
-
-void SetActorList::DeclareReferencesLate(const std::string& prefix)
-{
- if (actors.empty())
+ delete actorList;
+ actorList = static_cast<ZActorList*>(parent->FindResource(segmentOffset));
+ assert(actorList != nullptr);
+ assert(actorList->GetResourceType() == ZResourceType::ActorList);
return;
-
- std::string declaration;
-
- size_t largestlength = 0;
- for (const auto& entry : actors)
- {
- size_t actorNameLength = ZNames::GetActorName(entry.GetActorId()).size();
- if (actorNameLength > largestlength)
- largestlength = actorNameLength;
}
- size_t index = 0;
- for (auto& entry : actors)
+ if (actorList->GetName() == "")
{
- entry.SetLargestActorName(largestlength);
- declaration += StringHelper::Sprintf("\t{ %s },", entry.GetBodySourceCode().c_str());
-
- if (index < actors.size() - 1)
- declaration += "\n";
-
- index++;
+ actorList->SetName(actorList->GetDefaultName(prefix));
}
-
- const auto& entry = actors.front();
-
- std::string varName = StringHelper::Sprintf("%sActorList_%06X", prefix.c_str(), segmentOffset);
- parent->AddDeclarationArray(segmentOffset, DeclarationAlignment::Align4,
- actors.size() * entry.GetRawDataSize(), entry.GetSourceTypeName(),
- varName, GetActorListArraySize(), declaration);
+ actorList->DeclareVar(prefix, "");
+ parent->AddResource(actorList);
}
std::string SetActorList::GetBodySourceCode() const
{
std::string listName;
Globals::Instance->GetSegmentedPtrName(cmdArg2, parent, "ActorEntry", listName);
- if (numActors != actors.size())
- {
- printf("%s: numActors(%i) ~ actors(%li)\n", parent->GetName().c_str(), numActors,
- actors.size());
- }
- return StringHelper::Sprintf("SCENE_CMD_ACTOR_LIST(%i, %s)", numActors, listName.c_str());
-}
-
-size_t SetActorList::GetActorListArraySize() const
-{
- size_t actorCount = 0;
-
- // Doing an else-if here so we only do the loop when the game is SW97.
- // Actor 0x22 is removed from SW97, so we need to ensure that we don't increment the actor count
- // for it.
- if (Globals::Instance->game == ZGame::OOT_SW97)
- {
- actorCount = 0;
-
- for (const auto& entry : actors)
- if (entry.GetActorId() != 0x22)
- actorCount++;
- }
- else
- {
- actorCount = actors.size();
- }
- return actorCount;
+ return StringHelper::Sprintf("SCENE_CMD_ACTOR_LIST(%i, %s)", numActors, listName.c_str());
}
std::string SetActorList::GetCommandCName() const
@@ -123,58 +62,3 @@ RoomCommand SetActorList::GetRoomCommand() const
{
return RoomCommand::SetActorList;
}
-
-ActorSpawnEntry::ActorSpawnEntry(const std::vector<uint8_t>& rawData, uint32_t rawDataIndex)
-{
- actorNum = BitConverter::ToInt16BE(rawData, rawDataIndex + 0);
- posX = BitConverter::ToInt16BE(rawData, rawDataIndex + 2);
- posY = BitConverter::ToInt16BE(rawData, rawDataIndex + 4);
- posZ = BitConverter::ToInt16BE(rawData, rawDataIndex + 6);
- rotX = BitConverter::ToUInt16BE(rawData, rawDataIndex + 8);
- rotY = BitConverter::ToUInt16BE(rawData, rawDataIndex + 10);
- rotZ = BitConverter::ToUInt16BE(rawData, rawDataIndex + 12);
- initVar = BitConverter::ToInt16BE(rawData, rawDataIndex + 14);
-}
-
-std::string ActorSpawnEntry::GetBodySourceCode() const
-{
- std::string body;
-
- std::string actorNameFmt = StringHelper::Sprintf("%%-%zus ", largestActorName + 1);
- body =
- StringHelper::Sprintf(actorNameFmt.c_str(), (ZNames::GetActorName(actorNum) + ",").c_str());
-
- body += StringHelper::Sprintf("{ %6i, %6i, %6i }, ", posX, posY, posZ);
- if (Globals::Instance->game == ZGame::MM_RETAIL)
- body += StringHelper::Sprintf("{ SPAWN_ROT_FLAGS(%#5hX, 0x%04X)"
- ", SPAWN_ROT_FLAGS(%#5hX, 0x%04X)"
- ", SPAWN_ROT_FLAGS(%#5hX, 0x%04X) }, ",
- (rotX >> 7) & 0b111111111, rotX & 0b1111111,
- (rotY >> 7) & 0b111111111, rotY & 0b1111111,
- (rotZ >> 7) & 0b111111111, rotZ & 0b1111111);
- else
- body += StringHelper::Sprintf("{ %#6hX, %#6hX, %#6hX }, ", rotX, rotY, rotZ);
- body += StringHelper::Sprintf("0x%04X", initVar);
-
- return body;
-}
-
-std::string ActorSpawnEntry::GetSourceTypeName() const
-{
- return "ActorEntry";
-}
-
-int32_t ActorSpawnEntry::GetRawDataSize() const
-{
- return 16;
-}
-
-uint16_t ActorSpawnEntry::GetActorId() const
-{
- return actorNum;
-}
-
-void ActorSpawnEntry::SetLargestActorName(size_t nameSize)
-{
- largestActorName = nameSize;
-}
diff --git a/ZAPD/ZRoom/Commands/SetActorList.h b/ZAPD/ZRoom/Commands/SetActorList.h
index 7b34125..f3eed93 100644
--- a/ZAPD/ZRoom/Commands/SetActorList.h
+++ b/ZAPD/ZRoom/Commands/SetActorList.h
@@ -1,44 +1,20 @@
#pragma once
#include "ZRoom/ZRoomCommand.h"
-
-class ActorSpawnEntry
-{
-public:
- uint16_t actorNum;
- int16_t posX;
- int16_t posY;
- int16_t posZ;
- uint16_t rotX;
- uint16_t rotY;
- uint16_t rotZ;
- uint16_t initVar;
- size_t largestActorName = 16;
-
- ActorSpawnEntry(const std::vector<uint8_t>& rawData, uint32_t rawDataIndex);
-
- std::string GetBodySourceCode() const;
-
- std::string GetSourceTypeName() const;
- int32_t GetRawDataSize() const;
-
- uint16_t GetActorId() const;
- void SetLargestActorName(size_t nameSize);
-};
+#include "ZActorList.h"
class SetActorList : public ZRoomCommand
{
public:
- uint8_t numActors;
- std::vector<ActorSpawnEntry> actors;
+ uint32_t numActors;
+ ZActorList* actorList = nullptr;
SetActorList(ZFile* nParent);
+ ~SetActorList();
void ParseRawData() override;
void DeclareReferences(const std::string& prefix) override;
- void ParseRawDataLate() override;
- void DeclareReferencesLate(const std::string& prefix) override;
std::string GetBodySourceCode() const override;