metaforce/DataSpec/DNAMP1/CMDL.hpp

152 lines
5.9 KiB
C++
Raw Normal View History

2015-07-25 03:43:49 +00:00
#ifndef _DNAMP1_CMDL_HPP_
#define _DNAMP1_CMDL_HPP_
#include "../DNACommon/DNACommon.hpp"
#include "../DNACommon/CMDL.hpp"
2015-07-25 03:43:49 +00:00
#include "CMDLMaterials.hpp"
#include "DNAMP1.hpp"
2015-08-13 07:29:00 +00:00
#include "CINF.hpp"
#include "CSKR.hpp"
2015-07-25 03:43:49 +00:00
2015-10-21 01:34:35 +00:00
#include <Athena/FileReader.hpp>
2016-02-13 09:02:47 +00:00
namespace DataSpec
2015-07-25 03:43:49 +00:00
{
namespace DNAMP1
{
2015-07-28 02:24:36 +00:00
struct CMDL
2015-07-25 03:43:49 +00:00
{
2015-08-05 21:46:07 +00:00
static bool Extract(const SpecBase& dataSpec,
PAKEntryReadStream& rs,
const HECL::ProjectPath& outPath,
PAKRouter<PAKBridge>& pakRouter,
2015-08-11 23:32:02 +00:00
const PAK::Entry& entry,
bool force,
std::function<void(const HECL::SystemChar*)> fileChanged)
2015-07-28 02:24:36 +00:00
{
/* Check for RigPair */
const PAKRouter<PAKBridge>::RigPair* rp = pakRouter.lookupCMDLRigPair(entry.id);
CINF cinf;
CSKR cskr;
std::pair<CSKR*,CINF*> loadRp(nullptr, nullptr);
if (rp)
{
pakRouter.lookupAndReadDNA(rp->first, cskr);
pakRouter.lookupAndReadDNA(rp->second, cinf);
loadRp.first = &cskr;
loadRp.second = &cinf;
}
/* Do extract */
2015-07-28 02:24:36 +00:00
HECL::BlenderConnection& conn = HECL::BlenderConnection::SharedConnection();
2015-11-21 01:16:07 +00:00
if (!conn.createBlend(outPath, HECL::BlenderConnection::BlendType::Mesh))
2015-07-28 02:24:36 +00:00
return false;
DNACMDL::ReadCMDLToBlender<PAKRouter<PAKBridge>, MaterialSet, std::pair<CSKR*,CINF*>, DNACMDL::SurfaceHeader_1, 2>
(conn, rs, pakRouter, entry, dataSpec, loadRp);
2015-10-21 01:34:35 +00:00
conn.saveBlend();
2015-11-14 23:42:58 +00:00
#if 0
2015-10-21 01:34:35 +00:00
/* Cook and re-extract test */
HECL::ProjectPath tempOut = outPath.getWithExtension(_S(".recook"), true);
HECL::BlenderConnection::DataStream ds = conn.beginData();
2015-11-14 02:28:45 +00:00
DNACMDL::Mesh mesh = ds.compileMesh(HECL::TopologyTriStrips, -1);
2015-10-21 01:34:35 +00:00
ds.close();
DNACMDL::WriteCMDL<MaterialSet, DNACMDL::SurfaceHeader_1_2, 2>(tempOut, outPath, mesh);
Athena::io::FileReader reader(tempOut.getAbsolutePath());
HECL::ProjectPath tempBlend = outPath.getWithExtension(_S(".recook.blend"), true);
if (!conn.createBlend(tempBlend, HECL::BlenderConnection::TypeMesh))
return false;
DNACMDL::ReadCMDLToBlender<PAKRouter<PAKBridge>, MaterialSet, std::pair<CSKR*,CINF*>, DNACMDL::SurfaceHeader_1_2, 2>
(conn, reader, pakRouter, entry, dataSpec, loadRp);
2015-08-05 21:46:07 +00:00
return conn.saveBlend();
#elif 0
2015-11-14 23:42:58 +00:00
/* HMDL cook test */
HECL::ProjectPath tempOut = outPath.getWithExtension(_S(".recook"), true);
HECL::BlenderConnection::DataStream ds = conn.beginData();
2015-11-21 01:16:07 +00:00
DNACMDL::Mesh mesh = ds.compileMesh(HECL::HMDLTopology::TriStrips, 16);
2015-11-14 23:42:58 +00:00
ds.close();
DNACMDL::WriteHMDLCMDL<HMDLMaterialSet, DNACMDL::SurfaceHeader_1, 2>(tempOut, outPath, mesh);
2015-11-14 23:42:58 +00:00
#endif
return true;
2015-07-28 02:24:36 +00:00
}
2015-10-07 01:17:17 +00:00
static void Name(const SpecBase& dataSpec,
PAKEntryReadStream& rs,
PAKRouter<PAKBridge>& pakRouter,
PAK::Entry& entry)
{
DNACMDL::NameCMDL<PAKRouter<PAKBridge>, MaterialSet>(rs, pakRouter, entry, dataSpec);
}
2015-10-14 23:07:29 +00:00
static bool Cook(const HECL::ProjectPath& outPath,
const HECL::ProjectPath& inPath,
const DNACMDL::Mesh& mesh)
2015-10-07 01:17:17 +00:00
{
2015-10-21 01:34:35 +00:00
HECL::ProjectPath tempOut = outPath.getWithExtension(_S(".recook"));
if (mesh.skins.size())
{
DNACMDL::Mesh skinMesh = mesh.getContiguousSkinningVersion();
if (!DNACMDL::WriteCMDL<MaterialSet, DNACMDL::SurfaceHeader_1, 2>(tempOut, inPath, skinMesh))
return false;
/* Output skinning intermediate */
auto vertCountIt = skinMesh.contiguousSkinVertCounts.cbegin();
Athena::io::FileWriter writer(outPath.getWithExtension(_S(".skin")).getAbsolutePath());
writer.writeUint32Big(skinMesh.skins.size());
for (const std::vector<DNACMDL::Mesh::SkinBind> skin : skinMesh.skins)
{
writer.writeUint32Big(skin.size());
for (const DNACMDL::Mesh::SkinBind& bind : skin)
{
writer.writeUint32Big(bind.boneIdx);
writer.writeFloatBig(bind.weight);
}
writer.writeUint32Big(*vertCountIt++);
}
2015-10-23 00:45:26 +00:00
writer.writeUint32Big(skinMesh.pos.size());
writer.writeUint32Big(skinMesh.boneNames.size());
for (const std::string& boneName : skinMesh.boneNames)
writer.writeString(boneName);
}
else if (!DNACMDL::WriteCMDL<MaterialSet, DNACMDL::SurfaceHeader_1, 2>(tempOut, inPath, mesh))
return false;
return true;
2015-10-07 01:17:17 +00:00
}
2015-11-14 02:28:45 +00:00
static bool HMDLCook(const HECL::ProjectPath& outPath,
const HECL::ProjectPath& inPath,
const DNACMDL::Mesh& mesh)
{
HECL::ProjectPath tempOut = outPath.getWithExtension(_S(".recook"));
if (mesh.skins.size())
{
if (!DNACMDL::WriteHMDLCMDL<HMDLMaterialSet, DNACMDL::SurfaceHeader_1, 2>(tempOut, inPath, mesh))
2015-11-14 02:28:45 +00:00
return false;
/* Output skinning intermediate */
Athena::io::FileWriter writer(outPath.getWithExtension(_S(".skin")).getAbsolutePath());
writer.writeUint32Big(mesh.skinBanks.banks.size());
for (const DNACMDL::Mesh::SkinBanks::Bank& sb : mesh.skinBanks.banks)
{
writer.writeUint32Big(sb.m_boneIdxs.size());
for (uint32_t bind : sb.m_boneIdxs)
writer.writeUint32Big(bind);
}
writer.writeUint32Big(mesh.boneNames.size());
for (const std::string& boneName : mesh.boneNames)
writer.writeString(boneName);
}
else if (!DNACMDL::WriteHMDLCMDL<HMDLMaterialSet, DNACMDL::SurfaceHeader_1, 2>(tempOut, inPath, mesh))
2015-11-14 02:28:45 +00:00
return false;
return true;
}
2015-07-25 03:43:49 +00:00
};
}
}
#endif // _DNAMP1_CMDL_HPP_