Nothing works
This commit is contained in:
@@ -7,7 +7,7 @@ import Scene;
|
||||
FragmentParameter vertexMain(
|
||||
VertexInput input
|
||||
){
|
||||
InstanceData inst = pScene.instances[input.instanceId];
|
||||
InstanceData inst = pScene.instances[pOffsets.instanceOffset + input.instanceId];
|
||||
VertexAttributes attr = pVertexData.getAttributes(input.vertexId);
|
||||
return attr.getParameter(inst.transformMatrix);
|
||||
}
|
||||
@@ -18,8 +18,9 @@ void meshMain(
|
||||
out vertices FragmentParameter vertices[MAX_VERTICES],
|
||||
out indices uint3 indices[MAX_PRIMITIVES]
|
||||
){
|
||||
InstanceData inst = pScene.instances[meshPayload.instanceId];
|
||||
MeshletDescription m = pScene.meshletInfos[pScene.culledMeshlets[meshPayload.cullingOffset + groupID]];
|
||||
InstanceData inst = meshPayload.instanceData;
|
||||
MeshData data = meshPayload.meshData;
|
||||
MeshletDescription m = pScene.meshletInfos[data.meshletOffset + groupID];
|
||||
SetMeshOutputCounts(m.vertexCount, m.primitiveCount);
|
||||
|
||||
for(uint i = threadID; i < MAX_PRIMITIVES; i += MESH_GROUP_SIZE)
|
||||
@@ -32,7 +33,7 @@ void meshMain(
|
||||
indices[p] = uint3(local_idx0, local_idx1, local_idx2);
|
||||
}
|
||||
}
|
||||
for(uint i = threadID; i < MAX_VERTICES; i+=MESH_GROUP_SIZE)
|
||||
for(uint i = threadID; i < MAX_VERTICES; i += MESH_GROUP_SIZE)
|
||||
{
|
||||
uint v = min(i, m.vertexCount - 1);
|
||||
{
|
||||
|
||||
@@ -28,21 +28,24 @@ void taskMain(
|
||||
viewFrustum.sides[1] = computePlane(origin, corners[1], corners[3]);
|
||||
viewFrustum.sides[2] = computePlane(origin, corners[0], corners[1]);
|
||||
viewFrustum.sides[3] = computePlane(origin, corners[3], corners[2]);
|
||||
p.instanceId = pOffsets.instanceOffset + groupID;
|
||||
p.cullingOffset = pScene.cullingOffsets[pOffsets.cullingCounterOffset + groupID];
|
||||
//p.instanceId = pOffsets.instanceOffset + groupID;
|
||||
p.instanceData = instance;
|
||||
p.meshData = mesh;
|
||||
//p.cullingOffset = pScene.cullingOffsets[pOffsets.cullingCounterOffset + groupID];
|
||||
}
|
||||
GroupMemoryBarrierWithGroupSync();
|
||||
for(uint i = threadID; i < mesh.numMeshlets; i += TASK_GROUP_SIZE)
|
||||
{
|
||||
uint m = mesh.meshletOffset + i;
|
||||
MeshletDescription meshlet = pScene.meshletInfos[m];
|
||||
if(meshlet.bounding.insideFrustum(viewFrustum))
|
||||
{
|
||||
uint index;
|
||||
InterlockedAdd(head, 1, index);
|
||||
pScene.culledMeshlets[p.cullingOffset + index] = m;
|
||||
}
|
||||
}
|
||||
GroupMemoryBarrierWithGroupSync();
|
||||
DispatchMesh(head, 1, 1, p);
|
||||
//for(uint i = threadID; i < mesh.numMeshlets; i += TASK_GROUP_SIZE)
|
||||
//{
|
||||
// uint m = mesh.meshletOffset + i;
|
||||
// MeshletDescription meshlet = pScene.meshletInfos[m];
|
||||
// //if(meshlet.bounding.insideFrustum(viewFrustum))
|
||||
// {
|
||||
// uint index;
|
||||
// InterlockedAdd(head, 1, index);
|
||||
// p.culledMeshlets[index] = m;
|
||||
// //pScene.culledMeshlets[p.cullingOffset + index] = m;
|
||||
// }
|
||||
//}
|
||||
//GroupMemoryBarrierWithGroupSync();
|
||||
DispatchMesh(mesh.numMeshlets, 1, 1, p);
|
||||
}
|
||||
@@ -34,7 +34,6 @@ struct InstanceData
|
||||
struct DrawCallOffsets
|
||||
{
|
||||
uint32_t instanceOffset;
|
||||
uint32_t cullingCounterOffset;
|
||||
};
|
||||
layout(push_constant)
|
||||
ConstantBuffer<DrawCallOffsets> pOffsets;
|
||||
@@ -46,15 +45,16 @@ struct Scene
|
||||
StructuredBuffer<MeshletDescription> meshletInfos;
|
||||
StructuredBuffer<uint8_t> primitiveIndices;
|
||||
StructuredBuffer<uint32_t> vertexIndices;
|
||||
StructuredBuffer<uint32_t> cullingOffsets;
|
||||
RWStructuredBuffer<uint32_t> culledMeshlets;
|
||||
// StructuredBuffer<uint32_t> cullingOffsets;
|
||||
// RWStructuredBuffer<uint32_t> culledMeshlets;
|
||||
};
|
||||
layout(set=2)
|
||||
ParameterBlock<Scene> pScene;
|
||||
|
||||
struct MeshPayload
|
||||
{
|
||||
uint instanceId;
|
||||
uint cullingOffset;
|
||||
InstanceData instanceData;
|
||||
MeshData meshData;
|
||||
uint culledMeshlets[2048];
|
||||
};
|
||||
|
||||
|
||||
@@ -44,51 +44,19 @@ IndexBuffer::~IndexBuffer()
|
||||
}
|
||||
UniformBuffer::UniformBuffer(QueueFamilyMapping mapping, const DataSource& sourceData)
|
||||
: Buffer(mapping, sourceData.owner)
|
||||
, contents(sourceData.size)
|
||||
{
|
||||
if (sourceData.data != nullptr)
|
||||
{
|
||||
std::memcpy(contents.data(), sourceData.data, contents.size());
|
||||
}
|
||||
}
|
||||
{}
|
||||
|
||||
UniformBuffer::~UniformBuffer()
|
||||
{
|
||||
}
|
||||
|
||||
bool UniformBuffer::updateContents(const DataSource& sourceData)
|
||||
{
|
||||
assert(contents.size() == sourceData.size);
|
||||
if (std::memcmp(contents.data(), sourceData.data, contents.size()) == 0)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
std::memcpy(contents.data(), sourceData.data, contents.size());
|
||||
return true;
|
||||
}
|
||||
|
||||
ShaderBuffer::ShaderBuffer(QueueFamilyMapping mapping, uint32 numElements, const DataSource& sourceData)
|
||||
: Buffer(mapping, sourceData.owner)
|
||||
, contents(sourceData.size)
|
||||
, numElements(numElements)
|
||||
{
|
||||
if (sourceData.data != nullptr)
|
||||
{
|
||||
std::memcpy(contents.data(), sourceData.data, sourceData.size);
|
||||
}
|
||||
}
|
||||
|
||||
ShaderBuffer::~ShaderBuffer()
|
||||
{
|
||||
}
|
||||
|
||||
void ShaderBuffer::updateContents(const ShaderBufferCreateInfo& createInfo)
|
||||
{
|
||||
contents.resize(createInfo.sourceData.size);
|
||||
numElements = createInfo.numElements;
|
||||
if (createInfo.sourceData.data != nullptr)
|
||||
{
|
||||
std::memcpy(contents.data(), createInfo.sourceData.data, createInfo.sourceData.size);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -64,25 +64,11 @@ class UniformBuffer : public Buffer {
|
||||
public:
|
||||
UniformBuffer(QueueFamilyMapping mapping, const DataSource &sourceData);
|
||||
virtual ~UniformBuffer();
|
||||
// returns true if an update was performed, false if the old contents == new
|
||||
// contents
|
||||
virtual bool updateContents(const DataSource &sourceData);
|
||||
bool isDataEquals(PUniformBuffer other) {
|
||||
if (other == nullptr) {
|
||||
return false;
|
||||
}
|
||||
if (contents.size() != other->contents.size()) {
|
||||
return false;
|
||||
}
|
||||
if (std::memcmp(contents.data(), other->contents.data(), contents.size()) !=
|
||||
0) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual void rotateBuffer(uint64 size) = 0;
|
||||
virtual void updateContents(const DataSource &sourceData) = 0;
|
||||
|
||||
protected:
|
||||
Array<uint8> contents;
|
||||
// Inherited via QueueOwnedResource
|
||||
virtual void executeOwnershipBarrier(QueueType newOwner) = 0;
|
||||
virtual void executePipelineBarrier(SeAccessFlags srcAccess,
|
||||
@@ -97,7 +83,7 @@ public:
|
||||
const DataSource &bulkResourceData);
|
||||
virtual ~ShaderBuffer();
|
||||
virtual void rotateBuffer(uint64 size) = 0;
|
||||
virtual void updateContents(const ShaderBufferCreateInfo &sourceData);
|
||||
virtual void updateContents(const ShaderBufferCreateInfo &sourceData) = 0;
|
||||
constexpr uint32 getNumElements() const { return numElements; }
|
||||
virtual void *mapRegion(uint64 offset = 0, uint64 size = -1,
|
||||
bool writeOnly = true) = 0;
|
||||
@@ -111,7 +97,6 @@ protected:
|
||||
SeAccessFlags dstAccess,
|
||||
SePipelineStageFlags dstStage) = 0;
|
||||
|
||||
Array<uint8> contents;
|
||||
uint32 numElements;
|
||||
};
|
||||
DEFINE_REF(ShaderBuffer)
|
||||
|
||||
@@ -33,7 +33,7 @@ BasePass::BasePass(Gfx::PGraphics graphics, PScene scene)
|
||||
|
||||
basePassLayout->addDescriptorLayout(lightCullingLayout);
|
||||
basePassLayout->addPushConstants(Gfx::SePushConstantRange{
|
||||
.stageFlags = Gfx::SE_SHADER_STAGE_TASK_BIT_EXT,
|
||||
.stageFlags = Gfx::SE_SHADER_STAGE_TASK_BIT_EXT | Gfx::SE_SHADER_STAGE_VERTEX_BIT,
|
||||
.offset = 0,
|
||||
.size = sizeof(VertexData::DrawCallOffsets),
|
||||
});
|
||||
@@ -145,7 +145,7 @@ void BasePass::render()
|
||||
pipelineInfo.renderPass = renderPass;
|
||||
pipelineInfo.depthStencilState.depthCompareOp = Gfx::SE_COMPARE_OP_GREATER_OR_EQUAL;
|
||||
pipelineInfo.multisampleState.samples = viewport->getSamples();
|
||||
pipelineInfo.colorBlend.attachmentCount = 1;
|
||||
pipelineInfo.colorBlend.attachmentCount = 2;
|
||||
Gfx::PGraphicsPipeline pipeline = graphics->createGraphicsPipeline(std::move(pipelineInfo));
|
||||
command->bindPipeline(pipeline);
|
||||
}
|
||||
@@ -153,27 +153,24 @@ void BasePass::render()
|
||||
command->bindDescriptor(viewParamsSet);
|
||||
command->bindDescriptor(scene->getLightEnvironment()->getDescriptorSet());
|
||||
command->bindDescriptor(opaqueCulling);
|
||||
command->bindDescriptor(vertexData->getInstanceDataSet());
|
||||
for (const auto& drawCall : materialData.instances)
|
||||
{
|
||||
command->bindDescriptor(drawCall.materialInstance->getDescriptorSet());
|
||||
command->bindDescriptor(vertexData->getInstanceDataSet());
|
||||
command->pushConstants(Gfx::SE_SHADER_STAGE_TASK_BIT_EXT, 0, sizeof(VertexData::DrawCallOffsets), &drawCall.offsets);
|
||||
command->bindDescriptor(drawCall.materialInstance->getDescriptorSet());
|
||||
command->pushConstants(Gfx::SE_SHADER_STAGE_TASK_BIT_EXT | Gfx::SE_SHADER_STAGE_VERTEX_BIT, 0, sizeof(VertexData::DrawCallOffsets), &drawCall.offsets);
|
||||
if (graphics->supportMeshShading())
|
||||
{
|
||||
command->drawMesh(drawCall.numMeshes, 1, 1);
|
||||
command->drawMesh(drawCall.instanceMeshData.size(), 1, 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
//command->bindIndexBuffer(vertexData->getIndexBuffer());
|
||||
//uint32 instanceOffset = 0;
|
||||
//for (const auto& meshData : vertexData->getMeshData(instance.meshId))
|
||||
//{
|
||||
// if (meshData.numIndices > 0)
|
||||
// {
|
||||
// command->drawIndexed(meshData.numIndices, 1, meshData.firstIndex, meshData.indicesOffset, instanceOffset);
|
||||
// }
|
||||
// instanceOffset++;
|
||||
//}
|
||||
command->bindIndexBuffer(vertexData->getIndexBuffer());
|
||||
for (const auto& meshData : drawCall.instanceMeshData)
|
||||
{
|
||||
// all meshlets of a mesh share the same indices offset
|
||||
command->drawIndexed(meshData.numIndices, 1, meshData.firstIndex, vertexData->getIndicesOffset(meshData.meshletOffset), 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
commands.add(std::move(command));
|
||||
|
||||
@@ -19,7 +19,7 @@ DepthPrepass::DepthPrepass(Gfx::PGraphics graphics, PScene scene)
|
||||
depthPrepassLayout = graphics->createPipelineLayout("DepthPrepassLayout");
|
||||
depthPrepassLayout->addDescriptorLayout(viewParamsLayout);
|
||||
depthPrepassLayout->addPushConstants(Gfx::SePushConstantRange{
|
||||
.stageFlags = Gfx::SE_SHADER_STAGE_TASK_BIT_EXT,
|
||||
.stageFlags = Gfx::SE_SHADER_STAGE_TASK_BIT_EXT | Gfx::SE_SHADER_STAGE_VERTEX_BIT,
|
||||
.offset = 0,
|
||||
.size = sizeof(VertexData::DrawCallOffsets),
|
||||
});
|
||||
@@ -117,23 +117,19 @@ void DepthPrepass::render()
|
||||
for (const auto& drawCall : materialData.instances)
|
||||
{
|
||||
command->bindDescriptor(vertexData->getInstanceDataSet());
|
||||
command->pushConstants(Gfx::SE_SHADER_STAGE_TASK_BIT_EXT, 0, sizeof(VertexData::DrawCallOffsets), &drawCall.offsets);
|
||||
command->pushConstants(Gfx::SE_SHADER_STAGE_TASK_BIT_EXT | Gfx::SE_SHADER_STAGE_VERTEX_BIT, 0, sizeof(VertexData::DrawCallOffsets), &drawCall.offsets);
|
||||
if (graphics->supportMeshShading())
|
||||
{
|
||||
command->drawMesh(drawCall.numMeshes, 1, 1);
|
||||
command->drawMesh(drawCall.instanceMeshData.size(), 1, 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
//command->bindIndexBuffer(vertexData->getIndexBuffer());
|
||||
//uint32 instanceOffset = 0;
|
||||
//for (const auto& meshData : vertexData->getMeshData(instance.meshId))
|
||||
//{
|
||||
// if (meshData.numIndices > 0)
|
||||
// {
|
||||
// command->drawIndexed(meshData.numIndices, 1, meshData.firstIndex, meshData.indicesOffset, instanceOffset);
|
||||
// }
|
||||
// instanceOffset++;
|
||||
//}
|
||||
command->bindIndexBuffer(vertexData->getIndexBuffer());
|
||||
for (const auto& meshData : drawCall.instanceMeshData)
|
||||
{
|
||||
// all meshlets of a mesh share the same indices offset
|
||||
command->drawIndexed(meshData.numIndices, 1, meshData.firstIndex, vertexData->getIndicesOffset(meshData.meshletOffset), 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
commands.add(std::move(command));
|
||||
|
||||
@@ -38,6 +38,7 @@ void RenderPass::beginFrame(const Component::Camera& cam)
|
||||
.size = sizeof(ViewParameter),
|
||||
.data = (uint8*)&viewParams,
|
||||
};
|
||||
viewParamsBuffer->rotateBuffer(sizeof(ViewParameter));
|
||||
viewParamsBuffer->updateContents(uniformUpdate);
|
||||
viewParamsBuffer->pipelineBarrier(
|
||||
Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
|
||||
@@ -18,7 +18,7 @@ void VertexData::resetMeshData()
|
||||
std::unique_lock l(materialDataLock);
|
||||
for (auto& mat : materialData)
|
||||
{
|
||||
for (auto inst : mat.instances)
|
||||
for (auto& inst : mat.instances)
|
||||
{
|
||||
inst.instanceData.clear();
|
||||
inst.instanceMeshData.clear();
|
||||
@@ -51,15 +51,15 @@ void VertexData::updateMesh(PMesh mesh, Component::Transform& transform)
|
||||
matData.instances.resize(referencedInstance->getId() + 1);
|
||||
}
|
||||
BatchedDrawCall& matInstanceData = matData.instances[referencedInstance->getId()];
|
||||
const auto& data = meshData[mesh->id];
|
||||
matInstanceData.materialInstance = referencedInstance;
|
||||
|
||||
Matrix4 transformMatrix = transform.toMatrix() * mesh->transform;
|
||||
matInstanceData.instanceData.add(InstanceData{
|
||||
.transformMatrix = transformMatrix,
|
||||
.inverseTransformMatrix = glm::inverse(transformMatrix),
|
||||
});
|
||||
const auto& data = meshData[mesh->id];
|
||||
matInstanceData.instanceMeshData.add(data);
|
||||
matInstanceData.numMeshes++;
|
||||
for (size_t i = 0; i < 0; ++i)
|
||||
{
|
||||
auto bounding = meshlets[data.meshletOffset + i].bounding;
|
||||
@@ -100,7 +100,6 @@ void VertexData::updateMesh(PMesh mesh, Component::Transform& transform)
|
||||
addDebugVertex(DebugVertex{ .position = corners[7], .color = meshlets[data.meshletOffset + i].color });
|
||||
}
|
||||
|
||||
matInstanceData.materialInstance = referencedInstance;
|
||||
referencedInstance->updateDescriptor();
|
||||
}
|
||||
|
||||
@@ -111,53 +110,52 @@ void VertexData::createDescriptors()
|
||||
instanceData.clear();
|
||||
instanceMeshData.clear();
|
||||
|
||||
uint32 numMeshlets = 0;
|
||||
Array<uint32> cullingOffsets;
|
||||
//uint32 numMeshlets = 0;
|
||||
//Array<uint32> cullingOffsets;
|
||||
for (auto& mat : materialData)
|
||||
{
|
||||
for (auto& instance : mat.instances)
|
||||
{
|
||||
instance.offsets.instanceOffset = instanceData.size();
|
||||
instance.offsets.cullingCounterOffset = cullingOffsets.size();
|
||||
instance.numMeshes = instance.instanceData.size();
|
||||
instance.numMeshlets = 0;
|
||||
//instance.offsets.cullingCounterOffset = cullingOffsets.size();
|
||||
//instance.numMeshlets = 0;
|
||||
for (size_t i = 0; i < instance.instanceData.size(); ++i)
|
||||
{
|
||||
instanceData.add(instance.instanceData[i]);
|
||||
instanceMeshData.add(instance.instanceMeshData[i]);
|
||||
instance.numMeshlets += instance.instanceMeshData[i].numMeshlets;
|
||||
cullingOffsets.add(numMeshlets);
|
||||
numMeshlets += instance.numMeshlets;
|
||||
//instance.numMeshlets += instance.instanceMeshData[i].numMeshlets;
|
||||
//cullingOffsets.add(numMeshlets);
|
||||
//numMeshlets += instance.numMeshlets;
|
||||
}
|
||||
}
|
||||
}
|
||||
cullingOffsetBuffer->rotateBuffer(cullingOffsets.size() * sizeof(uint32));
|
||||
cullingOffsetBuffer->updateContents(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
.size = cullingOffsets.size() * sizeof(uint32),
|
||||
.data = (uint8*)cullingOffsets.data(),
|
||||
},
|
||||
.numElements = cullingOffsets.size()
|
||||
});
|
||||
cullingOffsetBuffer->pipelineBarrier(
|
||||
Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
Gfx::SE_ACCESS_MEMORY_READ_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_TASK_SHADER_BIT_EXT
|
||||
);
|
||||
cullingBuffer->rotateBuffer(numMeshlets * sizeof(uint32));
|
||||
cullingBuffer->updateContents(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
.size = numMeshlets * sizeof(uint32),
|
||||
},
|
||||
.numElements = numMeshlets
|
||||
});
|
||||
cullingBuffer->pipelineBarrier(
|
||||
Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
Gfx::SE_ACCESS_MEMORY_WRITE_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_MESH_SHADER_BIT_EXT
|
||||
);
|
||||
//cullingOffsetBuffer->rotateBuffer(cullingOffsets.size() * sizeof(uint32));
|
||||
//cullingOffsetBuffer->updateContents(ShaderBufferCreateInfo{
|
||||
// .sourceData = {
|
||||
// .size = cullingOffsets.size() * sizeof(uint32),
|
||||
// .data = (uint8*)cullingOffsets.data(),
|
||||
// },
|
||||
// .numElements = cullingOffsets.size()
|
||||
// });
|
||||
//cullingOffsetBuffer->pipelineBarrier(
|
||||
// Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
// Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
// Gfx::SE_ACCESS_MEMORY_READ_BIT,
|
||||
// Gfx::SE_PIPELINE_STAGE_TOP_OF_PIPE_BIT
|
||||
//);
|
||||
//cullingBuffer->rotateBuffer(numMeshlets * sizeof(uint32));
|
||||
//cullingBuffer->updateContents(ShaderBufferCreateInfo{
|
||||
// .sourceData = {
|
||||
// .size = numMeshlets * sizeof(uint32),
|
||||
// },
|
||||
// .numElements = numMeshlets
|
||||
// });
|
||||
//cullingBuffer->pipelineBarrier(
|
||||
// Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
// Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
// Gfx::SE_ACCESS_MEMORY_WRITE_BIT,
|
||||
// Gfx::SE_PIPELINE_STAGE_TOP_OF_PIPE_BIT
|
||||
//);
|
||||
instanceBuffer->rotateBuffer(instanceData.size() * sizeof(InstanceData));
|
||||
instanceBuffer->updateContents(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
@@ -170,7 +168,7 @@ void VertexData::createDescriptors()
|
||||
Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
Gfx::SE_ACCESS_MEMORY_READ_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_VERTEX_SHADER_BIT | Gfx::SE_PIPELINE_STAGE_TASK_SHADER_BIT_EXT
|
||||
Gfx::SE_PIPELINE_STAGE_TOP_OF_PIPE_BIT
|
||||
);
|
||||
|
||||
instanceMeshDataBuffer->rotateBuffer(sizeof(MeshData) * instanceMeshData.size());
|
||||
@@ -185,7 +183,7 @@ void VertexData::createDescriptors()
|
||||
Gfx::SE_ACCESS_TRANSFER_WRITE_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_TRANSFER_BIT,
|
||||
Gfx::SE_ACCESS_MEMORY_READ_BIT,
|
||||
Gfx::SE_PIPELINE_STAGE_VERTEX_SHADER_BIT | Gfx::SE_PIPELINE_STAGE_TASK_SHADER_BIT_EXT
|
||||
Gfx::SE_PIPELINE_STAGE_TOP_OF_PIPE_BIT
|
||||
);
|
||||
instanceDataLayout->reset();
|
||||
descriptorSet = instanceDataLayout->allocateDescriptorSet();
|
||||
@@ -194,14 +192,15 @@ void VertexData::createDescriptors()
|
||||
descriptorSet->updateBuffer(2, meshletBuffer);
|
||||
descriptorSet->updateBuffer(3, primitiveIndicesBuffer);
|
||||
descriptorSet->updateBuffer(4, vertexIndicesBuffer);
|
||||
descriptorSet->updateBuffer(5, cullingOffsetBuffer);
|
||||
descriptorSet->updateBuffer(6, cullingBuffer);
|
||||
//descriptorSet->updateBuffer(5, cullingOffsetBuffer);
|
||||
//descriptorSet->updateBuffer(6, cullingBuffer);
|
||||
|
||||
descriptorSet->writeChanges();
|
||||
}
|
||||
|
||||
void VertexData::loadMesh(MeshId id, Array<uint32> loadedIndices, Array<Meshlet> loadedMeshlets)
|
||||
{
|
||||
assert(loadedMeshlets.size() < 2048);
|
||||
std::unique_lock l(vertexDataLock);
|
||||
meshlets.reserve(meshlets.size() + loadedMeshlets.size());
|
||||
vertexIndices.reserve(vertexIndices.size() + loadedMeshlets.size() * Gfx::numVerticesPerMeshlet);
|
||||
@@ -232,10 +231,10 @@ void VertexData::loadMesh(MeshId id, Array<uint32> loadedIndices, Array<Meshlet>
|
||||
.bounding = meshAABB,//.toSphere(),
|
||||
.numMeshlets = (uint32)loadedMeshlets.size(),
|
||||
.meshletOffset = meshletOffset,
|
||||
.firstIndex = (uint32)indices.size(),
|
||||
.numIndices = (uint32)loadedIndices.size(),
|
||||
};
|
||||
|
||||
meshData[id].firstIndex = indices.size();
|
||||
meshData[id].numIndices = loadedIndices.size();
|
||||
if (!graphics->supportMeshShading())
|
||||
{
|
||||
indices.resize(indices.size() + loadedIndices.size());
|
||||
@@ -340,18 +339,18 @@ void VertexData::init(Gfx::PGraphics _graphics)
|
||||
// vertexIndices
|
||||
instanceDataLayout->addDescriptorBinding(Gfx::DescriptorBinding{ .binding = 4, .descriptorType = Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER });
|
||||
// cullingList
|
||||
instanceDataLayout->addDescriptorBinding(Gfx::DescriptorBinding{ .binding = 5, .descriptorType = Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER });
|
||||
//instanceDataLayout->addDescriptorBinding(Gfx::DescriptorBinding{ .binding = 5, .descriptorType = Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER });
|
||||
// cullingOffset
|
||||
instanceDataLayout->addDescriptorBinding(Gfx::DescriptorBinding{ .binding = 6, .descriptorType = Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER });
|
||||
//instanceDataLayout->addDescriptorBinding(Gfx::DescriptorBinding{ .binding = 6, .descriptorType = Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER });
|
||||
|
||||
cullingOffsetBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.dynamic = true,
|
||||
.name = "MeshletOffset",
|
||||
});
|
||||
cullingBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.dynamic = true,
|
||||
.name = "MeshletCulling",
|
||||
});
|
||||
//cullingOffsetBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
// .dynamic = true,
|
||||
// .name = "MeshletOffset",
|
||||
// });
|
||||
//cullingBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
// .dynamic = true,
|
||||
// .name = "MeshletCulling",
|
||||
// });
|
||||
instanceBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.dynamic = true,
|
||||
.name = "InstanceBuffer",
|
||||
|
||||
@@ -44,13 +44,10 @@ public:
|
||||
struct DrawCallOffsets
|
||||
{
|
||||
uint32 instanceOffset = 0;
|
||||
uint32 cullingCounterOffset = 0;
|
||||
};
|
||||
struct BatchedDrawCall
|
||||
{
|
||||
PMaterialInstance materialInstance;
|
||||
uint64 numMeshes = 0;
|
||||
uint64 numMeshlets = 0;
|
||||
DrawCallOffsets offsets;
|
||||
Array<InstanceData> instanceData;
|
||||
Array<MeshData> instanceMeshData;
|
||||
@@ -78,6 +75,7 @@ public:
|
||||
Gfx::PDescriptorSet getInstanceDataSet() { return descriptorSet; }
|
||||
const Array<MaterialData>& getMaterialData() const { return materialData; }
|
||||
const MeshData& getMeshData(MeshId id) { return meshData[id]; }
|
||||
uint64 getIndicesOffset(uint32 meshletIndex) { return meshlets[meshletIndex].indicesOffset; }
|
||||
static List<VertexData*> getList();
|
||||
static VertexData* findByTypeName(std::string name);
|
||||
virtual void init(Gfx::PGraphics graphics);
|
||||
@@ -113,8 +111,8 @@ protected:
|
||||
Gfx::OShaderBuffer vertexIndicesBuffer;
|
||||
Gfx::OShaderBuffer primitiveIndicesBuffer;
|
||||
// temporary meshlet culling buffer, passed from task to mesh shader
|
||||
Gfx::OShaderBuffer cullingBuffer;
|
||||
Gfx::OShaderBuffer cullingOffsetBuffer;
|
||||
//Gfx::OShaderBuffer cullingBuffer;
|
||||
//Gfx::OShaderBuffer cullingOffsetBuffer;
|
||||
// for legacy pipeline
|
||||
Gfx::OIndexBuffer indexBuffer;
|
||||
// Material data
|
||||
|
||||
@@ -222,6 +222,7 @@ void Buffer::unmap() {
|
||||
}
|
||||
|
||||
void Buffer::rotateBuffer(uint64 size) {
|
||||
assert(dynamic);
|
||||
size = std::max(getSize(), size);
|
||||
for (size_t i = 0; i < buffers.size(); ++i) {
|
||||
if (buffers[i]->isCurrentlyBound()) {
|
||||
@@ -316,15 +317,15 @@ UniformBuffer::UniformBuffer(PGraphics graphics,
|
||||
|
||||
UniformBuffer::~UniformBuffer() {}
|
||||
|
||||
bool UniformBuffer::updateContents(const DataSource &sourceData) {
|
||||
if (!Gfx::UniformBuffer::updateContents(sourceData)) {
|
||||
// no update was performed, skip
|
||||
return false;
|
||||
}
|
||||
void UniformBuffer::updateContents(const DataSource &sourceData) {
|
||||
void *data = map();
|
||||
std::memcpy(data, sourceData.data, sourceData.size);
|
||||
unmap();
|
||||
return true;
|
||||
}
|
||||
|
||||
void UniformBuffer::rotateBuffer(uint64 size)
|
||||
{
|
||||
Vulkan::Buffer::rotateBuffer(size);
|
||||
}
|
||||
|
||||
void UniformBuffer::requestOwnershipTransfer(Gfx::QueueType newOwner) {
|
||||
@@ -368,11 +369,10 @@ ShaderBuffer::ShaderBuffer(PGraphics graphics,
|
||||
ShaderBuffer::~ShaderBuffer() {}
|
||||
|
||||
void ShaderBuffer::updateContents(const ShaderBufferCreateInfo &createInfo) {
|
||||
Gfx::ShaderBuffer::updateContents(createInfo);
|
||||
// We always want to update, as the contents could be different on the GPU
|
||||
if (createInfo.sourceData.data == nullptr) {
|
||||
return;
|
||||
}
|
||||
// We always want to update, as the contents could be different on the GPU
|
||||
void *data = map();
|
||||
std::memcpy((char*)data + createInfo.sourceData.offset, createInfo.sourceData.data, createInfo.sourceData.size);
|
||||
unmap();
|
||||
|
||||
@@ -103,7 +103,8 @@ class UniformBuffer : public Gfx::UniformBuffer, public Buffer {
|
||||
public:
|
||||
UniformBuffer(PGraphics graphics, const UniformBufferCreateInfo &sourceData);
|
||||
virtual ~UniformBuffer();
|
||||
virtual bool updateContents(const DataSource &sourceData) override;
|
||||
virtual void updateContents(const DataSource &sourceData) override;
|
||||
virtual void rotateBuffer(uint64 size) override;
|
||||
|
||||
protected:
|
||||
// Inherited via Vulkan::Buffer
|
||||
|
||||
@@ -399,7 +399,7 @@ void Graphics::initInstance(GraphicsInitializer initInfo)
|
||||
.applicationVersion = VK_MAKE_VERSION(0, 0, 1),
|
||||
.pEngineName = initInfo.engineName,
|
||||
.engineVersion = VK_MAKE_VERSION(0, 0, 1),
|
||||
.apiVersion = VK_API_VERSION_1_2,
|
||||
.apiVersion = VK_API_VERSION_1_3,
|
||||
};
|
||||
|
||||
Array<const char*> extensions = getRequiredExtensions();
|
||||
@@ -496,7 +496,7 @@ void Graphics::pickPhysicalDevice()
|
||||
{
|
||||
if (std::strcmp(VK_EXT_MESH_SHADER_EXTENSION_NAME, extensionProps[i].extensionName) == 0)
|
||||
{
|
||||
meshShadingEnabled = true;
|
||||
//meshShadingEnabled = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,8 +50,12 @@ PipelineCache::~PipelineCache()
|
||||
|
||||
PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gfxInfo)
|
||||
{
|
||||
uint32 hash = CRC::Calculate(&gfxInfo, sizeof(Gfx::LegacyPipelineCreateInfo), CRC::CRC_32());
|
||||
if (graphicsPipelines.contains(hash))
|
||||
{
|
||||
return graphicsPipelines[hash];
|
||||
}
|
||||
PPipelineLayout layout = Gfx::PPipelineLayout(gfxInfo.pipelineLayout).cast<PipelineLayout>();
|
||||
uint32 hash = layout->getHash();
|
||||
Array<VkVertexInputBindingDescription> bindings;
|
||||
Array<VkVertexInputAttributeDescription> attributes;
|
||||
if (gfxInfo.vertexInput != nullptr)
|
||||
@@ -74,8 +78,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.offset = a.offset,
|
||||
};
|
||||
}
|
||||
hash = CRC::Calculate(bindings.data(), sizeof(VkVertexInputBindingDescription) * bindings.size(), CRC::CRC_32(), hash);
|
||||
hash = CRC::Calculate(attributes.data(), sizeof(VkVertexInputAttributeDescription) * attributes.size(), CRC::CRC_32(), hash);
|
||||
}
|
||||
VkPipelineVertexInputStateCreateInfo vertexInput = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
|
||||
@@ -116,7 +118,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.pSpecializationInfo = nullptr,
|
||||
};
|
||||
}
|
||||
hash = CRC::Calculate(stageInfos, sizeof(stageInfos), CRC::CRC_32(), hash);
|
||||
VkPipelineInputAssemblyStateCreateInfo assemblyInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -124,7 +125,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.topology = cast(gfxInfo.topology),
|
||||
.primitiveRestartEnable = false,
|
||||
};
|
||||
hash = CRC::Calculate(&assemblyInfo, sizeof(assemblyInfo), CRC::CRC_32(), hash);
|
||||
VkPipelineViewportStateCreateInfo viewportInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -134,7 +134,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.scissorCount = 1,
|
||||
.pScissors = nullptr,
|
||||
};
|
||||
hash = CRC::Calculate(&viewportInfo, sizeof(viewportInfo), CRC::CRC_32(), hash);
|
||||
VkPipelineRasterizationStateCreateInfo rasterizationState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -150,8 +149,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.depthBiasSlopeFactor = gfxInfo.rasterizationState.depthBiasSlopeFactor,
|
||||
.lineWidth = gfxInfo.rasterizationState.lineWidth,
|
||||
};
|
||||
hash = CRC::Calculate(&rasterizationState, sizeof(rasterizationState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineMultisampleStateCreateInfo multisampleState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -162,8 +159,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.alphaToCoverageEnable = gfxInfo.multisampleState.alphaCoverageEnable,
|
||||
.alphaToOneEnable = gfxInfo.multisampleState.alphaToOneEnable,
|
||||
};
|
||||
hash = CRC::Calculate(&multisampleState, sizeof(multisampleState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDepthStencilStateCreateInfo depthStencilState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -177,8 +172,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.minDepthBounds = gfxInfo.depthStencilState.minDepthBounds,
|
||||
.maxDepthBounds = gfxInfo.depthStencilState.maxDepthBounds,
|
||||
};
|
||||
hash = CRC::Calculate(&depthStencilState, sizeof(depthStencilState), CRC::CRC_32(), hash);
|
||||
|
||||
Array<VkPipelineColorBlendAttachmentState> blendAttachments;
|
||||
for(uint32 i = 0; i < gfxInfo.colorBlend.attachmentCount; ++i)
|
||||
{
|
||||
@@ -194,8 +187,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.colorWriteMask = attachment.colorWriteMask,
|
||||
};
|
||||
}
|
||||
hash = CRC::Calculate(blendAttachments.data(), blendAttachments.size() * sizeof(VkPipelineColorBlendAttachmentState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineColorBlendStateCreateInfo blendState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
@@ -206,13 +197,11 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.pAttachments = blendAttachments.data(),
|
||||
};
|
||||
std::memcpy(blendState.blendConstants, gfxInfo.colorBlend.blendConstants.data(), sizeof(blendState.blendConstants));
|
||||
hash = CRC::Calculate(&blendState, sizeof(blendState), CRC::CRC_32(), hash);
|
||||
|
||||
uint32 numDynamicEnabled = 0;
|
||||
StaticArray<VkDynamicState, 2> dynamicEnabled;
|
||||
dynamicEnabled[numDynamicEnabled++] = VK_DYNAMIC_STATE_VIEWPORT;
|
||||
dynamicEnabled[numDynamicEnabled++] = VK_DYNAMIC_STATE_SCISSOR;
|
||||
hash = CRC::Calculate(dynamicEnabled.data(), dynamicEnabled.size() * sizeof(VkDynamicState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDynamicStateCreateInfo dynamicState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
|
||||
@@ -221,11 +210,6 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
.dynamicStateCount = (uint32)dynamicEnabled.size(),
|
||||
.pDynamicStates = dynamicEnabled.data(),
|
||||
};
|
||||
|
||||
if (graphicsPipelines.contains(hash))
|
||||
{
|
||||
return graphicsPipelines[hash];
|
||||
}
|
||||
VkPipeline pipelineHandle;
|
||||
|
||||
VkGraphicsPipelineCreateInfo createInfo = {
|
||||
|
||||
Reference in New Issue
Block a user