2
0
mirror of https://github.com/Laupetin/OpenAssetTools.git synced 2026-02-14 19:33:02 +00:00

chore: consider specified obj containers when post processing

This commit is contained in:
Jan
2025-01-02 16:26:42 +01:00
parent a7254aa11c
commit fe5d0f79ff
21 changed files with 296 additions and 53 deletions

View File

@@ -3,15 +3,39 @@
#include <format>
#include <iostream>
void IPakCreator::AddImage(std::string imageName)
IPakToCreate::IPakToCreate(std::string name)
: m_name(std::move(name))
{
}
void IPakToCreate::AddImage(std::string imageName)
{
m_image_names.emplace_back(std::move(imageName));
}
void IPakCreator::Finalize(ISearchPath& searchPath, const std::filesystem::path& outPath)
void IPakToCreate::Build(ISearchPath& searchPath, const std::filesystem::path& outPath)
{
std::cout << std::format("Creating ipak with {} entries:\n", m_image_names.size());
std::cout << std::format("Creating ipak {} with {} entries:\n", m_name, m_image_names.size());
for (const auto& imageName : m_image_names)
std::cout << std::format(" {}\n", imageName);
}
IPakToCreate* IPakCreator::GetOrAddIPak(const std::string& ipakName)
{
const auto existingIPak = m_ipak_lookup.find(ipakName);
if (existingIPak != m_ipak_lookup.end())
return existingIPak->second;
auto newIPak = std::make_unique<IPakToCreate>(ipakName);
auto* result = newIPak.get();
m_ipaks.emplace_back(std::move(newIPak));
return result;
}
void IPakCreator::Finalize(ISearchPath& searchPath, const std::filesystem::path& outPath)
{
for (const auto& ipakToCreate : m_ipaks)
ipakToCreate->Build(searchPath, outPath);
}

View File

@@ -4,13 +4,30 @@
#include "SearchPath/ISearchPath.h"
#include <filesystem>
#include <memory>
#include <string>
#include <unordered_map>
class IPakToCreate
{
public:
explicit IPakToCreate(std::string name);
void AddImage(std::string imageName);
void Build(ISearchPath& searchPath, const std::filesystem::path& outPath);
private:
std::string m_name;
std::vector<std::string> m_image_names;
};
class IPakCreator : public IZoneAssetLoaderState
{
public:
void AddImage(std::string imageName);
IPakToCreate* GetOrAddIPak(const std::string& ipakName);
void Finalize(ISearchPath& searchPath, const std::filesystem::path& outPath);
private:
std::vector<std::string> m_image_names;
std::unordered_map<std::string, IPakToCreate*> m_ipak_lookup;
std::vector<std::unique_ptr<IPakToCreate>> m_ipaks;
};

View File

