Files
Seele/src/Engine/Graphics/VertexData.h
T

126 lines
3.9 KiB
C++

#pragma once
#include "Graphics/Initializer.h"
#include "Material/MaterialInstance.h"
#include "Component/Transform.h"
#include "Containers/List.h"
#include "Graphics/Command.h"
#include "Graphics/Descriptor.h"
#include "Graphics/Buffer.h"
#include "Math/AABB.h"
namespace Seele
{
DECLARE_REF(Mesh)
struct MeshId
{
uint64 id;
std::strong_ordering operator<=>(const MeshId& other) const
{
return id <=> other.id;
}
bool operator==(const MeshId& other) const
{
return id == other.id;
}
};
struct Meshlet
{
AABB boundingBox;
uint32 uniqueVertices[Gfx::numVerticesPerMeshlet]; // unique vertiex indices in the vertex data
uint8 primitiveLayout[Gfx::numPrimitivesPerMeshlet * 3]; // indices into the uniqueVertices array, only uint8 needed
uint32 numVertices;
uint32 numPrimitives;
static void build(const Array<uint32>& indices, Array<Meshlet>& meshlets);
void calcBoundingBox(const Array<Vector>& positions);
};
class VertexData
{
public:
struct InstanceData
{
Matrix4 transformMatrix;
};
struct MeshData
{
uint32 numMeshlets = 0;
uint32 meshletOffset = 0;
uint32 firstIndex = 0;
uint32 numIndices = 0;
uint32 indicesOffset = 0;
uint32 pad0[3];
};
struct MeshInstanceData
{
InstanceData instance;
MeshData data;
};
struct MaterialInstanceData
{
PMaterialInstance materialInstance;
Gfx::OShaderBuffer instanceBuffer;
Gfx::OShaderBuffer meshDataBuffer;
Gfx::PDescriptorSet descriptorSet;
Array<MeshInstanceData> meshes;
};
struct MaterialData
{
PMaterial material;
Map<uint64, MaterialInstanceData> instances;
};
void resetMeshData();
void updateMesh(PMesh mesh, Component::Transform& transform);
void createDescriptors();
void loadMesh(MeshId id, Array<uint32> indices, Array<Meshlet> meshlets);
MeshId allocateVertexData(uint64 numVertices);
uint64 getMeshOffset(MeshId id);
uint64 getMeshVertexCount(MeshId id);
virtual void serializeMesh(MeshId id, uint64 numVertices, ArchiveBuffer& buffer) = 0;
virtual void deserializeMesh(MeshId id, ArchiveBuffer& buffer) = 0;
virtual void bindBuffers(Gfx::PRenderCommand command) = 0;
virtual Gfx::PDescriptorLayout getVertexDataLayout() = 0;
virtual Gfx::PDescriptorSet getVertexDataSet() = 0;
virtual std::string getTypeName() const = 0;
Gfx::PIndexBuffer getIndexBuffer() { return indexBuffer; }
Gfx::PDescriptorLayout getInstanceDataLayout() { return instanceDataLayout; }
const Map<std::string, MaterialData>& getMaterialData() const { return materialData; }
const Array<MeshData>& getMeshData(MeshId id) { return meshData[id]; }
static List<VertexData*> getList();
static VertexData* findByTypeName(std::string name);
virtual void init(Gfx::PGraphics graphics);
virtual void destroy();
protected:
virtual void resizeBuffers() = 0;
virtual void updateBuffers() = 0;
VertexData();
struct MeshletDescription
{
AABB boundingBox;
uint32_t vertexCount;
uint32_t primitiveCount;
uint32_t vertexOffset;
uint32_t primitiveOffset;
};
std::mutex materialDataLock;
Map<std::string, MaterialData> materialData;
Map<MeshId, Array<MeshData>> meshData;
Map<MeshId, uint64> meshOffsets;
Map<MeshId, uint64> meshVertexCounts;
Array<MeshletDescription> meshlets;
Array<uint8> primitiveIndices;
Array<uint32> vertexIndices;
Array<uint32> indices;
Gfx::PGraphics graphics;
Gfx::ODescriptorLayout instanceDataLayout;
// for mesh shading
Gfx::OShaderBuffer meshletBuffer;
Gfx::OShaderBuffer vertexIndicesBuffer;
Gfx::OShaderBuffer primitiveIndicesBuffer;
// for legacy pipeline
Gfx::OIndexBuffer indexBuffer;
uint64 idCounter;
uint64 head;
uint64 verticesAllocated;
bool dirty;
};
}