1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168
|
/* This file is part of the Spring engine (GPL v2 or later), see LICENSE.html */
#ifndef SPRING_3DOPARSER_H
#define SPRING_3DOPARSER_H
#include <vector>
#include <string>
#include "3DModel.h"
#include "IModelParser.h"
#include "Rendering/Textures/3DOTextureHandler.h"
#include "System/float3.h"
#include "System/UnorderedSet.hpp"
typedef SVertexData S3DOVertex;
namespace TA3DO {
typedef struct _3DObject
{
int VersionSignature;
int NumberOfVertices;
int NumberOfPrimitives;
int SelectionPrimitive;
int XFromParent;
int YFromParent;
int ZFromParent;
int OffsetToObjectName;
int Always_0;
int OffsetToVertexArray;
int OffsetToPrimitiveArray;
int OffsetToSiblingObject;
int OffsetToChildObject;
} _3DObject;
typedef struct _Primitive
{
int PaletteEntry;
int NumberOfVertexIndexes;
int Always_0;
int OffsetToVertexIndexArray;
int OffsetToTextureName;
int Unknown_1;
int Unknown_2;
int Unknown_3;
} _Primitive;
};
struct S3DOPrimitive
{
std::vector<int> indices; ///< indices to S3DOPiece::verts
std::vector<float3> vnormals; ///< per-vertex normals
// the raw normal for this primitive (-v0v1.cross(v0v2))
// used iff we have less than 3 or more than 4 vertices
float3 primNormal;
C3DOTextureHandler::UnitTexture* texture = nullptr;
// which piece this primitive belongs to
unsigned int pieceIndex = 0;
};
struct S3DOPiece: public S3DModelPiece
{
S3DOPiece() = default;
S3DOPiece(const S3DOPiece&) = delete;
S3DOPiece(S3DOPiece&& p) { *this = std::move(p); }
S3DOPiece& operator = (const S3DOPiece& p) = delete;
S3DOPiece& operator = (S3DOPiece&& p) {
#if 0
// piece is never actually moved, just need the operator for pool
emitPos = p.emitPos;
emitDir = p.emitDir;
verts = std::move(p.verts);
prims = std::move(p.prims);
vertexAttribs = std::move(p.vertexAttribs);
vertexIndices = std::move(p.vertexIndices);
#endif
return *this;
}
void Clear() override {
S3DModelPiece::Clear();
verts.clear();
prims.clear();
vertexAttribs.clear();
vertexIndices.clear();
emitPos = ZeroVector;
emitDir = ZeroVector;
}
unsigned int GetVertexCount() const override { return (vertexAttribs.size()); }
unsigned int GetVertexDrawIndexCount() const override { return (vertexIndices.size()); }
const float3& GetVertexPos(const int idx) const override { return vertexAttribs[idx].pos; }
const float3& GetNormal(const int idx) const override { return vertexAttribs[idx].normal; }
const std::vector<S3DOVertex>& GetVertexElements() const override { return vertexAttribs; }
const std::vector<unsigned>& GetVertexIndices() const override { return vertexIndices; }
float3 GetEmitPos() const override { return emitPos; }
float3 GetEmitDir() const override { return emitDir; }
public:
void SetMinMaxExtends();
void CalcNormals();
void GenTriangleGeometry();
void GetVertices(const TA3DO::_3DObject* o, const std::vector<unsigned char>& fileBuf);
void GetPrimitives(
const S3DModel* model,
int pos,
int num,
int excludePrim,
const std::vector<unsigned char>& fileBuf,
const spring::unordered_set<std::string>& teamTextures
);
bool IsBasePlate(const S3DOPrimitive* face) const;
C3DOTextureHandler::UnitTexture* GetTexture(
const TA3DO::_Primitive* p,
const std::vector<unsigned char>& fileBuf,
const spring::unordered_set<std::string>& teamTextures
) const;
public:
std::vector<float3> verts; //FIXME
std::vector<S3DOPrimitive> prims;
std::vector<S3DOVertex> vertexAttribs;
std::vector<unsigned int> vertexIndices;
float3 emitPos;
float3 emitDir;
};
class C3DOParser: public IModelParser
{
public:
void Init() override;
void Kill() override;
S3DModel Load(const std::string& name) override;
S3DOPiece* AllocPiece();
S3DOPiece* LoadPiece(S3DModel* model, S3DOPiece* parent, const std::vector<uint8_t>& buf, int pos);
private:
spring::unordered_set<std::string> teamTextures;
std::vector<S3DOPiece> piecePool;
spring::mutex poolMutex;
unsigned int numPoolPieces = 0;
};
#endif // SPRING_3DOPARSER_H
|