@@ -4,19 +4,68 @@
#include <format>
AbstractImageIPakPostProcessor::AbstractImageIPakPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir)
: m_search_path(searchPath),
m_out_dir(outDir)
AbstractImageIPakPostProcessor::AbstractImageIPakPostProcessor(const ZoneDefinitionContext& zoneDefinition,
ISearchPath& searchPath,
const std::filesystem::path& outDir)
: m_zone_definition(zoneDefinition),
m_search_path(searchPath),
m_out_dir(outDir),
m_initialized(false),
m_obj_container_index(0u),
m_current_ipak(nullptr),
m_current_ipak_start_index(0u),
m_current_ipak_end_index(0u)
{
}
bool AbstractImageIPakPostProcessor::AppliesToZoneDefinition(const ZoneDefinitionContext& zoneDefinition)
{
for (const auto& objContainer : zoneDefinition.m_zone_definition.m_obj_containers)
{
if (objContainer.m_type == ZoneDefinitionObjContainerType::IPAK)
return true;
}
return false;
}
void AbstractImageIPakPostProcessor::FindNextObjContainer(AssetCreationContext& context)
{
const auto objContainerCount = m_zone_definition.m_zone_definition.m_obj_containers.size();
while (m_obj_container_index < objContainerCount)
{
const auto& objContainer = m_zone_definition.m_zone_definition.m_obj_containers[m_obj_container_index++];
if (objContainer.m_type != ZoneDefinitionObjContainerType::IPAK)
continue;
auto* ipakCreator = context.GetZoneAssetLoaderState<IPakCreator>();
m_current_ipak = ipakCreator->GetOrAddIPak(objContainer.m_name);
m_current_ipak_start_index = objContainer.m_asset_start;
m_current_ipak_end_index = objContainer.m_asset_end;
return;
}
m_current_ipak = nullptr;
}
void AbstractImageIPakPostProcessor::PostProcessAsset(XAssetInfoGeneric& assetInfo, AssetCreationContext& context)
{
if (assetInfo.m_name.empty() || assetInfo.m_name[0] == ',')
return;
auto* ipakCreator = context.GetZoneAssetLoaderState<IPakCreator>();
ipakCreator->AddImage(assetInfo.m_name);
// Initialize on first image occurance
if (!m_initialized)
{
FindNextObjContainer(context);
m_initialized = true;
}
while (m_current_ipak && m_zone_definition.m_asset_index_in_definition >= m_current_ipak_end_index)
FindNextObjContainer(context);
if (m_current_ipak && m_zone_definition.m_asset_index_in_definition <= m_current_ipak_start_index)
m_current_ipak->AddImage(assetInfo.m_name);
}
void AbstractImageIPakPostProcessor::FinalizeZone(AssetCreationContext& context)

View File

@@ -1,20 +1,33 @@
#pragma once
#include "Asset/IAssetPostProcessor.h"
#include "Asset/ZoneDefinitionContext.h"
#include "Image/IPak/IPakCreator.h"
#include <filesystem>
class AbstractImageIPakPostProcessor : public IAssetPostProcessor
{
public:
AbstractImageIPakPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir);
AbstractImageIPakPostProcessor(const ZoneDefinitionContext& zoneDefinition, ISearchPath& searchPath, const std::filesystem::path& outDir);
static bool AppliesToZoneDefinition(const ZoneDefinitionContext& zoneDefinition);
void PostProcessAsset(XAssetInfoGeneric& assetInfo, AssetCreationContext& context) override;
void FinalizeZone(AssetCreationContext& context) override;
private:
void FindNextObjContainer(AssetCreationContext& context);
const ZoneDefinitionContext& m_zone_definition;
ISearchPath& m_search_path;
const std::filesystem::path& m_out_dir;
bool m_initialized;
unsigned m_obj_container_index;
IPakToCreate* m_current_ipak;
unsigned m_current_ipak_start_index;
unsigned m_current_ipak_end_index;
};
template<typename AssetType> class ImageIPakPostProcessor final : public AbstractImageIPakPostProcessor
@@ -22,8 +35,8 @@ template<typename AssetType> class ImageIPakPostProcessor final : public Abstrac
public:
static_assert(std::is_base_of_v<IAssetBase, AssetType>);
ImageIPakPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir)
: AbstractImageIPakPostProcessor(searchPath, outDir)
ImageIPakPostProcessor(const ZoneDefinitionContext& zoneDefinition, ISearchPath& searchPath, const std::filesystem::path& outDir)
: AbstractImageIPakPostProcessor(zoneDefinition, searchPath, outDir)
{
}

View File

