More Refactoring
This commit is contained in:
@@ -1,10 +1,5 @@
|
||||
import Common;
|
||||
|
||||
struct VertexShaderInput
|
||||
{
|
||||
float3 position;
|
||||
};
|
||||
|
||||
struct VertexShaderOutput
|
||||
{
|
||||
float4 clipPos : SV_Position;
|
||||
@@ -18,13 +13,69 @@ struct SkyboxData
|
||||
layout(set=1)
|
||||
ParameterBlock<SkyboxData> pSkyboxData;
|
||||
|
||||
float3 vertices[] = {
|
||||
// Back
|
||||
float3(-512, -512, 512),
|
||||
float3(-512, 512, 512),
|
||||
float3( 512, -512, 512),
|
||||
|
||||
float3( 512, -512, 512),
|
||||
float3(-512, 512, 512),
|
||||
float3( 512, 512, 512),
|
||||
|
||||
// Front
|
||||
float3( 512, -512, -512),
|
||||
float3( 512, 512, -512),
|
||||
float3(-512, -512, -512),
|
||||
|
||||
float3(-512, -512, -512),
|
||||
float3( 512, 512, -512),
|
||||
float3(-512, 512, -512),
|
||||
|
||||
// Top
|
||||
float3(-512, -512, -512),
|
||||
float3(-512, -512, 512),
|
||||
float3( 512, -512, -512),
|
||||
|
||||
float3( 512, -512, -512),
|
||||
float3(-512, -512, 512),
|
||||
float3( 512, -512, 512),
|
||||
|
||||
// Bottom
|
||||
float3(-512, 512, 512),
|
||||
float3(-512, 512, -512),
|
||||
float3( 512, 512, 512),
|
||||
|
||||
float3( 512, 512, 512),
|
||||
float3(-512, 512, -512),
|
||||
float3( 512, 512, -512),
|
||||
|
||||
// Left
|
||||
float3(-512, -512, -512),
|
||||
float3(-512, 512, -512),
|
||||
float3(-512, -512, 512),
|
||||
|
||||
float3(-512, -512, 512),
|
||||
float3(-512, 512, -512),
|
||||
float3(-512, 512, 512),
|
||||
|
||||
// Right
|
||||
float3( 512, -512, 512),
|
||||
float3( 512, 512, 512),
|
||||
float3( 512, -512, -512),
|
||||
|
||||
float3( 512, -512, -512),
|
||||
float3( 512, 512, 512),
|
||||
float3( 512, 512, -512),
|
||||
};
|
||||
|
||||
[shader("vertex")]
|
||||
VertexShaderOutput vertexMain(
|
||||
VertexShaderInput input)
|
||||
uint vertexIndex : SV_VertexId)
|
||||
{
|
||||
VertexShaderOutput output;
|
||||
float3x3 cameraRotation = float3x3(pViewParams.viewMatrix);
|
||||
float4 worldPos = float4(mul(cameraRotation, input.position), 1.0f);
|
||||
float4 worldPos = float4(mul(cameraRotation, vertices[vertexIndex]), 1.0f);
|
||||
//clip(dot(worldPos, clipPlane));
|
||||
output.clipPos = mul(pViewParams.projectionMatrix, worldPos);
|
||||
output.texCoords = normalize(input.position);
|
||||
|
||||
@@ -13,15 +13,24 @@ ParameterBlock<SamplerState> glyphSampler;
|
||||
//layout(set = 1)
|
||||
//ShaderBuffer<GlyphData> glyphData;
|
||||
ParameterBuffer<Texture2D<uint>[]> pGlyphTextures;
|
||||
[[vk::push_constant]]
|
||||
ConstantBuffer<TextData> textData;
|
||||
|
||||
struct VertexInput
|
||||
struct GlyphInstanceData
|
||||
{
|
||||
float2 position;
|
||||
float2 widthHeight;
|
||||
uint glyphIndex;
|
||||
};
|
||||
struct TextRender
|
||||
{
|
||||
StructuredBuffer<GlyphInstanceData> instances;
|
||||
TextData textData;
|
||||
}
|
||||
ParameterBuffer<TextRender> pRender;
|
||||
|
||||
struct VertexInput
|
||||
{
|
||||
uint vertexId : SV_VertexID;
|
||||
uint instanceId : SV_InstanceID;
|
||||
};
|
||||
|
||||
struct VertexOutput
|
||||
@@ -34,11 +43,11 @@ struct VertexOutput
|
||||
[shader("vertex")]
|
||||
VertexOutput vertexMain(VertexInput input)
|
||||
{
|
||||
float xpos = input.position.x;
|
||||
float ypos = input.position.y;
|
||||
float xpos = pRender.instances[input.instanceId].position.x;
|
||||
float ypos = pRender.instances[input.instanceId].position.y;
|
||||
|
||||
float w = input.widthHeight.x;
|
||||
float h = input.widthHeight.y;
|
||||
float w = pRender.instances[input.instanceId].widthHeight.x;
|
||||
float h = pRender.instances[input.instanceId].widthHeight.y;
|
||||
|
||||
float4 coordinates[4] = {
|
||||
float4(xpos, ypos, 0, 1),
|
||||
@@ -50,7 +59,7 @@ VertexOutput vertexMain(VertexInput input)
|
||||
VertexStageOutput output;
|
||||
output.texCoords = vertex.zw;
|
||||
output.position = mul(viewData.projectionMatrix, float4(vertex.xy, 0, 1));
|
||||
output.glyphIndex = input.glyphIndex;
|
||||
output.glyphIndex = pRender.instances[input.instanceId].glyphIndex;
|
||||
return output;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
#include "MaterialLoader.h"
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Graphics/Shader.h"
|
||||
#include "Asset/MaterialAsset.h"
|
||||
#include "Asset/AssetRegistry.h"
|
||||
#include "Material/Material.h"
|
||||
@@ -109,11 +110,11 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
|
||||
parameters.add(p->key);
|
||||
expressions.add(std::move(p));
|
||||
}
|
||||
else if(type.compare("SamplerState") == 0)
|
||||
else if(type.compare("Sampler") == 0)
|
||||
{
|
||||
OSamplerParameter p = new SamplerParameter(param.key(), 0, bindingCounter);
|
||||
layout->addDescriptorBinding(bindingCounter++, Gfx::SE_DESCRIPTOR_TYPE_SAMPLER);
|
||||
p->data = graphics->createSamplerState({});
|
||||
p->data = graphics->createSampler({});
|
||||
parameters.add(p->key);
|
||||
expressions.add(std::move(p));
|
||||
}
|
||||
|
||||
@@ -107,6 +107,7 @@ AssetRegistry &AssetRegistry::get()
|
||||
}
|
||||
|
||||
AssetRegistry::AssetRegistry()
|
||||
: assetRoot(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@@ -100,13 +100,13 @@ void FontAsset::load(ArchiveBuffer& buffer)
|
||||
.data = ktxTexture_GetData(ktxTexture(kTexture)),
|
||||
.owner = Gfx::QueueType::GRAPHICS,
|
||||
},
|
||||
.format = Vulkan::cast((VkFormat)kTexture->vkFormat),
|
||||
.width = kTexture->baseWidth,
|
||||
.height = kTexture->baseHeight,
|
||||
.depth = kTexture->baseDepth,
|
||||
.bArray = kTexture->isArray,
|
||||
.arrayLayers = kTexture->isArray ? kTexture->numLayers : kTexture->numFaces,
|
||||
.mipLevels = kTexture->numLevels,
|
||||
.format = Vulkan::cast((VkFormat)kTexture->vkFormat),
|
||||
.layers = kTexture->numFaces,
|
||||
.elements = kTexture->numLayers,
|
||||
.usage = Gfx::SE_IMAGE_USAGE_SAMPLED_BIT,
|
||||
};
|
||||
|
||||
|
||||
@@ -91,13 +91,13 @@ void TextureAsset::load(ArchiveBuffer& buffer)
|
||||
.data = ktxTexture_GetData(ktxTexture(kTexture)),
|
||||
.owner = Gfx::QueueType::DEDICATED_TRANSFER,
|
||||
},
|
||||
.format = Vulkan::cast((VkFormat)kTexture->vkFormat),
|
||||
.width = kTexture->baseWidth,
|
||||
.height = kTexture->baseHeight,
|
||||
.depth = kTexture->baseDepth,
|
||||
.bArray = kTexture->isArray,
|
||||
.arrayLayers = kTexture->isArray ? kTexture->numLayers : kTexture->numFaces,
|
||||
.mipLevels = kTexture->numLevels,
|
||||
.format = Vulkan::cast((VkFormat)kTexture->vkFormat),
|
||||
.layers = kTexture->numFaces,
|
||||
.elements = kTexture->numLayers,
|
||||
.usage = Gfx::SE_IMAGE_USAGE_SAMPLED_BIT,
|
||||
};
|
||||
if (kTexture->isCubemap)
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
#pragma once
|
||||
#include "Enums.h"
|
||||
#include "Descriptor.h"
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
|
||||
@@ -31,11 +31,11 @@ DescriptorBinding& DescriptorBinding::operator=(const DescriptorBinding& other)
|
||||
return *this;
|
||||
}
|
||||
|
||||
DescriptorAllocator::DescriptorAllocator()
|
||||
DescriptorPool::DescriptorPool()
|
||||
{
|
||||
}
|
||||
|
||||
DescriptorAllocator::~DescriptorAllocator()
|
||||
DescriptorPool::~DescriptorPool()
|
||||
{
|
||||
}
|
||||
|
||||
@@ -87,12 +87,12 @@ void DescriptorLayout::addDescriptorBinding(uint32 bindingIndex, SeDescriptorTyp
|
||||
|
||||
PDescriptorSet DescriptorLayout::allocateDescriptorSet()
|
||||
{
|
||||
return allocator->allocateDescriptorSet();
|
||||
return pool->allocateDescriptorSet();
|
||||
}
|
||||
|
||||
void DescriptorLayout::reset()
|
||||
{
|
||||
allocator->reset();
|
||||
pool->reset();
|
||||
}
|
||||
|
||||
PipelineLayout::PipelineLayout()
|
||||
|
||||
@@ -21,15 +21,15 @@ public:
|
||||
DEFINE_REF(DescriptorBinding)
|
||||
|
||||
DECLARE_REF(DescriptorSet)
|
||||
class DescriptorAllocator
|
||||
class DescriptorPool
|
||||
{
|
||||
public:
|
||||
DescriptorAllocator();
|
||||
virtual ~DescriptorAllocator();
|
||||
DescriptorPool();
|
||||
virtual ~DescriptorPool();
|
||||
virtual PDescriptorSet allocateDescriptorSet() = 0;
|
||||
virtual void reset() = 0;
|
||||
};
|
||||
DEFINE_REF(DescriptorAllocator)
|
||||
DEFINE_REF(DescriptorPool)
|
||||
DECLARE_REF(UniformBuffer)
|
||||
DECLARE_REF(ShaderBuffer)
|
||||
DECLARE_REF(Texture)
|
||||
@@ -68,11 +68,11 @@ public:
|
||||
|
||||
protected:
|
||||
Array<DescriptorBinding> descriptorBindings;
|
||||
ODescriptorAllocator allocator;
|
||||
ODescriptorPool pool;
|
||||
uint32 setIndex;
|
||||
std::string name;
|
||||
friend class PipelineLayout;
|
||||
friend class DescriptorAllocator;
|
||||
friend class DescriptorPool;
|
||||
};
|
||||
DEFINE_REF(DescriptorLayout)
|
||||
class PipelineLayout
|
||||
@@ -85,9 +85,10 @@ public:
|
||||
virtual void reset() = 0;
|
||||
void addDescriptorLayout(uint32 setIndex, PDescriptorLayout layout);
|
||||
void addPushConstants(const SePushConstantRange& pushConstants);
|
||||
virtual uint32 getHash() const = 0;
|
||||
constexpr uint32 getHash() const { return layoutHash; }
|
||||
|
||||
protected:
|
||||
uint32 layoutHash;
|
||||
Array<PDescriptorLayout> descriptorSetLayouts;
|
||||
Array<SePushConstantRange> pushConstants;
|
||||
};
|
||||
|
||||
@@ -29,6 +29,8 @@ DECLARE_REF(UniformBuffer)
|
||||
DECLARE_REF(PipelineLayout)
|
||||
DECLARE_REF(GraphicsPipeline)
|
||||
DECLARE_REF(ComputePipeline)
|
||||
DECLARE_REF(RenderCommand)
|
||||
DECLARE_REF(ComputeCommand)
|
||||
class Graphics
|
||||
{
|
||||
public:
|
||||
@@ -75,7 +77,7 @@ public:
|
||||
virtual PGraphicsPipeline createGraphicsPipeline(LegacyPipelineCreateInfo createInfo) = 0;
|
||||
virtual PGraphicsPipeline createGraphicsPipeline(MeshPipelineCreateInfo createInfo) = 0;
|
||||
virtual PComputePipeline createComputePipeline(ComputePipelineCreateInfo createInfo) = 0;
|
||||
virtual OSampler createSamplerState(const SamplerCreateInfo& createInfo) = 0;
|
||||
virtual OSampler createSampler(const SamplerCreateInfo& createInfo) = 0;
|
||||
|
||||
virtual ODescriptorLayout createDescriptorLayout(const std::string& name = "") = 0;
|
||||
virtual OPipelineLayout createPipelineLayout(PPipelineLayout baseLayout = nullptr) = 0;
|
||||
|
||||
@@ -17,8 +17,8 @@ LegacyPipelineCreateInfo::LegacyPipelineCreateInfo()
|
||||
, depthStencilState(DepthStencilState{
|
||||
.depthTestEnable = true,
|
||||
.depthWriteEnable = true,
|
||||
.stencilTestEnable = false,
|
||||
.depthCompareOp = Gfx::SE_COMPARE_OP_LESS_OR_EQUAL,
|
||||
.stencilTestEnable = false,
|
||||
.minDepthBounds = 0.0f,
|
||||
.maxDepthBounds = 1.0f,
|
||||
})
|
||||
@@ -61,8 +61,8 @@ MeshPipelineCreateInfo::MeshPipelineCreateInfo()
|
||||
, depthStencilState(DepthStencilState{
|
||||
.depthTestEnable = true,
|
||||
.depthWriteEnable = true,
|
||||
.stencilTestEnable = false,
|
||||
.depthCompareOp = Gfx::SE_COMPARE_OP_LESS_OR_EQUAL,
|
||||
.stencilTestEnable = false,
|
||||
.minDepthBounds = 0.0f,
|
||||
.maxDepthBounds = 1.0f,
|
||||
})
|
||||
|
||||
@@ -62,7 +62,8 @@ struct TextureCreateInfo
|
||||
uint32 height = 1;
|
||||
uint32 depth = 1;
|
||||
uint32 mipLevels = 1;
|
||||
uint32 arrayLayers = 1;
|
||||
uint32 layers = 1;
|
||||
uint32 elements = 1;
|
||||
uint32 samples = 1;
|
||||
Gfx::SeImageUsageFlagBits usage = Gfx::SE_IMAGE_USAGE_SAMPLED_BIT;
|
||||
};
|
||||
@@ -105,6 +106,7 @@ struct UniformBufferCreateInfo
|
||||
struct ShaderBufferCreateInfo
|
||||
{
|
||||
DataSource sourceData = DataSource();
|
||||
uint64 numElements = 1;
|
||||
uint8 dynamic = 0;
|
||||
};
|
||||
struct ShaderCreateInfo
|
||||
|
||||
@@ -4,7 +4,7 @@ using namespace Seele;
|
||||
using namespace Seele::Gfx;
|
||||
|
||||
GraphicsPipeline::GraphicsPipeline(OPipelineLayout layout)
|
||||
: layout(std::move(layout)) {}
|
||||
: layout(std::move(layout))
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "RenderGraph.h"
|
||||
#include "Material/MaterialInstance.h"
|
||||
#include "Graphics/Descriptor.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -128,7 +129,6 @@ void BasePass::render()
|
||||
else
|
||||
{
|
||||
Gfx::LegacyPipelineCreateInfo pipelineInfo;
|
||||
pipelineInfo.vertexDeclaration = collection->vertexDeclaration;
|
||||
pipelineInfo.vertexShader = collection->vertexShader;
|
||||
pipelineInfo.fragmentShader = collection->fragmentShader;
|
||||
pipelineInfo.pipelineLayout = std::move(layout);
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include "Actor/CameraActor.h"
|
||||
#include "Math/Vector.h"
|
||||
#include "RenderGraph.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -89,7 +90,6 @@ void DepthPrepass::render()
|
||||
else
|
||||
{
|
||||
Gfx::LegacyPipelineCreateInfo pipelineInfo;
|
||||
pipelineInfo.vertexDeclaration = collection->vertexDeclaration;
|
||||
pipelineInfo.vertexShader = collection->vertexShader;
|
||||
pipelineInfo.fragmentShader = collection->fragmentShader;
|
||||
pipelineInfo.pipelineLayout = std::move(layout);
|
||||
@@ -141,13 +141,14 @@ void DepthPrepass::endFrame()
|
||||
|
||||
void DepthPrepass::publishOutputs()
|
||||
{
|
||||
TextureCreateInfo depthBufferInfo;
|
||||
// If we render to a part of an image, the depth buffer itself must
|
||||
// still match the size of the whole image or their coordinate systems go out of sync
|
||||
depthBufferInfo.width = viewport->getOwner()->getWidth();
|
||||
depthBufferInfo.height = viewport->getOwner()->getHeight();
|
||||
depthBufferInfo.format = Gfx::SE_FORMAT_D32_SFLOAT;
|
||||
depthBufferInfo.usage = Gfx::SE_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
|
||||
TextureCreateInfo depthBufferInfo = {
|
||||
.format = Gfx::SE_FORMAT_D32_SFLOAT,
|
||||
.width = viewport->getOwner()->getWidth(),
|
||||
.height = viewport->getOwner()->getHeight(),
|
||||
.usage = Gfx::SE_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT,
|
||||
};
|
||||
depthBuffer = graphics->createTexture2D(depthBufferInfo);
|
||||
depthAttachment =
|
||||
new Gfx::RenderTargetAttachment(depthBuffer, Gfx::SE_ATTACHMENT_LOAD_OP_CLEAR, Gfx::SE_ATTACHMENT_STORE_OP_STORE);
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
#include "Actor/CameraActor.h"
|
||||
#include "Component/Camera.h"
|
||||
#include "RenderGraph.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -130,14 +131,13 @@ void LightCullingPass::publishOutputs()
|
||||
cullingPipeline = graphics->createComputePipeline(std::move(pipelineInfo));
|
||||
|
||||
uint32 counterReset = 0;
|
||||
ShaderBufferCreateInfo structInfo =
|
||||
{
|
||||
ShaderBufferCreateInfo structInfo = {
|
||||
.sourceData = {
|
||||
.size = sizeof(uint32),
|
||||
.data = (uint8*)&counterReset,
|
||||
.owner = Gfx::QueueType::COMPUTE,
|
||||
},
|
||||
.stride = sizeof(uint32),
|
||||
.numElements = 1,
|
||||
.dynamic = true,
|
||||
};
|
||||
oLightIndexCounter = graphics->createShaderBuffer(structInfo);
|
||||
@@ -151,7 +151,6 @@ void LightCullingPass::publishOutputs()
|
||||
.data = nullptr,
|
||||
.owner = Gfx::QueueType::COMPUTE
|
||||
},
|
||||
.stride = sizeof(uint32),
|
||||
.dynamic = false,
|
||||
};
|
||||
oLightIndexList = graphics->createShaderBuffer(structInfo);
|
||||
@@ -160,9 +159,9 @@ void LightCullingPass::publishOutputs()
|
||||
resources->registerBufferOutput("LIGHTCULLING_TLIGHTLIST", tLightIndexList);
|
||||
|
||||
TextureCreateInfo textureInfo = {
|
||||
.format = Gfx::SE_FORMAT_R32G32_UINT,
|
||||
.width = dispatchParams.numThreadGroups.x,
|
||||
.height = dispatchParams.numThreadGroups.y,
|
||||
.format = Gfx::SE_FORMAT_R32G32_UINT,
|
||||
.usage = Gfx::SE_IMAGE_USAGE_STORAGE_BIT,
|
||||
};
|
||||
oLightGrid = graphics->createTexture2D(textureInfo);
|
||||
@@ -226,7 +225,7 @@ void LightCullingPass::setupFrustums()
|
||||
.size = sizeof(Frustum) * numThreads.x * numThreads.y * numThreads.z,
|
||||
.data = nullptr,
|
||||
},
|
||||
.stride = sizeof(Frustum),
|
||||
.numElements = numThreads.x * numThreads.y * numThreads.z,
|
||||
.dynamic = false,
|
||||
});
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#pragma once
|
||||
#include "RenderPass.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Graphics/Shader.h"
|
||||
#include "Scene/Scene.h"
|
||||
|
||||
namespace Seele
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
#include "SkyboxRenderPass.h"
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Asset/AssetRegistry.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -13,71 +14,6 @@ SkyboxRenderPass::SkyboxRenderPass(Gfx::PGraphics graphics, PScene scene)
|
||||
.fogColor = Vector(0.2, 0.1, 0.6),
|
||||
.blendFactor = 0,
|
||||
};
|
||||
Array<Vector> vertices = {
|
||||
// Back
|
||||
Vector(-512, -512, 512),
|
||||
Vector(-512, 512, 512),
|
||||
Vector( 512, -512, 512),
|
||||
|
||||
Vector( 512, -512, 512),
|
||||
Vector(-512, 512, 512),
|
||||
Vector( 512, 512, 512),
|
||||
|
||||
// Front
|
||||
Vector( 512, -512, -512),
|
||||
Vector( 512, 512, -512),
|
||||
Vector(-512, -512, -512),
|
||||
|
||||
Vector(-512, -512, -512),
|
||||
Vector( 512, 512, -512),
|
||||
Vector(-512, 512, -512),
|
||||
|
||||
// Top
|
||||
Vector(-512, -512, -512),
|
||||
Vector(-512, -512, 512),
|
||||
Vector( 512, -512, -512),
|
||||
|
||||
Vector( 512, -512, -512),
|
||||
Vector(-512, -512, 512),
|
||||
Vector( 512, -512, 512),
|
||||
|
||||
// Bottom
|
||||
Vector(-512, 512, 512),
|
||||
Vector(-512, 512, -512),
|
||||
Vector( 512, 512, 512),
|
||||
|
||||
Vector( 512, 512, 512),
|
||||
Vector(-512, 512, -512),
|
||||
Vector( 512, 512, -512),
|
||||
|
||||
// Left
|
||||
Vector(-512, -512, -512),
|
||||
Vector(-512, 512, -512),
|
||||
Vector(-512, -512, 512),
|
||||
|
||||
Vector(-512, -512, 512),
|
||||
Vector(-512, 512, -512),
|
||||
Vector(-512, 512, 512),
|
||||
|
||||
// Right
|
||||
Vector( 512, -512, 512),
|
||||
Vector( 512, 512, 512),
|
||||
Vector( 512, -512, -512),
|
||||
|
||||
Vector( 512, -512, -512),
|
||||
Vector( 512, 512, 512),
|
||||
Vector( 512, 512, -512),
|
||||
};
|
||||
|
||||
VertexBufferCreateInfo vertexBufferInfo = {
|
||||
.sourceData = {
|
||||
.size = sizeof(Vector) * vertices.size(),
|
||||
.data = (uint8*)vertices.data(),
|
||||
},
|
||||
.vertexSize = sizeof(Vector),
|
||||
.numVertices = (uint32)vertices.size(),
|
||||
};
|
||||
cubeBuffer = graphics->createVertexBuffer(vertexBufferInfo);
|
||||
}
|
||||
SkyboxRenderPass::~SkyboxRenderPass()
|
||||
{
|
||||
@@ -146,7 +82,7 @@ void SkyboxRenderPass::publishOutputs()
|
||||
textureLayout->addDescriptorBinding(2, Gfx::SE_DESCRIPTOR_TYPE_SAMPLER);
|
||||
textureLayout->create();
|
||||
|
||||
skyboxSampler = graphics->createSamplerState({});
|
||||
skyboxSampler = graphics->createSampler({});
|
||||
}
|
||||
|
||||
void SkyboxRenderPass::createRenderPass()
|
||||
@@ -169,16 +105,6 @@ void SkyboxRenderPass::createRenderPass()
|
||||
createInfo.entryPoint = "fragmentMain";
|
||||
fragmentShader = graphics->createFragmentShader(createInfo);
|
||||
|
||||
declaration = graphics->createVertexDeclaration({
|
||||
Gfx::VertexElement {
|
||||
.binding = 0,
|
||||
.offset = 0,
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32B32_SFLOAT,
|
||||
.attributeIndex = 0,
|
||||
.stride = sizeof(Vector),
|
||||
}
|
||||
});
|
||||
|
||||
Gfx::OPipelineLayout pipelineLayout = graphics->createPipelineLayout();
|
||||
pipelineLayout->addDescriptorLayout(0, viewParamsLayout);
|
||||
pipelineLayout->addDescriptorLayout(1, skyboxDataLayout);
|
||||
@@ -186,7 +112,6 @@ void SkyboxRenderPass::createRenderPass()
|
||||
pipelineLayout->create();
|
||||
|
||||
Gfx::LegacyPipelineCreateInfo gfxInfo;
|
||||
gfxInfo.vertexDeclaration = declaration;
|
||||
gfxInfo.vertexShader = vertexShader;
|
||||
gfxInfo.fragmentShader = fragmentShader;
|
||||
gfxInfo.rasterizationState.polygonMode = Gfx::SE_POLYGON_MODE_FILL;
|
||||
|
||||
@@ -1,13 +1,10 @@
|
||||
#pragma once
|
||||
#include "RenderPass.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Graphics/Shader.h"
|
||||
#include "Component/Skybox.h"
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
DECLARE_REF(CameraActor)
|
||||
DECLARE_REF(Scene)
|
||||
DECLARE_REF(Viewport)
|
||||
class SkyboxRenderPass : public RenderPass
|
||||
{
|
||||
public:
|
||||
@@ -27,11 +24,10 @@ private:
|
||||
Gfx::PDescriptorSet skyboxDataSet;
|
||||
Gfx::ODescriptorLayout textureLayout;
|
||||
Gfx::PDescriptorSet textureSet;
|
||||
Gfx::OVertexDeclaration declaration;
|
||||
Gfx::OVertexShader vertexShader;
|
||||
Gfx::OFragmentShader fragmentShader;
|
||||
Gfx::PGraphicsPipeline pipeline;
|
||||
Gfx::OSamplerState skyboxSampler;
|
||||
Gfx::OSampler skyboxSampler;
|
||||
Component::Skybox skybox;
|
||||
};
|
||||
DEFINE_REF(SkyboxRenderPass)
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
#include "RenderGraph.h"
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Graphics/RenderTarget.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -43,15 +44,13 @@ void TextPass::beginFrame(const Component::Camera& cam)
|
||||
});
|
||||
x += (glyph.advance >> 6) * render.scale;
|
||||
}
|
||||
VertexBufferCreateInfo vbInfo = {
|
||||
res.instanceBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
.size = static_cast<uint32>(instanceData.size() * sizeof(GlyphInstanceData)),
|
||||
.data = reinterpret_cast<uint8*>(instanceData.data()),
|
||||
},
|
||||
.vertexSize = sizeof(GlyphInstanceData),
|
||||
.numVertices = static_cast<uint32>(instanceData.size()),
|
||||
};
|
||||
res.vertexBuffer = graphics->createVertexBuffer(vbInfo);
|
||||
},
|
||||
.numElements = instanceData.size(),
|
||||
});
|
||||
|
||||
res.textureArraySet = fd.textureArraySet;
|
||||
|
||||
@@ -83,10 +82,10 @@ void TextPass::render()
|
||||
for(const auto& resource : res)
|
||||
{
|
||||
command->bindDescriptor({generalSet, resource.textureArraySet});
|
||||
command->bindVertexBuffer({resource.vertexBuffer});
|
||||
//command->bindVertexBuffer({resource.vertexBuffer});
|
||||
|
||||
command->pushConstants(layoutRef, Gfx::SE_SHADER_STAGE_VERTEX_BIT | Gfx::SE_SHADER_STAGE_FRAGMENT_BIT, 0, sizeof(TextData), &resource.textData);
|
||||
command->draw(4, static_cast<uint32>(resource.vertexBuffer->getNumVertices()), 0, 0);
|
||||
//command->draw(4, static_cast<uint32>(resource.vertexBuffer->getNumVertices()), 0, 0);
|
||||
}
|
||||
commands.add(command);
|
||||
}
|
||||
@@ -120,33 +119,6 @@ void TextPass::createRenderPass()
|
||||
createInfo.name = "TextFragment";
|
||||
createInfo.entryPoint = "fragmentMain";
|
||||
fragmentShader = graphics->createFragmentShader(createInfo);
|
||||
Array<Gfx::VertexElement> elements;
|
||||
elements.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(GlyphInstanceData, position),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32_SFLOAT,
|
||||
.attributeIndex = 0,
|
||||
.stride = sizeof(GlyphInstanceData),
|
||||
.instanced = 1
|
||||
});
|
||||
elements.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(GlyphInstanceData, widthHeight),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32_SFLOAT,
|
||||
.attributeIndex = 1,
|
||||
.stride = sizeof(GlyphInstanceData),
|
||||
.instanced = 1
|
||||
});
|
||||
elements.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(GlyphInstanceData, glyphIndex),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32_UINT,
|
||||
.attributeIndex = 2,
|
||||
.stride = sizeof(GlyphInstanceData),
|
||||
.instanced = 1
|
||||
});
|
||||
declaration = graphics->createVertexDeclaration(elements);
|
||||
|
||||
generalLayout = graphics->createDescriptorLayout("TextGeneral");
|
||||
generalLayout->addDescriptorBinding(0, Gfx::SE_DESCRIPTOR_TYPE_UNIFORM_BUFFER);
|
||||
generalLayout->addDescriptorBinding(1, Gfx::SE_DESCRIPTOR_TYPE_SAMPLER);
|
||||
@@ -164,7 +136,7 @@ void TextPass::createRenderPass()
|
||||
.dynamic = true,
|
||||
});
|
||||
|
||||
glyphSampler = graphics->createSamplerState({
|
||||
glyphSampler = graphics->createSampler({
|
||||
.magFilter = Gfx::SE_FILTER_LINEAR,
|
||||
.minFilter = Gfx::SE_FILTER_LINEAR,
|
||||
.addressModeU = Gfx::SE_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
|
||||
@@ -190,7 +162,6 @@ void TextPass::createRenderPass()
|
||||
renderPass = graphics->createRenderPass(std::move(layout), viewport);
|
||||
|
||||
Gfx::LegacyPipelineCreateInfo pipelineInfo;
|
||||
pipelineInfo.vertexDeclaration = declaration;
|
||||
pipelineInfo.vertexShader = vertexShader;
|
||||
pipelineInfo.fragmentShader = fragmentShader;
|
||||
pipelineInfo.renderPass = renderPass;
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
#pragma once
|
||||
#include "RenderPass.h"
|
||||
#include "UI/RenderHierarchy.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Asset/FontAsset.h"
|
||||
#include "Graphics/Shader.h"
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
@@ -58,7 +58,7 @@ private:
|
||||
|
||||
struct TextResources
|
||||
{
|
||||
Gfx::PVertexBuffer vertexBuffer;
|
||||
Gfx::PShaderBuffer instanceBuffer;
|
||||
Gfx::PDescriptorSet textureArraySet;
|
||||
TextData textData;
|
||||
};
|
||||
@@ -73,9 +73,8 @@ private:
|
||||
Gfx::PDescriptorSet generalSet;
|
||||
|
||||
Gfx::OUniformBuffer projectionBuffer;
|
||||
Gfx::OSamplerState glyphSampler;
|
||||
Gfx::OSampler glyphSampler;
|
||||
|
||||
Gfx::OVertexDeclaration declaration;
|
||||
Gfx::OVertexShader vertexShader;
|
||||
Gfx::OFragmentShader fragmentShader;
|
||||
Gfx::PPipelineLayout layoutRef;
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
#include "RenderGraph.h"
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Graphics/RenderTarget.h"
|
||||
#include "Graphics/Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -61,9 +62,9 @@ void UIPass::endFrame()
|
||||
void UIPass::publishOutputs()
|
||||
{
|
||||
TextureCreateInfo depthBufferInfo = {
|
||||
.format = Gfx::SE_FORMAT_D32_SFLOAT,
|
||||
.width = viewport->getWidth(),
|
||||
.height = viewport->getHeight(),
|
||||
.format = Gfx::SE_FORMAT_D32_SFLOAT,
|
||||
.usage = Gfx::SE_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT,
|
||||
};
|
||||
|
||||
@@ -74,9 +75,9 @@ void UIPass::publishOutputs()
|
||||
resources->registerRenderPassOutput("UIPASS_DEPTH", depthAttachment);
|
||||
|
||||
TextureCreateInfo colorBufferInfo = {
|
||||
.format = Gfx::SE_FORMAT_R16G16B16A16_SFLOAT,
|
||||
.width = viewport->getWidth(),
|
||||
.height = viewport->getHeight(),
|
||||
.format = Gfx::SE_FORMAT_R16G16B16A16_SFLOAT,
|
||||
.usage = Gfx::SE_IMAGE_USAGE_COLOR_ATTACHMENT_BIT,
|
||||
};
|
||||
colorBuffer = graphics->createTexture2D(colorBufferInfo);
|
||||
@@ -97,48 +98,6 @@ void UIPass::createRenderPass()
|
||||
createInfo.name = "UIFragment";
|
||||
createInfo.entryPoint = "fragmentMain";
|
||||
fragmentShader = graphics->createFragmentShader(createInfo);
|
||||
Array<Gfx::VertexElement> decl;
|
||||
decl.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(UI::RenderElementStyle, position),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32B32_SFLOAT,
|
||||
.attributeIndex = 0,
|
||||
.stride = sizeof(UI::RenderElementStyle),
|
||||
.instanced = 1
|
||||
});
|
||||
decl.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(UI::RenderElementStyle, backgroundImageIndex),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32_UINT,
|
||||
.attributeIndex = 1,
|
||||
.stride = sizeof(UI::RenderElementStyle),
|
||||
.instanced = 1
|
||||
});
|
||||
decl.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(UI::RenderElementStyle, backgroundColor),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32B32_SFLOAT,
|
||||
.attributeIndex = 2,
|
||||
.stride = sizeof(UI::RenderElementStyle),
|
||||
.instanced = 1
|
||||
});
|
||||
decl.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(UI::RenderElementStyle, opacity),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32_SFLOAT,
|
||||
.attributeIndex = 3,
|
||||
.stride = sizeof(UI::RenderElementStyle),
|
||||
.instanced = 1
|
||||
});
|
||||
decl.add({
|
||||
.binding = 0,
|
||||
.offset = offsetof(UI::RenderElementStyle, dimensions),
|
||||
.vertexFormat = Gfx::SE_FORMAT_R32G32_SFLOAT,
|
||||
.attributeIndex = 4,
|
||||
.stride = sizeof(UI::RenderElementStyle),
|
||||
.instanced = 1
|
||||
});
|
||||
declaration = graphics->createVertexDeclaration(decl);
|
||||
|
||||
descriptorLayout = graphics->createDescriptorLayout("UIDescriptorLayout");
|
||||
descriptorLayout->addDescriptorBinding(0, Gfx::SE_DESCRIPTOR_TYPE_UNIFORM_BUFFER);
|
||||
@@ -156,7 +115,7 @@ void UIPass::createRenderPass()
|
||||
.dynamic = false,
|
||||
};
|
||||
Gfx::OUniformBuffer uniformBuffer = graphics->createUniformBuffer(info);
|
||||
Gfx::OSamplerState backgroundSampler = graphics->createSamplerState({});
|
||||
Gfx::OSampler backgroundSampler = graphics->createSampler({});
|
||||
|
||||
info = {
|
||||
.sourceData = {
|
||||
@@ -181,7 +140,6 @@ void UIPass::createRenderPass()
|
||||
renderPass = graphics->createRenderPass(std::move(layout), viewport);
|
||||
|
||||
Gfx::LegacyPipelineCreateInfo pipelineInfo;
|
||||
pipelineInfo.vertexDeclaration = declaration;
|
||||
pipelineInfo.vertexShader = vertexShader;
|
||||
pipelineInfo.fragmentShader = fragmentShader;
|
||||
pipelineInfo.renderPass = renderPass;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
#pragma once
|
||||
#include "RenderPass.h"
|
||||
#include "UI/RenderHierarchy.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Graphics/Shader.h"
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
@@ -31,7 +31,6 @@ private:
|
||||
Gfx::OUniformBuffer numTexturesBuffer;
|
||||
Gfx::OVertexBuffer elementBuffer;
|
||||
|
||||
Gfx::OVertexDeclaration declaration;
|
||||
Gfx::OVertexShader vertexShader;
|
||||
Gfx::OFragmentShader fragmentShader;
|
||||
Gfx::PGraphicsPipeline pipeline;
|
||||
|
||||
@@ -38,10 +38,10 @@ Matrix4 Viewport::getProjectionMatrix() const
|
||||
}
|
||||
}
|
||||
RenderTargetAttachment::RenderTargetAttachment(PTexture2D texture,
|
||||
SeAttachmentLoadOp loadOp = SE_ATTACHMENT_LOAD_OP_LOAD,
|
||||
SeAttachmentStoreOp storeOp = SE_ATTACHMENT_STORE_OP_STORE,
|
||||
SeAttachmentLoadOp stencilLoadOp = SE_ATTACHMENT_LOAD_OP_DONT_CARE,
|
||||
SeAttachmentStoreOp stencilStoreOp = SE_ATTACHMENT_STORE_OP_DONT_CARE)
|
||||
SeAttachmentLoadOp loadOp,
|
||||
SeAttachmentStoreOp storeOp,
|
||||
SeAttachmentLoadOp stencilLoadOp,
|
||||
SeAttachmentStoreOp stencilStoreOp)
|
||||
: clear()
|
||||
, componentFlags(0)
|
||||
, loadOp(loadOp)
|
||||
@@ -57,10 +57,10 @@ RenderTargetAttachment::~RenderTargetAttachment()
|
||||
}
|
||||
|
||||
SwapchainAttachment::SwapchainAttachment(PWindow owner,
|
||||
SeAttachmentLoadOp loadOp = SE_ATTACHMENT_LOAD_OP_LOAD,
|
||||
SeAttachmentStoreOp storeOp = SE_ATTACHMENT_STORE_OP_STORE,
|
||||
SeAttachmentLoadOp stencilLoadOp = SE_ATTACHMENT_LOAD_OP_DONT_CARE,
|
||||
SeAttachmentStoreOp stencilStoreOp = SE_ATTACHMENT_STORE_OP_DONT_CARE)
|
||||
SeAttachmentLoadOp loadOp,
|
||||
SeAttachmentStoreOp storeOp,
|
||||
SeAttachmentLoadOp stencilLoadOp,
|
||||
SeAttachmentStoreOp stencilStoreOp)
|
||||
: RenderTargetAttachment(nullptr, loadOp, storeOp, stencilLoadOp, stencilStoreOp), owner(owner)
|
||||
{
|
||||
clear.color.float32[0] = 0.0f;
|
||||
|
||||
@@ -149,7 +149,7 @@ void StaticMeshVertexData::resizeBuffers()
|
||||
.sourceData = {
|
||||
.size = verticesAllocated * sizeof(Vector),
|
||||
},
|
||||
.stride = sizeof(Vector),
|
||||
.numElements = verticesAllocated * 3,
|
||||
.dynamic = true,
|
||||
};
|
||||
positions = graphics->createShaderBuffer(createInfo);
|
||||
@@ -158,7 +158,7 @@ void StaticMeshVertexData::resizeBuffers()
|
||||
biTangents = graphics->createShaderBuffer(createInfo);
|
||||
colors = graphics->createShaderBuffer(createInfo);
|
||||
createInfo.sourceData.size = verticesAllocated * sizeof(Vector2);
|
||||
createInfo.stride = sizeof(Vector2);
|
||||
createInfo.numElements = verticesAllocated * 2;
|
||||
texCoords = graphics->createShaderBuffer(createInfo);
|
||||
|
||||
positionData.resize(verticesAllocated);
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Graphics/Descriptor.h"
|
||||
#include "Component/Mesh.h"
|
||||
#include "Graphics/Shader.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -62,7 +63,8 @@ void VertexData::createDescriptors()
|
||||
.size = sizeof(InstanceData) * instanceData.size(),
|
||||
.data = (uint8*)instanceData.data(),
|
||||
},
|
||||
.stride = sizeof(InstanceData)
|
||||
.numElements = instanceData.size(),
|
||||
.dynamic = false,
|
||||
});
|
||||
matInst.descriptorSet = instanceDataLayout->allocateDescriptorSet();
|
||||
matInst.descriptorSet->updateBuffer(0, matInst.instanceBuffer);
|
||||
@@ -73,7 +75,8 @@ void VertexData::createDescriptors()
|
||||
.size = sizeof(MeshData) * meshes.size(),
|
||||
.data = (uint8*)meshes.data(),
|
||||
},
|
||||
.stride = sizeof(MeshData)
|
||||
.numElements = meshes.size(),
|
||||
.dynamic = false,
|
||||
});
|
||||
matInst.descriptorSet->updateBuffer(1, matInst.meshDataBuffer);
|
||||
matInst.descriptorSet->updateBuffer(2, meshletBuffer);
|
||||
@@ -123,25 +126,25 @@ void VertexData::loadMesh(MeshId id, Array<Meshlet> loadedMeshlets)
|
||||
.size = sizeof(MeshletDescription) * meshlets.size(),
|
||||
.data = (uint8*)meshlets.data()
|
||||
},
|
||||
.stride = sizeof(MeshletDescription),
|
||||
.numElements = meshlets.size(),
|
||||
.dynamic = true,
|
||||
});
|
||||
});
|
||||
vertexIndicesBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
.size = sizeof(uint32) * vertexIndices.size(),
|
||||
.data = (uint8*)vertexIndices.data(),
|
||||
},
|
||||
.stride = sizeof(uint32),
|
||||
.numElements = vertexIndices.size(),
|
||||
.dynamic = true,
|
||||
});
|
||||
});
|
||||
primitiveIndicesBuffer = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
.sourceData = {
|
||||
.size = sizeof(uint8) * primitiveIndices.size(),
|
||||
.data = (uint8*)primitiveIndices.data(),
|
||||
},
|
||||
.stride = sizeof(uint8),
|
||||
.numElements = primitiveIndices.size(),
|
||||
.dynamic = true,
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
MeshId VertexData::allocateVertexData(uint64 numVertices)
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
#include "Material/MaterialInstance.h"
|
||||
#include "Component/Transform.h"
|
||||
#include "Containers/List.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Graphics/Command.h"
|
||||
#include "Graphics/Descriptor.h"
|
||||
#include "Graphics/Buffer.h"
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
#include "Allocator.h"
|
||||
#include "Graphics.h"
|
||||
#include "Initializer.h"
|
||||
#include "Resources.h"
|
||||
#include "Enums.h"
|
||||
#include "Command.h"
|
||||
|
||||
using namespace Seele::Vulkan;
|
||||
|
||||
@@ -24,11 +25,6 @@ VkDeviceMemory SubAllocation::getHandle() const
|
||||
return owner->getHandle();
|
||||
}
|
||||
|
||||
bool SubAllocation::isReadable() const
|
||||
{
|
||||
return owner->isReadable();
|
||||
}
|
||||
|
||||
void *SubAllocation::map()
|
||||
{
|
||||
return (uint8 *)owner->map() + alignedOffset;
|
||||
@@ -44,14 +40,14 @@ void SubAllocation::invalidate()
|
||||
owner->invalidate();
|
||||
}
|
||||
|
||||
Allocation::Allocation(PGraphics graphics, PAllocator allocator, VkDeviceSize size, uint8 memoryTypeIndex,
|
||||
Allocation::Allocation(PGraphics graphics, PAllocator pool, VkDeviceSize size, uint8 memoryTypeIndex,
|
||||
VkMemoryPropertyFlags properties, VkMemoryDedicatedAllocateInfo *dedicatedInfo)
|
||||
: device(graphics->getDevice())
|
||||
, allocator(allocator)
|
||||
, pool(pool)
|
||||
, bytesAllocated(0)
|
||||
, bytesUsed(0)
|
||||
, canMap((properties & VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT) == VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT),
|
||||
, isMapped(false),
|
||||
, canMap((properties & VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT) == VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT)
|
||||
, isMapped(false)
|
||||
, properties(properties)
|
||||
, memoryTypeIndex(memoryTypeIndex)
|
||||
{
|
||||
@@ -97,7 +93,7 @@ OSubAllocation Allocation::getSuballocation(VkDeviceSize requestedSize, VkDevice
|
||||
alignedOffset /= alignment;
|
||||
alignedOffset *= alignment;
|
||||
VkDeviceSize allocatedSize = requestedSize + (alignedOffset - lower);
|
||||
if (size <= allocatedSize)
|
||||
if (size >= allocatedSize)
|
||||
{
|
||||
VkDeviceSize newSize = size - allocatedSize;
|
||||
VkDeviceSize newLower = lower + allocatedSize;
|
||||
@@ -140,7 +136,7 @@ void Allocation::markFree(PSubAllocation allocation)
|
||||
bytesUsed -= allocation->allocatedSize;
|
||||
if (bytesUsed == 0)
|
||||
{
|
||||
allocator->free(this);
|
||||
pool->free(this);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -209,7 +205,7 @@ OSubAllocation Allocator::allocate(const VkMemoryRequirements2 &memRequirements2
|
||||
{
|
||||
OAllocation newAllocation = new Allocation(graphics, this, requirements.size, memoryTypeIndex, properties, dedicatedInfo);
|
||||
heaps[heapIndex].inUse += newAllocation->bytesAllocated;
|
||||
//std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
heaps[heapIndex].allocations.add(std::move(newAllocation));
|
||||
return heaps[heapIndex].allocations.back()->getSuballocation(requirements.size, requirements.alignment);
|
||||
}
|
||||
@@ -229,7 +225,7 @@ OSubAllocation Allocator::allocate(const VkMemoryRequirements2 &memRequirements2
|
||||
// no suitable allocations found, allocate new block
|
||||
OAllocation newAllocation = new Allocation(graphics, this, (requirements.size > DEFAULT_ALLOCATION) ? requirements.size : DEFAULT_ALLOCATION, memoryTypeIndex, properties, nullptr);
|
||||
heaps[heapIndex].inUse += newAllocation->bytesAllocated;
|
||||
//std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
heaps[heapIndex].allocations.add(std::move(newAllocation));
|
||||
return heaps[heapIndex].allocations.back()->getSuballocation(requirements.size, requirements.alignment);
|
||||
}
|
||||
@@ -244,7 +240,7 @@ void Allocator::free(PAllocation allocation)
|
||||
if (heaps[heapIndex].allocations[alloc] == allocation)
|
||||
{
|
||||
heaps[heapIndex].inUse -= allocation->bytesAllocated;
|
||||
//std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
std::cout << "Heap " << heapIndex << ": " << (float)heaps[heapIndex].inUse / heaps[heapIndex].maxSize << "%" << std::endl;
|
||||
heaps[heapIndex].allocations.removeAt(alloc, false);
|
||||
return;
|
||||
}
|
||||
@@ -277,6 +273,8 @@ StagingBuffer::~StagingBuffer()
|
||||
{
|
||||
graphics->getDestructionManager()->queueBuffer(
|
||||
graphics->getDedicatedTransferCommands()->getCommands(), buffer);
|
||||
graphics->getDestructionManager()->queueAllocation(
|
||||
graphics->getDedicatedTransferCommands()->getCommands(), std::move(allocation));
|
||||
}
|
||||
|
||||
void* StagingBuffer::map()
|
||||
@@ -314,8 +312,8 @@ void StagingBuffer::executePipelineBarrier(Gfx::SeAccessFlags srcAccess, Gfx::Se
|
||||
assert(false);
|
||||
}
|
||||
|
||||
StagingManager::StagingManager(PGraphics graphics, PAllocator allocator)
|
||||
: graphics(graphics), allocator(allocator)
|
||||
StagingManager::StagingManager(PGraphics graphics, PAllocator pool)
|
||||
: graphics(graphics), pool(pool)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -358,7 +356,7 @@ OStagingBuffer StagingManager::create(uint64 size)
|
||||
|
||||
OStagingBuffer stagingBuffer = new StagingBuffer(
|
||||
graphics,
|
||||
allocator->allocate(memReqs, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_CACHED_BIT, buffer),
|
||||
pool->allocate(memReqs, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_CACHED_BIT, buffer),
|
||||
buffer,
|
||||
size
|
||||
);
|
||||
|
||||
@@ -30,8 +30,6 @@ public:
|
||||
return alignedOffset;
|
||||
}
|
||||
|
||||
bool isReadable() const;
|
||||
|
||||
void *map();
|
||||
void flushMemory();
|
||||
void invalidate();
|
||||
@@ -49,7 +47,7 @@ DEFINE_REF(SubAllocation)
|
||||
class Allocation
|
||||
{
|
||||
public:
|
||||
Allocation(PGraphics graphics, PAllocator allocator, VkDeviceSize size, uint8 memoryTypeIndex,
|
||||
Allocation(PGraphics graphics, PAllocator pool, VkDeviceSize size, uint8 memoryTypeIndex,
|
||||
VkMemoryPropertyFlags properties, VkMemoryDedicatedAllocateInfo *dedicatedInfo = nullptr);
|
||||
~Allocation();
|
||||
OSubAllocation getSuballocation(VkDeviceSize size, VkDeviceSize alignment);
|
||||
@@ -78,16 +76,16 @@ public:
|
||||
|
||||
private:
|
||||
VkDevice device;
|
||||
PAllocator allocator;
|
||||
PAllocator pool;
|
||||
VkDeviceSize bytesAllocated;
|
||||
VkDeviceSize bytesUsed;
|
||||
VkDeviceMemory allocatedMemory;
|
||||
Array<PSubAllocation> activeAllocations;
|
||||
Map<VkDeviceSize, VkDeviceSize> freeRanges;
|
||||
void *mappedPointer;
|
||||
uint8 isDedicated : 1;
|
||||
uint8 canMap : 1;
|
||||
uint8 isMapped : 1;
|
||||
uint8 isDedicated : 1;
|
||||
VkMemoryPropertyFlags properties;
|
||||
uint8 memoryTypeIndex;
|
||||
friend class Allocator;
|
||||
@@ -104,21 +102,23 @@ public:
|
||||
OSubAllocation allocate(const VkMemoryRequirements2 &requirements, VkMemoryPropertyFlags props,
|
||||
VkBuffer buffer)
|
||||
{
|
||||
VkMemoryDedicatedAllocateInfo allocInfo;
|
||||
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO;
|
||||
allocInfo.pNext = nullptr;
|
||||
allocInfo.buffer = buffer;
|
||||
allocInfo.image = VK_NULL_HANDLE;
|
||||
VkMemoryDedicatedAllocateInfo allocInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.image = VK_NULL_HANDLE,
|
||||
.buffer = buffer,
|
||||
};
|
||||
return allocate(requirements, props, &allocInfo);
|
||||
}
|
||||
OSubAllocation allocate(const VkMemoryRequirements2 &requirements, VkMemoryPropertyFlags props,
|
||||
VkImage image)
|
||||
{
|
||||
VkMemoryDedicatedAllocateInfo allocInfo;
|
||||
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO;
|
||||
allocInfo.pNext = nullptr;
|
||||
allocInfo.buffer = VK_NULL_HANDLE;
|
||||
allocInfo.image = image;
|
||||
VkMemoryDedicatedAllocateInfo allocInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.image = image,
|
||||
.buffer = VK_NULL_HANDLE,
|
||||
};
|
||||
return allocate(requirements, props, &allocInfo);
|
||||
}
|
||||
|
||||
@@ -174,13 +174,13 @@ DEFINE_REF(StagingBuffer)
|
||||
class StagingManager
|
||||
{
|
||||
public:
|
||||
StagingManager(PGraphics graphics, PAllocator allocator);
|
||||
StagingManager(PGraphics graphics, PAllocator pool);
|
||||
~StagingManager();
|
||||
OStagingBuffer create(uint64 size);
|
||||
|
||||
private:
|
||||
PGraphics graphics;
|
||||
PAllocator allocator;
|
||||
PAllocator pool;
|
||||
};
|
||||
DEFINE_REF(StagingManager)
|
||||
} // namespace Vulkan
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Buffer.h"
|
||||
#include "Initializer.h"
|
||||
#include "CommandBuffer.h"
|
||||
#include "Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
using namespace Seele::Vulkan;
|
||||
@@ -79,15 +78,19 @@ VkDeviceSize Buffer::getOffset() const
|
||||
|
||||
void Buffer::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
VkBufferMemoryBarrier barrier =
|
||||
init::BufferMemoryBarrier();
|
||||
PCommandBufferManager sourceManager = graphics->getQueueCommands(owner);
|
||||
PCommandBufferManager dstManager = nullptr;
|
||||
Gfx::QueueFamilyMapping mapping = graphics->getFamilyMapping();
|
||||
VkBufferMemoryBarrier barrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.srcQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(owner),
|
||||
.dstQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(newOwner),
|
||||
.offset = 0,
|
||||
.size = size,
|
||||
};
|
||||
PCommandPool sourcePool = graphics->getQueueCommands(owner);
|
||||
PCommandPool dstPool = nullptr;
|
||||
VkPipelineStageFlags srcStage = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT;
|
||||
VkPipelineStageFlags dstStage = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT;
|
||||
Gfx::QueueFamilyMapping mapping = graphics->getFamilyMapping();
|
||||
barrier.srcQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(owner);
|
||||
barrier.dstQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(newOwner);
|
||||
assert(barrier.srcQueueFamilyIndex != barrier.dstQueueFamilyIndex);
|
||||
if (owner == Gfx::QueueType::TRANSFER || owner == Gfx::QueueType::DEDICATED_TRANSFER)
|
||||
{
|
||||
@@ -108,31 +111,29 @@ void Buffer::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_TRANSFER_BIT;
|
||||
dstManager = graphics->getTransferCommands();
|
||||
dstPool = graphics->getTransferCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::DEDICATED_TRANSFER)
|
||||
{
|
||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_TRANSFER_BIT;
|
||||
dstManager = graphics->getDedicatedTransferCommands();
|
||||
dstPool = graphics->getDedicatedTransferCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::COMPUTE)
|
||||
{
|
||||
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT;
|
||||
dstManager = graphics->getComputeCommands();
|
||||
dstPool = graphics->getComputeCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::GRAPHICS)
|
||||
{
|
||||
barrier.dstAccessMask = getDestAccessMask();
|
||||
dstStage = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT;
|
||||
dstManager = graphics->getGraphicsCommands();
|
||||
dstPool = graphics->getGraphicsCommands();
|
||||
}
|
||||
VkCommandBuffer srcCommand = sourceManager->getCommands()->getHandle();
|
||||
VkCommandBuffer dstCommand = dstManager->getCommands()->getHandle();
|
||||
VkCommandBuffer srcCommand = sourcePool->getCommands()->getHandle();
|
||||
VkCommandBuffer dstCommand = dstPool->getCommands()->getHandle();
|
||||
VkBufferMemoryBarrier dynamicBarriers[Gfx::numFramesBuffered];
|
||||
barrier.offset = 0;
|
||||
barrier.size = size;
|
||||
for (uint32 i = 0; i < numBuffers; ++i)
|
||||
{
|
||||
dynamicBarriers[i] = barrier;
|
||||
@@ -140,20 +141,23 @@ void Buffer::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
}
|
||||
vkCmdPipelineBarrier(srcCommand, srcStage, srcStage, 0, 0, nullptr, numBuffers, dynamicBarriers, 0, nullptr);
|
||||
vkCmdPipelineBarrier(dstCommand, dstStage, dstStage, 0, 0, nullptr, numBuffers, dynamicBarriers, 0, nullptr);
|
||||
sourceManager->submitCommands();
|
||||
sourcePool->submitCommands();
|
||||
}
|
||||
|
||||
void Buffer::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage)
|
||||
{
|
||||
PCmdBuffer commandBuffer = graphics->getQueueCommands(owner)->getCommands();
|
||||
VkBufferMemoryBarrier barrier = init::BufferMemoryBarrier();
|
||||
barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
barrier.dstAccessMask = dstAccess;
|
||||
barrier.srcAccessMask = srcAccess;
|
||||
barrier.offset = 0;
|
||||
barrier.size = size;
|
||||
PCommand commandBuffer = graphics->getQueueCommands(owner)->getCommands();
|
||||
VkBufferMemoryBarrier barrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.srcAccessMask = srcAccess,
|
||||
.dstAccessMask = dstAccess,
|
||||
.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.offset = 0,
|
||||
.size = size,
|
||||
};
|
||||
VkBufferMemoryBarrier dynamicBarriers[Gfx::numFramesBuffered];
|
||||
for(uint32 i = 0; i < numBuffers; ++i)
|
||||
{
|
||||
@@ -194,36 +198,39 @@ void * Buffer::mapRegion(uint64 regionOffset, uint64 regionSize, bool writeOnly)
|
||||
if (writeOnly)
|
||||
{
|
||||
//requestOwnershipTransfer(Gfx::QueueType::DEDICATED_TRANSFER);
|
||||
OStagingBuffer stagingBuffer = graphics->getStagingManager()->create(regionSize, VK_BUFFER_USAGE_TRANSFER_SRC_BIT);
|
||||
OStagingBuffer stagingBuffer = graphics->getStagingManager()->create(regionSize);
|
||||
data = stagingBuffer->map();
|
||||
pending.stagingBuffer = std::move(stagingBuffer);
|
||||
}
|
||||
else
|
||||
{
|
||||
PCmdBuffer current = graphics->getQueueCommands(owner)->getCommands();
|
||||
PCommand current = graphics->getQueueCommands(owner)->getCommands();
|
||||
current->waitForCommand();
|
||||
|
||||
requestOwnershipTransfer(Gfx::QueueType::DEDICATED_TRANSFER);
|
||||
VkCommandBuffer handle = graphics->getQueueCommands(owner)->getCommands()->getHandle();
|
||||
|
||||
VkBufferMemoryBarrier barrier =
|
||||
init::BufferMemoryBarrier();
|
||||
barrier.srcAccessMask = VK_ACCESS_MEMORY_WRITE_BIT;
|
||||
barrier.dstAccessMask = VK_ACCESS_MEMORY_READ_BIT;
|
||||
barrier.buffer = buffers[currentBuffer].buffer;
|
||||
barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
barrier.offset = 0;
|
||||
barrier.size = size;
|
||||
VkBufferMemoryBarrier barrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.srcAccessMask = VK_ACCESS_MEMORY_WRITE_BIT,
|
||||
.dstAccessMask = VK_ACCESS_MEMORY_READ_BIT,
|
||||
.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.buffer = buffers[currentBuffer].buffer,
|
||||
.offset = 0,
|
||||
.size = size,
|
||||
};
|
||||
vkCmdPipelineBarrier(handle, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, 0, nullptr, 1, &barrier, 0, nullptr);
|
||||
|
||||
OStagingBuffer stagingBuffer = graphics->getStagingManager()->create(size, VK_BUFFER_USAGE_TRANSFER_DST_BIT, true);
|
||||
|
||||
VkBufferCopy regions;
|
||||
regions.size = size;
|
||||
regions.srcOffset = 0;
|
||||
regions.dstOffset = 0;
|
||||
OStagingBuffer stagingBuffer = graphics->getStagingManager()->create(size);
|
||||
|
||||
VkBufferCopy regions = {
|
||||
.srcOffset = 0,
|
||||
.dstOffset = 0,
|
||||
.size = size,
|
||||
};
|
||||
|
||||
vkCmdCopyBuffer(handle, buffers[currentBuffer].buffer, stagingBuffer->getHandle(), 1, ®ions);
|
||||
|
||||
graphics->getQueueCommands(owner)->submitCommands();
|
||||
@@ -251,18 +258,18 @@ void Buffer::unmap()
|
||||
if (pending.writeOnly)
|
||||
{
|
||||
PStagingBuffer stagingBuffer = pending.stagingBuffer;
|
||||
PCmdBuffer cmdBuffer = graphics->getQueueCommands(owner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = cmdBuffer->getHandle();
|
||||
PCommand command = graphics->getQueueCommands(owner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = command->getHandle();
|
||||
|
||||
VkBufferCopy region;
|
||||
std::memset(®ion, 0, sizeof(VkBufferCopy));
|
||||
region.size = pending.size;
|
||||
region.dstOffset = pending.offset;
|
||||
VkBufferCopy region = {
|
||||
.srcOffset = 0,
|
||||
.dstOffset = pending.offset,
|
||||
.size = pending.size,
|
||||
};
|
||||
vkCmdCopyBuffer(cmdHandle, stagingBuffer->getHandle(), buffers[currentBuffer].buffer, 1, ®ion);
|
||||
graphics->getQueueCommands(owner)->submitCommands();
|
||||
}
|
||||
//requestOwnershipTransfer(pending.prevQueue);
|
||||
graphics->getStagingManager()->release(std::move(pending.stagingBuffer));
|
||||
pendingBuffers.erase(this);
|
||||
}
|
||||
}
|
||||
@@ -274,7 +281,7 @@ UniformBuffer::UniformBuffer(PGraphics graphics, const UniformBufferCreateInfo &
|
||||
{
|
||||
if(createInfo.dynamic)
|
||||
{
|
||||
dedicatedStagingBuffer = graphics->getStagingManager()->create(createInfo.sourceData.size, VK_BUFFER_USAGE_TRANSFER_SRC_BIT);
|
||||
dedicatedStagingBuffer = graphics->getStagingManager()->create(createInfo.sourceData.size);
|
||||
}
|
||||
if (createInfo.sourceData.data != nullptr)
|
||||
{
|
||||
@@ -286,7 +293,6 @@ UniformBuffer::UniformBuffer(PGraphics graphics, const UniformBufferCreateInfo &
|
||||
|
||||
UniformBuffer::~UniformBuffer()
|
||||
{
|
||||
graphics->getStagingManager()->release(std::move(dedicatedStagingBuffer));
|
||||
}
|
||||
|
||||
bool UniformBuffer::updateContents(const DataSource &sourceData)
|
||||
@@ -315,8 +321,8 @@ void UniformBuffer::unmap()
|
||||
if(dedicatedStagingBuffer != nullptr)
|
||||
{
|
||||
dedicatedStagingBuffer->flush();
|
||||
PCmdBuffer cmdBuffer = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = cmdBuffer->getHandle();
|
||||
PCommand command = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = command->getHandle();
|
||||
|
||||
VkBufferCopy region;
|
||||
std::memset(®ion, 0, sizeof(VkBufferCopy));
|
||||
@@ -357,13 +363,13 @@ VkAccessFlags UniformBuffer::getDestAccessMask()
|
||||
}
|
||||
|
||||
ShaderBuffer::ShaderBuffer(PGraphics graphics, const ShaderBufferCreateInfo &sourceData)
|
||||
: Gfx::ShaderBuffer(graphics->getFamilyMapping(), sourceData.stride, sourceData.sourceData.size / sourceData.stride, sourceData.sourceData)
|
||||
: Gfx::ShaderBuffer(graphics->getFamilyMapping(), sourceData.numElements, sourceData.sourceData)
|
||||
, Vulkan::Buffer(graphics, sourceData.sourceData.size, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, currentOwner, sourceData.dynamic)
|
||||
, dedicatedStagingBuffer(nullptr)
|
||||
{
|
||||
if(sourceData.dynamic)
|
||||
{
|
||||
dedicatedStagingBuffer = graphics->getStagingManager()->create(sourceData.sourceData.size, VK_BUFFER_USAGE_TRANSFER_SRC_BIT);
|
||||
dedicatedStagingBuffer = graphics->getStagingManager()->create(sourceData.sourceData.size);
|
||||
}
|
||||
if (sourceData.sourceData.data != nullptr)
|
||||
{
|
||||
@@ -375,7 +381,6 @@ ShaderBuffer::ShaderBuffer(PGraphics graphics, const ShaderBufferCreateInfo &sou
|
||||
|
||||
ShaderBuffer::~ShaderBuffer()
|
||||
{
|
||||
graphics->getStagingManager()->release(std::move(dedicatedStagingBuffer));
|
||||
}
|
||||
|
||||
bool ShaderBuffer::updateContents(const DataSource &sourceData)
|
||||
@@ -402,12 +407,14 @@ void ShaderBuffer::unmap()
|
||||
if(dedicatedStagingBuffer != nullptr)
|
||||
{
|
||||
dedicatedStagingBuffer->flush();
|
||||
PCmdBuffer cmdBuffer = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = cmdBuffer->getHandle();
|
||||
PCommand command = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
VkCommandBuffer cmdHandle = command->getHandle();
|
||||
|
||||
VkBufferCopy region;
|
||||
std::memset(®ion, 0, sizeof(VkBufferCopy));
|
||||
region.size = Vulkan::Buffer::size;
|
||||
VkBufferCopy region = {
|
||||
.srcOffset = 0,
|
||||
.dstOffset = 0,
|
||||
.size = Vulkan::Buffer::size,
|
||||
};
|
||||
vkCmdCopyBuffer(cmdHandle, dedicatedStagingBuffer->getHandle(), buffers[currentBuffer].buffer, 1, ®ion);
|
||||
graphics->getQueueCommands(currentOwner)->submitCommands();
|
||||
}
|
||||
|
||||
@@ -6,6 +6,8 @@ target_sources(Engine
|
||||
Buffer.cpp
|
||||
Command.h
|
||||
Command.cpp
|
||||
Debug.h
|
||||
Debug.cpp
|
||||
Descriptor.h
|
||||
Descriptor.cpp
|
||||
Enums.h
|
||||
@@ -14,8 +16,6 @@ target_sources(Engine
|
||||
Framebuffer.cpp
|
||||
Graphics.h
|
||||
Graphics.cpp
|
||||
Initializer.h
|
||||
Initializer.cpp
|
||||
Pipeline.h
|
||||
Pipeline.cpp
|
||||
PipelineCache.h
|
||||
@@ -39,11 +39,11 @@ target_sources(Engine
|
||||
Allocator.h
|
||||
Buffer.h
|
||||
Command.h
|
||||
DescriptorSets.h
|
||||
Debug.h
|
||||
Descriptor.h
|
||||
Enums.h
|
||||
Framebuffer.h
|
||||
Graphics.h
|
||||
Initializer.h
|
||||
Pipeline.h
|
||||
PipelineCache.h
|
||||
Queue.h
|
||||
|
||||
@@ -1,12 +1,11 @@
|
||||
#include "CommandBuffer.h"
|
||||
#include "Initializer.h"
|
||||
#include "Command.h"
|
||||
#include "Graphics.h"
|
||||
#include "Pipeline.h"
|
||||
#include "Enums.h"
|
||||
#include "Framebuffer.h"
|
||||
#include "RenderPass.h"
|
||||
#include "Pipeline.h"
|
||||
#include "DescriptorSets.h"
|
||||
#include "Descriptor.h"
|
||||
#include "RenderTarget.h"
|
||||
#include <vulkan/vulkan_core.h>
|
||||
|
||||
@@ -14,9 +13,9 @@ using namespace Seele;
|
||||
using namespace Seele::Vulkan;
|
||||
|
||||
|
||||
Command::Command(PGraphics graphics, VkCommandPool cmdPool, PCommandBufferManager manager)
|
||||
Command::Command(PGraphics graphics, VkCommandPool cmdPool, PCommandPool pool)
|
||||
: graphics(graphics)
|
||||
, manager(manager)
|
||||
, pool(pool)
|
||||
, owner(cmdPool)
|
||||
{
|
||||
VkCommandBufferAllocateInfo allocInfo = {
|
||||
@@ -159,7 +158,7 @@ void Command::checkFence()
|
||||
|
||||
void Command::waitForCommand(uint32 timeout)
|
||||
{
|
||||
manager->submitCommands();
|
||||
pool->submitCommands();
|
||||
if (state == State::Begin)
|
||||
{
|
||||
// is already done
|
||||
@@ -174,9 +173,9 @@ PFence Command::getFence()
|
||||
return fence;
|
||||
}
|
||||
|
||||
PCommandBufferManager Command::getManager()
|
||||
PCommandPool Command::getPool()
|
||||
{
|
||||
return manager;
|
||||
return pool;
|
||||
}
|
||||
|
||||
RenderCommand::RenderCommand(PGraphics graphics, VkCommandPool cmdPool)
|
||||
@@ -203,15 +202,21 @@ void RenderCommand::begin(PRenderPass renderPass, PFramebuffer framebuffer)
|
||||
{
|
||||
threadId = std::this_thread::get_id();
|
||||
ready = false;
|
||||
VkCommandBufferBeginInfo beginInfo =
|
||||
init::CommandBufferBeginInfo();
|
||||
VkCommandBufferInheritanceInfo inheritanceInfo =
|
||||
init::CommandBufferInheritanceInfo();
|
||||
inheritanceInfo.framebuffer = framebuffer->getHandle();
|
||||
inheritanceInfo.renderPass = renderPass->getHandle();
|
||||
inheritanceInfo.subpass = 0;
|
||||
beginInfo.pInheritanceInfo = &inheritanceInfo;
|
||||
beginInfo.flags = VK_COMMAND_BUFFER_USAGE_RENDER_PASS_CONTINUE_BIT;
|
||||
VkCommandBufferInheritanceInfo inheritanceInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_INHERITANCE_INFO,
|
||||
.renderPass = renderPass->getHandle(),
|
||||
.subpass = 0,
|
||||
.framebuffer = framebuffer->getHandle(),
|
||||
.occlusionQueryEnable = 0,
|
||||
.queryFlags = 0,
|
||||
.pipelineStatistics = 0,
|
||||
};
|
||||
VkCommandBufferBeginInfo beginInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = VK_COMMAND_BUFFER_USAGE_RENDER_PASS_CONTINUE_BIT,
|
||||
.pInheritanceInfo = &inheritanceInfo,
|
||||
};
|
||||
VK_CHECK(vkBeginCommandBuffer(handle, &beginInfo));
|
||||
}
|
||||
|
||||
@@ -236,7 +241,16 @@ void RenderCommand::setViewport(Gfx::PViewport viewport)
|
||||
{
|
||||
assert(threadId == std::this_thread::get_id());
|
||||
VkViewport vp = viewport.cast<Viewport>()->getHandle();
|
||||
VkRect2D scissors = init::Rect2D(viewport->getWidth(), viewport->getHeight(), viewport->getOffsetX(), viewport->getOffsetY());
|
||||
VkRect2D scissors = {
|
||||
.offset = {
|
||||
.x = (int32)viewport->getOffsetX(),
|
||||
.y = (int32)viewport->getOffsetY(),
|
||||
},
|
||||
.extent = {
|
||||
.width = viewport->getWidth(),
|
||||
.height = viewport->getHeight(),
|
||||
},
|
||||
};
|
||||
vkCmdSetViewport(handle, 0, 1, &vp);
|
||||
vkCmdSetScissor(handle, 0, 1, &scissors);
|
||||
}
|
||||
@@ -321,10 +335,13 @@ ComputeCommand::ComputeCommand(PGraphics graphics, VkCommandPool cmdPool)
|
||||
: graphics(graphics)
|
||||
, owner(cmdPool)
|
||||
{
|
||||
VkCommandBufferAllocateInfo allocInfo =
|
||||
init::CommandBufferAllocateInfo(cmdPool,
|
||||
VK_COMMAND_BUFFER_LEVEL_SECONDARY,
|
||||
1);
|
||||
VkCommandBufferAllocateInfo allocInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.commandPool = owner,
|
||||
.level = VK_COMMAND_BUFFER_LEVEL_SECONDARY,
|
||||
.commandBufferCount = 1,
|
||||
};
|
||||
VK_CHECK(vkAllocateCommandBuffers(graphics->getDevice(), &allocInfo, &handle));
|
||||
}
|
||||
|
||||
@@ -334,18 +351,25 @@ ComputeCommand::~ComputeCommand()
|
||||
vkFreeCommandBuffers(graphics->getDevice(), owner, 1, &handle);
|
||||
}
|
||||
|
||||
void ComputeCommand::begin(PCmdBuffer)
|
||||
void ComputeCommand::begin()
|
||||
{
|
||||
threadId = std::this_thread::get_id();
|
||||
ready = false;
|
||||
VkCommandBufferBeginInfo beginInfo =
|
||||
init::CommandBufferBeginInfo();
|
||||
VkCommandBufferInheritanceInfo inheritanceInfo =
|
||||
init::CommandBufferInheritanceInfo();
|
||||
inheritanceInfo.framebuffer = VK_NULL_HANDLE;
|
||||
inheritanceInfo.renderPass = VK_NULL_HANDLE;
|
||||
inheritanceInfo.subpass = 0;
|
||||
beginInfo.pInheritanceInfo = &inheritanceInfo;
|
||||
VkCommandBufferInheritanceInfo inheritanceInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_INHERITANCE_INFO,
|
||||
.renderPass = VK_NULL_HANDLE,
|
||||
.subpass = 0,
|
||||
.framebuffer = VK_NULL_HANDLE,
|
||||
.occlusionQueryEnable = 0,
|
||||
.queryFlags = 0,
|
||||
.pipelineStatistics = 0,
|
||||
};
|
||||
VkCommandBufferBeginInfo beginInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.pInheritanceInfo = &inheritanceInfo,
|
||||
};
|
||||
VK_CHECK(vkBeginCommandBuffer(handle, &beginInfo));
|
||||
}
|
||||
|
||||
@@ -419,15 +443,15 @@ void ComputeCommand::dispatch(uint32 threadX, uint32 threadY, uint32 threadZ)
|
||||
CommandPool::CommandPool(PGraphics graphics, PQueue queue)
|
||||
: graphics(graphics), queue(queue), queueFamilyIndex(queue->getFamilyIndex())
|
||||
{
|
||||
VkCommandPoolCreateInfo info =
|
||||
init::CommandPoolCreateInfo();
|
||||
info.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT;
|
||||
info.queueFamilyIndex = queue->getFamilyIndex();
|
||||
|
||||
VkCommandPoolCreateInfo info = {
|
||||
.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT,
|
||||
.queueFamilyIndex = queue->getFamilyIndex(),
|
||||
};
|
||||
VK_CHECK(vkCreateCommandPool(graphics->getDevice(), &info, nullptr, &commandPool));
|
||||
|
||||
allocatedBuffers.add(new Command(graphics, commandPool, this));
|
||||
|
||||
|
||||
command = allocatedBuffers.back();
|
||||
command->begin();
|
||||
@@ -440,74 +464,65 @@ CommandPool::~CommandPool()
|
||||
queue = nullptr;
|
||||
}
|
||||
|
||||
PCmdBuffer CommandPool::getCommands()
|
||||
PCommand CommandPool::getCommands()
|
||||
{
|
||||
return command;
|
||||
}
|
||||
|
||||
PRenderCommand CommandPool::createRenderCommand(PRenderPass renderPass, PFramebuffer framebuffer, const std::string& name)
|
||||
PRenderCommand CommandPool::createRenderCommand(const std::string& name)
|
||||
{
|
||||
std::scoped_lock lck(allocatedRenderLock);
|
||||
for (uint32 i = 0; i < allocatedRenderCommands.size(); ++i)
|
||||
{
|
||||
PRenderCommand cmdBuffer = allocatedRenderCommands[i];
|
||||
if (cmdBuffer->isReady())
|
||||
{
|
||||
cmdBuffer->name = name;
|
||||
cmdBuffer->begin(renderPass, framebuffer);
|
||||
cmdBuffer->begin(command->boundRenderPass, command->boundFramebuffer);
|
||||
return cmdBuffer;
|
||||
}
|
||||
}
|
||||
allocatedRenderCommands.add(new RenderCommand(graphics, commandPool));
|
||||
PRenderCommand result = allocatedRenderCommands.back();
|
||||
result->name = name;
|
||||
result->begin(renderPass, framebuffer);
|
||||
result->begin(command->boundRenderPass, command->boundFramebuffer);
|
||||
return result;
|
||||
}
|
||||
|
||||
PComputeCommand CommandPool::createComputeCommand(const std::string& name)
|
||||
{
|
||||
std::scoped_lock lck(allocatedComputeLock);
|
||||
for (uint32 i = 0; i < allocatedComputeCommands.size(); ++i)
|
||||
{
|
||||
PComputeCommand cmdBuffer = allocatedComputeCommands[i];
|
||||
if (cmdBuffer->isReady())
|
||||
{
|
||||
cmdBuffer->name = name;
|
||||
cmdBuffer->begin(command);
|
||||
cmdBuffer->begin();
|
||||
return cmdBuffer;
|
||||
}
|
||||
}
|
||||
allocatedComputeCommands.add(new ComputeCommand(graphics, commandPool));
|
||||
PComputeCommand result = allocatedComputeCommands.back();
|
||||
result->name = name;
|
||||
result->begin(command);
|
||||
result->begin();
|
||||
return result;
|
||||
}
|
||||
|
||||
void CommandPool::submitCommands(PSemaphore signalSemaphore)
|
||||
{
|
||||
if (command->state == Command::State::Begin || command->state == Command::State::RenderPass)
|
||||
assert(command->state == Command::State::Begin); // Not in a renderpass
|
||||
command->end();
|
||||
if (signalSemaphore != nullptr)
|
||||
{
|
||||
if (command->state == Command::State::RenderPass)
|
||||
{
|
||||
std::cout << "End of renderpass forced" << std::endl;
|
||||
command->endRenderPass();
|
||||
}
|
||||
command->end();
|
||||
if (signalSemaphore != nullptr)
|
||||
{
|
||||
queue->submitCommandBuffer(command, signalSemaphore->getHandle());
|
||||
}
|
||||
else
|
||||
{
|
||||
queue->submitCommandBuffer(command);
|
||||
}
|
||||
queue->submitCommandBuffer(command, signalSemaphore->getHandle());
|
||||
}
|
||||
std::scoped_lock map(allocatedBufferLock);
|
||||
else
|
||||
{
|
||||
queue->submitCommandBuffer(command);
|
||||
}
|
||||
|
||||
for (uint32 i = 0; i < allocatedBuffers.size(); ++i)
|
||||
{
|
||||
PCmdBuffer cmdBuffer = allocatedBuffers[i];
|
||||
PCommand cmdBuffer = allocatedBuffers[i];
|
||||
cmdBuffer->checkFence();
|
||||
if (cmdBuffer->state == Command::State::Init)
|
||||
{
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#pragma once
|
||||
#include "Queue.h"
|
||||
#include "DescriptorSets.h"
|
||||
#include "Graphics/Command.h"
|
||||
#include "Buffer.h"
|
||||
|
||||
namespace Seele
|
||||
@@ -17,7 +17,7 @@ DECLARE_REF(CommandPool)
|
||||
class Command
|
||||
{
|
||||
public:
|
||||
Command(PGraphics graphics, VkCommandPool cmdPool, PCommandBufferManager manager);
|
||||
Command(PGraphics graphics, VkCommandPool cmdPool, PCommandPool pool);
|
||||
virtual ~Command();
|
||||
constexpr VkCommandBuffer getHandle()
|
||||
{
|
||||
@@ -34,7 +34,7 @@ public:
|
||||
void checkFence();
|
||||
void waitForCommand(uint32 timeToWait = 1000000u);
|
||||
PFence getFence();
|
||||
PCommandBufferManager getManager();
|
||||
PCommandPool getPool();
|
||||
enum State
|
||||
{
|
||||
Init,
|
||||
@@ -46,13 +46,15 @@ public:
|
||||
|
||||
private:
|
||||
PGraphics graphics;
|
||||
PCommandBufferManager manager;
|
||||
PCommandPool pool;
|
||||
OFence fence;
|
||||
State state;
|
||||
VkViewport currentViewport;
|
||||
VkRect2D currentScissor;
|
||||
VkCommandBuffer handle;
|
||||
VkCommandPool owner;
|
||||
PRenderPass boundRenderPass;
|
||||
PFramebuffer boundFramebuffer;
|
||||
Array<PSemaphore> waitSemaphores;
|
||||
Array<VkPipelineStageFlags> waitFlags;
|
||||
Array<PRenderCommand> executingRenders;
|
||||
@@ -112,7 +114,7 @@ public:
|
||||
{
|
||||
return handle;
|
||||
}
|
||||
void begin(PCmdBuffer parent);
|
||||
void begin();
|
||||
void end();
|
||||
void reset();
|
||||
virtual bool isReady() override;
|
||||
@@ -144,7 +146,7 @@ public:
|
||||
return queue;
|
||||
}
|
||||
PCommand getCommands();
|
||||
PRenderCommand createRenderCommand(PRenderPass renderPass, PFramebuffer framebuffer, const std::string& name);
|
||||
PRenderCommand createRenderCommand(const std::string& name);
|
||||
PComputeCommand createComputeCommand(const std::string& name);
|
||||
constexpr VkCommandPool getHandle() const
|
||||
{
|
||||
@@ -158,7 +160,7 @@ private:
|
||||
PQueue queue;
|
||||
uint32 queueFamilyIndex;
|
||||
PCommand command;
|
||||
Array<OCmdBuffer> allocatedBuffers;
|
||||
Array<OCommand> allocatedBuffers;
|
||||
Array<ORenderCommand> allocatedRenderCommands;
|
||||
Array<OComputeCommand> allocatedComputeCommands;
|
||||
};
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
#include "Debug.h"
|
||||
#include <iostream>
|
||||
|
||||
using namespace Seele::Vulkan;
|
||||
|
||||
VkBool32 Seele::Vulkan::debugCallback(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT, uint64_t, size_t, int32_t, const char *layerPrefix, const char *msg, void *)
|
||||
{
|
||||
std::cerr << layerPrefix << ": " << msg << std::endl;
|
||||
return VK_FALSE;
|
||||
}
|
||||
|
||||
VkResult Seele::Vulkan::CreateDebugReportCallbackEXT(VkInstance instance, const VkDebugReportCallbackCreateInfoEXT *pCreateInfo, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT *pCallback)
|
||||
{
|
||||
auto func = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(instance, "vkCreateDebugReportCallbackEXT");
|
||||
if (func != nullptr)
|
||||
{
|
||||
return func(instance, pCreateInfo, pAllocator, pCallback);
|
||||
}
|
||||
else
|
||||
{
|
||||
return VK_ERROR_EXTENSION_NOT_PRESENT;
|
||||
}
|
||||
}
|
||||
|
||||
void Seele::Vulkan::DestroyDebugReportCallbackEXT(VkInstance instance, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT pCallback)
|
||||
{
|
||||
auto func = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(instance, "vkDestroyDebugReportCallbackEXT");
|
||||
if (func != nullptr)
|
||||
{
|
||||
func(instance, pCallback, pAllocator);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
#pragma once
|
||||
#include "Containers/Array.h"
|
||||
#include <vulkan/vulkan.h>
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
namespace Vulkan
|
||||
{
|
||||
VkBool32 debugCallback(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT objType, uint64_t obj, size_t location, int32_t code, const char *layerPrefix, const char *msg, void *userData);
|
||||
|
||||
VkResult CreateDebugReportCallbackEXT(VkInstance instance, const VkDebugReportCallbackCreateInfoEXT *pCreateInfo, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT *pCallback);
|
||||
void DestroyDebugReportCallbackEXT(VkInstance instance, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT pCallback);
|
||||
} // namespace Vulkan
|
||||
} // namespace Seele
|
||||
@@ -1,8 +1,7 @@
|
||||
#include "DescriptorSets.h"
|
||||
#include "Descriptor.h"
|
||||
#include "Graphics.h"
|
||||
#include "Initializer.h"
|
||||
#include "CommandBuffer.h"
|
||||
#include "Texture.h"
|
||||
#include "Buffer.h"
|
||||
|
||||
using namespace Seele;
|
||||
using namespace Seele::Vulkan;
|
||||
@@ -31,27 +30,32 @@ void DescriptorLayout::create()
|
||||
Array<VkDescriptorBindingFlags> bindingFlags(descriptorBindings.size());
|
||||
for (size_t i = 0; i < descriptorBindings.size(); ++i)
|
||||
{
|
||||
VkDescriptorSetLayoutBinding &binding = bindings[i];
|
||||
const Gfx::DescriptorBinding &gfxBinding = descriptorBindings[i];
|
||||
binding.binding = gfxBinding.binding;
|
||||
binding.descriptorCount = gfxBinding.descriptorCount;
|
||||
binding.descriptorType = cast(gfxBinding.descriptorType);
|
||||
binding.stageFlags = gfxBinding.shaderStages;
|
||||
binding.pImmutableSamplers = nullptr;
|
||||
bindings[i] = {
|
||||
.binding = gfxBinding.binding,
|
||||
.descriptorType = cast(gfxBinding.descriptorType),
|
||||
.descriptorCount = gfxBinding.descriptorCount,
|
||||
.stageFlags = gfxBinding.shaderStages,
|
||||
.pImmutableSamplers = nullptr,
|
||||
};
|
||||
bindingFlags[i] = gfxBinding.bindingFlags;
|
||||
}
|
||||
VkDescriptorSetLayoutCreateInfo createInfo =
|
||||
init::DescriptorSetLayoutCreateInfo(bindings.data(), (uint32)bindings.size());
|
||||
VkDescriptorSetLayoutBindingFlagsCreateInfo bindingFlagsInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_BINDING_FLAGS_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.bindingCount = static_cast<uint32>(bindingFlags.size()),
|
||||
.pBindingFlags = bindingFlags.data(),
|
||||
};
|
||||
createInfo.pNext = &bindingFlagsInfo;
|
||||
VkDescriptorSetLayoutCreateInfo createInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO,
|
||||
.pNext = &bindingFlagsInfo,
|
||||
.flags = 0,
|
||||
.bindingCount = (uint32)bindings.size(),
|
||||
.pBindings = bindings.data(),
|
||||
};
|
||||
VK_CHECK(vkCreateDescriptorSetLayout(graphics->getDevice(), &createInfo, nullptr, &layoutHandle));
|
||||
|
||||
allocator = new DescriptorAllocator(graphics, *this);
|
||||
pool = new DescriptorPool(graphics, *this);
|
||||
|
||||
hash = CRC::Calculate(bindings.data(), sizeof(VkDescriptorSetLayoutBinding) * bindings.size(), CRC::CRC_32());
|
||||
}
|
||||
@@ -60,12 +64,10 @@ PipelineLayout::~PipelineLayout()
|
||||
{
|
||||
if (layoutHandle != VK_NULL_HANDLE)
|
||||
{
|
||||
//vkDestroyPipelineLayout(graphics->getDevice(), layoutHandle, nullptr);
|
||||
vkDestroyPipelineLayout(graphics->getDevice(), layoutHandle, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
static Map<uint32, VkPipelineLayout> layoutCache;
|
||||
|
||||
void PipelineLayout::create()
|
||||
{
|
||||
vulkanDescriptorLayouts.resize(descriptorSetLayouts.size());
|
||||
@@ -82,8 +84,6 @@ void PipelineLayout::create()
|
||||
vulkanDescriptorLayouts[i] = layout->getHandle();
|
||||
}
|
||||
|
||||
VkPipelineLayoutCreateInfo createInfo =
|
||||
init::PipelineLayoutCreateInfo(vulkanDescriptorLayouts.data(), (uint32)vulkanDescriptorLayouts.size());
|
||||
Array<VkPushConstantRange> vkPushConstants(pushConstants.size());
|
||||
for (size_t i = 0; i < pushConstants.size(); i++)
|
||||
{
|
||||
@@ -91,20 +91,21 @@ void PipelineLayout::create()
|
||||
vkPushConstants[i].size = pushConstants[i].size;
|
||||
vkPushConstants[i].stageFlags = (VkShaderStageFlagBits)pushConstants[i].stageFlags;
|
||||
}
|
||||
createInfo.pushConstantRangeCount = (uint32)vkPushConstants.size();
|
||||
createInfo.pPushConstantRanges = vkPushConstants.data();
|
||||
|
||||
VkPipelineLayoutCreateInfo createInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.setLayoutCount = (uint32)vulkanDescriptorLayouts.size(),
|
||||
.pSetLayouts = vulkanDescriptorLayouts.data(),
|
||||
.pushConstantRangeCount = (uint32)vkPushConstants.size(),
|
||||
.pPushConstantRanges = vkPushConstants.data(),
|
||||
};
|
||||
|
||||
layoutHash = CRC::Calculate(createInfo.pPushConstantRanges, sizeof(VkPushConstantRange) * createInfo.pushConstantRangeCount, CRC::CRC_32());
|
||||
layoutHash = CRC::Calculate(createInfo.pSetLayouts, sizeof(VkDescriptorSetLayout) * createInfo.setLayoutCount, CRC::CRC_32(), layoutHash);
|
||||
|
||||
if(layoutCache[layoutHash] != VK_NULL_HANDLE)
|
||||
{
|
||||
layoutHandle = layoutCache[layoutHash];
|
||||
return;
|
||||
}
|
||||
|
||||
VK_CHECK(vkCreatePipelineLayout(graphics->getDevice(), &createInfo, nullptr, &layoutHandle));
|
||||
layoutCache[layoutHash] = layoutHandle;
|
||||
}
|
||||
|
||||
void PipelineLayout::reset()
|
||||
@@ -127,10 +128,22 @@ void DescriptorSet::updateBuffer(uint32_t binding, Gfx::PUniformBuffer uniformBu
|
||||
//std::cout << "uniform data equal, skip" << std::endl;
|
||||
return;
|
||||
}
|
||||
bufferInfos.add(init::DescriptorBufferInfo(vulkanBuffer->getHandle(), 0, vulkanBuffer->getSize()));
|
||||
bufferInfos.add(VkDescriptorBufferInfo{
|
||||
.buffer = vulkanBuffer->getHandle(),
|
||||
.offset = 0,
|
||||
.range = vulkanBuffer->getSize(),
|
||||
});
|
||||
|
||||
VkWriteDescriptorSet writeDescriptor = init::WriteDescriptorSet(setHandle, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, binding, &bufferInfos.back());
|
||||
writeDescriptors.add(writeDescriptor);
|
||||
writeDescriptors.add(VkWriteDescriptorSet{
|
||||
.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET,
|
||||
.pNext = nullptr,
|
||||
.dstSet = setHandle,
|
||||
.dstBinding = binding,
|
||||
.dstArrayElement = 0,
|
||||
.descriptorCount = 1,
|
||||
.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER,
|
||||
.pBufferInfo = &bufferInfos.back(),
|
||||
});
|
||||
|
||||
cachedData[binding] = vulkanBuffer.getHandle();
|
||||
}
|
||||
@@ -143,55 +156,69 @@ void DescriptorSet::updateBuffer(uint32_t binding, Gfx::PShaderBuffer shaderBuff
|
||||
{
|
||||
return;
|
||||
}
|
||||
bufferInfos.add(init::DescriptorBufferInfo(vulkanBuffer->getHandle(), 0, vulkanBuffer->getSize()));
|
||||
|
||||
VkWriteDescriptorSet writeDescriptor = init::WriteDescriptorSet(setHandle, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, binding, &bufferInfos.back());
|
||||
writeDescriptors.add(writeDescriptor);
|
||||
bufferInfos.add(VkDescriptorBufferInfo{
|
||||
.buffer = vulkanBuffer->getHandle(),
|
||||
.offset = 0,
|
||||
.range = vulkanBuffer->getSize(),
|
||||
});
|
||||
|
||||
writeDescriptors.add(VkWriteDescriptorSet{
|
||||
.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET,
|
||||
.pNext = nullptr,
|
||||
.dstSet = setHandle,
|
||||
.dstBinding = binding,
|
||||
.dstArrayElement = 0,
|
||||
.descriptorCount = 1,
|
||||
.descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER,
|
||||
.pBufferInfo = &bufferInfos.back(),
|
||||
});
|
||||
|
||||
cachedData[binding] = vulkanBuffer.getHandle();
|
||||
}
|
||||
|
||||
void DescriptorSet::updateSampler(uint32_t binding, Gfx::PSamplerState samplerState)
|
||||
void DescriptorSet::updateSampler(uint32_t binding, Gfx::PSampler samplerState)
|
||||
{
|
||||
PSamplerState vulkanSampler = samplerState.cast<Sampler>();
|
||||
PSampler vulkanSampler = samplerState.cast<Sampler>();
|
||||
Sampler* cachedSampler = reinterpret_cast<Sampler*>(cachedData[binding]);
|
||||
if(vulkanSampler.getHandle() == cachedSampler)
|
||||
{
|
||||
return;
|
||||
}
|
||||
VkDescriptorImageInfo imageInfo =
|
||||
init::DescriptorImageInfo(
|
||||
vulkanSampler->sampler,
|
||||
VK_NULL_HANDLE,
|
||||
VK_IMAGE_LAYOUT_UNDEFINED);
|
||||
imageInfos.add(imageInfo);
|
||||
imageInfos.add(VkDescriptorImageInfo{
|
||||
.sampler = vulkanSampler->sampler,
|
||||
.imageView = VK_NULL_HANDLE,
|
||||
.imageLayout = VK_IMAGE_LAYOUT_UNDEFINED,
|
||||
});
|
||||
|
||||
VkWriteDescriptorSet writeDescriptor = init::WriteDescriptorSet(setHandle, VK_DESCRIPTOR_TYPE_SAMPLER, binding, &imageInfos.back());
|
||||
writeDescriptors.add(writeDescriptor);
|
||||
writeDescriptors.add(VkWriteDescriptorSet{
|
||||
.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET,
|
||||
.pNext = nullptr,
|
||||
.dstSet = setHandle,
|
||||
.dstBinding = binding,
|
||||
.dstArrayElement = 0,
|
||||
.descriptorCount = 1,
|
||||
.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER,
|
||||
.pImageInfo = &imageInfos.back(),
|
||||
});
|
||||
|
||||
cachedData[binding] = vulkanSampler.getHandle();
|
||||
}
|
||||
|
||||
void DescriptorSet::updateTexture(uint32_t binding, Gfx::PTexture texture, Gfx::PSamplerState samplerState)
|
||||
void DescriptorSet::updateTexture(uint32_t binding, Gfx::PTexture texture, Gfx::PSampler samplerState)
|
||||
{
|
||||
TextureHandle* vulkanTexture = TextureBase::cast(texture);
|
||||
TextureHandle* cachedTexture = reinterpret_cast<TextureHandle*>(cachedData[binding]);
|
||||
TextureBase* vulkanTexture = texture.cast<TextureBase>().getHandle();
|
||||
TextureBase* cachedTexture = reinterpret_cast<TextureBase*>(cachedData[binding]);
|
||||
if(vulkanTexture == cachedTexture)
|
||||
{
|
||||
return;
|
||||
}
|
||||
//It is assumed that the image is in the correct layout
|
||||
VkDescriptorImageInfo imageInfo =
|
||||
init::DescriptorImageInfo(
|
||||
VK_NULL_HANDLE,
|
||||
vulkanTexture->getView(),
|
||||
cast(vulkanTexture->getLayout()));
|
||||
if (samplerState != nullptr)
|
||||
{
|
||||
PSamplerState vulkanSampler = samplerState.cast<Sampler>();
|
||||
imageInfo.sampler = vulkanSampler->sampler;
|
||||
}
|
||||
imageInfos.add(imageInfo);
|
||||
imageInfos.add(VkDescriptorImageInfo{
|
||||
.sampler = samplerState != nullptr ? samplerState.cast<Sampler>()->sampler : VK_NULL_HANDLE,
|
||||
.imageView = vulkanTexture->getView(),
|
||||
.imageLayout = cast(vulkanTexture->getLayout()),
|
||||
});
|
||||
VkDescriptorType descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
|
||||
if(samplerState != nullptr)
|
||||
{
|
||||
@@ -201,14 +228,16 @@ void DescriptorSet::updateTexture(uint32_t binding, Gfx::PTexture texture, Gfx::
|
||||
{
|
||||
descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE;
|
||||
}
|
||||
VkWriteDescriptorSet writeDescriptor =
|
||||
init::WriteDescriptorSet(
|
||||
setHandle,
|
||||
descriptorType,
|
||||
binding,
|
||||
&imageInfos.back());
|
||||
|
||||
writeDescriptors.add(writeDescriptor);
|
||||
writeDescriptors.add(VkWriteDescriptorSet{
|
||||
.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET,
|
||||
.pNext = nullptr,
|
||||
.dstSet = setHandle,
|
||||
.dstBinding = binding,
|
||||
.dstArrayElement = 0,
|
||||
.descriptorCount = 1,
|
||||
.descriptorType = descriptorType,
|
||||
.pImageInfo = &imageInfos.back(),
|
||||
});
|
||||
|
||||
cachedData[binding] = vulkanTexture;
|
||||
}
|
||||
@@ -216,28 +245,30 @@ void DescriptorSet::updateTextureArray(uint32_t binding, Array<Gfx::PTexture> te
|
||||
{
|
||||
// maybe make this a parameter?
|
||||
uint32 arrayElement = 0;
|
||||
for(const auto& gfxTexture : textures)
|
||||
for(auto& gfxTexture : textures)
|
||||
{
|
||||
TextureHandle* vulkanTexture = TextureBase::cast(gfxTexture);
|
||||
imageInfos.add(
|
||||
init::DescriptorImageInfo(
|
||||
VK_NULL_HANDLE,
|
||||
vulkanTexture->getView(),
|
||||
cast(vulkanTexture->getLayout())));
|
||||
TextureBase* vulkanTexture = gfxTexture.cast<TextureBase>().getHandle();
|
||||
imageInfos.add(VkDescriptorImageInfo{
|
||||
.sampler = VK_NULL_HANDLE,
|
||||
.imageView = vulkanTexture->getView(),
|
||||
.imageLayout = cast(vulkanTexture->getLayout()),
|
||||
});
|
||||
|
||||
VkDescriptorType descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
|
||||
if (vulkanTexture->getUsage() & VK_IMAGE_USAGE_STORAGE_BIT)
|
||||
{
|
||||
descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE;
|
||||
}
|
||||
VkWriteDescriptorSet& write = writeDescriptors.add(
|
||||
init::WriteDescriptorSet(
|
||||
setHandle,
|
||||
descriptorType,
|
||||
binding,
|
||||
&imageInfos.back()
|
||||
));
|
||||
write.dstArrayElement = arrayElement++;
|
||||
writeDescriptors.add(VkWriteDescriptorSet{
|
||||
.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET,
|
||||
.pNext = nullptr,
|
||||
.dstSet = setHandle,
|
||||
.dstBinding = binding,
|
||||
.dstArrayElement = arrayElement++,
|
||||
.descriptorCount = 1,
|
||||
.descriptorType = descriptorType,
|
||||
.pImageInfo = &imageInfos.back(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -268,7 +299,7 @@ void DescriptorSet::writeChanges()
|
||||
}
|
||||
}
|
||||
|
||||
DescriptorAllocator::DescriptorAllocator(PGraphics graphics, DescriptorLayout &layout)
|
||||
DescriptorPool::DescriptorPool(PGraphics graphics, DescriptorLayout &layout)
|
||||
: graphics(graphics)
|
||||
, layout(layout)
|
||||
{
|
||||
@@ -296,15 +327,18 @@ DescriptorAllocator::DescriptorAllocator(PGraphics graphics, DescriptorLayout &l
|
||||
poolSizes.add(size);
|
||||
}
|
||||
}
|
||||
VkDescriptorPoolCreateInfo createInfo
|
||||
= init::DescriptorPoolCreateInfo(
|
||||
(uint32)poolSizes.size(),
|
||||
poolSizes.data(),
|
||||
maxSets * Gfx::numFramesBuffered);
|
||||
VkDescriptorPoolCreateInfo createInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.maxSets = maxSets * Gfx::numFramesBuffered,
|
||||
.poolSizeCount = (uint32)poolSizes.size(),
|
||||
.pPoolSizes = poolSizes.data(),
|
||||
};
|
||||
VK_CHECK(vkCreateDescriptorPool(graphics->getDevice(), &createInfo, nullptr, &poolHandle));
|
||||
}
|
||||
|
||||
DescriptorAllocator::~DescriptorAllocator()
|
||||
DescriptorPool::~DescriptorPool()
|
||||
{
|
||||
vkDestroyDescriptorPool(graphics->getDevice(), poolHandle, nullptr);
|
||||
graphics = nullptr;
|
||||
@@ -314,15 +348,21 @@ DescriptorAllocator::~DescriptorAllocator()
|
||||
}
|
||||
}
|
||||
|
||||
Gfx::PDescriptorSet DescriptorAllocator::allocateDescriptorSet()
|
||||
Gfx::PDescriptorSet DescriptorPool::allocateDescriptorSet()
|
||||
{
|
||||
VkDescriptorSetLayout layoutHandle = layout.getHandle();
|
||||
VkDescriptorSetAllocateInfo allocInfo =
|
||||
init::DescriptorSetAllocateInfo(poolHandle, &layoutHandle, 1);
|
||||
VkDescriptorSetVariableDescriptorCountAllocateInfo setCounts = {};
|
||||
setCounts.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_VARIABLE_DESCRIPTOR_COUNT_ALLOCATE_INFO;
|
||||
setCounts.pNext = nullptr;
|
||||
setCounts.descriptorSetCount = 1;
|
||||
VkDescriptorSetVariableDescriptorCountAllocateInfo setCounts = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_VARIABLE_DESCRIPTOR_COUNT_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.descriptorSetCount = 1,
|
||||
};
|
||||
VkDescriptorSetAllocateInfo allocInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.descriptorPool = poolHandle,
|
||||
.descriptorSetCount = 1,
|
||||
.pSetLayouts = &layoutHandle,
|
||||
};
|
||||
uint32 counts = 0;
|
||||
for(const auto& binding : layout.bindings)
|
||||
{
|
||||
@@ -364,13 +404,13 @@ Gfx::PDescriptorSet DescriptorAllocator::allocateDescriptorSet()
|
||||
}
|
||||
if(nextAlloc == nullptr)
|
||||
{
|
||||
nextAlloc = new DescriptorAllocator(graphics, layout);
|
||||
nextAlloc = new DescriptorPool(graphics, layout);
|
||||
}
|
||||
return nextAlloc->allocateDescriptorSet();
|
||||
//throw std::logic_error("Out of descriptor sets");
|
||||
}
|
||||
|
||||
void DescriptorAllocator::reset()
|
||||
void DescriptorPool::reset()
|
||||
{
|
||||
for(uint32 i = 0; i < cachedHandles.size(); ++i)
|
||||
{
|
||||
|
||||
@@ -24,7 +24,7 @@ private:
|
||||
PGraphics graphics;
|
||||
Array<VkDescriptorSetLayoutBinding> bindings;
|
||||
VkDescriptorSetLayout layoutHandle;
|
||||
friend class DescriptorAllocator;
|
||||
friend class DescriptorPool;
|
||||
};
|
||||
DEFINE_REF(DescriptorLayout)
|
||||
class PipelineLayout : public Gfx::PipelineLayout
|
||||
@@ -33,25 +33,19 @@ public:
|
||||
PipelineLayout(PGraphics graphics, Gfx::PPipelineLayout baseLayout)
|
||||
: Gfx::PipelineLayout(baseLayout)
|
||||
, graphics(graphics)
|
||||
, layoutHash(0)
|
||||
, layoutHandle(VK_NULL_HANDLE)
|
||||
{}
|
||||
virtual ~PipelineLayout();
|
||||
virtual void create();
|
||||
virtual void reset();
|
||||
inline VkPipelineLayout getHandle() const
|
||||
constexpr VkPipelineLayout getHandle() const
|
||||
{
|
||||
return layoutHandle;
|
||||
}
|
||||
virtual uint32 getHash() const
|
||||
{
|
||||
return layoutHash;
|
||||
}
|
||||
|
||||
private:
|
||||
Array<VkDescriptorSetLayout> vulkanDescriptorLayouts;
|
||||
PGraphics graphics;
|
||||
uint32 layoutHash;
|
||||
VkPipelineLayout layoutHandle;
|
||||
};
|
||||
DEFINE_REF(PipelineLayout)
|
||||
@@ -59,7 +53,7 @@ DEFINE_REF(PipelineLayout)
|
||||
class DescriptorSet : public Gfx::DescriptorSet
|
||||
{
|
||||
public:
|
||||
DescriptorSet(PGraphics graphics, PDescriptorAllocator owner)
|
||||
DescriptorSet(PGraphics graphics, PDescriptorPool owner)
|
||||
: setHandle(VK_NULL_HANDLE)
|
||||
, graphics(graphics)
|
||||
, owner(owner)
|
||||
@@ -71,8 +65,8 @@ public:
|
||||
virtual void writeChanges();
|
||||
virtual void updateBuffer(uint32_t binding, Gfx::PUniformBuffer uniformBuffer);
|
||||
virtual void updateBuffer(uint32_t binding, Gfx::PShaderBuffer uniformBuffer);
|
||||
virtual void updateSampler(uint32_t binding, Gfx::PSamplerState samplerState);
|
||||
virtual void updateTexture(uint32_t binding, Gfx::PTexture texture, Gfx::PSamplerState sampler = nullptr);
|
||||
virtual void updateSampler(uint32_t binding, Gfx::PSampler samplerState);
|
||||
virtual void updateTexture(uint32_t binding, Gfx::PTexture texture, Gfx::PSampler sampler = nullptr);
|
||||
virtual void updateTextureArray(uint32_t binding, Array<Gfx::PTexture> texture);
|
||||
virtual bool operator<(Gfx::PDescriptorSet other);
|
||||
|
||||
@@ -116,29 +110,29 @@ private:
|
||||
Array<void*> cachedData;
|
||||
VkDescriptorSet setHandle;
|
||||
PGraphics graphics;
|
||||
PDescriptorAllocator owner;
|
||||
PDescriptorPool owner;
|
||||
bool currentlyBound;
|
||||
bool currentlyInUse;
|
||||
friend class DescriptorAllocator;
|
||||
friend class DescriptorPool;
|
||||
friend class Command;
|
||||
friend class RenderCommand;
|
||||
friend class ComputeCommand;
|
||||
};
|
||||
DEFINE_REF(DescriptorSet)
|
||||
|
||||
class DescriptorAllocator : public Gfx::DescriptorAllocator
|
||||
class DescriptorPool : public Gfx::DescriptorPool
|
||||
{
|
||||
public:
|
||||
DescriptorAllocator(PGraphics graphics, DescriptorLayout &layout);
|
||||
virtual ~DescriptorAllocator();
|
||||
DescriptorPool(PGraphics graphics, DescriptorLayout &layout);
|
||||
virtual ~DescriptorPool();
|
||||
virtual Gfx::PDescriptorSet allocateDescriptorSet() override;
|
||||
virtual void reset();
|
||||
|
||||
inline VkDescriptorPool getHandle() const
|
||||
constexpr VkDescriptorPool getHandle() const
|
||||
{
|
||||
return poolHandle;
|
||||
}
|
||||
inline DescriptorLayout& getLayout() const
|
||||
constexpr DescriptorLayout& getLayout() const
|
||||
{
|
||||
return layout;
|
||||
}
|
||||
@@ -149,8 +143,8 @@ private:
|
||||
const static int maxSets = 64;
|
||||
StaticArray<ODescriptorSet, maxSets> cachedHandles;
|
||||
VkDescriptorPool poolHandle;
|
||||
DescriptorAllocator* nextAlloc = nullptr;
|
||||
DescriptorPool* nextAlloc = nullptr;
|
||||
};
|
||||
DEFINE_REF(DescriptorAllocator)
|
||||
DEFINE_REF(DescriptorPool)
|
||||
} // namespace Vulkan
|
||||
} // namespace Seele
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Framebuffer.h"
|
||||
#include "Enums.h"
|
||||
#include "Initializer.h"
|
||||
#include "RenderPass.h"
|
||||
#include "Graphics.h"
|
||||
#include "Texture.h"
|
||||
@@ -16,41 +15,43 @@ Framebuffer::Framebuffer(PGraphics graphics, PRenderPass renderPass, Gfx::PRende
|
||||
FramebufferDescription description;
|
||||
std::memset(&description, 0, sizeof(FramebufferDescription));
|
||||
Array<VkImageView> attachments;
|
||||
uint32 sizeX = 0;
|
||||
uint32 sizeY = 0;
|
||||
uint32 width = 0;
|
||||
uint32 height = 0;
|
||||
for (auto inputAttachment : layout->inputAttachments)
|
||||
{
|
||||
PTexture2D vkInputAttachment = inputAttachment->getTexture().cast<Texture2D>();
|
||||
attachments.add(vkInputAttachment->getView());
|
||||
description.inputAttachments[description.numInputAttachments++] = vkInputAttachment->getView();
|
||||
sizeX = std::max(sizeX, vkInputAttachment->getWidth());
|
||||
sizeY = std::max(sizeY, vkInputAttachment->getHeight());
|
||||
width = std::max(width, vkInputAttachment->getWidth());
|
||||
height = std::max(height, vkInputAttachment->getHeight());
|
||||
}
|
||||
for (auto colorAttachment : layout->colorAttachments)
|
||||
{
|
||||
PTexture2D vkColorAttachment = colorAttachment->getTexture().cast<Texture2D>();
|
||||
attachments.add(vkColorAttachment->getView());
|
||||
description.colorAttachments[description.numColorAttachments++] = vkColorAttachment->getView();
|
||||
sizeX = std::max(sizeX, vkColorAttachment->getWidth());
|
||||
sizeY = std::max(sizeY, vkColorAttachment->getHeight());
|
||||
width = std::max(width, vkColorAttachment->getWidth());
|
||||
height = std::max(height, vkColorAttachment->getHeight());
|
||||
}
|
||||
if (layout->depthAttachment != nullptr)
|
||||
{
|
||||
PTexture2D vkDepthAttachment = layout->depthAttachment->getTexture().cast<Texture2D>();
|
||||
attachments.add(vkDepthAttachment->getView());
|
||||
description.depthAttachment = vkDepthAttachment->getView();
|
||||
sizeX = std::max(sizeX, vkDepthAttachment->getWidth());
|
||||
sizeY = std::max(sizeY, vkDepthAttachment->getHeight());
|
||||
width = std::max(width, vkDepthAttachment->getWidth());
|
||||
height = std::max(height, vkDepthAttachment->getHeight());
|
||||
}
|
||||
VkFramebufferCreateInfo createInfo =
|
||||
init::FramebufferCreateInfo(
|
||||
renderPass->getHandle(),
|
||||
(uint32)attachments.size(),
|
||||
attachments.data(),
|
||||
sizeX,
|
||||
sizeY,
|
||||
1);
|
||||
|
||||
VkFramebufferCreateInfo createInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.renderPass = renderPass->getHandle(),
|
||||
.attachmentCount = (uint32)attachments.size(),
|
||||
.pAttachments = attachments.data(),
|
||||
.width = width,
|
||||
.height = height,
|
||||
.layers = 1,
|
||||
};
|
||||
VK_CHECK(vkCreateFramebuffer(graphics->getDevice(), &createInfo, nullptr, &handle));
|
||||
|
||||
hash = CRC::Calculate(&description, sizeof(FramebufferDescription), CRC::CRC_32());
|
||||
|
||||
@@ -10,8 +10,8 @@ namespace Vulkan
|
||||
DECLARE_REF(RenderPass)
|
||||
struct FramebufferDescription
|
||||
{
|
||||
VkImageView inputAttachments[16];
|
||||
VkImageView colorAttachments[16];
|
||||
StaticArray<VkImageView, 16> inputAttachments;
|
||||
StaticArray<VkImageView, 16> colorAttachments;
|
||||
VkImageView depthAttachment;
|
||||
uint32 numInputAttachments;
|
||||
uint32 numColorAttachments;
|
||||
@@ -21,11 +21,11 @@ class Framebuffer
|
||||
public:
|
||||
Framebuffer(PGraphics graphics, PRenderPass renderpass, Gfx::PRenderTargetLayout renderTargetLayout);
|
||||
virtual ~Framebuffer();
|
||||
inline VkFramebuffer getHandle() const
|
||||
constexpr VkFramebuffer getHandle() const
|
||||
{
|
||||
return handle;
|
||||
}
|
||||
inline uint32 getHash() const
|
||||
constexpr uint32 getHash() const
|
||||
{
|
||||
return hash;
|
||||
}
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
#include "Containers/Array.h"
|
||||
#include "Graphics.h"
|
||||
#include "Debug.h"
|
||||
#include "Allocator.h"
|
||||
#include "Buffer.h"
|
||||
#include "Graphics/Enums.h"
|
||||
#include "PipelineCache.h"
|
||||
#include "Command.h"
|
||||
#include "Initializer.h"
|
||||
#include "Descriptor.h"
|
||||
#include "RenderTarget.h"
|
||||
#include "RenderPass.h"
|
||||
#include "Framebuffer.h"
|
||||
@@ -17,10 +17,10 @@
|
||||
using namespace Seele;
|
||||
using namespace Seele::Vulkan;
|
||||
|
||||
thread_local OCommandBufferManager Seele::Vulkan::Graphics::graphicsCommands = nullptr;
|
||||
thread_local OCommandBufferManager Seele::Vulkan::Graphics::computeCommands = nullptr;
|
||||
thread_local OCommandBufferManager Seele::Vulkan::Graphics::transferCommands = nullptr;
|
||||
thread_local OCommandBufferManager Seele::Vulkan::Graphics::dedicatedTransferCommands = nullptr;
|
||||
thread_local OCommandPool Seele::Vulkan::Graphics::graphicsCommands = nullptr;
|
||||
thread_local OCommandPool Seele::Vulkan::Graphics::computeCommands = nullptr;
|
||||
thread_local OCommandPool Seele::Vulkan::Graphics::transferCommands = nullptr;
|
||||
thread_local OCommandPool Seele::Vulkan::Graphics::dedicatedTransferCommands = nullptr;
|
||||
|
||||
Graphics::Graphics()
|
||||
: instance(VK_NULL_HANDLE)
|
||||
@@ -32,7 +32,6 @@ Graphics::Graphics()
|
||||
|
||||
Graphics::~Graphics()
|
||||
{
|
||||
viewports.clear();
|
||||
vkDestroyDevice(handle, nullptr);
|
||||
DestroyDebugReportCallbackEXT(instance, nullptr, callback);
|
||||
vkDestroyInstance(instance, nullptr);
|
||||
@@ -54,21 +53,16 @@ void Graphics::init(GraphicsInitializer initInfo)
|
||||
|
||||
Gfx::OWindow Graphics::createWindow(const WindowCreateInfo &createInfo)
|
||||
{
|
||||
OWindow result = new Window(this, createInfo);
|
||||
return result;
|
||||
return new Window(this, createInfo);
|
||||
}
|
||||
|
||||
Gfx::OViewport Graphics::createViewport(Gfx::PWindow owner, const ViewportCreateInfo &viewportInfo)
|
||||
{
|
||||
OViewport result = new Viewport(this, owner, viewportInfo);
|
||||
std::scoped_lock lock(viewportLock);
|
||||
viewports.add(result);
|
||||
return result;
|
||||
return new Viewport(this, owner, viewportInfo);
|
||||
}
|
||||
Gfx::ORenderPass Graphics::createRenderPass(Gfx::ORenderTargetLayout layout, Gfx::PViewport renderArea)
|
||||
{
|
||||
ORenderPass result = new RenderPass(this, std::move(layout), renderArea);
|
||||
return result;
|
||||
return new RenderPass(this, std::move(layout), renderArea);
|
||||
}
|
||||
void Graphics::beginRenderPass(Gfx::PRenderPass renderPass)
|
||||
{
|
||||
@@ -76,7 +70,6 @@ void Graphics::beginRenderPass(Gfx::PRenderPass renderPass)
|
||||
uint32 framebufferHash = rp->getFramebufferHash();
|
||||
PFramebuffer framebuffer;
|
||||
{
|
||||
std::scoped_lock lock(allocatedFrameBufferLock);
|
||||
auto found = allocatedFramebuffers.find(framebufferHash);
|
||||
if (found == allocatedFramebuffers.end())
|
||||
{
|
||||
@@ -89,18 +82,12 @@ void Graphics::beginRenderPass(Gfx::PRenderPass renderPass)
|
||||
}
|
||||
}
|
||||
getGraphicsCommands()->getCommands()->beginRenderPass(rp, framebuffer);
|
||||
std::scoped_lock lock(renderPassLock);
|
||||
activeRenderPass = rp;
|
||||
activeFramebuffer = framebuffer;
|
||||
}
|
||||
|
||||
void Graphics::endRenderPass()
|
||||
{
|
||||
getGraphicsCommands()->getCommands()->endRenderPass();
|
||||
getGraphicsCommands()->submitCommands();
|
||||
std::scoped_lock lock(renderPassLock);
|
||||
activeRenderPass = nullptr;
|
||||
activeFramebuffer = nullptr;
|
||||
}
|
||||
|
||||
void Graphics::executeCommands(const Array<Gfx::PRenderCommand>& commands)
|
||||
@@ -148,7 +135,7 @@ Gfx::OIndexBuffer Graphics::createIndexBuffer(const IndexBufferCreateInfo &bulkD
|
||||
}
|
||||
Gfx::PRenderCommand Graphics::createRenderCommand(const std::string& name)
|
||||
{
|
||||
return getGraphicsCommands()->createRenderCommand(activeRenderPass, activeFramebuffer, name);
|
||||
return getGraphicsCommands()->createRenderCommand(name);
|
||||
}
|
||||
|
||||
Gfx::PComputeCommand Graphics::createComputeCommand(const std::string& name)
|
||||
@@ -156,10 +143,6 @@ Gfx::PComputeCommand Graphics::createComputeCommand(const std::string& name)
|
||||
return getComputeCommands()->createComputeCommand(name);
|
||||
}
|
||||
|
||||
Gfx::OVertexDeclaration Graphics::createVertexDeclaration(const Array<Gfx::VertexElement>& element)
|
||||
{
|
||||
return new VertexDeclaration(element);
|
||||
}
|
||||
|
||||
Gfx::OVertexShader Graphics::createVertexShader(const ShaderCreateInfo& createInfo)
|
||||
{
|
||||
@@ -206,27 +189,29 @@ Gfx::PComputePipeline Graphics::createComputePipeline(Gfx::ComputePipelineCreate
|
||||
return pipelineCache->createPipeline(std::move(createInfo));
|
||||
}
|
||||
|
||||
Gfx::OSamplerState Graphics::createSamplerState(const SamplerCreateInfo& createInfo)
|
||||
Gfx::OSampler Graphics::createSampler(const SamplerCreateInfo& createInfo)
|
||||
{
|
||||
OSamplerState sampler = new SamplerState();
|
||||
VkSamplerCreateInfo vkInfo =
|
||||
init::SamplerCreateInfo();
|
||||
vkInfo.addressModeU = cast(createInfo.addressModeU);
|
||||
vkInfo.addressModeV = cast(createInfo.addressModeV);
|
||||
vkInfo.addressModeW = cast(createInfo.addressModeW);
|
||||
vkInfo.anisotropyEnable = createInfo.anisotropyEnable;
|
||||
vkInfo.borderColor = cast(createInfo.borderColor);
|
||||
vkInfo.compareEnable = createInfo.compareEnable;
|
||||
vkInfo.compareOp = cast(createInfo.compareOp);
|
||||
vkInfo.flags = createInfo.flags;
|
||||
vkInfo.magFilter = cast(createInfo.magFilter);
|
||||
vkInfo.maxAnisotropy = createInfo.maxAnisotropy;
|
||||
vkInfo.maxLod = createInfo.maxLod;
|
||||
vkInfo.minFilter = cast(createInfo.minFilter);
|
||||
vkInfo.minLod = createInfo.minLod;
|
||||
vkInfo.mipLodBias = createInfo.mipLodBias;
|
||||
vkInfo.mipmapMode = cast(createInfo.mipmapMode);
|
||||
vkInfo.unnormalizedCoordinates = createInfo.unnormalizedCoordinates;
|
||||
OSampler sampler = new Sampler();
|
||||
VkSamplerCreateInfo vkInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = createInfo.flags,
|
||||
.magFilter = cast(createInfo.magFilter),
|
||||
.minFilter = cast(createInfo.minFilter),
|
||||
.mipmapMode = cast(createInfo.mipmapMode),
|
||||
.addressModeU = cast(createInfo.addressModeU),
|
||||
.addressModeV = cast(createInfo.addressModeV),
|
||||
.addressModeW = cast(createInfo.addressModeW),
|
||||
.mipLodBias = createInfo.mipLodBias,
|
||||
.anisotropyEnable = createInfo.anisotropyEnable,
|
||||
.maxAnisotropy = createInfo.maxAnisotropy,
|
||||
.compareEnable = createInfo.compareEnable,
|
||||
.compareOp = cast(createInfo.compareOp),
|
||||
.minLod = createInfo.minLod,
|
||||
.maxLod = createInfo.maxLod,
|
||||
.borderColor = cast(createInfo.borderColor),
|
||||
.unnormalizedCoordinates = createInfo.unnormalizedCoordinates,
|
||||
};
|
||||
VK_CHECK(vkCreateSampler(handle, &vkInfo, nullptr, &sampler->sampler));
|
||||
return sampler;
|
||||
}
|
||||
@@ -246,7 +231,7 @@ void Graphics::vkCmdDrawMeshTasksEXT(VkCommandBuffer handle, uint32 groupX, uint
|
||||
cmdDrawMeshTasks(handle, groupX, groupY, groupZ);
|
||||
}
|
||||
|
||||
PCommandBufferManager Graphics::getQueueCommands(Gfx::QueueType queueType)
|
||||
PCommandPool Graphics::getQueueCommands(Gfx::QueueType queueType)
|
||||
{
|
||||
switch (queueType)
|
||||
{
|
||||
@@ -262,7 +247,7 @@ PCommandBufferManager Graphics::getQueueCommands(Gfx::QueueType queueType)
|
||||
throw new std::logic_error("invalid queue type");
|
||||
}
|
||||
}
|
||||
PCommandBufferManager Graphics::getGraphicsCommands()
|
||||
PCommandPool Graphics::getGraphicsCommands()
|
||||
{
|
||||
if(graphicsCommands == nullptr)
|
||||
{
|
||||
@@ -270,7 +255,7 @@ PCommandBufferManager Graphics::getGraphicsCommands()
|
||||
}
|
||||
return graphicsCommands;
|
||||
}
|
||||
PCommandBufferManager Graphics::getComputeCommands()
|
||||
PCommandPool Graphics::getComputeCommands()
|
||||
{
|
||||
if(computeCommands == nullptr)
|
||||
{
|
||||
@@ -278,7 +263,7 @@ PCommandBufferManager Graphics::getComputeCommands()
|
||||
}
|
||||
return computeCommands;
|
||||
}
|
||||
PCommandBufferManager Graphics::getTransferCommands()
|
||||
PCommandPool Graphics::getTransferCommands()
|
||||
{
|
||||
if(transferCommands == nullptr)
|
||||
{
|
||||
@@ -286,7 +271,7 @@ PCommandBufferManager Graphics::getTransferCommands()
|
||||
}
|
||||
return transferCommands;
|
||||
}
|
||||
PCommandBufferManager Graphics::getDedicatedTransferCommands()
|
||||
PCommandPool Graphics::getDedicatedTransferCommands()
|
||||
{
|
||||
if(dedicatedTransferCommands == nullptr)
|
||||
{
|
||||
@@ -356,9 +341,13 @@ void Graphics::initInstance(GraphicsInitializer initInfo)
|
||||
}
|
||||
void Graphics::setupDebugCallback()
|
||||
{
|
||||
VkDebugReportCallbackCreateInfoEXT createInfo =
|
||||
init::DebugReportCallbackCreateInfo(
|
||||
VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT);
|
||||
VkDebugReportCallbackCreateInfoEXT createInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT,
|
||||
.pNext = nullptr,
|
||||
.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT,
|
||||
.pfnCallback = &debugCallback,
|
||||
.pUserData = nullptr,
|
||||
};
|
||||
|
||||
VK_CHECK(CreateDebugReportCallbackEXT(instance, &createInfo, nullptr, &callback));
|
||||
}
|
||||
@@ -488,8 +477,13 @@ void Graphics::createDevice(GraphicsInitializer initializer)
|
||||
}
|
||||
if (numQueuesForFamily > 0)
|
||||
{
|
||||
VkDeviceQueueCreateInfo info =
|
||||
init::DeviceQueueCreateInfo(familyIndex, numQueuesForFamily);
|
||||
VkDeviceQueueCreateInfo info = {
|
||||
.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.queueFamilyIndex = familyIndex,
|
||||
.queueCount = numQueuesForFamily,
|
||||
};
|
||||
numPriorities += numQueuesForFamily;
|
||||
queueInfos.add(info);
|
||||
}
|
||||
@@ -507,11 +501,6 @@ void Graphics::createDevice(GraphicsInitializer initializer)
|
||||
*currentPriority++ = 1.0f;
|
||||
}
|
||||
}
|
||||
VkDeviceCreateInfo deviceInfo = init::DeviceCreateInfo(
|
||||
queueInfos.data(),
|
||||
(uint32)queueInfos.size(),
|
||||
nullptr);
|
||||
|
||||
VkPhysicalDeviceDescriptorIndexingFeatures descriptorIndexing = {
|
||||
.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_INDEXING_FEATURES,
|
||||
.shaderSampledImageArrayNonUniformIndexing = VK_TRUE,
|
||||
@@ -519,17 +508,6 @@ void Graphics::createDevice(GraphicsInitializer initializer)
|
||||
.descriptorBindingVariableDescriptorCount = VK_TRUE,
|
||||
.runtimeDescriptorArray = VK_TRUE,
|
||||
};
|
||||
deviceInfo.pNext = &descriptorIndexing;
|
||||
#if ENABLE_VALIDATION
|
||||
VkDeviceDiagnosticsConfigCreateInfoNV crashDiagInfo;
|
||||
crashDiagInfo.sType = VK_STRUCTURE_TYPE_DEVICE_DIAGNOSTICS_CONFIG_CREATE_INFO_NV;
|
||||
crashDiagInfo.pNext = nullptr;
|
||||
crashDiagInfo.flags =
|
||||
VK_DEVICE_DIAGNOSTICS_CONFIG_ENABLE_RESOURCE_TRACKING_BIT_NV |
|
||||
VK_DEVICE_DIAGNOSTICS_CONFIG_ENABLE_AUTOMATIC_CHECKPOINTS_BIT_NV |
|
||||
VK_DEVICE_DIAGNOSTICS_CONFIG_ENABLE_SHADER_DEBUG_INFO_BIT_NV;
|
||||
descriptorIndexing.pNext = &crashDiagInfo;
|
||||
#endif
|
||||
VkPhysicalDeviceMeshShaderFeaturesEXT enabledMeshShaderFeatures = {
|
||||
.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT,
|
||||
.taskShader = VK_TRUE,
|
||||
@@ -540,11 +518,17 @@ void Graphics::createDevice(GraphicsInitializer initializer)
|
||||
descriptorIndexing.pNext = &enabledMeshShaderFeatures;
|
||||
initializer.deviceExtensions.add("VK_EXT_mesh_shader");
|
||||
}
|
||||
deviceInfo.enabledExtensionCount = (uint32)initializer.deviceExtensions.size();
|
||||
deviceInfo.ppEnabledExtensionNames = initializer.deviceExtensions.data();
|
||||
deviceInfo.enabledLayerCount = (uint32_t)initializer.layers.size();
|
||||
deviceInfo.ppEnabledLayerNames = initializer.layers.data();
|
||||
deviceInfo.pEnabledFeatures = &features;
|
||||
VkDeviceCreateInfo deviceInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO,
|
||||
.pNext = &descriptorIndexing,
|
||||
.queueCreateInfoCount = (uint32)queueInfos.size(),
|
||||
.pQueueCreateInfos = queueInfos.data(),
|
||||
.enabledLayerCount = (uint32_t)initializer.layers.size(),
|
||||
.ppEnabledLayerNames = initializer.layers.data(),
|
||||
.enabledExtensionCount = (uint32)initializer.deviceExtensions.size(),
|
||||
.ppEnabledExtensionNames = initializer.deviceExtensions.data(),
|
||||
.pEnabledFeatures = &features,
|
||||
};
|
||||
|
||||
VK_CHECK(vkCreateDevice(physicalDevice, &deviceInfo, nullptr, &handle));
|
||||
std::cout << "Vulkan handle: " << handle << std::endl;
|
||||
|
||||
@@ -12,6 +12,7 @@ DECLARE_REF(DestructionManager)
|
||||
DECLARE_REF(CommandPool)
|
||||
DECLARE_REF(Queue)
|
||||
DECLARE_REF(PipelineCache)
|
||||
DECLARE_REF(Framebuffer)
|
||||
class Graphics : public Gfx::Graphics
|
||||
{
|
||||
public:
|
||||
@@ -21,11 +22,11 @@ public:
|
||||
constexpr VkDevice getDevice() const { return handle; };
|
||||
constexpr VkPhysicalDevice getPhysicalDevice() const { return physicalDevice; };
|
||||
|
||||
PCommandBufferManager getQueueCommands(Gfx::QueueType queueType);
|
||||
PCommandBufferManager getGraphicsCommands();
|
||||
PCommandBufferManager getComputeCommands();
|
||||
PCommandBufferManager getTransferCommands();
|
||||
PCommandBufferManager getDedicatedTransferCommands();
|
||||
PCommandPool getQueueCommands(Gfx::QueueType queueType);
|
||||
PCommandPool getGraphicsCommands();
|
||||
PCommandPool getComputeCommands();
|
||||
PCommandPool getTransferCommands();
|
||||
PCommandPool getDedicatedTransferCommands();
|
||||
|
||||
PAllocator getAllocator();
|
||||
PStagingManager getStagingManager();
|
||||
@@ -62,12 +63,11 @@ public:
|
||||
virtual Gfx::PGraphicsPipeline createGraphicsPipeline(Gfx::LegacyPipelineCreateInfo createInfo) override;
|
||||
virtual Gfx::PGraphicsPipeline createGraphicsPipeline(Gfx::MeshPipelineCreateInfo createInfo) override;
|
||||
virtual Gfx::PComputePipeline createComputePipeline(Gfx::ComputePipelineCreateInfo createInfo) override;
|
||||
virtual Gfx::OSampler createSamplerState(const SamplerCreateInfo& createInfo) override;
|
||||
virtual Gfx::OSampler createSampler(const SamplerCreateInfo& createInfo) override;
|
||||
|
||||
virtual Gfx::ODescriptorLayout createDescriptorLayout(const std::string& name = "") override;
|
||||
virtual Gfx::OPipelineLayout createPipelineLayout(Gfx::PPipelineLayout baseLayout = nullptr) override;
|
||||
|
||||
virtual void copyTexture(Gfx::PTexture srcTexture, Gfx::PTexture dstTexture) override;
|
||||
void vkCmdDrawMeshTasksEXT(VkCommandBuffer handle, uint32 groupX, uint32 groupY, uint32 groupZ);
|
||||
protected:
|
||||
PFN_vkCmdDrawMeshTasksEXT cmdDrawMeshTasks;
|
||||
@@ -86,15 +86,13 @@ protected:
|
||||
OQueue transferQueue;
|
||||
OQueue dedicatedTransferQueue;
|
||||
OPipelineCache pipelineCache;
|
||||
thread_local static OCommandBufferManager graphicsCommands;
|
||||
thread_local static OCommandBufferManager computeCommands;
|
||||
thread_local static OCommandBufferManager transferCommands;
|
||||
thread_local static OCommandBufferManager dedicatedTransferCommands;
|
||||
thread_local static OCommandPool graphicsCommands;
|
||||
thread_local static OCommandPool computeCommands;
|
||||
thread_local static OCommandPool transferCommands;
|
||||
thread_local static OCommandPool dedicatedTransferCommands;
|
||||
VkPhysicalDeviceProperties props;
|
||||
VkPhysicalDeviceFeatures features;
|
||||
VkDebugReportCallbackEXT callback;
|
||||
Array<PViewport> viewports;
|
||||
std::mutex allocatedFrameBufferLock;
|
||||
Map<uint32, OFramebuffer> allocatedFramebuffers;
|
||||
OAllocator allocator;
|
||||
OStagingManager stagingManager;
|
||||
|
||||
@@ -1,807 +0,0 @@
|
||||
#include "Initializer.h"
|
||||
#include <iostream>
|
||||
#include "Initializer.h"
|
||||
#include "Initializer.h"
|
||||
|
||||
using namespace Seele::Vulkan;
|
||||
|
||||
VkApplicationInfo init::ApplicationInfo(const char *appName, uint32_t appVersion, const char *engineName, uint32_t engineVersion, uint32_t apiVersion)
|
||||
{
|
||||
VkApplicationInfo info = {};
|
||||
info.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO;
|
||||
info.pApplicationName = appName;
|
||||
info.applicationVersion = appVersion;
|
||||
info.pEngineName = engineName;
|
||||
info.engineVersion = engineVersion;
|
||||
info.apiVersion = apiVersion;
|
||||
return info;
|
||||
}
|
||||
|
||||
VkInstanceCreateInfo init::InstanceCreateInfo(VkApplicationInfo *appInfo, const Array<const char *> &extensions, const Array<const char *> &layers)
|
||||
{
|
||||
VkInstanceCreateInfo info = {};
|
||||
info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
|
||||
info.pApplicationInfo = appInfo;
|
||||
info.enabledExtensionCount = (uint32_t)extensions.size();
|
||||
info.ppEnabledExtensionNames = extensions.data();
|
||||
info.enabledLayerCount = (uint32_t)layers.size();
|
||||
info.ppEnabledLayerNames = layers.data();
|
||||
return info;
|
||||
}
|
||||
|
||||
VkDebugReportCallbackCreateInfoEXT init::DebugReportCallbackCreateInfo(VkDebugReportFlagsEXT flags)
|
||||
{
|
||||
VkDebugReportCallbackCreateInfoEXT createInfo = {};
|
||||
createInfo.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
|
||||
createInfo.flags = flags;
|
||||
createInfo.pfnCallback = (PFN_vkDebugReportCallbackEXT)debugCallback;
|
||||
return createInfo;
|
||||
}
|
||||
|
||||
VkDeviceQueueCreateInfo init::DeviceQueueCreateInfo(int queueFamilyIndex, int queueCount)
|
||||
{
|
||||
float priority = 1.0f;
|
||||
return DeviceQueueCreateInfo(queueFamilyIndex, queueCount, &priority);
|
||||
}
|
||||
|
||||
VkDeviceQueueCreateInfo init::DeviceQueueCreateInfo(int queueFamilyIndex, int queueCount, float *queuePriority)
|
||||
{
|
||||
VkDeviceQueueCreateInfo createInfo = {};
|
||||
createInfo.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
|
||||
createInfo.queueFamilyIndex = queueFamilyIndex;
|
||||
createInfo.queueCount = queueCount;
|
||||
createInfo.pQueuePriorities = queuePriority;
|
||||
return createInfo;
|
||||
}
|
||||
|
||||
VkDeviceCreateInfo init::DeviceCreateInfo(VkDeviceQueueCreateInfo *queueInfos, uint32_t queueCount, VkPhysicalDeviceFeatures *features)
|
||||
{
|
||||
return DeviceCreateInfo(queueInfos, queueCount, features, nullptr, 0, nullptr, 0);
|
||||
}
|
||||
|
||||
VkSwapchainCreateInfoKHR init::SwapchainCreateInfo(VkSurfaceKHR surface, uint32_t minImageCount, VkFormat imageFormat, VkColorSpaceKHR colorSpace, VkExtent2D extent, uint32_t arrayLayers, VkImageUsageFlags usage, VkSurfaceTransformFlagBitsKHR Transform, VkCompositeAlphaFlagBitsKHR alpha, VkPresentModeKHR presentMode, VkBool32 clipped)
|
||||
{
|
||||
VkSwapchainCreateInfoKHR createInfo = {};
|
||||
createInfo.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR;
|
||||
createInfo.surface = surface;
|
||||
createInfo.minImageCount = minImageCount;
|
||||
createInfo.imageFormat = imageFormat;
|
||||
createInfo.imageColorSpace = colorSpace;
|
||||
createInfo.imageExtent = extent;
|
||||
createInfo.imageArrayLayers = arrayLayers;
|
||||
createInfo.imageUsage = usage;
|
||||
createInfo.preTransform = Transform;
|
||||
createInfo.compositeAlpha = alpha;
|
||||
createInfo.presentMode = presentMode;
|
||||
createInfo.clipped = clipped;
|
||||
return createInfo;
|
||||
}
|
||||
|
||||
VkSwapchainCreateInfoKHR init::SwapchainCreateInfo(VkSurfaceKHR surface, uint32_t minImageCount, VkFormat imageFormat, VkColorSpaceKHR colorSpace, uint32_t width, uint32_t height, uint32_t arrayLayers, VkImageUsageFlags usage, VkSurfaceTransformFlagBitsKHR Transform, VkCompositeAlphaFlagBitsKHR alpha, VkPresentModeKHR presentMode, VkBool32 clipped)
|
||||
{
|
||||
VkSwapchainCreateInfoKHR createInfo = {};
|
||||
createInfo.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR;
|
||||
createInfo.surface = surface;
|
||||
createInfo.minImageCount = minImageCount;
|
||||
createInfo.imageFormat = imageFormat;
|
||||
createInfo.imageColorSpace = colorSpace;
|
||||
createInfo.imageExtent.width = width;
|
||||
createInfo.imageExtent.height = height;
|
||||
createInfo.imageArrayLayers = arrayLayers;
|
||||
createInfo.imageUsage = usage;
|
||||
createInfo.preTransform = Transform;
|
||||
createInfo.compositeAlpha = alpha;
|
||||
createInfo.presentMode = presentMode;
|
||||
createInfo.clipped = clipped;
|
||||
return createInfo;
|
||||
}
|
||||
|
||||
VkFramebufferCreateInfo init::FramebufferCreateInfo(VkRenderPass renderPass, uint32_t attachmentCount, VkImageView *attachments, uint32_t width, uint32_t height, uint32_t layers)
|
||||
{
|
||||
VkFramebufferCreateInfo frameBufferCreateInfo = {};
|
||||
frameBufferCreateInfo.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO;
|
||||
frameBufferCreateInfo.pNext = nullptr;
|
||||
frameBufferCreateInfo.renderPass = renderPass;
|
||||
frameBufferCreateInfo.attachmentCount = attachmentCount;
|
||||
frameBufferCreateInfo.pAttachments = attachments;
|
||||
frameBufferCreateInfo.width = width;
|
||||
frameBufferCreateInfo.height = height;
|
||||
frameBufferCreateInfo.layers = layers;
|
||||
return frameBufferCreateInfo;
|
||||
}
|
||||
|
||||
VkAttachmentDescription init::AttachmentDescription(VkFormat format, VkSampleCountFlagBits sample, VkAttachmentLoadOp loadOp, VkAttachmentStoreOp storeOp, VkAttachmentLoadOp stencilLoadOp, VkAttachmentStoreOp stencilStoreOp, VkImageLayout imageLayout, VkImageLayout finalLayout)
|
||||
{
|
||||
VkAttachmentDescription desc = {};
|
||||
desc.format = format;
|
||||
desc.samples = sample;
|
||||
desc.loadOp = loadOp;
|
||||
desc.storeOp = storeOp;
|
||||
desc.stencilLoadOp = stencilLoadOp;
|
||||
desc.stencilStoreOp = stencilStoreOp;
|
||||
desc.initialLayout = imageLayout;
|
||||
desc.finalLayout = finalLayout;
|
||||
return desc;
|
||||
}
|
||||
|
||||
VkSubpassDescription init::SubpassDescription(VkPipelineBindPoint bindPoint,
|
||||
uint32_t colorAttachmentCount, VkAttachmentReference *colorReference,
|
||||
VkAttachmentReference *depthReference,
|
||||
uint32_t inputAttachmentCount, VkAttachmentReference *inputReference,
|
||||
VkAttachmentReference *resolveReference, uint32_t preserveAttachmentCount, uint32_t *preserveReference)
|
||||
{
|
||||
VkSubpassDescription desc = {};
|
||||
desc.pipelineBindPoint = bindPoint;
|
||||
desc.colorAttachmentCount = colorAttachmentCount;
|
||||
desc.pColorAttachments = colorReference;
|
||||
desc.inputAttachmentCount = inputAttachmentCount;
|
||||
desc.pInputAttachments = inputReference;
|
||||
desc.pResolveAttachments = resolveReference;
|
||||
desc.preserveAttachmentCount = preserveAttachmentCount;
|
||||
desc.pPreserveAttachments = preserveReference;
|
||||
desc.pDepthStencilAttachment = depthReference;
|
||||
return desc;
|
||||
}
|
||||
|
||||
VkRenderPassCreateInfo init::RenderPassCreateInfo(uint32_t attachmentCount, const VkAttachmentDescription *attachments, uint32_t subpassCount, const VkSubpassDescription *subpasses, uint32_t dependencyCount, const VkSubpassDependency *subpassDependencies)
|
||||
{
|
||||
VkRenderPassCreateInfo info = {};
|
||||
info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO;
|
||||
info.attachmentCount = attachmentCount;
|
||||
info.pAttachments = attachments;
|
||||
info.subpassCount = subpassCount;
|
||||
info.pSubpasses = subpasses;
|
||||
info.dependencyCount = dependencyCount;
|
||||
info.pDependencies = subpassDependencies;
|
||||
|
||||
return info;
|
||||
}
|
||||
VkDeviceCreateInfo init::DeviceCreateInfo(VkDeviceQueueCreateInfo *queueInfos, uint32_t queueCount, VkPhysicalDeviceFeatures *features, const char *const *deviceExtensions, uint32_t deviceExtensionCount, const char *const *layers, uint32_t layerCount)
|
||||
{
|
||||
VkDeviceCreateInfo createInfo = {};
|
||||
createInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO;
|
||||
createInfo.pQueueCreateInfos = queueInfos;
|
||||
createInfo.queueCreateInfoCount = queueCount;
|
||||
|
||||
createInfo.pEnabledFeatures = features;
|
||||
|
||||
createInfo.ppEnabledExtensionNames = deviceExtensions;
|
||||
createInfo.enabledExtensionCount = deviceExtensionCount;
|
||||
|
||||
#ifdef ENABLE_VALIDATION
|
||||
createInfo.enabledLayerCount = layerCount;
|
||||
createInfo.ppEnabledLayerNames = layers;
|
||||
#else
|
||||
(void)layers;
|
||||
(void)layerCount;
|
||||
createInfo.enabledLayerCount = 0;
|
||||
layerCount = 0;
|
||||
layers = nullptr;
|
||||
#endif // ENABLE_VALIDATION
|
||||
|
||||
return createInfo;
|
||||
}
|
||||
|
||||
VkMemoryAllocateInfo init::MemoryAllocateInfo()
|
||||
{
|
||||
VkMemoryAllocateInfo memAllocInfo = {};
|
||||
memAllocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
|
||||
memAllocInfo.pNext = NULL;
|
||||
return memAllocInfo;
|
||||
}
|
||||
|
||||
VkCommandBufferAllocateInfo init::CommandBufferAllocateInfo(VkCommandPool commandPool, VkCommandBufferLevel level, uint32_t bufferCount)
|
||||
{
|
||||
VkCommandBufferAllocateInfo commandBufferAllocateInfo = {};
|
||||
commandBufferAllocateInfo.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO;
|
||||
commandBufferAllocateInfo.commandPool = commandPool;
|
||||
commandBufferAllocateInfo.level = level;
|
||||
commandBufferAllocateInfo.commandBufferCount = bufferCount;
|
||||
return commandBufferAllocateInfo;
|
||||
}
|
||||
|
||||
VkCommandPoolCreateInfo init::CommandPoolCreateInfo()
|
||||
{
|
||||
VkCommandPoolCreateInfo cmdPoolCreateInfo = {};
|
||||
cmdPoolCreateInfo.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO;
|
||||
return cmdPoolCreateInfo;
|
||||
}
|
||||
|
||||
VkCommandBufferBeginInfo init::CommandBufferBeginInfo()
|
||||
{
|
||||
VkCommandBufferBeginInfo cmdBufferBeginInfo = {};
|
||||
cmdBufferBeginInfo.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO;
|
||||
cmdBufferBeginInfo.pNext = NULL;
|
||||
return cmdBufferBeginInfo;
|
||||
}
|
||||
|
||||
VkCommandBufferInheritanceInfo init::CommandBufferInheritanceInfo()
|
||||
{
|
||||
VkCommandBufferInheritanceInfo cmdBufferInheritanceInfo = {};
|
||||
cmdBufferInheritanceInfo.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_INHERITANCE_INFO;
|
||||
return cmdBufferInheritanceInfo;
|
||||
}
|
||||
|
||||
VkRenderPassBeginInfo init::RenderPassBeginInfo()
|
||||
{
|
||||
VkRenderPassBeginInfo renderPassBeginInfo = {};
|
||||
renderPassBeginInfo.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO;
|
||||
renderPassBeginInfo.pNext = NULL;
|
||||
return renderPassBeginInfo;
|
||||
}
|
||||
|
||||
VkRenderPassCreateInfo init::RenderPassCreateInfo()
|
||||
{
|
||||
VkRenderPassCreateInfo renderPassCreateInfo = {};
|
||||
renderPassCreateInfo.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO;
|
||||
renderPassCreateInfo.pNext = NULL;
|
||||
return renderPassCreateInfo;
|
||||
}
|
||||
|
||||
VkImageMemoryBarrier init::ImageMemoryBarrier(VkImage image, VkImageLayout oldLayout, VkImageLayout newLayout, uint32_t srcQueue, uint32_t dstQueue)
|
||||
{
|
||||
VkImageMemoryBarrier barrier = {};
|
||||
barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
||||
barrier.oldLayout = oldLayout;
|
||||
barrier.newLayout = newLayout;
|
||||
barrier.srcQueueFamilyIndex = srcQueue;
|
||||
barrier.dstQueueFamilyIndex = dstQueue;
|
||||
barrier.image = image;
|
||||
if (newLayout == VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL)
|
||||
{
|
||||
barrier.subresourceRange.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT;
|
||||
}
|
||||
else
|
||||
{
|
||||
barrier.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
|
||||
}
|
||||
barrier.subresourceRange.baseMipLevel = 0;
|
||||
barrier.subresourceRange.levelCount = 1;
|
||||
barrier.subresourceRange.baseArrayLayer = 0;
|
||||
barrier.subresourceRange.layerCount = 1;
|
||||
if (oldLayout == VK_IMAGE_LAYOUT_PREINITIALIZED && newLayout == VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL)
|
||||
{
|
||||
barrier.srcAccessMask = VK_ACCESS_HOST_WRITE_BIT;
|
||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||
}
|
||||
else if (oldLayout == VK_IMAGE_LAYOUT_PREINITIALIZED && newLayout == VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
|
||||
{
|
||||
barrier.srcAccessMask = VK_ACCESS_HOST_WRITE_BIT;
|
||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
}
|
||||
else if (oldLayout == VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL && newLayout == VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL)
|
||||
{
|
||||
barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||
}
|
||||
else if (oldLayout == VK_IMAGE_LAYOUT_UNDEFINED && newLayout == VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL)
|
||||
{
|
||||
barrier.srcAccessMask = 0;
|
||||
barrier.dstAccessMask = VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_READ_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT;
|
||||
}
|
||||
else if (oldLayout == VK_IMAGE_LAYOUT_UNDEFINED && newLayout == VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
|
||||
{
|
||||
barrier.srcAccessMask = 0;
|
||||
barrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
}
|
||||
return barrier;
|
||||
}
|
||||
|
||||
VkImageMemoryBarrier init::ImageMemoryBarrier()
|
||||
{
|
||||
VkImageMemoryBarrier barrier = {};
|
||||
barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
||||
barrier.pNext = nullptr;
|
||||
return barrier;
|
||||
}
|
||||
|
||||
VkBufferMemoryBarrier init::BufferMemoryBarrier()
|
||||
{
|
||||
VkBufferMemoryBarrier bufferMemoryBarrier = {};
|
||||
bufferMemoryBarrier.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER;
|
||||
bufferMemoryBarrier.pNext = NULL;
|
||||
bufferMemoryBarrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
bufferMemoryBarrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
return bufferMemoryBarrier;
|
||||
}
|
||||
|
||||
VkMemoryBarrier init::MemoryBarrier()
|
||||
{
|
||||
VkMemoryBarrier memoryBarrier = {};
|
||||
memoryBarrier.sType = VK_STRUCTURE_TYPE_MEMORY_BARRIER;
|
||||
memoryBarrier.pNext = NULL;
|
||||
return memoryBarrier;
|
||||
}
|
||||
|
||||
VkImageCreateInfo init::ImageCreateInfo()
|
||||
{
|
||||
VkImageCreateInfo imageCreateInfo = {};
|
||||
imageCreateInfo.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO;
|
||||
imageCreateInfo.pNext = NULL;
|
||||
return imageCreateInfo;
|
||||
}
|
||||
|
||||
VkSamplerCreateInfo init::SamplerCreateInfo()
|
||||
{
|
||||
VkSamplerCreateInfo samplerCreateInfo = {};
|
||||
samplerCreateInfo.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO;
|
||||
samplerCreateInfo.pNext = NULL;
|
||||
samplerCreateInfo.magFilter = VK_FILTER_LINEAR;
|
||||
samplerCreateInfo.minFilter = VK_FILTER_LINEAR;
|
||||
samplerCreateInfo.addressModeU = VK_SAMPLER_ADDRESS_MODE_REPEAT;
|
||||
samplerCreateInfo.addressModeV = VK_SAMPLER_ADDRESS_MODE_REPEAT;
|
||||
samplerCreateInfo.addressModeW = VK_SAMPLER_ADDRESS_MODE_REPEAT;
|
||||
|
||||
samplerCreateInfo.anisotropyEnable = VK_FALSE;
|
||||
samplerCreateInfo.maxAnisotropy = 1.0f;
|
||||
samplerCreateInfo.borderColor = VK_BORDER_COLOR_INT_OPAQUE_BLACK;
|
||||
samplerCreateInfo.unnormalizedCoordinates = VK_FALSE;
|
||||
samplerCreateInfo.compareEnable = VK_FALSE;
|
||||
samplerCreateInfo.compareOp = VK_COMPARE_OP_ALWAYS;
|
||||
|
||||
samplerCreateInfo.mipmapMode = VK_SAMPLER_MIPMAP_MODE_LINEAR;
|
||||
samplerCreateInfo.mipLodBias = 0.0f;
|
||||
samplerCreateInfo.minLod = 0.0f;
|
||||
samplerCreateInfo.maxLod = 0.0f;
|
||||
return samplerCreateInfo;
|
||||
}
|
||||
|
||||
VkImageViewCreateInfo init::ImageViewCreateInfo()
|
||||
{
|
||||
VkImageViewCreateInfo imageViewCreateInfo = {};
|
||||
imageViewCreateInfo.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
||||
imageViewCreateInfo.pNext = NULL;
|
||||
return imageViewCreateInfo;
|
||||
}
|
||||
|
||||
VkSemaphoreCreateInfo init::SemaphoreCreateInfo()
|
||||
{
|
||||
VkSemaphoreCreateInfo semaphoreCreateInfo = {};
|
||||
semaphoreCreateInfo.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO;
|
||||
semaphoreCreateInfo.pNext = NULL;
|
||||
semaphoreCreateInfo.flags = 0;
|
||||
return semaphoreCreateInfo;
|
||||
}
|
||||
|
||||
VkFenceCreateInfo init::FenceCreateInfo(VkFenceCreateFlags flags)
|
||||
{
|
||||
VkFenceCreateInfo fenceCreateInfo = {};
|
||||
fenceCreateInfo.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO;
|
||||
fenceCreateInfo.flags = flags;
|
||||
return fenceCreateInfo;
|
||||
}
|
||||
|
||||
VkEventCreateInfo init::EventCreateInfo()
|
||||
{
|
||||
VkEventCreateInfo eventCreateInfo = {};
|
||||
eventCreateInfo.sType = VK_STRUCTURE_TYPE_EVENT_CREATE_INFO;
|
||||
return eventCreateInfo;
|
||||
}
|
||||
|
||||
VkSubmitInfo init::SubmitInfo()
|
||||
{
|
||||
VkSubmitInfo submitInfo = {};
|
||||
submitInfo.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
|
||||
submitInfo.pNext = NULL;
|
||||
return submitInfo;
|
||||
}
|
||||
|
||||
VkImageSubresourceRange init::ImageSubresourceRange(VkImageAspectFlags aspect, uint32_t startMip)
|
||||
{
|
||||
VkImageSubresourceRange range;
|
||||
std::memset(&range, 0, sizeof(VkImageSubresourceRange));
|
||||
range.aspectMask = aspect;
|
||||
range.baseMipLevel = startMip;
|
||||
range.levelCount = 1;
|
||||
range.baseArrayLayer = 0;
|
||||
range.layerCount = 1;
|
||||
return range;
|
||||
}
|
||||
|
||||
VkViewport init::Viewport(
|
||||
float width,
|
||||
float height,
|
||||
float minDepth,
|
||||
float maxDepth)
|
||||
{
|
||||
VkViewport viewport = {};
|
||||
viewport.width = width;
|
||||
viewport.height = height;
|
||||
viewport.minDepth = minDepth;
|
||||
viewport.maxDepth = maxDepth;
|
||||
return viewport;
|
||||
}
|
||||
|
||||
VkRect2D init::Rect2D(
|
||||
int32_t width,
|
||||
int32_t height,
|
||||
int32_t offsetX,
|
||||
int32_t offsetY)
|
||||
{
|
||||
VkRect2D rect2D = {};
|
||||
rect2D.extent.width = width;
|
||||
rect2D.extent.height = height;
|
||||
rect2D.offset.x = offsetX;
|
||||
rect2D.offset.y = offsetY;
|
||||
return rect2D;
|
||||
}
|
||||
|
||||
VkBufferCreateInfo init::BufferCreateInfo()
|
||||
{
|
||||
VkBufferCreateInfo bufCreateInfo = {};
|
||||
bufCreateInfo.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
|
||||
return bufCreateInfo;
|
||||
}
|
||||
|
||||
VkBufferCreateInfo init::BufferCreateInfo(
|
||||
VkBufferUsageFlags usage,
|
||||
VkDeviceSize size)
|
||||
{
|
||||
VkBufferCreateInfo bufCreateInfo = {};
|
||||
bufCreateInfo.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
|
||||
bufCreateInfo.pNext = NULL;
|
||||
bufCreateInfo.usage = usage;
|
||||
bufCreateInfo.size = size;
|
||||
bufCreateInfo.flags = 0;
|
||||
return bufCreateInfo;
|
||||
}
|
||||
|
||||
VkDescriptorPoolCreateInfo init::DescriptorPoolCreateInfo(
|
||||
uint32_t poolSizeCount,
|
||||
VkDescriptorPoolSize *pPoolSizes,
|
||||
uint32_t maxSets)
|
||||
{
|
||||
VkDescriptorPoolCreateInfo descriptorPoolInfo = {};
|
||||
descriptorPoolInfo.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;
|
||||
descriptorPoolInfo.pNext = NULL;
|
||||
descriptorPoolInfo.poolSizeCount = poolSizeCount;
|
||||
descriptorPoolInfo.pPoolSizes = pPoolSizes;
|
||||
descriptorPoolInfo.maxSets = maxSets;
|
||||
return descriptorPoolInfo;
|
||||
}
|
||||
|
||||
VkDescriptorPoolSize init::DescriptorPoolSize(
|
||||
VkDescriptorType type,
|
||||
uint32_t descriptorCount)
|
||||
{
|
||||
VkDescriptorPoolSize descriptorPoolSize = {};
|
||||
descriptorPoolSize.type = type;
|
||||
descriptorPoolSize.descriptorCount = descriptorCount;
|
||||
return descriptorPoolSize;
|
||||
}
|
||||
|
||||
VkDescriptorSetLayoutBinding init::DescriptorSetLayoutBinding(
|
||||
VkDescriptorType type,
|
||||
VkShaderStageFlags stageFlags,
|
||||
uint32_t binding,
|
||||
uint32_t count)
|
||||
{
|
||||
VkDescriptorSetLayoutBinding setLayoutBinding = {};
|
||||
setLayoutBinding.descriptorType = type;
|
||||
setLayoutBinding.stageFlags = stageFlags;
|
||||
setLayoutBinding.binding = binding;
|
||||
setLayoutBinding.descriptorCount = count;
|
||||
return setLayoutBinding;
|
||||
}
|
||||
|
||||
VkDescriptorSetLayoutCreateInfo init::DescriptorSetLayoutCreateInfo(
|
||||
const VkDescriptorSetLayoutBinding *pBindings,
|
||||
uint32_t bindingCount)
|
||||
{
|
||||
VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = {};
|
||||
descriptorSetLayoutCreateInfo.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
|
||||
descriptorSetLayoutCreateInfo.pNext = NULL;
|
||||
descriptorSetLayoutCreateInfo.pBindings = pBindings;
|
||||
descriptorSetLayoutCreateInfo.bindingCount = bindingCount;
|
||||
return descriptorSetLayoutCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineLayoutCreateInfo init::PipelineLayoutCreateInfo(
|
||||
const VkDescriptorSetLayout *pSetLayouts,
|
||||
uint32_t setLayoutCount)
|
||||
{
|
||||
VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo = {};
|
||||
pipelineLayoutCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
|
||||
pipelineLayoutCreateInfo.pNext = NULL;
|
||||
pipelineLayoutCreateInfo.setLayoutCount = setLayoutCount;
|
||||
pipelineLayoutCreateInfo.pSetLayouts = pSetLayouts;
|
||||
return pipelineLayoutCreateInfo;
|
||||
}
|
||||
|
||||
VkDescriptorSetAllocateInfo init::DescriptorSetAllocateInfo(
|
||||
VkDescriptorPool descriptorPool,
|
||||
const VkDescriptorSetLayout *pSetLayouts,
|
||||
uint32_t descriptorSetCount)
|
||||
{
|
||||
VkDescriptorSetAllocateInfo descriptorSetAllocateInfo = {};
|
||||
descriptorSetAllocateInfo.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
|
||||
descriptorSetAllocateInfo.pNext = NULL;
|
||||
descriptorSetAllocateInfo.descriptorPool = descriptorPool;
|
||||
descriptorSetAllocateInfo.pSetLayouts = pSetLayouts;
|
||||
descriptorSetAllocateInfo.descriptorSetCount = descriptorSetCount;
|
||||
return descriptorSetAllocateInfo;
|
||||
}
|
||||
|
||||
VkDescriptorBufferInfo init::DescriptorBufferInfo(VkBuffer buffer, VkDeviceSize offset, VkDeviceSize range)
|
||||
{
|
||||
VkDescriptorBufferInfo bufferInfo = {};
|
||||
bufferInfo.buffer = buffer;
|
||||
bufferInfo.offset = offset;
|
||||
bufferInfo.range = range;
|
||||
|
||||
return bufferInfo;
|
||||
}
|
||||
|
||||
VkDescriptorImageInfo init::DescriptorImageInfo(
|
||||
VkSampler sampler,
|
||||
VkImageView imageView,
|
||||
VkImageLayout imageLayout)
|
||||
{
|
||||
VkDescriptorImageInfo descriptorImageInfo = {};
|
||||
descriptorImageInfo.sampler = sampler;
|
||||
descriptorImageInfo.imageView = imageView;
|
||||
descriptorImageInfo.imageLayout = imageLayout;
|
||||
return descriptorImageInfo;
|
||||
}
|
||||
|
||||
VkWriteDescriptorSet init::WriteDescriptorSet(
|
||||
VkDescriptorSet dstSet,
|
||||
VkDescriptorType type,
|
||||
uint32_t binding,
|
||||
VkDescriptorBufferInfo *bufferInfo)
|
||||
{
|
||||
VkWriteDescriptorSet writeDescriptorSet = {};
|
||||
writeDescriptorSet.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
|
||||
writeDescriptorSet.pNext = NULL;
|
||||
writeDescriptorSet.dstSet = dstSet;
|
||||
writeDescriptorSet.descriptorType = type;
|
||||
writeDescriptorSet.dstBinding = binding;
|
||||
writeDescriptorSet.pBufferInfo = bufferInfo;
|
||||
// Default value in all examples
|
||||
writeDescriptorSet.descriptorCount = 1;
|
||||
return writeDescriptorSet;
|
||||
}
|
||||
|
||||
VkWriteDescriptorSet init::WriteDescriptorSet(
|
||||
VkDescriptorSet dstSet,
|
||||
VkDescriptorType type,
|
||||
uint32_t binding,
|
||||
VkDescriptorImageInfo *bufferInfo)
|
||||
{
|
||||
VkWriteDescriptorSet writeDescriptorSet = {};
|
||||
writeDescriptorSet.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
|
||||
writeDescriptorSet.pNext = NULL;
|
||||
writeDescriptorSet.dstSet = dstSet;
|
||||
writeDescriptorSet.descriptorType = type;
|
||||
writeDescriptorSet.dstBinding = binding;
|
||||
writeDescriptorSet.pImageInfo = bufferInfo;
|
||||
// Default value in all examples
|
||||
writeDescriptorSet.descriptorCount = 1;
|
||||
return writeDescriptorSet;
|
||||
}
|
||||
|
||||
VkVertexInputBindingDescription init::VertexInputBindingDescription(
|
||||
uint32_t binding,
|
||||
uint32_t stride,
|
||||
VkVertexInputRate inputRate)
|
||||
{
|
||||
VkVertexInputBindingDescription vInputBindDescription = {};
|
||||
vInputBindDescription.binding = binding;
|
||||
vInputBindDescription.stride = stride;
|
||||
vInputBindDescription.inputRate = inputRate;
|
||||
return vInputBindDescription;
|
||||
}
|
||||
|
||||
VkVertexInputAttributeDescription init::VertexInputAttributeDescription(
|
||||
uint32_t binding,
|
||||
uint32_t location,
|
||||
VkFormat format,
|
||||
uint32_t offset)
|
||||
{
|
||||
VkVertexInputAttributeDescription vInputAttribDescription = {};
|
||||
vInputAttribDescription.location = location;
|
||||
vInputAttribDescription.binding = binding;
|
||||
vInputAttribDescription.format = format;
|
||||
vInputAttribDescription.offset = offset;
|
||||
return vInputAttribDescription;
|
||||
}
|
||||
|
||||
VkPipelineVertexInputStateCreateInfo init::PipelineVertexInputStateCreateInfo()
|
||||
{
|
||||
VkPipelineVertexInputStateCreateInfo pipelineVertexInputStateCreateInfo = {};
|
||||
pipelineVertexInputStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO;
|
||||
pipelineVertexInputStateCreateInfo.pNext = NULL;
|
||||
return pipelineVertexInputStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineInputAssemblyStateCreateInfo init::PipelineInputAssemblyStateCreateInfo(
|
||||
VkPrimitiveTopology topology,
|
||||
VkPipelineInputAssemblyStateCreateFlags flags,
|
||||
VkBool32 primitiveRestartEnable)
|
||||
{
|
||||
VkPipelineInputAssemblyStateCreateInfo pipelineInputAssemblyStateCreateInfo = {};
|
||||
pipelineInputAssemblyStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
|
||||
pipelineInputAssemblyStateCreateInfo.topology = topology;
|
||||
pipelineInputAssemblyStateCreateInfo.flags = flags;
|
||||
pipelineInputAssemblyStateCreateInfo.primitiveRestartEnable = primitiveRestartEnable;
|
||||
return pipelineInputAssemblyStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineRasterizationStateCreateInfo init::PipelineRasterizationStateCreateInfo(
|
||||
VkPolygonMode polygonMode,
|
||||
VkCullModeFlags cullMode,
|
||||
VkFrontFace frontFace,
|
||||
VkPipelineRasterizationStateCreateFlags flags)
|
||||
{
|
||||
VkPipelineRasterizationStateCreateInfo pipelineRasterizationStateCreateInfo = {};
|
||||
pipelineRasterizationStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO;
|
||||
pipelineRasterizationStateCreateInfo.polygonMode = polygonMode;
|
||||
pipelineRasterizationStateCreateInfo.cullMode = cullMode;
|
||||
pipelineRasterizationStateCreateInfo.frontFace = frontFace;
|
||||
pipelineRasterizationStateCreateInfo.flags = flags;
|
||||
pipelineRasterizationStateCreateInfo.depthClampEnable = VK_FALSE;
|
||||
pipelineRasterizationStateCreateInfo.lineWidth = 1.0f;
|
||||
return pipelineRasterizationStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineColorBlendAttachmentState init::PipelineColorBlendAttachmentState(
|
||||
VkColorComponentFlags colorWriteMask,
|
||||
VkBool32 blendEnable)
|
||||
{
|
||||
VkPipelineColorBlendAttachmentState pipelineColorBlendAttachmentState = {};
|
||||
pipelineColorBlendAttachmentState.colorWriteMask = colorWriteMask;
|
||||
pipelineColorBlendAttachmentState.blendEnable = blendEnable;
|
||||
return pipelineColorBlendAttachmentState;
|
||||
}
|
||||
|
||||
VkPipelineColorBlendStateCreateInfo init::PipelineColorBlendStateCreateInfo(
|
||||
uint32_t attachmentCount,
|
||||
const VkPipelineColorBlendAttachmentState *pAttachments)
|
||||
{
|
||||
VkPipelineColorBlendStateCreateInfo pipelineColorBlendStateCreateInfo = {};
|
||||
pipelineColorBlendStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
|
||||
pipelineColorBlendStateCreateInfo.pNext = NULL;
|
||||
pipelineColorBlendStateCreateInfo.attachmentCount = attachmentCount;
|
||||
pipelineColorBlendStateCreateInfo.pAttachments = pAttachments;
|
||||
return pipelineColorBlendStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineDepthStencilStateCreateInfo init::PipelineDepthStencilStateCreateInfo(
|
||||
VkBool32 depthTestEnable,
|
||||
VkBool32 depthWriteEnable,
|
||||
VkCompareOp depthCompareOp)
|
||||
{
|
||||
VkPipelineDepthStencilStateCreateInfo pipelineDepthStencilStateCreateInfo = {};
|
||||
pipelineDepthStencilStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO;
|
||||
pipelineDepthStencilStateCreateInfo.depthTestEnable = depthTestEnable;
|
||||
pipelineDepthStencilStateCreateInfo.depthWriteEnable = depthWriteEnable;
|
||||
pipelineDepthStencilStateCreateInfo.depthCompareOp = depthCompareOp;
|
||||
pipelineDepthStencilStateCreateInfo.front = pipelineDepthStencilStateCreateInfo.back;
|
||||
pipelineDepthStencilStateCreateInfo.back.compareOp = VK_COMPARE_OP_ALWAYS;
|
||||
return pipelineDepthStencilStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineViewportStateCreateInfo init::PipelineViewportStateCreateInfo(
|
||||
uint32_t viewportCount,
|
||||
uint32_t scissorCount,
|
||||
VkPipelineViewportStateCreateFlags flags)
|
||||
{
|
||||
VkPipelineViewportStateCreateInfo pipelineViewportStateCreateInfo = {};
|
||||
pipelineViewportStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO;
|
||||
pipelineViewportStateCreateInfo.viewportCount = viewportCount;
|
||||
pipelineViewportStateCreateInfo.scissorCount = scissorCount;
|
||||
pipelineViewportStateCreateInfo.flags = flags;
|
||||
return pipelineViewportStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineMultisampleStateCreateInfo init::PipelineMultisampleStateCreateInfo(
|
||||
VkSampleCountFlagBits rasterizationSamples,
|
||||
VkPipelineMultisampleStateCreateFlags flags)
|
||||
{
|
||||
VkPipelineMultisampleStateCreateInfo pipelineMultisampleStateCreateInfo = {};
|
||||
pipelineMultisampleStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO;
|
||||
pipelineMultisampleStateCreateInfo.flags = flags;
|
||||
pipelineMultisampleStateCreateInfo.rasterizationSamples = rasterizationSamples;
|
||||
return pipelineMultisampleStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineDynamicStateCreateInfo init::PipelineDynamicStateCreateInfo(
|
||||
const VkDynamicState *pDynamicStates,
|
||||
uint32_t dynamicStateCount,
|
||||
VkPipelineDynamicStateCreateFlags flags)
|
||||
{
|
||||
VkPipelineDynamicStateCreateInfo pipelineDynamicStateCreateInfo = {};
|
||||
pipelineDynamicStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO;
|
||||
pipelineDynamicStateCreateInfo.flags = flags;
|
||||
pipelineDynamicStateCreateInfo.pDynamicStates = pDynamicStates;
|
||||
pipelineDynamicStateCreateInfo.dynamicStateCount = dynamicStateCount;
|
||||
return pipelineDynamicStateCreateInfo;
|
||||
}
|
||||
|
||||
VkPipelineTessellationStateCreateInfo init::PipelineTessellationStateCreateInfo(uint32_t patchControlPoints)
|
||||
{
|
||||
VkPipelineTessellationStateCreateInfo pipelineTessellationStateCreateInfo = {};
|
||||
pipelineTessellationStateCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_TESSELLATION_STATE_CREATE_INFO;
|
||||
pipelineTessellationStateCreateInfo.patchControlPoints = patchControlPoints;
|
||||
return pipelineTessellationStateCreateInfo;
|
||||
}
|
||||
|
||||
VkGraphicsPipelineCreateInfo init::PipelineCreateInfo(
|
||||
VkPipelineLayout layout,
|
||||
VkRenderPass renderPass,
|
||||
VkPipelineCreateFlags flags)
|
||||
{
|
||||
VkGraphicsPipelineCreateInfo pipelineCreateInfo = {};
|
||||
pipelineCreateInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO;
|
||||
pipelineCreateInfo.pNext = NULL;
|
||||
pipelineCreateInfo.layout = layout;
|
||||
pipelineCreateInfo.renderPass = renderPass;
|
||||
pipelineCreateInfo.flags = flags;
|
||||
return pipelineCreateInfo;
|
||||
}
|
||||
|
||||
VkComputePipelineCreateInfo init::ComputePipelineCreateInfo(VkPipelineLayout layout, VkPipelineCreateFlags flags)
|
||||
{
|
||||
VkComputePipelineCreateInfo computePipelineCreateInfo = {};
|
||||
computePipelineCreateInfo.sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO;
|
||||
computePipelineCreateInfo.layout = layout;
|
||||
computePipelineCreateInfo.flags = flags;
|
||||
return computePipelineCreateInfo;
|
||||
}
|
||||
|
||||
VkPushConstantRange init::PushConstantRange(
|
||||
VkShaderStageFlags stageFlags,
|
||||
uint32_t size,
|
||||
uint32_t offset)
|
||||
{
|
||||
VkPushConstantRange pushConstantRange = {};
|
||||
pushConstantRange.stageFlags = stageFlags;
|
||||
pushConstantRange.offset = offset;
|
||||
pushConstantRange.size = size;
|
||||
return pushConstantRange;
|
||||
}
|
||||
|
||||
VkPipelineShaderStageCreateInfo init::PipelineShaderStageCreateInfo(VkShaderStageFlagBits stage, VkShaderModule module, const char *entryName)
|
||||
{
|
||||
VkPipelineShaderStageCreateInfo info = {};
|
||||
info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
|
||||
info.module = module;
|
||||
info.stage = stage;
|
||||
info.pName = entryName;
|
||||
return info;
|
||||
}
|
||||
|
||||
VkBool32 Seele::Vulkan::debugCallback(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT, uint64_t, size_t, int32_t, const char *layerPrefix, const char *msg, void *)
|
||||
{
|
||||
if(flags & VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT)
|
||||
{
|
||||
return VK_FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cerr << layerPrefix << ": " << msg << std::endl;
|
||||
return VK_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
VkResult Seele::Vulkan::CreateDebugReportCallbackEXT(VkInstance instance, const VkDebugReportCallbackCreateInfoEXT *pCreateInfo, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT *pCallback)
|
||||
{
|
||||
auto func = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(instance, "vkCreateDebugReportCallbackEXT");
|
||||
if (func != nullptr)
|
||||
{
|
||||
return func(instance, pCreateInfo, pAllocator, pCallback);
|
||||
}
|
||||
else
|
||||
{
|
||||
return VK_ERROR_EXTENSION_NOT_PRESENT;
|
||||
}
|
||||
}
|
||||
|
||||
void Seele::Vulkan::DestroyDebugReportCallbackEXT(VkInstance instance, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT pCallback)
|
||||
{
|
||||
auto func = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(instance, "vkDestroyDebugReportCallbackEXT");
|
||||
if (func != nullptr)
|
||||
{
|
||||
func(instance, pCallback, pAllocator);
|
||||
}
|
||||
}
|
||||
@@ -1,302 +0,0 @@
|
||||
#pragma once
|
||||
#include "Containers/Array.h"
|
||||
#include <vulkan/vulkan.h>
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
namespace Vulkan
|
||||
{
|
||||
VkBool32 debugCallback(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT objType, uint64_t obj, size_t location, int32_t code, const char *layerPrefix, const char *msg, void *userData);
|
||||
|
||||
VkResult CreateDebugReportCallbackEXT(VkInstance instance, const VkDebugReportCallbackCreateInfoEXT *pCreateInfo, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT *pCallback);
|
||||
void DestroyDebugReportCallbackEXT(VkInstance instance, const VkAllocationCallbacks *pAllocator, VkDebugReportCallbackEXT pCallback);
|
||||
|
||||
namespace init
|
||||
{
|
||||
VkApplicationInfo ApplicationInfo(
|
||||
const char *appName,
|
||||
uint32_t appVersion,
|
||||
const char *engineName,
|
||||
uint32_t engineVersion,
|
||||
uint32_t apiVersion);
|
||||
|
||||
VkInstanceCreateInfo InstanceCreateInfo(
|
||||
VkApplicationInfo *appInfo,
|
||||
const Array<const char *> &extensions,
|
||||
const Array<const char *> &layers);
|
||||
|
||||
VkDebugReportCallbackCreateInfoEXT DebugReportCallbackCreateInfo(
|
||||
VkDebugReportFlagsEXT flags);
|
||||
|
||||
VkDeviceQueueCreateInfo DeviceQueueCreateInfo(
|
||||
int queueFamilyIndex,
|
||||
int queueCount);
|
||||
|
||||
VkDeviceQueueCreateInfo DeviceQueueCreateInfo(
|
||||
int queueFamilyIndex,
|
||||
int queueCount,
|
||||
float *queuePriority);
|
||||
|
||||
VkDeviceCreateInfo DeviceCreateInfo(
|
||||
VkDeviceQueueCreateInfo *queueInfos,
|
||||
uint32_t queueCount,
|
||||
VkPhysicalDeviceFeatures *features,
|
||||
const char *const *deviceExtensions,
|
||||
uint32_t deviceExtensionCount,
|
||||
const char *const *layers,
|
||||
uint32_t layerCount);
|
||||
|
||||
VkDeviceCreateInfo DeviceCreateInfo(
|
||||
VkDeviceQueueCreateInfo *queueInfos,
|
||||
uint32_t queueCount,
|
||||
VkPhysicalDeviceFeatures *features);
|
||||
|
||||
VkSwapchainCreateInfoKHR SwapchainCreateInfo(
|
||||
VkSurfaceKHR surface,
|
||||
uint32_t minImageCount,
|
||||
VkFormat imageFormat,
|
||||
VkColorSpaceKHR colorSpace,
|
||||
VkExtent2D extent,
|
||||
uint32_t arrayLayers,
|
||||
VkImageUsageFlags usage,
|
||||
VkSurfaceTransformFlagBitsKHR Transform,
|
||||
VkCompositeAlphaFlagBitsKHR alpha,
|
||||
VkPresentModeKHR presentMode,
|
||||
VkBool32 clipped);
|
||||
|
||||
VkSwapchainCreateInfoKHR SwapchainCreateInfo(
|
||||
VkSurfaceKHR surface,
|
||||
uint32_t minImageCount,
|
||||
VkFormat imageFormat,
|
||||
VkColorSpaceKHR colorSpace,
|
||||
uint32_t width,
|
||||
uint32_t height,
|
||||
uint32_t arrayLayers,
|
||||
VkImageUsageFlags usage,
|
||||
VkSurfaceTransformFlagBitsKHR Transform,
|
||||
VkCompositeAlphaFlagBitsKHR alpha,
|
||||
VkPresentModeKHR presentMode,
|
||||
VkBool32 clipped);
|
||||
|
||||
VkFramebufferCreateInfo FramebufferCreateInfo(
|
||||
VkRenderPass renderPass,
|
||||
uint32_t attachmentCount,
|
||||
VkImageView *attachments,
|
||||
uint32_t width,
|
||||
uint32_t height,
|
||||
uint32_t layers);
|
||||
|
||||
VkAttachmentDescription AttachmentDescription(
|
||||
VkFormat format,
|
||||
VkSampleCountFlagBits sample,
|
||||
VkAttachmentLoadOp loadOp,
|
||||
VkAttachmentStoreOp storeOp,
|
||||
VkAttachmentLoadOp stencilLoadOp,
|
||||
VkAttachmentStoreOp stencilStoreOp,
|
||||
VkImageLayout imageLayout,
|
||||
VkImageLayout finalLayout);
|
||||
|
||||
VkSubpassDescription SubpassDescription(
|
||||
VkPipelineBindPoint bindPoint,
|
||||
uint32_t colorAttachmentCount,
|
||||
VkAttachmentReference *colorReference,
|
||||
VkAttachmentReference *depthReference = nullptr,
|
||||
uint32_t inputAttachmentCount = 0,
|
||||
VkAttachmentReference *inputReference = nullptr,
|
||||
VkAttachmentReference *resolveReference = nullptr,
|
||||
uint32_t preserveAttachmentCount = 0,
|
||||
uint32_t *preserveReference = nullptr);
|
||||
|
||||
VkRenderPassCreateInfo RenderPassCreateInfo(
|
||||
uint32_t attachmentCount,
|
||||
const VkAttachmentDescription *attachments,
|
||||
uint32_t subpassCount,
|
||||
const VkSubpassDescription *subpasses,
|
||||
uint32_t dependencyCount,
|
||||
const VkSubpassDependency *subpassDependencies);
|
||||
|
||||
VkMemoryAllocateInfo MemoryAllocateInfo();
|
||||
|
||||
VkCommandBufferAllocateInfo CommandBufferAllocateInfo(
|
||||
VkCommandPool cmdPool,
|
||||
VkCommandBufferLevel level,
|
||||
uint32_t bufferCount);
|
||||
|
||||
VkCommandPoolCreateInfo CommandPoolCreateInfo();
|
||||
|
||||
VkCommandBufferBeginInfo CommandBufferBeginInfo();
|
||||
|
||||
VkCommandBufferInheritanceInfo CommandBufferInheritanceInfo();
|
||||
|
||||
VkRenderPassBeginInfo RenderPassBeginInfo();
|
||||
|
||||
VkRenderPassCreateInfo RenderPassCreateInfo();
|
||||
|
||||
VkImageMemoryBarrier ImageMemoryBarrier(VkImage image, VkImageLayout oldLayout, VkImageLayout newLayout, uint32_t srcQueue = VK_QUEUE_FAMILY_IGNORED, uint32_t dstQueue = VK_QUEUE_FAMILY_IGNORED);
|
||||
VkImageMemoryBarrier ImageMemoryBarrier();
|
||||
|
||||
VkBufferMemoryBarrier BufferMemoryBarrier();
|
||||
|
||||
VkMemoryBarrier MemoryBarrier();
|
||||
|
||||
VkImageCreateInfo ImageCreateInfo();
|
||||
|
||||
VkSamplerCreateInfo SamplerCreateInfo();
|
||||
|
||||
VkImageViewCreateInfo ImageViewCreateInfo();
|
||||
|
||||
VkSemaphoreCreateInfo SemaphoreCreateInfo();
|
||||
|
||||
VkFenceCreateInfo FenceCreateInfo(
|
||||
VkFenceCreateFlags flags);
|
||||
|
||||
VkEventCreateInfo EventCreateInfo();
|
||||
|
||||
VkSubmitInfo SubmitInfo();
|
||||
|
||||
VkImageSubresourceRange ImageSubresourceRange(
|
||||
VkImageAspectFlags aspect = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||
uint32_t startMip = 0);
|
||||
|
||||
VkViewport Viewport(
|
||||
float width,
|
||||
float height,
|
||||
float minDepth,
|
||||
float maxDepth);
|
||||
|
||||
VkRect2D Rect2D(
|
||||
int32_t width,
|
||||
int32_t height,
|
||||
int32_t offsetX,
|
||||
int32_t offsetY);
|
||||
|
||||
VkBufferCreateInfo BufferCreateInfo();
|
||||
|
||||
VkBufferCreateInfo BufferCreateInfo(
|
||||
VkBufferUsageFlags usage,
|
||||
VkDeviceSize size);
|
||||
|
||||
VkDescriptorPoolCreateInfo DescriptorPoolCreateInfo(
|
||||
uint32_t poolSizeCount,
|
||||
VkDescriptorPoolSize *pPoolSizes,
|
||||
uint32_t maxSets);
|
||||
|
||||
VkDescriptorPoolSize DescriptorPoolSize(
|
||||
VkDescriptorType type,
|
||||
uint32_t descriptorCount);
|
||||
|
||||
VkDescriptorSetLayoutBinding DescriptorSetLayoutBinding(
|
||||
VkDescriptorType type,
|
||||
VkShaderStageFlags stageFlags,
|
||||
uint32_t binding,
|
||||
uint32_t count);
|
||||
|
||||
VkDescriptorSetLayoutCreateInfo DescriptorSetLayoutCreateInfo(
|
||||
const VkDescriptorSetLayoutBinding *pBindings,
|
||||
uint32_t bindingCount);
|
||||
|
||||
VkPipelineLayoutCreateInfo PipelineLayoutCreateInfo(
|
||||
const VkDescriptorSetLayout *pSetLayouts,
|
||||
uint32_t setLayoutCount);
|
||||
|
||||
VkDescriptorSetAllocateInfo DescriptorSetAllocateInfo(
|
||||
VkDescriptorPool descriptorPool,
|
||||
const VkDescriptorSetLayout *pSetLayouts,
|
||||
uint32_t descriptorSetCount);
|
||||
|
||||
VkDescriptorBufferInfo DescriptorBufferInfo(
|
||||
VkBuffer buffer,
|
||||
VkDeviceSize offset,
|
||||
VkDeviceSize range);
|
||||
VkDescriptorImageInfo DescriptorImageInfo(
|
||||
VkSampler sampler,
|
||||
VkImageView imageView,
|
||||
VkImageLayout imageLayout);
|
||||
|
||||
VkWriteDescriptorSet WriteDescriptorSet(
|
||||
VkDescriptorSet dstSet,
|
||||
VkDescriptorType type,
|
||||
uint32_t binding,
|
||||
VkDescriptorBufferInfo *bufferInfo);
|
||||
|
||||
VkWriteDescriptorSet WriteDescriptorSet(
|
||||
VkDescriptorSet dstSet,
|
||||
VkDescriptorType type,
|
||||
uint32_t binding,
|
||||
VkDescriptorImageInfo *bufferInfo);
|
||||
|
||||
VkVertexInputBindingDescription VertexInputBindingDescription(
|
||||
uint32_t binding,
|
||||
uint32_t stride,
|
||||
VkVertexInputRate inputRate);
|
||||
|
||||
VkVertexInputAttributeDescription VertexInputAttributeDescription(
|
||||
uint32_t binding,
|
||||
uint32_t location,
|
||||
VkFormat format,
|
||||
uint32_t offset);
|
||||
|
||||
VkPipelineVertexInputStateCreateInfo PipelineVertexInputStateCreateInfo();
|
||||
|
||||
VkPipelineInputAssemblyStateCreateInfo PipelineInputAssemblyStateCreateInfo(
|
||||
VkPrimitiveTopology topology,
|
||||
VkPipelineInputAssemblyStateCreateFlags flags,
|
||||
VkBool32 primitiveRestartEnable);
|
||||
|
||||
VkPipelineRasterizationStateCreateInfo PipelineRasterizationStateCreateInfo(
|
||||
VkPolygonMode polygonMode,
|
||||
VkCullModeFlags cullMode,
|
||||
VkFrontFace frontFace,
|
||||
VkPipelineRasterizationStateCreateFlags flags);
|
||||
|
||||
VkPipelineColorBlendAttachmentState PipelineColorBlendAttachmentState(
|
||||
VkColorComponentFlags colorWriteMask,
|
||||
VkBool32 blendEnable);
|
||||
|
||||
VkPipelineColorBlendStateCreateInfo PipelineColorBlendStateCreateInfo(
|
||||
uint32_t attachmentCount,
|
||||
const VkPipelineColorBlendAttachmentState *pAttachments);
|
||||
|
||||
VkPipelineDepthStencilStateCreateInfo PipelineDepthStencilStateCreateInfo(
|
||||
VkBool32 depthTestEnable,
|
||||
VkBool32 depthWriteEnable,
|
||||
VkCompareOp depthCompareOp);
|
||||
|
||||
VkPipelineViewportStateCreateInfo PipelineViewportStateCreateInfo(
|
||||
uint32_t viewportCount,
|
||||
uint32_t scissorCount,
|
||||
VkPipelineViewportStateCreateFlags flags);
|
||||
|
||||
VkPipelineMultisampleStateCreateInfo PipelineMultisampleStateCreateInfo(
|
||||
VkSampleCountFlagBits rasterizationSamples,
|
||||
VkPipelineMultisampleStateCreateFlags flags);
|
||||
|
||||
VkPipelineDynamicStateCreateInfo PipelineDynamicStateCreateInfo(
|
||||
const VkDynamicState *pDynamicStates,
|
||||
uint32_t dynamicStateCount,
|
||||
VkPipelineDynamicStateCreateFlags flags);
|
||||
|
||||
VkPipelineTessellationStateCreateInfo PipelineTessellationStateCreateInfo(
|
||||
uint32_t patchControlPoints);
|
||||
|
||||
VkGraphicsPipelineCreateInfo PipelineCreateInfo(
|
||||
VkPipelineLayout layout,
|
||||
VkRenderPass renderPass,
|
||||
VkPipelineCreateFlags flags);
|
||||
|
||||
VkComputePipelineCreateInfo ComputePipelineCreateInfo(
|
||||
VkPipelineLayout layout,
|
||||
VkPipelineCreateFlags flags);
|
||||
|
||||
VkPushConstantRange PushConstantRange(
|
||||
VkShaderStageFlags stageFlags,
|
||||
uint32_t size,
|
||||
uint32_t offset);
|
||||
|
||||
VkPipelineShaderStageCreateInfo PipelineShaderStageCreateInfo(
|
||||
VkShaderStageFlagBits stage,
|
||||
VkShaderModule module,
|
||||
const char *entryName);
|
||||
} // namespace init
|
||||
} // namespace Vulkan
|
||||
} // namespace Seele
|
||||
@@ -1,5 +1,5 @@
|
||||
#include "Pipeline.h"
|
||||
#include "DescriptorSets.h"
|
||||
#include "Descriptor.h"
|
||||
#include "Graphics.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#pragma once
|
||||
#include "Enums.h"
|
||||
#include "Graphics/Resources.h"
|
||||
#include "Graphics/Pipeline.h"
|
||||
|
||||
namespace Seele
|
||||
{
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
#include "PipelineCache.h"
|
||||
#include "Graphics.h"
|
||||
#include "Enums.h"
|
||||
#include "Initializer.h"
|
||||
#include "RenderPass.h"
|
||||
#include "DescriptorSets.h"
|
||||
#include "Descriptor.h"
|
||||
#include "Shader.h"
|
||||
#include <fstream>
|
||||
|
||||
@@ -15,11 +14,12 @@ PipelineCache::PipelineCache(PGraphics graphics, const std::string& cacheFilePat
|
||||
, cacheFile(cacheFilePath)
|
||||
{
|
||||
std::ifstream stream(cacheFilePath, std::ios::binary | std::ios::ate);
|
||||
VkPipelineCacheCreateInfo cacheCreateInfo;
|
||||
cacheCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_CACHE_CREATE_INFO;
|
||||
cacheCreateInfo.pNext = nullptr;
|
||||
cacheCreateInfo.flags = 0;
|
||||
cacheCreateInfo.initialDataSize = 0;
|
||||
VkPipelineCacheCreateInfo cacheCreateInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_CACHE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.initialDataSize = 0,
|
||||
};
|
||||
if(stream.good())
|
||||
{
|
||||
Array<uint8> cacheData;
|
||||
@@ -52,41 +52,11 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
{
|
||||
PPipelineLayout layout = Gfx::PPipelineLayout(gfxInfo.pipelineLayout).cast<PipelineLayout>();
|
||||
uint32 hash = layout->getHash();
|
||||
VkPipelineVertexInputStateCreateInfo vertexInput =
|
||||
init::PipelineVertexInputStateCreateInfo();
|
||||
|
||||
Array<VkVertexInputBindingDescription> bindings;
|
||||
Array<VkVertexInputAttributeDescription> attributes;
|
||||
if (gfxInfo.vertexDeclaration != nullptr)
|
||||
{
|
||||
PVertexDeclaration decl = gfxInfo.vertexDeclaration.cast<VertexDeclaration>();
|
||||
for (const auto& elem : decl->elementList)
|
||||
{
|
||||
attributes.add(VkVertexInputAttributeDescription{
|
||||
.location = elem.attributeIndex,
|
||||
.binding = elem.binding,
|
||||
.format = cast(elem.vertexFormat),
|
||||
.offset = elem.offset,
|
||||
});
|
||||
auto res = bindings.find([elem](const VkVertexInputBindingDescription& b) {return b.binding == elem.binding; });
|
||||
if (res == bindings.end())
|
||||
{
|
||||
bindings.add({});
|
||||
res = bindings.end();
|
||||
}
|
||||
*res = VkVertexInputBindingDescription{
|
||||
.binding = elem.binding,
|
||||
.stride = elem.stride,
|
||||
.inputRate = elem.instanced ? VK_VERTEX_INPUT_RATE_INSTANCE : VK_VERTEX_INPUT_RATE_VERTEX,
|
||||
};
|
||||
}
|
||||
vertexInput.pVertexAttributeDescriptions = attributes.data();
|
||||
vertexInput.vertexAttributeDescriptionCount = attributes.size();
|
||||
vertexInput.pVertexBindingDescriptions = bindings.data();
|
||||
vertexInput.vertexBindingDescriptionCount = bindings.size();
|
||||
}
|
||||
hash = CRC::Calculate(bindings.data(), bindings.size() * sizeof(VkVertexInputBindingDescription), CRC::CRC_32(), hash);
|
||||
hash = CRC::Calculate(attributes.data(), attributes.size() * sizeof(VkVertexInputAttributeDescription), CRC::CRC_32(), hash);
|
||||
VkPipelineVertexInputStateCreateInfo vertexInput = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
};
|
||||
uint32 stageCount = 0;
|
||||
|
||||
VkPipelineShaderStageCreateInfo stageInfos[2];
|
||||
@@ -112,52 +82,64 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
};
|
||||
}
|
||||
hash = CRC::Calculate(stageInfos, sizeof(stageInfos), CRC::CRC_32(), hash);
|
||||
VkPipelineInputAssemblyStateCreateInfo assemblyInfo =
|
||||
init::PipelineInputAssemblyStateCreateInfo(
|
||||
cast(gfxInfo.topology),
|
||||
0,
|
||||
false
|
||||
);
|
||||
VkPipelineInputAssemblyStateCreateInfo assemblyInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.topology = cast(gfxInfo.topology),
|
||||
.primitiveRestartEnable = false,
|
||||
};
|
||||
hash = CRC::Calculate(&assemblyInfo, sizeof(assemblyInfo), CRC::CRC_32(), hash);
|
||||
VkPipelineViewportStateCreateInfo viewportInfo =
|
||||
init::PipelineViewportStateCreateInfo(
|
||||
1,
|
||||
1,
|
||||
0
|
||||
);
|
||||
VkPipelineViewportStateCreateInfo viewportInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.viewportCount = 1,
|
||||
.scissorCount = 1,
|
||||
};
|
||||
hash = CRC::Calculate(&viewportInfo, sizeof(viewportInfo), CRC::CRC_32(), hash);
|
||||
VkPipelineRasterizationStateCreateInfo rasterizationState =
|
||||
init::PipelineRasterizationStateCreateInfo(
|
||||
cast(gfxInfo.rasterizationState.polygonMode),
|
||||
gfxInfo.rasterizationState.cullMode,
|
||||
(VkFrontFace)gfxInfo.rasterizationState.frontFace,
|
||||
0
|
||||
);
|
||||
rasterizationState.depthBiasEnable = gfxInfo.rasterizationState.depthBiasEnable;
|
||||
rasterizationState.depthBiasClamp = gfxInfo.rasterizationState.depthBiasClamp;
|
||||
rasterizationState.depthBiasConstantFactor = gfxInfo.rasterizationState.depthBiasConstantFactor;
|
||||
rasterizationState.depthBiasSlopeFactor = gfxInfo.rasterizationState.depthBiasSlopeFactor;
|
||||
rasterizationState.depthClampEnable = gfxInfo.rasterizationState.depthClampEnable;
|
||||
rasterizationState.lineWidth = gfxInfo.rasterizationState.lineWidth;
|
||||
rasterizationState.rasterizerDiscardEnable = gfxInfo.rasterizationState.rasterizerDiscardEnable;
|
||||
VkPipelineRasterizationStateCreateInfo rasterizationState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.depthClampEnable = gfxInfo.rasterizationState.depthClampEnable,
|
||||
.rasterizerDiscardEnable = gfxInfo.rasterizationState.rasterizerDiscardEnable,
|
||||
.polygonMode = cast(gfxInfo.rasterizationState.polygonMode),
|
||||
.cullMode = gfxInfo.rasterizationState.cullMode,
|
||||
.frontFace = (VkFrontFace)gfxInfo.rasterizationState.frontFace,
|
||||
.depthBiasEnable = gfxInfo.rasterizationState.depthBiasEnable,
|
||||
.depthBiasConstantFactor = gfxInfo.rasterizationState.depthBiasConstantFactor,
|
||||
.depthBiasClamp = gfxInfo.rasterizationState.depthBiasClamp,
|
||||
.depthBiasSlopeFactor = gfxInfo.rasterizationState.depthBiasSlopeFactor,
|
||||
.lineWidth = 0,
|
||||
};
|
||||
hash = CRC::Calculate(&rasterizationState, sizeof(rasterizationState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineMultisampleStateCreateInfo multisampleState =
|
||||
init::PipelineMultisampleStateCreateInfo(
|
||||
(VkSampleCountFlagBits)gfxInfo.multisampleState.samples,
|
||||
0);
|
||||
multisampleState.alphaToCoverageEnable = gfxInfo.multisampleState.alphaCoverageEnable;
|
||||
multisampleState.alphaToOneEnable = gfxInfo.multisampleState.alphaToOneEnable;
|
||||
multisampleState.minSampleShading = gfxInfo.multisampleState.minSampleShading;
|
||||
multisampleState.sampleShadingEnable = gfxInfo.multisampleState.sampleShadingEnable;
|
||||
VkPipelineMultisampleStateCreateInfo multisampleState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.rasterizationSamples = (VkSampleCountFlagBits)gfxInfo.multisampleState.samples,
|
||||
.sampleShadingEnable = gfxInfo.multisampleState.sampleShadingEnable,
|
||||
.minSampleShading = gfxInfo.multisampleState.minSampleShading,
|
||||
.alphaToCoverageEnable = gfxInfo.multisampleState.alphaCoverageEnable,
|
||||
.alphaToOneEnable = gfxInfo.multisampleState.alphaToOneEnable,
|
||||
};
|
||||
hash = CRC::Calculate(&multisampleState, sizeof(multisampleState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDepthStencilStateCreateInfo depthStencilState =
|
||||
init::PipelineDepthStencilStateCreateInfo(
|
||||
gfxInfo.depthStencilState.depthTestEnable,
|
||||
gfxInfo.depthStencilState.depthWriteEnable,
|
||||
cast(gfxInfo.depthStencilState.depthCompareOp)
|
||||
);
|
||||
VkPipelineDepthStencilStateCreateInfo depthStencilState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.depthTestEnable = gfxInfo.depthStencilState.depthTestEnable,
|
||||
.depthWriteEnable = gfxInfo.depthStencilState.depthWriteEnable,
|
||||
.depthCompareOp = cast(gfxInfo.depthStencilState.depthCompareOp),
|
||||
.depthBoundsTestEnable = gfxInfo.depthStencilState.depthBoundsTestEnable,
|
||||
.front = (VkStencilOp)gfxInfo.depthStencilState.front,
|
||||
.back = (VkStencilOp)gfxInfo.depthStencilState.back,
|
||||
.minDepthBounds = gfxInfo.depthStencilState.minDepthBounds,
|
||||
.maxDepthBounds = gfxInfo.depthStencilState.maxDepthBounds,
|
||||
};
|
||||
hash = CRC::Calculate(&depthStencilState, sizeof(depthStencilState), CRC::CRC_32(), hash);
|
||||
|
||||
const auto& colorAttachments = gfxInfo.renderPass->getLayout()->colorAttachments;
|
||||
@@ -178,14 +160,16 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
}
|
||||
hash = CRC::Calculate(blendAttachments.data(), blendAttachments.size() * sizeof(VkPipelineColorBlendAttachmentState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineColorBlendStateCreateInfo blendState =
|
||||
init::PipelineColorBlendStateCreateInfo(
|
||||
(uint32)blendAttachments.size(),
|
||||
blendAttachments.data()
|
||||
);
|
||||
blendState.logicOpEnable = gfxInfo.colorBlend.logicOpEnable;
|
||||
blendState.logicOp = (VkLogicOp)gfxInfo.colorBlend.logicOp;
|
||||
std::memcpy(blendState.blendConstants, gfxInfo.colorBlend.blendConstants, sizeof(gfxInfo.colorBlend.blendConstants));
|
||||
VkPipelineColorBlendStateCreateInfo blendState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.logicOpEnable = gfxInfo.colorBlend.logicOpEnable,
|
||||
.logicOp = (VkLogicOp)gfxInfo.colorBlend.logicOp,
|
||||
.attachmentCount = (uint32)blendAttachments.size(),
|
||||
.pAttachments = blendAttachments.data(),
|
||||
};
|
||||
std::memcpy(blendState.blendConstants, gfxInfo.colorBlend.blendConstants.data(), sizeof(blendState.blendConstants));
|
||||
|
||||
uint32 numDynamicEnabled = 0;
|
||||
StaticArray<VkDynamicState, 2> dynamicEnabled;
|
||||
@@ -193,12 +177,12 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::LegacyPipelineCreateInfo gf
|
||||
dynamicEnabled[numDynamicEnabled++] = VK_DYNAMIC_STATE_SCISSOR;
|
||||
hash = CRC::Calculate(dynamicEnabled.data(), dynamicEnabled.size() * sizeof(VkDynamicState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDynamicStateCreateInfo dynamicState =
|
||||
init::PipelineDynamicStateCreateInfo(
|
||||
dynamicEnabled.data(),
|
||||
numDynamicEnabled,
|
||||
0
|
||||
);
|
||||
VkPipelineDynamicStateCreateInfo dynamicState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.dynamicStateCount = (uint32)dynamicEnabled.size(),
|
||||
.pDynamicStates = dynamicEnabled.data(),
|
||||
};
|
||||
|
||||
if (graphicsPipelines.contains(hash))
|
||||
{
|
||||
@@ -278,46 +262,56 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::MeshPipelineCreateInfo gfxI
|
||||
}
|
||||
hash = CRC::Calculate(stageInfos, sizeof(stageInfos), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineViewportStateCreateInfo viewportInfo =
|
||||
init::PipelineViewportStateCreateInfo(
|
||||
1,
|
||||
1,
|
||||
0
|
||||
);
|
||||
VkPipelineViewportStateCreateInfo viewportInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.viewportCount = 1,
|
||||
.scissorCount = 1,
|
||||
};
|
||||
hash = CRC::Calculate(&viewportInfo, sizeof(viewportInfo), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineRasterizationStateCreateInfo rasterizationState =
|
||||
init::PipelineRasterizationStateCreateInfo(
|
||||
cast(gfxInfo.rasterizationState.polygonMode),
|
||||
gfxInfo.rasterizationState.cullMode,
|
||||
(VkFrontFace)gfxInfo.rasterizationState.frontFace,
|
||||
0
|
||||
);
|
||||
rasterizationState.depthBiasEnable = gfxInfo.rasterizationState.depthBiasEnable;
|
||||
rasterizationState.depthBiasClamp = gfxInfo.rasterizationState.depthBiasClamp;
|
||||
rasterizationState.depthBiasConstantFactor = gfxInfo.rasterizationState.depthBiasConstantFactor;
|
||||
rasterizationState.depthBiasSlopeFactor = gfxInfo.rasterizationState.depthBiasSlopeFactor;
|
||||
rasterizationState.depthClampEnable = gfxInfo.rasterizationState.depthClampEnable;
|
||||
rasterizationState.lineWidth = gfxInfo.rasterizationState.lineWidth;
|
||||
rasterizationState.rasterizerDiscardEnable = gfxInfo.rasterizationState.rasterizerDiscardEnable;
|
||||
VkPipelineRasterizationStateCreateInfo rasterizationState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.depthClampEnable = gfxInfo.rasterizationState.depthClampEnable,
|
||||
.rasterizerDiscardEnable = gfxInfo.rasterizationState.rasterizerDiscardEnable,
|
||||
.polygonMode = cast(gfxInfo.rasterizationState.polygonMode),
|
||||
.cullMode = gfxInfo.rasterizationState.cullMode,
|
||||
.frontFace = (VkFrontFace)gfxInfo.rasterizationState.frontFace,
|
||||
.depthBiasEnable = gfxInfo.rasterizationState.depthBiasEnable,
|
||||
.depthBiasConstantFactor = gfxInfo.rasterizationState.depthBiasConstantFactor,
|
||||
.depthBiasClamp = gfxInfo.rasterizationState.depthBiasClamp,
|
||||
.depthBiasSlopeFactor = gfxInfo.rasterizationState.depthBiasSlopeFactor,
|
||||
.lineWidth = 0,
|
||||
};
|
||||
hash = CRC::Calculate(&rasterizationState, sizeof(rasterizationState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineMultisampleStateCreateInfo multisampleState =
|
||||
init::PipelineMultisampleStateCreateInfo(
|
||||
(VkSampleCountFlagBits)gfxInfo.multisampleState.samples,
|
||||
0);
|
||||
multisampleState.alphaToCoverageEnable = gfxInfo.multisampleState.alphaCoverageEnable;
|
||||
multisampleState.alphaToOneEnable = gfxInfo.multisampleState.alphaToOneEnable;
|
||||
multisampleState.minSampleShading = gfxInfo.multisampleState.minSampleShading;
|
||||
multisampleState.sampleShadingEnable = gfxInfo.multisampleState.sampleShadingEnable;
|
||||
VkPipelineMultisampleStateCreateInfo multisampleState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.rasterizationSamples = (VkSampleCountFlagBits)gfxInfo.multisampleState.samples,
|
||||
.sampleShadingEnable = gfxInfo.multisampleState.sampleShadingEnable,
|
||||
.minSampleShading = gfxInfo.multisampleState.minSampleShading,
|
||||
.alphaToCoverageEnable = gfxInfo.multisampleState.alphaCoverageEnable,
|
||||
.alphaToOneEnable = gfxInfo.multisampleState.alphaToOneEnable,
|
||||
};
|
||||
hash = CRC::Calculate(&multisampleState, sizeof(multisampleState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDepthStencilStateCreateInfo depthStencilState =
|
||||
init::PipelineDepthStencilStateCreateInfo(
|
||||
gfxInfo.depthStencilState.depthTestEnable,
|
||||
gfxInfo.depthStencilState.depthWriteEnable,
|
||||
cast(gfxInfo.depthStencilState.depthCompareOp)
|
||||
);
|
||||
VkPipelineDepthStencilStateCreateInfo depthStencilState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.depthTestEnable = gfxInfo.depthStencilState.depthTestEnable,
|
||||
.depthWriteEnable = gfxInfo.depthStencilState.depthWriteEnable,
|
||||
.depthCompareOp = cast(gfxInfo.depthStencilState.depthCompareOp),
|
||||
.depthBoundsTestEnable = gfxInfo.depthStencilState.depthBoundsTestEnable,
|
||||
.front = (VkStencilOp)gfxInfo.depthStencilState.front,
|
||||
.back = (VkStencilOp)gfxInfo.depthStencilState.back,
|
||||
.minDepthBounds = gfxInfo.depthStencilState.minDepthBounds,
|
||||
.maxDepthBounds = gfxInfo.depthStencilState.maxDepthBounds,
|
||||
};
|
||||
hash = CRC::Calculate(&depthStencilState, sizeof(depthStencilState), CRC::CRC_32(), hash);
|
||||
|
||||
const auto& colorAttachments = gfxInfo.renderPass->getLayout()->colorAttachments;
|
||||
@@ -338,14 +332,16 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::MeshPipelineCreateInfo gfxI
|
||||
}
|
||||
hash = CRC::Calculate(blendAttachments.data(), blendAttachments.size() * sizeof(VkPipelineColorBlendAttachmentState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineColorBlendStateCreateInfo blendState =
|
||||
init::PipelineColorBlendStateCreateInfo(
|
||||
(uint32)blendAttachments.size(),
|
||||
blendAttachments.data()
|
||||
);
|
||||
blendState.logicOpEnable = gfxInfo.colorBlend.logicOpEnable;
|
||||
blendState.logicOp = (VkLogicOp)gfxInfo.colorBlend.logicOp;
|
||||
std::memcpy(blendState.blendConstants, gfxInfo.colorBlend.blendConstants, sizeof(gfxInfo.colorBlend.blendConstants));
|
||||
VkPipelineColorBlendStateCreateInfo blendState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.logicOpEnable = gfxInfo.colorBlend.logicOpEnable,
|
||||
.logicOp = (VkLogicOp)gfxInfo.colorBlend.logicOp,
|
||||
.attachmentCount = (uint32)blendAttachments.size(),
|
||||
.pAttachments = blendAttachments.data(),
|
||||
};
|
||||
std::memcpy(blendState.blendConstants, gfxInfo.colorBlend.blendConstants.data(), sizeof(blendState.blendConstants));
|
||||
|
||||
uint32 numDynamicEnabled = 0;
|
||||
StaticArray<VkDynamicState, 2> dynamicEnabled;
|
||||
@@ -353,12 +349,12 @@ PGraphicsPipeline PipelineCache::createPipeline(Gfx::MeshPipelineCreateInfo gfxI
|
||||
dynamicEnabled[numDynamicEnabled++] = VK_DYNAMIC_STATE_SCISSOR;
|
||||
hash = CRC::Calculate(dynamicEnabled.data(), dynamicEnabled.size() * sizeof(VkDynamicState), CRC::CRC_32(), hash);
|
||||
|
||||
VkPipelineDynamicStateCreateInfo dynamicState =
|
||||
init::PipelineDynamicStateCreateInfo(
|
||||
dynamicEnabled.data(),
|
||||
numDynamicEnabled,
|
||||
0
|
||||
);
|
||||
VkPipelineDynamicStateCreateInfo dynamicState = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.dynamicStateCount = (uint32)dynamicEnabled.size(),
|
||||
.pDynamicStates = dynamicEnabled.data(),
|
||||
};
|
||||
|
||||
if (graphicsPipelines.contains(hash))
|
||||
{
|
||||
@@ -409,10 +405,14 @@ PComputePipeline PipelineCache::createPipeline(Gfx::ComputePipelineCreateInfo co
|
||||
.sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO,
|
||||
.pNext = 0,
|
||||
.flags = 0,
|
||||
.stage = init::PipelineShaderStageCreateInfo(
|
||||
VK_SHADER_STAGE_COMPUTE_BIT,
|
||||
computeStage->getModuleHandle(),
|
||||
computeStage->getEntryPointName()),
|
||||
.stage = {
|
||||
.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.stage = VK_SHADER_STAGE_COMPUTE_BIT,
|
||||
.module = computeStage->getModuleHandle(),
|
||||
.pName = computeStage->getEntryPointName(),
|
||||
},
|
||||
.layout = layout->getHandle(),
|
||||
.basePipelineHandle = VK_NULL_HANDLE,
|
||||
.basePipelineIndex = 0,
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
#include "Queue.h"
|
||||
#include "Initializer.h"
|
||||
#include "Graphics.h"
|
||||
#include "Allocator.h"
|
||||
#include "CommandBuffer.h"
|
||||
#include "Command.h"
|
||||
|
||||
using namespace Seele;
|
||||
using namespace Seele::Vulkan;
|
||||
@@ -19,45 +18,46 @@ Queue::~Queue()
|
||||
{
|
||||
}
|
||||
|
||||
void Queue::submitCommandBuffer(PCmdBuffer cmdBuffer, uint32 numSignalSemaphores, VkSemaphore *signalSemaphores)
|
||||
void Queue::submitCommandBuffer(PCommand command, uint32 numSignalSemaphores, VkSemaphore *signalSemaphores)
|
||||
{
|
||||
std::scoped_lock lck(queueLock);
|
||||
assert(cmdBuffer->state == Command::State::End);
|
||||
std::unique_lock lock(queueLock);
|
||||
assert(command->state == Command::State::End);
|
||||
|
||||
PFence fence = cmdBuffer->fence;
|
||||
PFence fence = command->fence;
|
||||
assert(!fence->isSignaled());
|
||||
|
||||
const VkCommandBuffer cmdBuffers[] = {cmdBuffer->handle};
|
||||
|
||||
VkSubmitInfo submitInfo =
|
||||
init::SubmitInfo();
|
||||
submitInfo.commandBufferCount = 1;
|
||||
submitInfo.pCommandBuffers = cmdBuffers;
|
||||
submitInfo.signalSemaphoreCount = static_cast<uint32>(numSignalSemaphores);
|
||||
submitInfo.pSignalSemaphores = signalSemaphores;
|
||||
VkCommandBuffer cmdHandle = command->handle;
|
||||
|
||||
Array<VkSemaphore> waitSemaphores;
|
||||
if (cmdBuffer->waitSemaphores.size() > 0)
|
||||
if (command->waitSemaphores.size() > 0)
|
||||
{
|
||||
for (PSemaphore semaphore : cmdBuffer->waitSemaphores)
|
||||
for (PSemaphore semaphore : command->waitSemaphores)
|
||||
{
|
||||
waitSemaphores.add(semaphore->getHandle());
|
||||
}
|
||||
submitInfo.waitSemaphoreCount = static_cast<uint32>(cmdBuffer->waitSemaphores.size());
|
||||
submitInfo.pWaitSemaphores = waitSemaphores.data();
|
||||
submitInfo.pWaitDstStageMask = cmdBuffer->waitFlags.data();
|
||||
}
|
||||
|
||||
VkSubmitInfo submitInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO,
|
||||
.pNext = nullptr,
|
||||
.waitSemaphoreCount = static_cast<uint32>(command->waitSemaphores.size()),
|
||||
.pWaitSemaphores = waitSemaphores.data(),
|
||||
.pWaitDstStageMask = command->waitFlags.data(),
|
||||
.commandBufferCount = 1,
|
||||
.pCommandBuffers = &cmdHandle,
|
||||
.signalSemaphoreCount = static_cast<uint32>(numSignalSemaphores),
|
||||
.pSignalSemaphores = signalSemaphores,
|
||||
};
|
||||
|
||||
VK_CHECK(vkQueueSubmit(queue, 1, &submitInfo, fence->getHandle()));
|
||||
cmdBuffer->state = Command::State::Submit;
|
||||
cmdBuffer->waitFlags.clear();
|
||||
cmdBuffer->waitSemaphores.clear();
|
||||
command->state = Command::State::Submit;
|
||||
command->waitFlags.clear();
|
||||
command->waitSemaphores.clear();
|
||||
|
||||
if (Gfx::waitIdleOnSubmit)
|
||||
{
|
||||
fence->wait(200 * 1000ull);
|
||||
}
|
||||
|
||||
cmdBuffer->checkFence();
|
||||
graphics->getStagingManager()->clearPending();
|
||||
|
||||
command->checkFence();
|
||||
}
|
||||
@@ -12,16 +12,16 @@ class Queue
|
||||
public:
|
||||
Queue(PGraphics graphics, Gfx::QueueType queueType, uint32 familyIndex, uint32 queueIndex);
|
||||
virtual ~Queue();
|
||||
void submitCommandBuffer(PCmdBuffer cmdBuffer, uint32 numSignalSemaphores = 0, VkSemaphore *signalSemaphore = nullptr);
|
||||
inline void submitCommandBuffer(PCmdBuffer cmdBuffer, VkSemaphore signalSemaphore)
|
||||
void submitCommandBuffer(PCommand command, uint32 numSignalSemaphores = 0, VkSemaphore *signalSemaphore = nullptr);
|
||||
void submitCommandBuffer(PCommand command, VkSemaphore signalSemaphore)
|
||||
{
|
||||
submitCommandBuffer(cmdBuffer, 1, &signalSemaphore);
|
||||
submitCommandBuffer(command, 1, &signalSemaphore);
|
||||
}
|
||||
uint32 getFamilyIndex() const
|
||||
constexpr uint32 getFamilyIndex() const
|
||||
{
|
||||
return familyIndex;
|
||||
}
|
||||
inline VkQueue getHandle() const
|
||||
constexpr VkQueue getHandle() const
|
||||
{
|
||||
return queue;
|
||||
}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
#include "RenderPass.h"
|
||||
#include "Initializer.h"
|
||||
#include "Graphics.h"
|
||||
#include "Framebuffer.h"
|
||||
#include "Texture.h"
|
||||
@@ -25,107 +24,104 @@ RenderPass::RenderPass(PGraphics graphics, Gfx::ORenderTargetLayout _layout, Gfx
|
||||
for (auto& inputAttachment : layout->inputAttachments)
|
||||
{
|
||||
PTexture2D image = inputAttachment->getTexture().cast<Texture2D>();
|
||||
VkAttachmentDescription& desc = attachments.add();
|
||||
desc.flags = 0;
|
||||
desc.format = cast(image->getFormat());
|
||||
desc.storeOp = cast(inputAttachment->getStoreOp());
|
||||
desc.loadOp = cast(inputAttachment->getLoadOp());
|
||||
desc.stencilStoreOp = cast(inputAttachment->getStencilStoreOp());
|
||||
desc.stencilLoadOp = cast(inputAttachment->getStencilLoadOp());
|
||||
desc.initialLayout = image->isDepthStencil() ? VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL : VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
|
||||
desc.finalLayout = desc.initialLayout;
|
||||
|
||||
VkAttachmentReference &ref = inputRefs.add();
|
||||
ref.layout = desc.initialLayout;
|
||||
ref.attachment = attachmentCounter;
|
||||
attachmentCounter++;
|
||||
VkAttachmentDescription& desc = attachments.add() = {
|
||||
.flags = 0,
|
||||
.format = cast(image->getFormat()),
|
||||
.loadOp = cast(inputAttachment->getLoadOp()),
|
||||
.storeOp = cast(inputAttachment->getStoreOp()),
|
||||
.stencilLoadOp = cast(inputAttachment->getStencilLoadOp()),
|
||||
.stencilStoreOp = cast(inputAttachment->getStencilStoreOp()),
|
||||
.initialLayout = image->isDepthStencil() ? VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL : VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
|
||||
.finalLayout = desc.initialLayout,
|
||||
};
|
||||
|
||||
inputRefs.add() = {
|
||||
.attachment = attachmentCounter++,
|
||||
.layout = desc.initialLayout,
|
||||
};
|
||||
}
|
||||
for (auto& colorAttachment : layout->colorAttachments)
|
||||
{
|
||||
VkAttachmentDescription& desc = attachments.add();
|
||||
desc.flags = 0;
|
||||
desc.samples = (VkSampleCountFlagBits)colorAttachment->getNumSamples();
|
||||
desc.format = cast(colorAttachment->getFormat());
|
||||
desc.storeOp = cast(colorAttachment->getStoreOp());
|
||||
desc.loadOp = cast(colorAttachment->getLoadOp());
|
||||
desc.stencilStoreOp = cast(colorAttachment->getStencilStoreOp());
|
||||
desc.stencilLoadOp = cast(colorAttachment->getStencilLoadOp());
|
||||
desc.initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
|
||||
desc.finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
|
||||
|
||||
attachments.add() = {
|
||||
.flags = 0,
|
||||
.format = cast(colorAttachment->getFormat()),
|
||||
.samples = (VkSampleCountFlagBits)colorAttachment->getNumSamples(),
|
||||
.loadOp = cast(colorAttachment->getLoadOp()),
|
||||
.storeOp = cast(colorAttachment->getStoreOp()),
|
||||
.stencilLoadOp = cast(colorAttachment->getStencilLoadOp()),
|
||||
.stencilStoreOp = cast(colorAttachment->getStencilStoreOp()),
|
||||
.initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
|
||||
.finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
|
||||
};
|
||||
|
||||
VkClearValue& clearValue = clearValues.add();
|
||||
if(desc.loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR)
|
||||
if(attachments.back().loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR)
|
||||
{
|
||||
clearValue = cast(colorAttachment->clear);
|
||||
}
|
||||
|
||||
VkAttachmentReference &ref = colorRefs.add();
|
||||
ref.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
|
||||
ref.attachment = attachmentCounter;
|
||||
attachmentCounter++;
|
||||
colorRefs.add() = {
|
||||
.attachment = attachmentCounter++,
|
||||
.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
|
||||
};
|
||||
}
|
||||
if (layout->depthAttachment != nullptr)
|
||||
{
|
||||
PTexture2D image = layout->depthAttachment->getTexture().cast<Texture2D>();
|
||||
VkAttachmentDescription& desc = attachments.add();
|
||||
desc.flags = 0;
|
||||
desc.samples = (VkSampleCountFlagBits)image->getNumSamples();
|
||||
desc.format = cast(image->getFormat());
|
||||
desc.storeOp = cast(layout->depthAttachment->getStoreOp());
|
||||
desc.loadOp = cast(layout->depthAttachment->getLoadOp());
|
||||
desc.stencilStoreOp = cast(layout->depthAttachment->getStencilStoreOp());
|
||||
desc.stencilLoadOp = cast(layout->depthAttachment->getStencilLoadOp());
|
||||
desc.initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
|
||||
desc.finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
|
||||
|
||||
attachments.add() = {
|
||||
.flags = 0,
|
||||
.format = cast(image->getFormat()),
|
||||
.samples = (VkSampleCountFlagBits)image->getNumSamples(),
|
||||
.loadOp = cast(layout->depthAttachment->getLoadOp()),
|
||||
.storeOp = cast(layout->depthAttachment->getStoreOp()),
|
||||
.stencilLoadOp = cast(layout->depthAttachment->getStencilLoadOp()),
|
||||
.stencilStoreOp = cast(layout->depthAttachment->getStencilStoreOp()),
|
||||
.initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
|
||||
.finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
|
||||
};
|
||||
|
||||
VkClearValue& clearValue = clearValues.add();
|
||||
if(desc.loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR)
|
||||
if(attachments.back().loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR)
|
||||
{
|
||||
clearValue = cast(layout->depthAttachment->clear);
|
||||
}
|
||||
|
||||
VkAttachmentReference &ref = depthRef;
|
||||
ref.layout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
|
||||
ref.attachment = attachmentCounter;
|
||||
attachmentCounter++;
|
||||
depthRef = {
|
||||
.attachment = attachmentCounter++,
|
||||
.layout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
|
||||
};
|
||||
}
|
||||
VkSubpassDescription subPassDesc =
|
||||
init::SubpassDescription(
|
||||
VK_PIPELINE_BIND_POINT_GRAPHICS,
|
||||
(uint32)colorRefs.size(),
|
||||
colorRefs.data(),
|
||||
&depthRef,
|
||||
(uint32)inputRefs.size(),
|
||||
inputRefs.data());
|
||||
VkSubpassDependency dependency = {};
|
||||
dependency.srcSubpass = VK_SUBPASS_EXTERNAL;
|
||||
dependency.dstSubpass = 0;
|
||||
|
||||
dependency.srcStageMask = VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT;
|
||||
dependency.srcAccessMask = VK_ACCESS_MEMORY_READ_BIT;
|
||||
|
||||
dependency.dstStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
|
||||
dependency.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT;
|
||||
|
||||
VkRenderPassCreateInfo info =
|
||||
init::RenderPassCreateInfo(
|
||||
(uint32)attachments.size(),
|
||||
attachments.data(),
|
||||
1,
|
||||
&subPassDesc,
|
||||
1,
|
||||
&dependency);
|
||||
VkSubpassDescription subPassDesc = {
|
||||
.flags = 0,
|
||||
.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS,
|
||||
.inputAttachmentCount = (uint32)inputRefs.size(),
|
||||
.pInputAttachments = inputRefs.data(),
|
||||
.colorAttachmentCount = (uint32)colorRefs.size(),
|
||||
.pColorAttachments = colorRefs.data(),
|
||||
.pDepthStencilAttachment = &depthRef,
|
||||
};
|
||||
VkSubpassDependency dependency = {
|
||||
.srcSubpass = VK_SUBPASS_EXTERNAL,
|
||||
.dstSubpass = 0,
|
||||
.srcStageMask = VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
|
||||
.dstStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
|
||||
.srcAccessMask = VK_ACCESS_MEMORY_READ_BIT,
|
||||
.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
|
||||
};
|
||||
|
||||
VkRenderPassCreateInfo info = {
|
||||
.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.attachmentCount = (uint32)attachments.size(),
|
||||
.pAttachments = attachments.data(),
|
||||
.subpassCount = 1,
|
||||
.pSubpasses = &subPassDesc,
|
||||
.dependencyCount = 1,
|
||||
.pDependencies = &dependency,
|
||||
};
|
||||
|
||||
VK_CHECK(vkCreateRenderPass(graphics->getDevice(), &info, nullptr, &renderPass));
|
||||
}
|
||||
|
||||
RenderPass::~RenderPass()
|
||||
{
|
||||
vkDestroyRenderPass(graphics->getDevice(), renderPass, nullptr);
|
||||
}
|
||||
|
||||
uint32 RenderPass::getFramebufferHash()
|
||||
{
|
||||
FramebufferDescription description;
|
||||
std::memset(&description, 0, sizeof(FramebufferDescription));
|
||||
for (auto& inputAttachment : layout->inputAttachments)
|
||||
@@ -143,6 +139,11 @@ uint32 RenderPass::getFramebufferHash()
|
||||
PTexture2D tex = layout->depthAttachment->getTexture().cast<Texture2D>();
|
||||
description.depthAttachment = tex->getView();
|
||||
}
|
||||
return CRC::Calculate(&description, sizeof(FramebufferDescription), CRC::CRC_32());
|
||||
framebufferHash = CRC::Calculate(&description, sizeof(FramebufferDescription), CRC::CRC_32());
|
||||
}
|
||||
|
||||
RenderPass::~RenderPass()
|
||||
{
|
||||
vkDestroyRenderPass(graphics->getDevice(), renderPass, nullptr);
|
||||
}
|
||||
|
||||
|
||||
@@ -11,28 +11,32 @@ class RenderPass : public Gfx::RenderPass
|
||||
public:
|
||||
RenderPass(PGraphics graphics, Gfx::ORenderTargetLayout layout, Gfx::PViewport viewport);
|
||||
virtual ~RenderPass();
|
||||
uint32 getFramebufferHash();
|
||||
inline VkRenderPass getHandle() const
|
||||
constexpr uint32 getFramebufferHash() const
|
||||
{
|
||||
return framebufferHash;
|
||||
}
|
||||
constexpr VkRenderPass getHandle() const
|
||||
{
|
||||
return renderPass;
|
||||
}
|
||||
inline size_t getClearValueCount() const
|
||||
constexpr size_t getClearValueCount() const
|
||||
{
|
||||
return clearValues.size();
|
||||
}
|
||||
inline VkClearValue *getClearValues() const
|
||||
constexpr VkClearValue *getClearValues() const
|
||||
{
|
||||
return clearValues.data();
|
||||
}
|
||||
inline VkRect2D getRenderArea() const
|
||||
constexpr VkRect2D getRenderArea() const
|
||||
{
|
||||
return renderArea;
|
||||
}
|
||||
inline VkSubpassContents getSubpassContents() const
|
||||
constexpr VkSubpassContents getSubpassContents() const
|
||||
{
|
||||
return subpassContents;
|
||||
}
|
||||
private:
|
||||
uint32 framebufferHash;
|
||||
PGraphics graphics;
|
||||
VkRenderPass renderPass;
|
||||
Array<VkClearValue> clearValues;
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
#include "RenderTarget.h"
|
||||
#include "Resources.h"
|
||||
#include "Graphics.h"
|
||||
#include "Initializer.h"
|
||||
#include "Enums.h"
|
||||
#include "CommandBuffer.h"
|
||||
#include "Command.h"
|
||||
#include <GLFW/glfw3.h>
|
||||
|
||||
using namespace Seele;
|
||||
@@ -184,11 +183,13 @@ void Window::advanceBackBuffer()
|
||||
|
||||
backBufferImages[currentImageIndex]->changeLayout(Gfx::SE_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);
|
||||
VkClearColorValue clearColor = {0.0f, 0.0f, 0.0f, 0.0f};
|
||||
PCmdBuffer cmdBuffer = graphics->getGraphicsCommands()->getCommands();
|
||||
VkImageSubresourceRange range = init::ImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT);
|
||||
PCommand command = graphics->getGraphicsCommands()->getCommands();
|
||||
VkImageSubresourceRange range = {
|
||||
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||
};
|
||||
vkCmdClearColorImage(
|
||||
cmdBuffer->getHandle(),
|
||||
backBufferImages[currentImageIndex]->getHandle(),
|
||||
command->getHandle(),
|
||||
backBufferHandles[currentImageIndex],
|
||||
VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
|
||||
&clearColor,
|
||||
1,
|
||||
@@ -264,23 +265,26 @@ void Window::createSwapchain()
|
||||
throw new std::logic_error("Trying to buffer more than the maximum number of frames");
|
||||
}
|
||||
|
||||
VkExtent2D extent = {
|
||||
.width = getWidth(),
|
||||
.height = getHeight(),
|
||||
VkSwapchainCreateInfoKHR swapchainInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.surface = surface,
|
||||
.minImageCount = desiredNumBuffers,
|
||||
.imageFormat = surfaceFormat.format,
|
||||
.imageColorSpace = surfaceFormat.colorSpace,
|
||||
.imageExtent = {
|
||||
.width = getWidth(),
|
||||
.height = getHeight(),
|
||||
},
|
||||
.imageArrayLayers = 1,
|
||||
.imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT,
|
||||
.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE,
|
||||
.preTransform = VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR,
|
||||
.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR,
|
||||
.presentMode = presentMode,
|
||||
.clipped = VK_TRUE,
|
||||
};
|
||||
VkSwapchainCreateInfoKHR swapchainInfo =
|
||||
init::SwapchainCreateInfo(
|
||||
surface,
|
||||
desiredNumBuffers,
|
||||
surfaceFormat.format,
|
||||
surfaceFormat.colorSpace,
|
||||
extent,
|
||||
1,
|
||||
VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT,
|
||||
VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR,
|
||||
VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR,
|
||||
presentMode,
|
||||
VK_TRUE);
|
||||
VK_CHECK(vkCreateSwapchainKHR(graphics->getDevice(), &swapchainInfo, nullptr, &swapchain));
|
||||
|
||||
uint32 numSwapchainImages;
|
||||
@@ -289,24 +293,34 @@ void Window::createSwapchain()
|
||||
VK_CHECK(vkGetSwapchainImagesKHR(graphics->getDevice(), swapchain, &numSwapchainImages, swapchainImages.data()));
|
||||
|
||||
|
||||
TextureCreateInfo backBufferCreateInfo;
|
||||
backBufferCreateInfo.width = getWidth();
|
||||
backBufferCreateInfo.height = getHeight();
|
||||
backBufferCreateInfo.usage = Gfx::SE_IMAGE_USAGE_COLOR_ATTACHMENT_BIT;
|
||||
backBufferCreateInfo.sourceData.owner = Gfx::QueueType::GRAPHICS;
|
||||
backBufferCreateInfo.format = cast(surfaceFormat.format);
|
||||
TextureCreateInfo backBufferCreateInfo = {
|
||||
.sourceData = {
|
||||
.owner = Gfx::QueueType::GRAPHICS,
|
||||
},
|
||||
.format = cast(surfaceFormat.format),
|
||||
.width = getWidth(),
|
||||
.height = getHeight(),
|
||||
.usage = Gfx::SE_IMAGE_USAGE_COLOR_ATTACHMENT_BIT,
|
||||
};
|
||||
for (uint32 i = 0; i < numSwapchainImages; ++i)
|
||||
{
|
||||
imageAcquired[i] = new Semaphore(graphics);
|
||||
renderFinished[i] = new Semaphore(graphics);
|
||||
backBufferImages[i] = new Texture2D(graphics, backBufferCreateInfo, swapchainImages[i]);
|
||||
backBufferHandles[i] = swapchainImages[i];
|
||||
|
||||
VkClearColorValue clearColor;
|
||||
std::memset(&clearColor, 0, sizeof(VkClearColorValue));
|
||||
backBufferImages[i]->changeLayout(Gfx::SE_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);
|
||||
VkImageSubresourceRange range = init::ImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT);
|
||||
VkImageSubresourceRange range = {
|
||||
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||
.baseMipLevel = 0,
|
||||
.levelCount = 1,
|
||||
.baseArrayLayer = 0,
|
||||
.layerCount = 1,
|
||||
};
|
||||
PCommand command = graphics->getGraphicsCommands()->getCommands();
|
||||
vkCmdClearColorImage(command->getHandle(), backBufferImages[i]->getHandle(), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearColor, 1, &range);
|
||||
vkCmdClearColorImage(command->getHandle(), backBufferHandles[i], VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearColor, 1, &range);
|
||||
backBufferImages[i]->changeLayout(Gfx::SE_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
|
||||
}
|
||||
graphics->getGraphicsCommands()->submitCommands();
|
||||
|
||||
@@ -45,6 +45,7 @@ protected:
|
||||
void choosePresentMode(const Array<VkPresentModeKHR> &modes);
|
||||
|
||||
OTexture2D backBufferImages[Gfx::numFramesBuffered];
|
||||
VkImage backBufferHandles[Gfx::numFramesBuffered];
|
||||
OSemaphore renderFinished[Gfx::numFramesBuffered];
|
||||
OSemaphore imageAcquired[Gfx::numFramesBuffered];
|
||||
PSemaphore imageAcquiredSemaphore;
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Resources.h"
|
||||
#include "Enums.h"
|
||||
#include "Initializer.h"
|
||||
#include "Graphics.h"
|
||||
|
||||
using namespace Seele;
|
||||
@@ -79,14 +78,18 @@ void Fence::reset()
|
||||
void Fence::wait(uint32 timeout)
|
||||
{
|
||||
VkFence fences[] = {fence};
|
||||
VkResult res = vkWaitForFences(graphics->getDevice(), 1, fences, true, timeout);
|
||||
if (res == VK_SUCCESS)
|
||||
VkResult r = vkWaitForFences(graphics->getDevice(), 1, fences, true, timeout);
|
||||
if (r == VK_SUCCESS)
|
||||
{
|
||||
signaled = true;
|
||||
}
|
||||
if (res != VK_NOT_READY)
|
||||
else if (r == VK_TIMEOUT)
|
||||
{
|
||||
VK_CHECK(res);
|
||||
return;
|
||||
}
|
||||
else if (r != VK_NOT_READY)
|
||||
{
|
||||
VK_CHECK(r);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -119,26 +122,32 @@ void DestructionManager::queueSemaphore(PCommand cmd, VkSemaphore sem)
|
||||
sems[cmd].add(sem);
|
||||
}
|
||||
|
||||
void DestructionManager::notifyCmdComplete(PCommand cmdbuffer)
|
||||
void DestructionManager::queueAllocation(PCommand cmd, OSubAllocation alloc)
|
||||
{
|
||||
for(auto buf : buffers[cmdbuffer])
|
||||
allocs[cmd].add(std::move(alloc));
|
||||
}
|
||||
|
||||
void DestructionManager::notifyCmdComplete(PCommand cmd)
|
||||
{
|
||||
for(auto buf : buffers[cmd])
|
||||
{
|
||||
vkDestroyBuffer(graphics->getDevice(), buf, nullptr);
|
||||
}
|
||||
for(auto view : views[cmdbuffer])
|
||||
for(auto view : views[cmd])
|
||||
{
|
||||
vkDestroyImageView(graphics->getDevice(), view, nullptr);
|
||||
}
|
||||
for(auto img : images[cmdbuffer])
|
||||
for(auto img : images[cmd])
|
||||
{
|
||||
vkDestroyImage(graphics->getDevice(), img, nullptr);
|
||||
}
|
||||
for (auto sem : sems[cmdbuffer])
|
||||
for (auto sem : sems[cmd])
|
||||
{
|
||||
vkDestroySemaphore(graphics->getDevice(), sem, nullptr);
|
||||
}
|
||||
buffers[cmdbuffer].clear();
|
||||
images[cmdbuffer].clear();
|
||||
views[cmdbuffer].clear();
|
||||
sems[cmdbuffer].clear();
|
||||
buffers[cmd].clear();
|
||||
images[cmd].clear();
|
||||
views[cmd].clear();
|
||||
sems[cmd].clear();
|
||||
allocs[cmd].clear();
|
||||
}
|
||||
|
||||
@@ -8,7 +8,7 @@ namespace Seele
|
||||
{
|
||||
namespace Vulkan
|
||||
{
|
||||
DECLARE_REF(DescriptorAllocator)
|
||||
DECLARE_REF(DescriptorPool)
|
||||
DECLARE_REF(CommandPool)
|
||||
DECLARE_REF(Command)
|
||||
DECLARE_REF(Graphics)
|
||||
@@ -61,6 +61,7 @@ public:
|
||||
void queueImage(PCommand cmd, VkImage image);
|
||||
void queueImageView(PCommand cmd, VkImageView view);
|
||||
void queueSemaphore(PCommand cmd, VkSemaphore sem);
|
||||
void queueAllocation(PCommand cmd, OSubAllocation alloc);
|
||||
void notifyCmdComplete(PCommand cmdbuffer);
|
||||
private:
|
||||
PGraphics graphics;
|
||||
@@ -68,6 +69,7 @@ private:
|
||||
Map<PCommand, List<VkImage>> images;
|
||||
Map<PCommand, List<VkImageView>> views;
|
||||
Map<PCommand, List<VkSemaphore>> sems;
|
||||
Map<PCommand, List<OSubAllocation>> allocs;
|
||||
};
|
||||
DEFINE_REF(DestructionManager)
|
||||
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Texture.h"
|
||||
#include "Initializer.h"
|
||||
#include "CommandBuffer.h"
|
||||
#include "Command.h"
|
||||
#include <math.h>
|
||||
|
||||
using namespace Seele;
|
||||
@@ -26,15 +25,15 @@ VkImageAspectFlags getAspectFromFormat(Gfx::SeFormat format)
|
||||
}
|
||||
}
|
||||
|
||||
TextureHandle::TextureHandle(PGraphics graphics, VkImageViewType viewType,
|
||||
TextureBase::TextureBase(PGraphics graphics, VkImageViewType viewType,
|
||||
const TextureCreateInfo& createInfo, Gfx::QueueType& owner, VkImage existingImage)
|
||||
: currentOwner(owner)
|
||||
, graphics(graphics)
|
||||
, sizeX(createInfo.width)
|
||||
, sizeY(createInfo.height)
|
||||
, sizeZ(createInfo.depth)
|
||||
, arrayCount(createInfo.bArray ? createInfo.arrayLayers : 1)
|
||||
, layerCount(1)
|
||||
, width(createInfo.width)
|
||||
, height(createInfo.height)
|
||||
, depth(createInfo.depth)
|
||||
, arrayCount(createInfo.elements)
|
||||
, layerCount(createInfo.layers)
|
||||
, mipLevels(createInfo.mipLevels)
|
||||
, samples(createInfo.samples)
|
||||
, format(createInfo.format)
|
||||
@@ -45,64 +44,73 @@ TextureHandle::TextureHandle(PGraphics graphics, VkImageViewType viewType,
|
||||
{
|
||||
if (existingImage == VK_NULL_HANDLE)
|
||||
{
|
||||
PAllocator allocator = graphics->getAllocator();
|
||||
VkImageCreateInfo info =
|
||||
init::ImageCreateInfo();
|
||||
info.extent.width = sizeX;
|
||||
info.extent.height = sizeY;
|
||||
info.extent.depth = sizeZ;
|
||||
info.format = cast(format);
|
||||
|
||||
PAllocator pool = graphics->getAllocator();
|
||||
VkImageType type = VK_IMAGE_TYPE_MAX_ENUM;
|
||||
VkImageCreateFlags flags = 0;
|
||||
switch (viewType)
|
||||
{
|
||||
case VK_IMAGE_VIEW_TYPE_1D:
|
||||
case VK_IMAGE_VIEW_TYPE_1D_ARRAY:
|
||||
info.imageType = VK_IMAGE_TYPE_1D;
|
||||
type = VK_IMAGE_TYPE_1D;
|
||||
break;
|
||||
case VK_IMAGE_VIEW_TYPE_2D:
|
||||
case VK_IMAGE_VIEW_TYPE_2D_ARRAY:
|
||||
info.imageType = VK_IMAGE_TYPE_2D;
|
||||
type = VK_IMAGE_TYPE_2D;
|
||||
break;
|
||||
case VK_IMAGE_VIEW_TYPE_3D:
|
||||
info.imageType = VK_IMAGE_TYPE_3D;
|
||||
type = VK_IMAGE_TYPE_3D;
|
||||
break;
|
||||
case VK_IMAGE_VIEW_TYPE_CUBE:
|
||||
case VK_IMAGE_VIEW_TYPE_CUBE_ARRAY:
|
||||
info.flags = VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT;
|
||||
info.imageType = VK_IMAGE_TYPE_2D;
|
||||
type = VK_IMAGE_TYPE_2D;
|
||||
flags = VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT;
|
||||
layerCount = 6 * arrayCount;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
VkImageCreateInfo info = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = flags,
|
||||
.imageType = type,
|
||||
.format = cast(format),
|
||||
.extent = {
|
||||
.width = width,
|
||||
.height = height,
|
||||
.depth = depth,
|
||||
},
|
||||
.mipLevels = mipLevels,
|
||||
.arrayLayers = arrayCount * layerCount,
|
||||
.samples = (VkSampleCountFlagBits)samples,
|
||||
.tiling = VK_IMAGE_TILING_OPTIMAL,
|
||||
.usage = usage
|
||||
| VK_IMAGE_USAGE_TRANSFER_DST_BIT
|
||||
| VK_IMAGE_USAGE_TRANSFER_SRC_BIT
|
||||
| VK_IMAGE_USAGE_SAMPLED_BIT,
|
||||
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
|
||||
.initialLayout = cast(layout),
|
||||
};
|
||||
|
||||
info.initialLayout = cast(layout);
|
||||
info.mipLevels = mipLevels;
|
||||
info.arrayLayers = arrayCount * layerCount;
|
||||
info.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
|
||||
info.samples = (VkSampleCountFlagBits)samples;
|
||||
info.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||
info.usage = usage;
|
||||
// Most of these flags will almost always be used
|
||||
info.usage |= VK_IMAGE_USAGE_TRANSFER_DST_BIT;
|
||||
info.usage |= VK_IMAGE_USAGE_TRANSFER_SRC_BIT;
|
||||
info.usage |= VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
|
||||
VK_CHECK(vkCreateImage(graphics->getDevice(), &info, nullptr, &image));
|
||||
|
||||
VkMemoryDedicatedRequirements memDedicatedRequirements;
|
||||
memDedicatedRequirements.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_REQUIREMENTS;
|
||||
memDedicatedRequirements.pNext = nullptr;
|
||||
VkImageMemoryRequirementsInfo2 reqInfo;
|
||||
reqInfo.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_REQUIREMENTS_INFO_2;
|
||||
reqInfo.pNext = nullptr;
|
||||
reqInfo.image = image;
|
||||
VkMemoryRequirements2 requirements;
|
||||
requirements.sType = VK_STRUCTURE_TYPE_MEMORY_REQUIREMENTS_2;
|
||||
requirements.pNext = &memDedicatedRequirements;
|
||||
VkMemoryDedicatedRequirements memDedicatedRequirements = {
|
||||
.sType = VK_STRUCTURE_TYPE_MEMORY_DEDICATED_REQUIREMENTS,
|
||||
.pNext = nullptr,
|
||||
};
|
||||
VkImageMemoryRequirementsInfo2 reqInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_REQUIREMENTS_INFO_2,
|
||||
.pNext = nullptr,
|
||||
.image = image,
|
||||
};
|
||||
VkMemoryRequirements2 requirements = {
|
||||
.sType = VK_STRUCTURE_TYPE_MEMORY_REQUIREMENTS_2,
|
||||
.pNext = &memDedicatedRequirements,
|
||||
};
|
||||
vkGetImageMemoryRequirements2(graphics->getDevice(), &reqInfo, &requirements);
|
||||
|
||||
allocation = allocator->allocate(requirements, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, image);
|
||||
allocation = pool->allocate(requirements, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, image);
|
||||
vkBindImageMemory(graphics->getDevice(), image, allocation->getHandle(), allocation->getOffset());
|
||||
}
|
||||
|
||||
@@ -110,31 +118,39 @@ TextureHandle::TextureHandle(PGraphics graphics, VkImageViewType viewType,
|
||||
if(sourceData.size > 0)
|
||||
{
|
||||
changeLayout(Gfx::SE_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);
|
||||
OStagingBuffer staging = graphics->getStagingManager()->create(sourceData.size, VK_BUFFER_USAGE_TRANSFER_SRC_BIT);
|
||||
OStagingBuffer staging = graphics->getStagingManager()->create(sourceData.size);
|
||||
void* data = staging->map();
|
||||
std::memcpy(data, sourceData.data, sourceData.size);
|
||||
staging->flush();
|
||||
|
||||
PCommandBufferManager cmdBufferManager = graphics->getQueueCommands(currentOwner);
|
||||
VkBufferImageCopy region;
|
||||
region.bufferOffset = 0;
|
||||
region.bufferRowLength = 0;
|
||||
region.bufferImageHeight = 0;
|
||||
|
||||
region.imageSubresource.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
|
||||
region.imageSubresource.mipLevel = 0;
|
||||
region.imageSubresource.baseArrayLayer = 0;
|
||||
region.imageSubresource.layerCount = arrayCount * layerCount;
|
||||
|
||||
region.imageOffset = {0, 0, 0};
|
||||
region.imageExtent = {sizeX, sizeY, sizeZ};
|
||||
|
||||
vkCmdCopyBufferToImage(cmdBufferManager->getCommands()->getHandle(),
|
||||
PCommandPool commandPool = graphics->getQueueCommands(currentOwner);
|
||||
VkBufferImageCopy region = {
|
||||
.bufferOffset = 0,
|
||||
.bufferRowLength = 0,
|
||||
.bufferImageHeight = 0,
|
||||
.imageSubresource = {
|
||||
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||
.mipLevel = 0,
|
||||
.baseArrayLayer = 0,
|
||||
.layerCount = arrayCount * layerCount,
|
||||
},
|
||||
.imageOffset = {
|
||||
.x = 0,
|
||||
.y = 0,
|
||||
.z = 0,
|
||||
},
|
||||
.imageExtent = {
|
||||
.width = width,
|
||||
.height = height,
|
||||
.depth = depth
|
||||
},
|
||||
};
|
||||
|
||||
vkCmdCopyBufferToImage(commandPool->getCommands()->getHandle(),
|
||||
staging->getHandle(), image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, ®ion);
|
||||
|
||||
// When loading a texture from a file, we will almost always use it as a texture map for fragment shaders
|
||||
changeLayout(Gfx::SE_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
|
||||
graphics->getStagingManager()->release(std::move(staging));
|
||||
}
|
||||
else if(usage & VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT)
|
||||
{
|
||||
@@ -145,74 +161,62 @@ TextureHandle::TextureHandle(PGraphics graphics, VkImageViewType viewType,
|
||||
changeLayout(Gfx::SE_IMAGE_LAYOUT_GENERAL);
|
||||
}
|
||||
|
||||
VkImageViewCreateInfo viewInfo =
|
||||
init::ImageViewCreateInfo();
|
||||
viewInfo.subresourceRange = init::ImageSubresourceRange(aspect);
|
||||
viewInfo.viewType = viewType;
|
||||
viewInfo.image = image;
|
||||
viewInfo.format = cast(format);
|
||||
viewInfo.subresourceRange.layerCount = layerCount;
|
||||
viewInfo.subresourceRange.levelCount = mipLevels;
|
||||
|
||||
VkImageViewCreateInfo viewInfo = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.flags = 0,
|
||||
.image = image,
|
||||
.viewType = viewType,
|
||||
.format = cast(format),
|
||||
.subresourceRange = {
|
||||
.aspectMask = aspect,
|
||||
.levelCount = mipLevels,
|
||||
.layerCount = layerCount,
|
||||
},
|
||||
};
|
||||
|
||||
VK_CHECK(vkCreateImageView(graphics->getDevice(), &viewInfo, nullptr, &defaultView));
|
||||
}
|
||||
|
||||
TextureHandle::~TextureHandle()
|
||||
TextureBase::~TextureBase()
|
||||
{
|
||||
graphics->getDestructionManager()->queueImage(graphics->getQueueCommands(currentOwner)->getCommands(), image);
|
||||
graphics->getDestructionManager()->queueImageView(graphics->getQueueCommands(currentOwner)->getCommands(), defaultView);
|
||||
}
|
||||
|
||||
TextureHandle* TextureBase::cast(Gfx::PTexture texture)
|
||||
{
|
||||
if(texture == nullptr)
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
if(texture->getTexture2D() != nullptr)
|
||||
{
|
||||
PTexture2D texture2D = texture.cast<Texture2D>();
|
||||
return texture2D->textureHandle;
|
||||
}
|
||||
if(texture->getTexture3D() != nullptr)
|
||||
{
|
||||
PTexture3D texture3D = texture.cast<Texture3D>();
|
||||
return texture3D->textureHandle;
|
||||
}
|
||||
if(texture->getTextureCube() != nullptr)
|
||||
{
|
||||
PTextureCube textureCube = texture.cast<TextureCube>();
|
||||
return textureCube->textureHandle;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void TextureHandle::changeLayout(Gfx::SeImageLayout newLayout)
|
||||
void TextureBase::changeLayout(Gfx::SeImageLayout newLayout)
|
||||
{
|
||||
VkImageMemoryBarrier barrier =
|
||||
init::ImageMemoryBarrier(
|
||||
image,
|
||||
cast(layout),
|
||||
cast(newLayout));
|
||||
barrier.subresourceRange =
|
||||
init::ImageSubresourceRange(aspect);
|
||||
barrier.subresourceRange.layerCount = layerCount;
|
||||
PCommandBufferManager cmdManager = graphics->getQueueCommands(currentOwner);
|
||||
vkCmdPipelineBarrier(cmdManager->getCommands()->getHandle(),
|
||||
VkImageMemoryBarrier barrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.oldLayout = cast(layout),
|
||||
.newLayout = cast(newLayout),
|
||||
.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.image = image,
|
||||
.subresourceRange = {
|
||||
.aspectMask = aspect,
|
||||
.levelCount = 1,
|
||||
.layerCount = layerCount,
|
||||
},
|
||||
};
|
||||
PCommandPool commandPool = graphics->getQueueCommands(currentOwner);
|
||||
vkCmdPipelineBarrier(commandPool->getCommands()->getHandle(),
|
||||
VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
|
||||
0, 0, nullptr, 0, nullptr, 1, &barrier);
|
||||
cmdManager->submitCommands();
|
||||
commandPool->submitCommands();
|
||||
layout = newLayout;
|
||||
}
|
||||
|
||||
void TextureHandle::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer)
|
||||
void TextureBase::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer)
|
||||
{
|
||||
uint64 imageSize = sizeX * sizeY * sizeZ * Gfx::getFormatInfo(format).blockSize;
|
||||
uint64 imageSize = width * height * depth * Gfx::getFormatInfo(format).blockSize;
|
||||
|
||||
OStagingBuffer stagingbuffer = graphics->getStagingManager()->create(imageSize, VK_BUFFER_USAGE_TRANSFER_DST_BIT, true);
|
||||
OStagingBuffer stagingbuffer = graphics->getStagingManager()->create(imageSize);
|
||||
auto prevlayout = layout;
|
||||
changeLayout(Gfx::SE_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL);
|
||||
PCmdBuffer cmdBuffer = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
PCommand cmdBuffer = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
//Gfx::FormatCompatibilityInfo formatInfo = Gfx::getFormatInfo(format);
|
||||
VkBufferImageCopy region = {
|
||||
.bufferOffset = 0,
|
||||
@@ -224,32 +228,43 @@ void TextureHandle::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Ar
|
||||
.baseArrayLayer = arrayLayer * layerCount + face,
|
||||
.layerCount = 1,
|
||||
},
|
||||
.imageOffset = { 0, 0, 0 },
|
||||
.imageExtent = { sizeX, sizeY, sizeZ },
|
||||
.imageOffset = {
|
||||
.x = 0,
|
||||
.y = 0,
|
||||
.z = 0,
|
||||
},
|
||||
.imageExtent = {
|
||||
.width = width,
|
||||
.height = height,
|
||||
.depth = depth
|
||||
},
|
||||
};
|
||||
vkCmdCopyImageToBuffer(cmdBuffer->getHandle(), image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, stagingbuffer->getHandle(), 1, ®ion);
|
||||
changeLayout(prevlayout);
|
||||
buffer.resize(stagingbuffer->getSize());
|
||||
void* data = stagingbuffer->map();
|
||||
std::memcpy(buffer.data(), data, buffer.size());
|
||||
graphics->getStagingManager()->release(std::move(stagingbuffer));
|
||||
}
|
||||
|
||||
void TextureHandle::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
void TextureBase::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
VkImageMemoryBarrier imageBarrier =
|
||||
init::ImageMemoryBarrier();
|
||||
imageBarrier.image = image;
|
||||
imageBarrier.oldLayout = cast(layout);
|
||||
imageBarrier.newLayout = cast(layout);
|
||||
imageBarrier.subresourceRange = init::ImageSubresourceRange(aspect);
|
||||
PCommandBufferManager sourceManager = graphics->getQueueCommands(currentOwner);
|
||||
PCommandBufferManager dstManager = nullptr;
|
||||
Gfx::QueueFamilyMapping mapping = graphics->getFamilyMapping();
|
||||
VkImageMemoryBarrier imageBarrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.oldLayout = cast(layout),
|
||||
.newLayout = cast(layout),
|
||||
.srcQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(currentOwner),
|
||||
.dstQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(newOwner),
|
||||
.image = image,
|
||||
.subresourceRange = {
|
||||
.aspectMask = aspect,
|
||||
},
|
||||
};
|
||||
PCommandPool sourcePool = graphics->getQueueCommands(currentOwner);
|
||||
PCommandPool dstPool = nullptr;
|
||||
VkPipelineStageFlags srcStage = VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT;
|
||||
VkPipelineStageFlags dstStage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;
|
||||
Gfx::QueueFamilyMapping mapping = graphics->getFamilyMapping();
|
||||
imageBarrier.srcQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(currentOwner);
|
||||
imageBarrier.dstQueueFamilyIndex = mapping.getQueueTypeFamilyIndex(newOwner);
|
||||
if (currentOwner == Gfx::QueueType::TRANSFER || currentOwner == Gfx::QueueType::DEDICATED_TRANSFER)
|
||||
{
|
||||
imageBarrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
@@ -269,56 +284,61 @@ void TextureHandle::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
imageBarrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_TRANSFER_BIT;
|
||||
dstManager = graphics->getTransferCommands();
|
||||
dstPool = graphics->getTransferCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::DEDICATED_TRANSFER)
|
||||
{
|
||||
imageBarrier.dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_TRANSFER_BIT;
|
||||
dstManager = graphics->getDedicatedTransferCommands();
|
||||
dstPool = graphics->getDedicatedTransferCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::COMPUTE)
|
||||
{
|
||||
imageBarrier.dstAccessMask = VK_ACCESS_MEMORY_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT;
|
||||
dstManager = graphics->getComputeCommands();
|
||||
dstPool = graphics->getComputeCommands();
|
||||
}
|
||||
else if (newOwner == Gfx::QueueType::GRAPHICS)
|
||||
{
|
||||
imageBarrier.dstAccessMask = VK_ACCESS_MEMORY_READ_BIT;
|
||||
dstStage = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT;
|
||||
dstManager = graphics->getGraphicsCommands();
|
||||
dstPool = graphics->getGraphicsCommands();
|
||||
}
|
||||
|
||||
VkCommandBuffer sourceCmd = sourceManager->getCommands()->getHandle();
|
||||
VkCommandBuffer destCmd = dstManager->getCommands()->getHandle();
|
||||
VkCommandBuffer sourceCmd = sourcePool->getCommands()->getHandle();
|
||||
VkCommandBuffer destCmd = dstPool->getCommands()->getHandle();
|
||||
vkCmdPipelineBarrier(sourceCmd, srcStage, srcStage, 0, 0, nullptr, 0, nullptr, 1, &imageBarrier);
|
||||
vkCmdPipelineBarrier(destCmd, dstStage, dstStage, 0, 0, nullptr, 0, nullptr, 1, &imageBarrier);
|
||||
currentOwner = newOwner;
|
||||
sourceManager->submitCommands();
|
||||
sourcePool->submitCommands();
|
||||
}
|
||||
|
||||
void TextureHandle::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
void TextureBase::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage)
|
||||
{
|
||||
VkImageMemoryBarrier imageBarrier =
|
||||
init::ImageMemoryBarrier(
|
||||
image,
|
||||
cast(layout),
|
||||
cast(layout)
|
||||
);
|
||||
imageBarrier.srcAccessMask = srcAccess;
|
||||
imageBarrier.dstAccessMask = dstAccess;
|
||||
imageBarrier.subresourceRange = init::ImageSubresourceRange(aspect);
|
||||
PCmdBuffer cmdBuffer = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
vkCmdPipelineBarrier(cmdBuffer->getHandle(), srcStage, dstStage, 0, 0, nullptr, 0, nullptr, 1, &imageBarrier);
|
||||
VkImageMemoryBarrier barrier = {
|
||||
.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,
|
||||
.pNext = nullptr,
|
||||
.srcAccessMask = srcAccess,
|
||||
.dstAccessMask = dstAccess,
|
||||
.oldLayout = cast(layout),
|
||||
.newLayout = cast(layout),
|
||||
.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
|
||||
.image = image,
|
||||
.subresourceRange = {
|
||||
.aspectMask = aspect,
|
||||
},
|
||||
};
|
||||
PCommand command = graphics->getQueueCommands(currentOwner)->getCommands();
|
||||
vkCmdPipelineBarrier(command->getHandle(), srcStage, dstStage, 0, 0, nullptr, 0, nullptr, 1, &barrier);
|
||||
}
|
||||
|
||||
Texture2D::Texture2D(PGraphics graphics, const TextureCreateInfo& createInfo, VkImage existingImage)
|
||||
: Gfx::Texture2D(graphics->getFamilyMapping(), createInfo.sourceData.owner)
|
||||
, TextureBase(graphics, createInfo.elements > 1 ? VK_IMAGE_VIEW_TYPE_2D_ARRAY : VK_IMAGE_VIEW_TYPE_2D,
|
||||
createInfo, Gfx::Texture2D::currentOwner, existingImage)
|
||||
{
|
||||
textureHandle = new TextureHandle(graphics, createInfo.bArray ? VK_IMAGE_VIEW_TYPE_2D_ARRAY : VK_IMAGE_VIEW_TYPE_2D,
|
||||
createInfo, currentOwner, existingImage);
|
||||
}
|
||||
|
||||
Texture2D::~Texture2D()
|
||||
@@ -327,30 +347,30 @@ Texture2D::~Texture2D()
|
||||
|
||||
void Texture2D::changeLayout(Gfx::SeImageLayout newLayout)
|
||||
{
|
||||
textureHandle->changeLayout(newLayout);
|
||||
TextureBase::changeLayout(newLayout);
|
||||
}
|
||||
|
||||
void Texture2D::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer)
|
||||
{
|
||||
textureHandle->download(mipLevel, arrayLayer, face, buffer);
|
||||
TextureBase::download(mipLevel, arrayLayer, face, buffer);
|
||||
}
|
||||
|
||||
void Texture2D::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
textureHandle->executeOwnershipBarrier(newOwner);
|
||||
TextureBase::executeOwnershipBarrier(newOwner);
|
||||
}
|
||||
|
||||
void Texture2D::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage)
|
||||
{
|
||||
textureHandle->executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
TextureBase::executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
}
|
||||
|
||||
Texture3D::Texture3D(PGraphics graphics, const TextureCreateInfo& createInfo, VkImage existingImage)
|
||||
: Gfx::Texture3D(graphics->getFamilyMapping(), createInfo.sourceData.owner)
|
||||
, TextureBase(graphics, VK_IMAGE_VIEW_TYPE_3D,
|
||||
createInfo, Gfx::Texture3D::currentOwner, existingImage)
|
||||
{
|
||||
textureHandle = new TextureHandle(graphics, VK_IMAGE_VIEW_TYPE_3D,
|
||||
createInfo, currentOwner, existingImage);
|
||||
}
|
||||
|
||||
Texture3D::~Texture3D()
|
||||
@@ -359,29 +379,29 @@ Texture3D::~Texture3D()
|
||||
|
||||
void Texture3D::changeLayout(Gfx::SeImageLayout newLayout)
|
||||
{
|
||||
textureHandle->changeLayout(newLayout);
|
||||
TextureBase::changeLayout(newLayout);
|
||||
}
|
||||
|
||||
void Texture3D::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer)
|
||||
{
|
||||
textureHandle->download(mipLevel, arrayLayer, face, buffer);
|
||||
TextureBase::download(mipLevel, arrayLayer, face, buffer);
|
||||
}
|
||||
void Texture3D::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
textureHandle->executeOwnershipBarrier(newOwner);
|
||||
TextureBase::executeOwnershipBarrier(newOwner);
|
||||
}
|
||||
|
||||
void Texture3D::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage)
|
||||
{
|
||||
textureHandle->executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
TextureBase::executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
}
|
||||
|
||||
TextureCube::TextureCube(PGraphics graphics, const TextureCreateInfo& createInfo, VkImage existingImage)
|
||||
: Gfx::TextureCube(graphics->getFamilyMapping(), createInfo.sourceData.owner)
|
||||
, TextureBase(graphics, createInfo.elements > 1? VK_IMAGE_VIEW_TYPE_CUBE_ARRAY : VK_IMAGE_VIEW_TYPE_CUBE,
|
||||
createInfo, Gfx::TextureCube::currentOwner, existingImage)
|
||||
{
|
||||
textureHandle = new TextureHandle(graphics, createInfo.bArray ? VK_IMAGE_VIEW_TYPE_CUBE_ARRAY : VK_IMAGE_VIEW_TYPE_CUBE,
|
||||
createInfo, currentOwner, existingImage);
|
||||
}
|
||||
|
||||
TextureCube::~TextureCube()
|
||||
@@ -390,20 +410,20 @@ TextureCube::~TextureCube()
|
||||
|
||||
void TextureCube::changeLayout(Gfx::SeImageLayout newLayout)
|
||||
{
|
||||
textureHandle->changeLayout(newLayout);
|
||||
TextureBase::changeLayout(newLayout);
|
||||
}
|
||||
|
||||
void TextureCube::download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer)
|
||||
{
|
||||
textureHandle->download(mipLevel, arrayLayer, face, buffer);
|
||||
TextureBase::download(mipLevel, arrayLayer, face, buffer);
|
||||
}
|
||||
void TextureCube::executeOwnershipBarrier(Gfx::QueueType newOwner)
|
||||
{
|
||||
textureHandle->executeOwnershipBarrier(newOwner);
|
||||
TextureBase::executeOwnershipBarrier(newOwner);
|
||||
}
|
||||
|
||||
void TextureCube::executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage)
|
||||
{
|
||||
textureHandle->executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
TextureBase::executePipelineBarrier(srcAccess, srcStage, dstAccess, dstStage);
|
||||
}
|
||||
|
||||
@@ -8,46 +8,46 @@ namespace Seele
|
||||
namespace Vulkan
|
||||
{
|
||||
|
||||
class TextureHandle
|
||||
class TextureBase
|
||||
{
|
||||
public:
|
||||
TextureHandle(PGraphics graphics, VkImageViewType viewType,
|
||||
TextureBase(PGraphics graphics, VkImageViewType viewType,
|
||||
const TextureCreateInfo& createInfo, Gfx::QueueType& owner, VkImage existingImage = VK_NULL_HANDLE);
|
||||
virtual ~TextureHandle();
|
||||
virtual ~TextureBase();
|
||||
|
||||
inline VkImage getImage() const
|
||||
constexpr VkImage getImage() const
|
||||
{
|
||||
return image;
|
||||
}
|
||||
inline VkImageView getView() const
|
||||
constexpr VkImageView getView() const
|
||||
{
|
||||
return defaultView;
|
||||
}
|
||||
inline Gfx::SeImageLayout getLayout() const
|
||||
constexpr Gfx::SeImageLayout getLayout() const
|
||||
{
|
||||
return layout;
|
||||
}
|
||||
inline VkImageAspectFlags getAspect() const
|
||||
constexpr VkImageAspectFlags getAspect() const
|
||||
{
|
||||
return aspect;
|
||||
}
|
||||
inline VkImageUsageFlags getUsage() const
|
||||
constexpr VkImageUsageFlags getUsage() const
|
||||
{
|
||||
return usage;
|
||||
}
|
||||
inline Gfx::SeFormat getFormat() const
|
||||
constexpr Gfx::SeFormat getFormat() const
|
||||
{
|
||||
return format;
|
||||
}
|
||||
inline Gfx::SeSampleCountFlags getNumSamples() const
|
||||
constexpr Gfx::SeSampleCountFlags getNumSamples() const
|
||||
{
|
||||
return samples;
|
||||
}
|
||||
inline uint32 getMipLevels() const
|
||||
constexpr uint32 getMipLevels() const
|
||||
{
|
||||
return mipLevels;
|
||||
}
|
||||
inline bool isDepthStencil() const
|
||||
constexpr bool isDepthStencil() const
|
||||
{
|
||||
return aspect & (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT);
|
||||
}
|
||||
@@ -57,14 +57,14 @@ public:
|
||||
void changeLayout(Gfx::SeImageLayout newLayout);
|
||||
void download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer);
|
||||
|
||||
private:
|
||||
protected:
|
||||
//Updates via reference
|
||||
Gfx::QueueType& currentOwner;
|
||||
PGraphics graphics;
|
||||
OSubAllocation allocation;
|
||||
uint32 sizeX;
|
||||
uint32 sizeY;
|
||||
uint32 sizeZ;
|
||||
uint32 width;
|
||||
uint32 height;
|
||||
uint32 depth;
|
||||
uint32 arrayCount;
|
||||
uint32 layerCount;
|
||||
uint32 mipLevels;
|
||||
@@ -75,23 +75,9 @@ private:
|
||||
VkImageView defaultView;
|
||||
VkImageAspectFlags aspect;
|
||||
Gfx::SeImageLayout layout;
|
||||
friend class TextureBase;
|
||||
friend class Texture2D;
|
||||
friend class Texture3D;
|
||||
friend class TextureCube;
|
||||
friend class Graphics;
|
||||
};
|
||||
|
||||
class TextureBase
|
||||
{
|
||||
public:
|
||||
static TextureHandle* cast(Gfx::PTexture texture);
|
||||
|
||||
protected:
|
||||
TextureHandle* textureHandle;
|
||||
friend class Graphics;
|
||||
};
|
||||
DECLARE_REF(TextureBase)
|
||||
class Texture2D : public Gfx::Texture2D, public TextureBase
|
||||
{
|
||||
public:
|
||||
@@ -99,46 +85,31 @@ public:
|
||||
virtual ~Texture2D();
|
||||
virtual uint32 getWidth() const override
|
||||
{
|
||||
return textureHandle->sizeX;
|
||||
return width;
|
||||
}
|
||||
virtual uint32 getHeight() const override
|
||||
{
|
||||
return textureHandle->sizeY;
|
||||
return height;
|
||||
}
|
||||
virtual uint32 getDepth() const override
|
||||
{
|
||||
return textureHandle->sizeZ;
|
||||
return depth;
|
||||
}
|
||||
virtual Gfx::SeFormat getFormat() const override
|
||||
{
|
||||
return textureHandle->format;
|
||||
return format;
|
||||
}
|
||||
virtual Gfx::SeSampleCountFlags getNumSamples() const override
|
||||
{
|
||||
return textureHandle->getNumSamples();
|
||||
return samples;
|
||||
}
|
||||
virtual uint32 getMipLevels() const override
|
||||
{
|
||||
return textureHandle->getMipLevels();
|
||||
return mipLevels;
|
||||
}
|
||||
virtual void changeLayout(Gfx::SeImageLayout newLayout) override;
|
||||
virtual void download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer) override;
|
||||
virtual void* getNativeHandle() override
|
||||
{
|
||||
return textureHandle;
|
||||
}
|
||||
inline VkImage getHandle() const
|
||||
{
|
||||
return textureHandle->image;
|
||||
}
|
||||
inline VkImageView getView() const
|
||||
{
|
||||
return textureHandle->defaultView;
|
||||
}
|
||||
inline bool isDepthStencil() const
|
||||
{
|
||||
return textureHandle->isDepthStencil();
|
||||
}
|
||||
|
||||
protected:
|
||||
// Inherited via QueueOwnedResource
|
||||
virtual void executeOwnershipBarrier(Gfx::QueueType newOwner);
|
||||
@@ -155,46 +126,31 @@ public:
|
||||
virtual ~Texture3D();
|
||||
virtual uint32 getWidth() const override
|
||||
{
|
||||
return textureHandle->sizeX;
|
||||
return width;
|
||||
}
|
||||
virtual uint32 getHeight() const override
|
||||
{
|
||||
return textureHandle->sizeY;
|
||||
return height;
|
||||
}
|
||||
virtual uint32 getDepth() const override
|
||||
{
|
||||
return textureHandle->sizeZ;
|
||||
return depth;
|
||||
}
|
||||
virtual Gfx::SeFormat getFormat() const override
|
||||
{
|
||||
return textureHandle->format;
|
||||
return format;
|
||||
}
|
||||
virtual Gfx::SeSampleCountFlags getNumSamples() const override
|
||||
{
|
||||
return textureHandle->getNumSamples();
|
||||
return samples;
|
||||
}
|
||||
virtual uint32 getMipLevels() const override
|
||||
{
|
||||
return textureHandle->getMipLevels();
|
||||
return mipLevels;
|
||||
}
|
||||
virtual void changeLayout(Gfx::SeImageLayout newLayout) override;
|
||||
virtual void download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer) override;
|
||||
virtual void* getNativeHandle() override
|
||||
{
|
||||
return textureHandle;
|
||||
}
|
||||
inline VkImage getHandle() const
|
||||
{
|
||||
return textureHandle->image;
|
||||
}
|
||||
inline VkImageView getView() const
|
||||
{
|
||||
return textureHandle->defaultView;
|
||||
}
|
||||
inline bool isDepthStencil() const
|
||||
{
|
||||
return textureHandle->isDepthStencil();
|
||||
}
|
||||
|
||||
protected:
|
||||
// Inherited via QueueOwnedResource
|
||||
virtual void executeOwnershipBarrier(Gfx::QueueType newOwner);
|
||||
@@ -211,54 +167,36 @@ public:
|
||||
virtual ~TextureCube();
|
||||
virtual uint32 getWidth() const override
|
||||
{
|
||||
return textureHandle->sizeX;
|
||||
return width;
|
||||
}
|
||||
virtual uint32 getHeight() const override
|
||||
{
|
||||
return textureHandle->sizeY;
|
||||
return height;
|
||||
}
|
||||
virtual uint32 getDepth() const override
|
||||
{
|
||||
return textureHandle->sizeZ;
|
||||
return depth;
|
||||
}
|
||||
virtual Gfx::SeFormat getFormat() const override
|
||||
{
|
||||
return textureHandle->format;
|
||||
return format;
|
||||
}
|
||||
virtual Gfx::SeSampleCountFlags getNumSamples() const override
|
||||
{
|
||||
return textureHandle->getNumSamples();
|
||||
return samples;
|
||||
}
|
||||
virtual uint32 getMipLevels() const override
|
||||
{
|
||||
return textureHandle->getMipLevels();
|
||||
return mipLevels;
|
||||
}
|
||||
virtual void changeLayout(Gfx::SeImageLayout newLayout) override;
|
||||
virtual void download(uint32 mipLevel, uint32 arrayLayer, uint32 face, Array<uint8>& buffer) override;
|
||||
virtual void* getNativeHandle() override
|
||||
{
|
||||
return textureHandle;
|
||||
}
|
||||
inline VkImage getHandle() const
|
||||
{
|
||||
return textureHandle->image;
|
||||
}
|
||||
inline VkImageView getView() const
|
||||
{
|
||||
return textureHandle->defaultView;
|
||||
}
|
||||
inline bool isDepthStencil() const
|
||||
{
|
||||
return textureHandle->isDepthStencil();
|
||||
}
|
||||
protected:
|
||||
// Inherited via QueueOwnedResource
|
||||
virtual void executeOwnershipBarrier(Gfx::QueueType newOwner);
|
||||
virtual void executePipelineBarrier(VkAccessFlags srcAccess, VkPipelineStageFlags srcStage,
|
||||
VkAccessFlags dstAccess, VkPipelineStageFlags dstStage);
|
||||
|
||||
};
|
||||
DEFINE_REF(TextureCube)
|
||||
|
||||
}
|
||||
}
|
||||
@@ -2,6 +2,7 @@
|
||||
#include "Window/WindowManager.h"
|
||||
#include "MaterialInstance.h"
|
||||
#include "Graphics/Graphics.h"
|
||||
#include "Graphics/Shader.h"
|
||||
|
||||
using namespace Seele;
|
||||
|
||||
|
||||
@@ -223,7 +223,7 @@ void SamplerParameter::save(ArchiveBuffer& buffer) const
|
||||
void SamplerParameter::load(ArchiveBuffer& buffer)
|
||||
{
|
||||
ShaderParameter::load(buffer);
|
||||
data = buffer.getGraphics()->createSamplerState({});
|
||||
data = buffer.getGraphics()->createSampler({});
|
||||
}
|
||||
|
||||
CombinedTextureParameter::CombinedTextureParameter(std::string name, uint32 byteOffset, uint32 binding)
|
||||
@@ -260,7 +260,7 @@ void CombinedTextureParameter::load(ArchiveBuffer& buffer)
|
||||
std::string filename;
|
||||
Serialization::load(buffer, filename);
|
||||
data = AssetRegistry::findTexture(filename);
|
||||
sampler = buffer.getGraphics()->createSamplerState({});
|
||||
sampler = buffer.getGraphics()->createSampler({});
|
||||
}
|
||||
|
||||
ConstantExpression::ConstantExpression()
|
||||
|
||||
@@ -105,11 +105,11 @@ struct TextureParameter : public ShaderParameter
|
||||
virtual void load(ArchiveBuffer& buffer) override;
|
||||
};
|
||||
DEFINE_REF(TextureParameter)
|
||||
DECLARE_NAME_REF(Gfx, SamplerState)
|
||||
DECLARE_NAME_REF(Gfx, Sampler)
|
||||
struct SamplerParameter : public ShaderParameter
|
||||
{
|
||||
static constexpr uint64 IDENTIFIER = 0x08;
|
||||
Gfx::OSamplerState data;
|
||||
Gfx::OSampler data;
|
||||
SamplerParameter() {}
|
||||
SamplerParameter(std::string name, uint32 byteOffset, uint32 binding);
|
||||
virtual ~SamplerParameter();
|
||||
@@ -124,7 +124,7 @@ struct CombinedTextureParameter : public ShaderParameter
|
||||
{
|
||||
static constexpr uint64 IDENTIFIER = 0x10;
|
||||
PTextureAsset data;
|
||||
Gfx::PSamplerState sampler;
|
||||
Gfx::PSampler sampler;
|
||||
CombinedTextureParameter() {}
|
||||
CombinedTextureParameter(std::string name, uint32 byteOffset, uint32 binding);
|
||||
virtual ~CombinedTextureParameter();
|
||||
|
||||
@@ -23,7 +23,7 @@ LightEnvironment::LightEnvironment(Gfx::PGraphics graphics)
|
||||
.size = sizeof(Component::DirectionalLight) * MAX_DIRECTIONAL_LIGHTS,
|
||||
.data = nullptr,
|
||||
},
|
||||
.stride = sizeof(Component::DirectionalLight),
|
||||
.numElements = MAX_DIRECTIONAL_LIGHTS,
|
||||
.dynamic = true,
|
||||
});
|
||||
pointLights = graphics->createShaderBuffer(ShaderBufferCreateInfo{
|
||||
@@ -31,7 +31,7 @@ LightEnvironment::LightEnvironment(Gfx::PGraphics graphics)
|
||||
.size = sizeof(Component::PointLight) * MAX_POINT_LIGHTS,
|
||||
.data = nullptr,
|
||||
},
|
||||
.stride = sizeof(Component::PointLight),
|
||||
.numElements = MAX_POINT_LIGHTS,
|
||||
.dynamic = true,
|
||||
});
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user