@@ -3,20 +3,70 @@
#include "Iwd/IwdCreator.h"
#include <format>
#include <iostream>
AbstractImageIwdPostProcessor::AbstractImageIwdPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir)
: m_search_path(searchPath),
m_out_dir(outDir)
AbstractImageIwdPostProcessor::AbstractImageIwdPostProcessor(const ZoneDefinitionContext& zoneDefinition,
ISearchPath& searchPath,
const std::filesystem::path& outDir)
: m_zone_definition(zoneDefinition),
m_search_path(searchPath),
m_out_dir(outDir),
m_initialized(false),
m_obj_container_index(0u),
m_current_iwd(nullptr),
m_current_iwd_start_index(0u),
m_current_iwd_end_index(0u)
{
}
bool AbstractImageIwdPostProcessor::AppliesToZoneDefinition(const ZoneDefinitionContext& zoneDefinition)
{
for (const auto& objContainer : zoneDefinition.m_zone_definition.m_obj_containers)
{
if (objContainer.m_type == ZoneDefinitionObjContainerType::IWD)
return true;
}
return false;
}
void AbstractImageIwdPostProcessor::FindNextObjContainer(AssetCreationContext& context)
{
const auto objContainerCount = m_zone_definition.m_zone_definition.m_obj_containers.size();
while (m_obj_container_index < objContainerCount)
{
const auto& objContainer = m_zone_definition.m_zone_definition.m_obj_containers[m_obj_container_index++];
if (objContainer.m_type != ZoneDefinitionObjContainerType::IWD)
continue;
auto* iwdCreator = context.GetZoneAssetLoaderState<IwdCreator>();
m_current_iwd = iwdCreator->GetOrAddIwd(objContainer.m_name);
m_current_iwd_start_index = objContainer.m_asset_start;
m_current_iwd_end_index = objContainer.m_asset_end;
return;
}
m_current_iwd = nullptr;
}
void AbstractImageIwdPostProcessor::PostProcessAsset(XAssetInfoGeneric& assetInfo, AssetCreationContext& context)
{
if (assetInfo.m_name.empty() || assetInfo.m_name[0] == ',')
return;
auto* iwdCreator = context.GetZoneAssetLoaderState<IwdCreator>();
iwdCreator->AddFile(std::format("images/{}.iwi", assetInfo.m_name));
// Initialize on first image occurance
if (!m_initialized)
{
FindNextObjContainer(context);
m_initialized = true;
}
while (m_current_iwd && m_zone_definition.m_asset_index_in_definition >= m_current_iwd_end_index)
FindNextObjContainer(context);
if (m_current_iwd && m_zone_definition.m_asset_index_in_definition <= m_current_iwd_start_index)
m_current_iwd->AddFile(std::format("images/{}.iwi", assetInfo.m_name));
}
void AbstractImageIwdPostProcessor::FinalizeZone(AssetCreationContext& context)

View File

@@ -1,20 +1,33 @@
#pragma once
#include "Asset/IAssetPostProcessor.h"
#include "Asset/ZoneDefinitionContext.h"
#include "Iwd/IwdCreator.h"
#include <filesystem>
class AbstractImageIwdPostProcessor : public IAssetPostProcessor
{
public:
AbstractImageIwdPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir);
AbstractImageIwdPostProcessor(const ZoneDefinitionContext& zoneDefinition, ISearchPath& searchPath, const std::filesystem::path& outDir);
static bool AppliesToZoneDefinition(const ZoneDefinitionContext& zoneDefinition);
void PostProcessAsset(XAssetInfoGeneric& assetInfo, AssetCreationContext& context) override;
void FinalizeZone(AssetCreationContext& context) override;
private:
void FindNextObjContainer(AssetCreationContext& context);
const ZoneDefinitionContext& m_zone_definition;
ISearchPath& m_search_path;
const std::filesystem::path& m_out_dir;
bool m_initialized;
unsigned m_obj_container_index;
IwdToCreate* m_current_iwd;
unsigned m_current_iwd_start_index;
unsigned m_current_iwd_end_index;
};
template<typename AssetType> class ImageIwdPostProcessor final : public AbstractImageIwdPostProcessor
@@ -22,8 +35,8 @@ template<typename AssetType> class ImageIwdPostProcessor final : public Abstract
public:
static_assert(std::is_base_of_v<IAssetBase, AssetType>);
ImageIwdPostProcessor(ISearchPath& searchPath, const std::filesystem::path& outDir)
: AbstractImageIwdPostProcessor(searchPath, outDir)
ImageIwdPostProcessor(const ZoneDefinitionContext& zoneDefinition, ISearchPath& searchPath, const std::filesystem::path& outDir)
: AbstractImageIwdPostProcessor(zoneDefinition, searchPath, outDir)
{
}