40 const std::string& vertShaderPath,
41 const std::string& fragShaderPath,
42 const VkVertexInputBindingDescription& bindingDescription,
43 const std::vector<VkVertexInputAttributeDescription>& attributeDescriptions
45 auto vertShaderCode =
readFile(vertShaderPath);
46 auto fragShaderCode =
readFile(fragShaderPath);
48 log(
"Creating shader modules...");
49 auto createShaderModule = [&](
const std::vector<char>& code) {
50 VkShaderModuleCreateInfo createInfo{};
51 createInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
52 createInfo.codeSize = code.size();
53 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
55 VkShaderModule shaderModule;
56 if (vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &shaderModule) != VK_SUCCESS) {
62 VkShaderModule vertShaderModule = createShaderModule(vertShaderCode);
63 VkShaderModule fragShaderModule = createShaderModule(fragShaderCode);
65 log(
"Defining shader stages...");
66 VkPipelineShaderStageCreateInfo vertShaderStageInfo{};
67 vertShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
68 vertShaderStageInfo.stage = VK_SHADER_STAGE_VERTEX_BIT;
69 vertShaderStageInfo.module = vertShaderModule;
70 vertShaderStageInfo.pName =
"main";
72 VkPipelineShaderStageCreateInfo fragShaderStageInfo{};
73 fragShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
74 fragShaderStageInfo.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
75 fragShaderStageInfo.module = fragShaderModule;
76 fragShaderStageInfo.pName =
"main";
78 VkPipelineShaderStageCreateInfo shaderStages[] = {vertShaderStageInfo, fragShaderStageInfo};
80 log(
"Creating vertex input state...");
81 VkPipelineVertexInputStateCreateInfo vertexInputInfo{};
82 vertexInputInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO;
83 vertexInputInfo.vertexBindingDescriptionCount = 1;
84 vertexInputInfo.pVertexBindingDescriptions = &bindingDescription;
85 vertexInputInfo.vertexAttributeDescriptionCount =
static_cast<uint32_t
>(attributeDescriptions.size());
86 vertexInputInfo.pVertexAttributeDescriptions = attributeDescriptions.data();
88 log(
"Creating pipeline state...");
89 VkPipelineInputAssemblyStateCreateInfo inputAssembly{};
90 inputAssembly.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
91 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
92 inputAssembly.primitiveRestartEnable = VK_FALSE;
94 VkViewport viewport{};
97 viewport.width =
static_cast<float>(
m_r_context.currentRenderResolution.x);
98 viewport.height =
static_cast<float>(
m_r_context.currentRenderResolution.y);
99 viewport.minDepth = 0.0f;
100 viewport.maxDepth = 1.0f;
103 scissor.offset = {0, 0};
104 scissor.extent = {m_currentRenderResolution.x, m_currentRenderResolution.y};
106 log(
"Creating viewport state...");
107 VkPipelineViewportStateCreateInfo viewportState{};
108 viewportState.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO;
109 viewportState.viewportCount = 1;
110 viewportState.pViewports = &viewport;
111 viewportState.scissorCount = 1;
112 viewportState.pScissors = &scissor;
114 log(
"Creating resterazer...");
115 VkPipelineRasterizationStateCreateInfo rasterizer{};
116 rasterizer.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO;
117 rasterizer.depthClampEnable = VK_FALSE;
118 rasterizer.rasterizerDiscardEnable = VK_FALSE;
119 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
120 rasterizer.lineWidth = 1.0f;
121 rasterizer.cullMode = VK_CULL_MODE_BACK_BIT;
122 rasterizer.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;
123 rasterizer.depthBiasEnable = VK_FALSE;
125 log(
"Creating multisampling...");
126 VkPipelineMultisampleStateCreateInfo multisampling{};
127 multisampling.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO;
128 multisampling.sampleShadingEnable = VK_FALSE;
129 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
131 VkPipelineColorBlendAttachmentState colorBlendAttachment{};
132 colorBlendAttachment.colorWriteMask =
133 VK_COLOR_COMPONENT_R_BIT |
134 VK_COLOR_COMPONENT_G_BIT |
135 VK_COLOR_COMPONENT_B_BIT |
136 VK_COLOR_COMPONENT_A_BIT;
137 colorBlendAttachment.blendEnable = VK_FALSE;
138 colorBlendAttachment.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;
139 colorBlendAttachment.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
140 colorBlendAttachment.colorBlendOp = VK_BLEND_OP_ADD;
141 colorBlendAttachment.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
142 colorBlendAttachment.dstAlphaBlendFactor = VK_BLEND_FACTOR_ZERO;
143 colorBlendAttachment.alphaBlendOp = VK_BLEND_OP_ADD;
145 VkPipelineColorBlendStateCreateInfo colorBlending{};
146 colorBlending.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
147 colorBlending.logicOpEnable = VK_FALSE;
148 colorBlending.attachmentCount = 1;
149 colorBlending.pAttachments = &colorBlendAttachment;
151 log(
"Creating Pipeline layout...");
152 VkPushConstantRange pushConstantRange{};
153 pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT;
154 pushConstantRange.offset = 0;
157 VkDescriptorSetLayout textureLayout =
m_r_context.supportsBindlessTextures
161 std::array<VkDescriptorSetLayout, 2> setLayouts = {
166 VkPipelineLayoutCreateInfo pipelineLayoutInfo{};
167 pipelineLayoutInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
168 pipelineLayoutInfo.setLayoutCount = setLayouts.size();
169 pipelineLayoutInfo.pSetLayouts = setLayouts.data();
170 pipelineLayoutInfo.pushConstantRangeCount = 1;
171 pipelineLayoutInfo.pPushConstantRanges = &pushConstantRange;
173 log(
"Creating pipeline layout with %d descriptor sets", setLayouts.size());
174 if (vkCreatePipelineLayout(
m_r_context.device, &pipelineLayoutInfo,
nullptr, &m_layout) != VK_SUCCESS) {
178 VkPipelineDepthStencilStateCreateInfo depthStencil{};
179 depthStencil.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO;
180 depthStencil.depthTestEnable = VK_TRUE;
181 depthStencil.depthWriteEnable = VK_TRUE;
182 depthStencil.depthCompareOp = VK_COMPARE_OP_LESS;
183 depthStencil.depthBoundsTestEnable = VK_FALSE;
184 depthStencil.minDepthBounds = 0.0f;
185 depthStencil.maxDepthBounds = 1.0f;
186 depthStencil.stencilTestEnable = VK_FALSE;
188 std::vector<VkDynamicState> dynamicStates = {
189 VK_DYNAMIC_STATE_VIEWPORT,
190 VK_DYNAMIC_STATE_SCISSOR
193 VkPipelineDynamicStateCreateInfo dynamicState{};
194 dynamicState.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO;
195 dynamicState.dynamicStateCount =
static_cast<uint32_t
>(dynamicStates.size());
196 dynamicState.pDynamicStates = dynamicStates.data();
198 VkPipelineRenderingCreateInfo renderingCreateInfo{};
199 renderingCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO;
200 renderingCreateInfo.colorAttachmentCount = 1;
201 renderingCreateInfo.pColorAttachmentFormats = &
m_r_context.swapchainImageFormat;
202 renderingCreateInfo.depthAttachmentFormat =
m_r_context.depthFormat;
204 log(
"Creating Graphics pipeline...");
205 VkGraphicsPipelineCreateInfo pipelineInfo{};
206 pipelineInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO;
207 pipelineInfo.stageCount = 2;
208 pipelineInfo.pStages = shaderStages;
209 pipelineInfo.pVertexInputState = &vertexInputInfo;
210 pipelineInfo.pInputAssemblyState = &inputAssembly;
211 pipelineInfo.pViewportState = &viewportState;
212 pipelineInfo.pRasterizationState = &rasterizer;
213 pipelineInfo.pMultisampleState = &multisampling;
214 pipelineInfo.pColorBlendState = &colorBlending;
215 pipelineInfo.pDepthStencilState = &depthStencil;
216 pipelineInfo.pDynamicState = &dynamicState;
217 pipelineInfo.layout = m_layout;
218 pipelineInfo.pNext = &renderingCreateInfo;
220 if (vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1, &pipelineInfo,
nullptr, &m_pipeline) != VK_SUCCESS) {
224 log(
"Cleanup shader modules...");
225 vkDestroyShaderModule(
m_r_context.device, vertShaderModule,
nullptr);
226 vkDestroyShaderModule(
m_r_context.device, fragShaderModule,
nullptr);
230 const std::string& vertShaderPath,
231 const std::string& fragShaderPath,
232 const VkVertexInputBindingDescription& bindingDescription,
233 const std::vector<VkVertexInputAttributeDescription>& attributeDescriptions
235 auto vertShaderCode =
readFile(vertShaderPath);
236 auto fragShaderCode =
readFile(fragShaderPath);
238 log(
"Creating shader modules...");
239 auto createShaderModule = [&](
const std::vector<char>& code) {
240 VkShaderModuleCreateInfo createInfo{};
241 createInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
242 createInfo.codeSize = code.size();
243 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
245 VkShaderModule shaderModule;
246 if (vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &shaderModule) != VK_SUCCESS) {
252 VkShaderModule vertShaderModule = createShaderModule(vertShaderCode);
253 VkShaderModule fragShaderModule = createShaderModule(fragShaderCode);
255 log(
"Defining shader stages...");
256 VkPipelineShaderStageCreateInfo vertShaderStageInfo{};
257 vertShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
258 vertShaderStageInfo.stage = VK_SHADER_STAGE_VERTEX_BIT;
259 vertShaderStageInfo.module = vertShaderModule;
260 vertShaderStageInfo.pName =
"main";
262 VkPipelineShaderStageCreateInfo fragShaderStageInfo{};
263 fragShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
264 fragShaderStageInfo.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
265 fragShaderStageInfo.module = fragShaderModule;
266 fragShaderStageInfo.pName =
"main";
268 VkPipelineShaderStageCreateInfo shaderStages[] = {vertShaderStageInfo, fragShaderStageInfo};
270 log(
"Creating vertex input state...");
271 VkPipelineVertexInputStateCreateInfo vertexInputInfo{};
272 vertexInputInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO;
273 vertexInputInfo.vertexBindingDescriptionCount = 1;
274 vertexInputInfo.pVertexBindingDescriptions = &bindingDescription;
275 vertexInputInfo.vertexAttributeDescriptionCount =
static_cast<uint32_t
>(attributeDescriptions.size());
276 vertexInputInfo.pVertexAttributeDescriptions = attributeDescriptions.data();
278 log(
"Creating pipeline state...");
279 VkPipelineInputAssemblyStateCreateInfo inputAssembly{};
280 inputAssembly.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
281 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
282 inputAssembly.primitiveRestartEnable = VK_FALSE;
284 VkViewport viewport{};
287 viewport.width =
static_cast<float>(
m_r_context.currentRenderResolution.x);
288 viewport.height =
static_cast<float>(
m_r_context.currentRenderResolution.y);
289 viewport.minDepth = 0.0f;
290 viewport.maxDepth = 1.0f;
293 scissor.offset = {0, 0};
294 scissor.extent = {m_currentRenderResolution.x, m_currentRenderResolution.y};
296 log(
"Creating viewport state...");
297 VkPipelineViewportStateCreateInfo viewportState{};
298 viewportState.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO;
299 viewportState.viewportCount = 1;
300 viewportState.pViewports = &viewport;
301 viewportState.scissorCount = 1;
302 viewportState.pScissors = &scissor;
304 log(
"Creating resterazer...");
305 VkPipelineRasterizationStateCreateInfo rasterizer{};
306 rasterizer.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO;
307 rasterizer.depthClampEnable = VK_FALSE;
308 rasterizer.rasterizerDiscardEnable = VK_FALSE;
309 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
310 rasterizer.lineWidth = 1.0f;
311 rasterizer.cullMode = VK_CULL_MODE_BACK_BIT;
312 rasterizer.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;
313 rasterizer.depthBiasEnable = VK_FALSE;
315 log(
"Creating multisampling...");
316 VkPipelineMultisampleStateCreateInfo multisampling{};
317 multisampling.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO;
318 multisampling.sampleShadingEnable = VK_FALSE;
319 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
321 VkPipelineColorBlendAttachmentState accumBlend{};
322 accumBlend.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT;
323 accumBlend.blendEnable = VK_TRUE;
324 accumBlend.srcColorBlendFactor = VK_BLEND_FACTOR_ONE;
325 accumBlend.dstColorBlendFactor = VK_BLEND_FACTOR_ONE;
326 accumBlend.colorBlendOp = VK_BLEND_OP_ADD;
327 accumBlend.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
328 accumBlend.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
329 accumBlend.alphaBlendOp = VK_BLEND_OP_ADD;
331 VkPipelineColorBlendAttachmentState revealBlend{};
332 revealBlend.colorWriteMask = VK_COLOR_COMPONENT_R_BIT;
333 revealBlend.blendEnable = VK_TRUE;
334 revealBlend.srcColorBlendFactor = VK_BLEND_FACTOR_ZERO;
335 revealBlend.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_COLOR;
336 revealBlend.colorBlendOp = VK_BLEND_OP_ADD;
337 revealBlend.srcAlphaBlendFactor = VK_BLEND_FACTOR_ZERO;
338 revealBlend.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
339 revealBlend.alphaBlendOp = VK_BLEND_OP_ADD;
341 VkPipelineColorBlendAttachmentState colorBlendAttachments[] = { accumBlend, revealBlend };
343 VkPipelineColorBlendStateCreateInfo colorBlending{};
344 colorBlending.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
345 colorBlending.logicOpEnable = VK_FALSE;
346 colorBlending.attachmentCount = 2;
347 colorBlending.pAttachments = colorBlendAttachments;
349 log(
"Creating Pipeline layout...");
350 VkPushConstantRange pushConstantRange{};
351 pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT;
352 pushConstantRange.offset = 0;
355 VkDescriptorSetLayout textureLayout =
m_r_context.supportsBindlessTextures
359 std::array<VkDescriptorSetLayout, 2> setLayouts = {
364 VkPipelineLayoutCreateInfo pipelineLayoutInfo{};
365 pipelineLayoutInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
366 pipelineLayoutInfo.setLayoutCount = setLayouts.size();
367 pipelineLayoutInfo.pSetLayouts = setLayouts.data();
368 pipelineLayoutInfo.pushConstantRangeCount = 1;
369 pipelineLayoutInfo.pPushConstantRanges = &pushConstantRange;
371 log(
"Creating pipeline layout with %d descriptor sets", setLayouts.size());
372 if (vkCreatePipelineLayout(
m_r_context.device, &pipelineLayoutInfo,
nullptr, &m_layout) != VK_SUCCESS) {
376 VkPipelineDepthStencilStateCreateInfo depthStencil{};
377 depthStencil.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO;
378 depthStencil.depthTestEnable = VK_TRUE;
379 depthStencil.depthWriteEnable = VK_FALSE;
380 depthStencil.depthCompareOp = VK_COMPARE_OP_LESS;
381 depthStencil.depthBoundsTestEnable = VK_FALSE;
382 depthStencil.minDepthBounds = 0.0f;
383 depthStencil.maxDepthBounds = 1.0f;
384 depthStencil.stencilTestEnable = VK_FALSE;
386 std::vector<VkDynamicState> dynamicStates = {
387 VK_DYNAMIC_STATE_VIEWPORT,
388 VK_DYNAMIC_STATE_SCISSOR
391 VkPipelineDynamicStateCreateInfo dynamicState{};
392 dynamicState.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO;
393 dynamicState.dynamicStateCount =
static_cast<uint32_t
>(dynamicStates.size());
394 dynamicState.pDynamicStates = dynamicStates.data();
396 VkFormat transFormats[] = { VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8_UNORM };
397 VkPipelineRenderingCreateInfo renderingCreateInfo{};
398 renderingCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO;
399 renderingCreateInfo.colorAttachmentCount = 2;
400 renderingCreateInfo.pColorAttachmentFormats = transFormats;
401 renderingCreateInfo.depthAttachmentFormat =
m_r_context.depthFormat;
403 log(
"Creating Graphics pipeline...");
404 VkGraphicsPipelineCreateInfo pipelineInfo{};
405 pipelineInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO;
406 pipelineInfo.stageCount = 2;
407 pipelineInfo.pStages = shaderStages;
408 pipelineInfo.pVertexInputState = &vertexInputInfo;
409 pipelineInfo.pInputAssemblyState = &inputAssembly;
410 pipelineInfo.pViewportState = &viewportState;
411 pipelineInfo.pRasterizationState = &rasterizer;
412 pipelineInfo.pMultisampleState = &multisampling;
413 pipelineInfo.pColorBlendState = &colorBlending;
414 pipelineInfo.pDepthStencilState = &depthStencil;
415 pipelineInfo.pDynamicState = &dynamicState;
416 pipelineInfo.layout = m_layout;
417 pipelineInfo.pNext = &renderingCreateInfo;
419 if (vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1, &pipelineInfo,
nullptr, &m_pipeline) != VK_SUCCESS) {
423 log(
"Cleanup shader modules...");
424 vkDestroyShaderModule(
m_r_context.device, vertShaderModule,
nullptr);
425 vkDestroyShaderModule(
m_r_context.device, fragShaderModule,
nullptr);
429 const std::string& vertShaderPath,
430 const std::string& fragShaderPath,
431 const VkVertexInputBindingDescription& bindingDescription,
432 const std::vector<VkVertexInputAttributeDescription>& attributeDescriptions
434 auto vertShaderCode =
readFile(vertShaderPath);
435 auto fragShaderCode =
readFile(fragShaderPath);
437 log(
"Creating shader modules...");
438 auto createShaderModule = [&](
const std::vector<char>& code) {
439 VkShaderModuleCreateInfo createInfo{};
440 createInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
441 createInfo.codeSize = code.size();
442 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
444 VkShaderModule shaderModule;
445 if (vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &shaderModule) != VK_SUCCESS) {
451 VkShaderModule vertShaderModule = createShaderModule(vertShaderCode);
452 VkShaderModule fragShaderModule = createShaderModule(fragShaderCode);
454 log(
"Defining shader stages...");
455 VkPipelineShaderStageCreateInfo vertShaderStageInfo{};
456 vertShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
457 vertShaderStageInfo.stage = VK_SHADER_STAGE_VERTEX_BIT;
458 vertShaderStageInfo.module = vertShaderModule;
459 vertShaderStageInfo.pName =
"main";
461 VkPipelineShaderStageCreateInfo fragShaderStageInfo{};
462 fragShaderStageInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
463 fragShaderStageInfo.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
464 fragShaderStageInfo.module = fragShaderModule;
465 fragShaderStageInfo.pName =
"main";
467 VkPipelineShaderStageCreateInfo shaderStages[] = {vertShaderStageInfo, fragShaderStageInfo};
469 log(
"Creating vertex input state...");
470 VkPipelineVertexInputStateCreateInfo vertexInputInfo{};
471 vertexInputInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO;
472 vertexInputInfo.vertexBindingDescriptionCount = 1;
473 vertexInputInfo.pVertexBindingDescriptions = &bindingDescription;
474 vertexInputInfo.vertexAttributeDescriptionCount =
static_cast<uint32_t
>(attributeDescriptions.size());
475 vertexInputInfo.pVertexAttributeDescriptions = attributeDescriptions.data();
477 log(
"Creating pipeline state...");
478 VkPipelineInputAssemblyStateCreateInfo inputAssembly{};
479 inputAssembly.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
480 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
481 inputAssembly.primitiveRestartEnable = VK_FALSE;
483 VkViewport viewport{};
486 viewport.width =
static_cast<float>(
m_r_context.currentRenderResolution.x);
487 viewport.height =
static_cast<float>(
m_r_context.currentRenderResolution.y);
488 viewport.minDepth = 0.0f;
489 viewport.maxDepth = 1.0f;
492 scissor.offset = {0, 0};
493 scissor.extent = {m_currentRenderResolution.x, m_currentRenderResolution.y};
495 log(
"Creating viewport state...");
496 VkPipelineViewportStateCreateInfo viewportState{};
497 viewportState.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO;
498 viewportState.viewportCount = 1;
499 viewportState.pViewports = &viewport;
500 viewportState.scissorCount = 1;
501 viewportState.pScissors = &scissor;
503 log(
"Creating resterazer...");
504 VkPipelineRasterizationStateCreateInfo rasterizer{};
505 rasterizer.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO;
506 rasterizer.depthClampEnable = VK_FALSE;
507 rasterizer.rasterizerDiscardEnable = VK_FALSE;
508 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
509 rasterizer.lineWidth = 1.0f;
510 rasterizer.cullMode = VK_CULL_MODE_NONE;
511 rasterizer.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;
512 rasterizer.depthBiasEnable = VK_FALSE;
514 log(
"Creating multisampling...");
515 VkPipelineMultisampleStateCreateInfo multisampling{};
516 multisampling.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO;
517 multisampling.sampleShadingEnable = VK_FALSE;
518 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
520 VkPipelineColorBlendAttachmentState colorBlendAttachment{};
521 colorBlendAttachment.colorWriteMask =
522 VK_COLOR_COMPONENT_R_BIT |
523 VK_COLOR_COMPONENT_G_BIT |
524 VK_COLOR_COMPONENT_B_BIT |
525 VK_COLOR_COMPONENT_A_BIT;
526 colorBlendAttachment.blendEnable = VK_FALSE;
527 colorBlendAttachment.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;
528 colorBlendAttachment.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
529 colorBlendAttachment.colorBlendOp = VK_BLEND_OP_ADD;
530 colorBlendAttachment.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
531 colorBlendAttachment.dstAlphaBlendFactor = VK_BLEND_FACTOR_ZERO;
532 colorBlendAttachment.alphaBlendOp = VK_BLEND_OP_ADD;
534 VkPipelineColorBlendStateCreateInfo colorBlending{};
535 colorBlending.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
536 colorBlending.logicOpEnable = VK_FALSE;
537 colorBlending.attachmentCount = 1;
538 colorBlending.pAttachments = &colorBlendAttachment;
540 log(
"Creating Pipeline layout...");
541 VkPushConstantRange pushConstantRange{};
542 pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT;
543 pushConstantRange.offset = 0;
546 VkDescriptorSetLayout textureLayout =
m_r_context.supportsBindlessTextures
550 std::array<VkDescriptorSetLayout, 2> setLayouts = {
555 VkPipelineLayoutCreateInfo pipelineLayoutInfo{};
556 pipelineLayoutInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
557 pipelineLayoutInfo.setLayoutCount = setLayouts.size();
558 pipelineLayoutInfo.pSetLayouts = setLayouts.data();
559 pipelineLayoutInfo.pushConstantRangeCount = 1;
560 pipelineLayoutInfo.pPushConstantRanges = &pushConstantRange;
562 log(
"Creating pipeline layout with %d descriptor sets", setLayouts.size());
563 if (vkCreatePipelineLayout(
m_r_context.device, &pipelineLayoutInfo,
nullptr, &m_layout) != VK_SUCCESS) {
567 VkPipelineDepthStencilStateCreateInfo depthStencil{};
568 depthStencil.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO;
569 depthStencil.depthTestEnable = VK_TRUE;
570 depthStencil.depthWriteEnable = VK_TRUE;
571 depthStencil.depthCompareOp = VK_COMPARE_OP_LESS;
572 depthStencil.depthBoundsTestEnable = VK_FALSE;
573 depthStencil.minDepthBounds = 0.0f;
574 depthStencil.maxDepthBounds = 1.0f;
575 depthStencil.stencilTestEnable = VK_FALSE;
577 std::vector<VkDynamicState> dynamicStates = {
578 VK_DYNAMIC_STATE_VIEWPORT,
579 VK_DYNAMIC_STATE_SCISSOR
582 VkPipelineDynamicStateCreateInfo dynamicState{};
583 dynamicState.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO;
584 dynamicState.dynamicStateCount =
static_cast<uint32_t
>(dynamicStates.size());
585 dynamicState.pDynamicStates = dynamicStates.data();
587 VkPipelineRenderingCreateInfo renderingCreateInfo{};
588 renderingCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO;
589 renderingCreateInfo.colorAttachmentCount = 1;
590 renderingCreateInfo.pColorAttachmentFormats = &
m_r_context.swapchainImageFormat;
591 renderingCreateInfo.depthAttachmentFormat =
m_r_context.depthFormat;
593 log(
"Creating Graphics pipeline...");
594 VkGraphicsPipelineCreateInfo pipelineInfo{};
595 pipelineInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO;
596 pipelineInfo.stageCount = 2;
597 pipelineInfo.pStages = shaderStages;
598 pipelineInfo.pVertexInputState = &vertexInputInfo;
599 pipelineInfo.pInputAssemblyState = &inputAssembly;
600 pipelineInfo.pViewportState = &viewportState;
601 pipelineInfo.pRasterizationState = &rasterizer;
602 pipelineInfo.pMultisampleState = &multisampling;
603 pipelineInfo.pColorBlendState = &colorBlending;
604 pipelineInfo.pDepthStencilState = &depthStencil;
605 pipelineInfo.pDynamicState = &dynamicState;
606 pipelineInfo.layout = m_layout;
607 pipelineInfo.pNext = &renderingCreateInfo;
609 if (vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1, &pipelineInfo,
nullptr, &m_pipeline) != VK_SUCCESS) {
613 log(
"Cleanup shader modules...");
614 vkDestroyShaderModule(
m_r_context.device, vertShaderModule,
nullptr);
615 vkDestroyShaderModule(
m_r_context.device, fragShaderModule,
nullptr);
619 auto vertShaderCode =
readFile(vertPath);
620 auto fragShaderCode =
readFile(fragPath);
622 auto createShaderModule = [&](
const std::vector<char>& code) {
623 VkShaderModuleCreateInfo createInfo{VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO};
624 createInfo.codeSize = code.size();
625 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
627 vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &mod);
630 VkShaderModule vertMod = createShaderModule(vertShaderCode);
631 VkShaderModule fragMod = createShaderModule(fragShaderCode);
633 VkPipelineShaderStageCreateInfo stages[] = {
634 {VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
nullptr, 0, VK_SHADER_STAGE_VERTEX_BIT, vertMod,
"main",
nullptr},
635 {VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
nullptr, 0, VK_SHADER_STAGE_FRAGMENT_BIT, fragMod,
"main",
nullptr}
638 VkPipelineVertexInputStateCreateInfo vertexInputInfo{VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO};
639 vertexInputInfo.vertexBindingDescriptionCount = 0;
640 vertexInputInfo.pVertexBindingDescriptions =
nullptr;
641 vertexInputInfo.vertexAttributeDescriptionCount = 0;
642 vertexInputInfo.pVertexAttributeDescriptions =
nullptr;
644 VkPipelineInputAssemblyStateCreateInfo inputAssembly{VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO};
645 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
646 inputAssembly.primitiveRestartEnable = VK_FALSE;
648 VkViewport viewport{0, 0, (float)
m_r_context.currentRenderResolution.x, (
float)
m_r_context.currentRenderResolution.y, 0.0f, 1.0f};
650 VkPipelineViewportStateCreateInfo viewportState{VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO,
nullptr, 0, 1, &viewport, 1, &scissor};
652 VkPipelineRasterizationStateCreateInfo rasterizer{VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO};
653 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
654 rasterizer.cullMode = VK_CULL_MODE_NONE;
655 rasterizer.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;
656 rasterizer.lineWidth = 1.0f;
657 rasterizer.depthClampEnable = VK_FALSE;
658 rasterizer.rasterizerDiscardEnable = VK_FALSE;
659 rasterizer.depthBiasEnable = VK_FALSE;
661 VkPipelineMultisampleStateCreateInfo multisampling{VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO};
662 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
663 multisampling.sampleShadingEnable = VK_FALSE;
665 VkPipelineColorBlendAttachmentState accumBlend{};
666 accumBlend.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT;
668 VkPipelineColorBlendAttachmentState revealBlend{};
669 revealBlend.colorWriteMask = VK_COLOR_COMPONENT_R_BIT;
671 VkPipelineColorBlendStateCreateInfo colorBlending{VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO};
672 colorBlending.logicOpEnable = VK_FALSE;
674 VkPipelineColorBlendAttachmentState transAttachments[2];
677 accumBlend.blendEnable = VK_TRUE;
678 accumBlend.srcColorBlendFactor = VK_BLEND_FACTOR_ONE;
679 accumBlend.dstColorBlendFactor = VK_BLEND_FACTOR_ONE;
680 accumBlend.colorBlendOp = VK_BLEND_OP_ADD;
681 accumBlend.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
682 accumBlend.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
683 accumBlend.alphaBlendOp = VK_BLEND_OP_ADD;
685 revealBlend.blendEnable = VK_TRUE;
686 revealBlend.srcColorBlendFactor = VK_BLEND_FACTOR_ZERO;
687 revealBlend.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_COLOR;
688 revealBlend.colorBlendOp = VK_BLEND_OP_ADD;
689 revealBlend.srcAlphaBlendFactor = VK_BLEND_FACTOR_ZERO;
690 revealBlend.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
691 revealBlend.alphaBlendOp = VK_BLEND_OP_ADD;
693 transAttachments[0] = accumBlend;
694 transAttachments[1] = revealBlend;
696 colorBlending.attachmentCount = 2;
697 colorBlending.pAttachments = transAttachments;
699 accumBlend.blendEnable = VK_FALSE;
700 accumBlend.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;
701 accumBlend.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
702 accumBlend.colorBlendOp = VK_BLEND_OP_ADD;
703 accumBlend.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
704 accumBlend.dstAlphaBlendFactor = VK_BLEND_FACTOR_ZERO;
705 accumBlend.alphaBlendOp = VK_BLEND_OP_ADD;
706 colorBlending.attachmentCount = 1;
707 colorBlending.pAttachments = &accumBlend;
710 VkPipelineDepthStencilStateCreateInfo depthStencil{VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO};
711 depthStencil.depthTestEnable = VK_TRUE;
712 depthStencil.depthWriteEnable = isTransparent ? VK_FALSE : VK_TRUE;
713 depthStencil.depthCompareOp = VK_COMPARE_OP_LESS;
714 depthStencil.depthBoundsTestEnable = VK_FALSE;
715 depthStencil.stencilTestEnable = VK_FALSE;
716 depthStencil.minDepthBounds = 0.0f;
717 depthStencil.maxDepthBounds = 1.0f;
719 std::vector<VkDynamicState> dynamicStates = { VK_DYNAMIC_STATE_VIEWPORT, VK_DYNAMIC_STATE_SCISSOR };
720 VkPipelineDynamicStateCreateInfo dynamicState{VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
nullptr, 0, (uint32_t)dynamicStates.size(), dynamicStates.data()};
722 std::vector<VkDescriptorSetLayout> setLayouts = {
m_r_context.uboDescriptorSetLayout };
725 setLayouts.push_back(
m_r_context.bindlessDescriptorSetLayout);
727 setLayouts.push_back(
m_r_context.textureDescriptorSetLayout);
731 setLayouts.push_back(
m_r_context.particleDescriptorSetLayout);
734 VkPushConstantRange pushConstantRange{};
735 pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT;
736 pushConstantRange.offset = 0;
737 pushConstantRange.size = isInstanced ? 0 : 48;
739 VkPipelineLayoutCreateInfo layoutInfo{VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO};
740 layoutInfo.setLayoutCount = setLayouts.size();
741 layoutInfo.pSetLayouts = setLayouts.data();
742 layoutInfo.pushConstantRangeCount = isInstanced ? 0 : 1;
743 layoutInfo.pPushConstantRanges = isInstanced ? nullptr : &pushConstantRange;
745 vkCreatePipelineLayout(
m_r_context.device, &layoutInfo,
nullptr, &m_layout);
747 VkFormat transFormats[] = { VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8_UNORM };
748 VkPipelineRenderingCreateInfo renderInfo{VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO};
749 renderInfo.colorAttachmentCount = isTransparent ? 2 : 1;
750 renderInfo.pColorAttachmentFormats = isTransparent ? transFormats : &
m_r_context.swapchainImageFormat;
751 renderInfo.depthAttachmentFormat =
m_r_context.depthFormat;
753 VkGraphicsPipelineCreateInfo pipelineInfo{VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO};
754 pipelineInfo.pNext = &renderInfo;
755 pipelineInfo.stageCount = 2;
756 pipelineInfo.pStages = stages;
757 pipelineInfo.pVertexInputState = &vertexInputInfo;
758 pipelineInfo.pInputAssemblyState = &inputAssembly;
759 pipelineInfo.pViewportState = &viewportState;
760 pipelineInfo.pRasterizationState = &rasterizer;
761 pipelineInfo.pMultisampleState = &multisampling;
762 pipelineInfo.pColorBlendState = &colorBlending;
763 pipelineInfo.pDepthStencilState = &depthStencil;
764 pipelineInfo.pDynamicState = &dynamicState;
765 pipelineInfo.layout = m_layout;
766 pipelineInfo.subpass = 0;
767 pipelineInfo.basePipelineHandle = VK_NULL_HANDLE;
769 vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1, &pipelineInfo,
nullptr, &m_pipeline);
771 vkDestroyShaderModule(
m_r_context.device, vertMod,
nullptr);
772 vkDestroyShaderModule(
m_r_context.device, fragMod,
nullptr);
776 const std::string& vertShaderPath,
777 const std::string& fragShaderPath,
778 const VkVertexInputBindingDescription& bindingDesc,
779 const std::vector<VkVertexInputAttributeDescription>& attrDesc)
781 auto vertShaderCode =
readFile(vertShaderPath);
782 auto fragShaderCode =
readFile(fragShaderPath);
784 auto createShaderModule = [&](
const std::vector<char>& code) {
785 VkShaderModuleCreateInfo createInfo{};
786 createInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
787 createInfo.codeSize = code.size();
788 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
790 VkShaderModule shaderModule;
791 if (vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &shaderModule) != VK_SUCCESS) {
797 VkShaderModule vertShaderModule = createShaderModule(vertShaderCode);
798 VkShaderModule fragShaderModule = createShaderModule(fragShaderCode);
800 VkPipelineShaderStageCreateInfo vertStage{};
801 vertStage.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
802 vertStage.stage = VK_SHADER_STAGE_VERTEX_BIT;
803 vertStage.module = vertShaderModule;
804 vertStage.pName =
"main";
806 VkPipelineShaderStageCreateInfo fragStage{};
807 fragStage.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
808 fragStage.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
809 fragStage.module = fragShaderModule;
810 fragStage.pName =
"main";
812 VkPipelineShaderStageCreateInfo shaderStages[] = { vertStage, fragStage };
814 VkPipelineVertexInputStateCreateInfo vertexInputInfo{};
815 vertexInputInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO;
816 vertexInputInfo.vertexBindingDescriptionCount = 1;
817 vertexInputInfo.pVertexBindingDescriptions = &bindingDesc;
818 vertexInputInfo.vertexAttributeDescriptionCount =
static_cast<uint32_t
>(attrDesc.size());
819 vertexInputInfo.pVertexAttributeDescriptions = attrDesc.data();
821 VkPipelineInputAssemblyStateCreateInfo inputAssembly{};
822 inputAssembly.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
823 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
824 inputAssembly.primitiveRestartEnable = VK_FALSE;
826 VkPipelineViewportStateCreateInfo viewportState{};
827 viewportState.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO;
828 viewportState.viewportCount = 1;
829 viewportState.scissorCount = 1;
831 VkPipelineRasterizationStateCreateInfo rasterizer{};
832 rasterizer.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO;
833 rasterizer.depthClampEnable = VK_FALSE;
834 rasterizer.rasterizerDiscardEnable = VK_FALSE;
835 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
836 rasterizer.lineWidth = 1.0f;
837 rasterizer.cullMode = VK_CULL_MODE_NONE;
838 rasterizer.frontFace = VK_FRONT_FACE_CLOCKWISE;
839 rasterizer.depthBiasEnable = VK_FALSE;
841 VkPipelineMultisampleStateCreateInfo multisampling{};
842 multisampling.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO;
843 multisampling.sampleShadingEnable = VK_FALSE;
844 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
846 VkPipelineColorBlendAttachmentState colorBlendAttachment{};
847 colorBlendAttachment.colorWriteMask =
848 VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT |
849 VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT;
850 colorBlendAttachment.blendEnable = VK_TRUE;
851 colorBlendAttachment.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;
852 colorBlendAttachment.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
853 colorBlendAttachment.colorBlendOp = VK_BLEND_OP_ADD;
854 colorBlendAttachment.srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE;
855 colorBlendAttachment.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;
856 colorBlendAttachment.alphaBlendOp = VK_BLEND_OP_ADD;
858 VkPipelineColorBlendStateCreateInfo colorBlending{};
859 colorBlending.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
860 colorBlending.logicOpEnable = VK_FALSE;
861 colorBlending.attachmentCount = 1;
862 colorBlending.pAttachments = &colorBlendAttachment;
864 VkPipelineDepthStencilStateCreateInfo depthStencil{};
865 depthStencil.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO;
866 depthStencil.depthTestEnable = VK_FALSE;
867 depthStencil.depthWriteEnable = VK_FALSE;
868 depthStencil.stencilTestEnable= VK_FALSE;
870 std::vector<VkDynamicState> dynamicStates = {
871 VK_DYNAMIC_STATE_VIEWPORT,
872 VK_DYNAMIC_STATE_SCISSOR
874 VkPipelineDynamicStateCreateInfo dynamicState{};
875 dynamicState.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO;
876 dynamicState.dynamicStateCount =
static_cast<uint32_t
>(dynamicStates.size());
877 dynamicState.pDynamicStates = dynamicStates.data();
879 VkPushConstantRange pushConstantRange{};
880 pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
881 pushConstantRange.offset = 0;
884 VkDescriptorSetLayout textureLayout =
m_r_context.supportsBindlessTextures
888 std::array<VkDescriptorSetLayout, 2> setLayouts = {
893 VkPipelineLayoutCreateInfo pipelineLayoutInfo{};
894 pipelineLayoutInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
895 pipelineLayoutInfo.setLayoutCount = setLayouts.size();
896 pipelineLayoutInfo.pSetLayouts = setLayouts.data();
897 pipelineLayoutInfo.pushConstantRangeCount = 1;
898 pipelineLayoutInfo.pPushConstantRanges = &pushConstantRange;
900 if (vkCreatePipelineLayout(
m_r_context.device, &pipelineLayoutInfo,
901 nullptr, &m_layout) != VK_SUCCESS) {
902 throw_error(
"Failed to create UI pipeline layout!");
905 VkPipelineRenderingCreateInfo renderingCreateInfo{};
906 renderingCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO;
907 renderingCreateInfo.colorAttachmentCount = 1;
908 renderingCreateInfo.pColorAttachmentFormats = &
m_r_context.swapchainImageFormat;
909 renderingCreateInfo.depthAttachmentFormat =
m_r_context.depthFormat;
911 VkGraphicsPipelineCreateInfo pipelineInfo{};
912 pipelineInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO;
913 pipelineInfo.stageCount = 2;
914 pipelineInfo.pStages = shaderStages;
915 pipelineInfo.pVertexInputState = &vertexInputInfo;
916 pipelineInfo.pInputAssemblyState = &inputAssembly;
917 pipelineInfo.pViewportState = &viewportState;
918 pipelineInfo.pRasterizationState = &rasterizer;
919 pipelineInfo.pMultisampleState = &multisampling;
920 pipelineInfo.pColorBlendState = &colorBlending;
921 pipelineInfo.pDepthStencilState = &depthStencil;
922 pipelineInfo.pDynamicState = &dynamicState;
923 pipelineInfo.layout = m_layout;
924 pipelineInfo.pNext = &renderingCreateInfo;
926 if (vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1,
927 &pipelineInfo,
nullptr, &m_pipeline) != VK_SUCCESS) {
928 throw_error(
"Failed to create UI graphics pipeline");
931 vkDestroyShaderModule(
m_r_context.device, vertShaderModule,
nullptr);
932 vkDestroyShaderModule(
m_r_context.device, fragShaderModule,
nullptr);
936 auto vertShaderCode =
readFile(vertPath);
937 auto fragShaderCode =
readFile(fragPath);
939 auto createShaderModule = [&](
const std::vector<char>& code) {
940 VkShaderModuleCreateInfo createInfo{};
941 createInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
942 createInfo.codeSize = code.size();
943 createInfo.pCode =
reinterpret_cast<const uint32_t*
>(code.data());
945 VkShaderModule shaderModule;
946 if (vkCreateShaderModule(
m_r_context.device, &createInfo,
nullptr, &shaderModule) != VK_SUCCESS) {
952 VkShaderModule vertModule = createShaderModule(vertShaderCode);
953 VkShaderModule fragModule = createShaderModule(fragShaderCode);
955 VkPipelineShaderStageCreateInfo vertStage{};
956 vertStage.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
957 vertStage.stage = VK_SHADER_STAGE_VERTEX_BIT;
958 vertStage.module = vertModule;
959 vertStage.pName =
"main";
961 VkPipelineShaderStageCreateInfo fragStage{};
962 fragStage.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
963 fragStage.stage = VK_SHADER_STAGE_FRAGMENT_BIT;
964 fragStage.module = fragModule;
965 fragStage.pName =
"main";
967 VkPipelineShaderStageCreateInfo stages[] = { vertStage, fragStage };
969 VkPipelineVertexInputStateCreateInfo vertexInputInfo{VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO};
971 VkPipelineInputAssemblyStateCreateInfo inputAssembly{VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO};
972 inputAssembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
974 VkPipelineViewportStateCreateInfo viewportState{VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO};
975 viewportState.viewportCount = 1;
976 viewportState.scissorCount = 1;
978 VkPipelineRasterizationStateCreateInfo rasterizer{VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO};
979 rasterizer.polygonMode = VK_POLYGON_MODE_FILL;
980 rasterizer.lineWidth = 1.0f;
981 rasterizer.cullMode = VK_CULL_MODE_NONE;
982 rasterizer.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;
984 VkPipelineMultisampleStateCreateInfo multisampling{VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO};
985 multisampling.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;
987 VkPipelineColorBlendAttachmentState colorBlendAttachment{};
988 colorBlendAttachment.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT;
989 colorBlendAttachment.blendEnable = VK_FALSE;
991 VkPipelineColorBlendStateCreateInfo colorBlending{VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO};
992 colorBlending.attachmentCount = 1;
993 colorBlending.pAttachments = &colorBlendAttachment;
995 std::array<VkDescriptorSetLayout, 2> setLayouts = {
1000 VkPipelineLayoutCreateInfo pipelineLayoutInfo{VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO};
1001 pipelineLayoutInfo.setLayoutCount = setLayouts.size();
1002 pipelineLayoutInfo.pSetLayouts = setLayouts.data();
1004 if (vkCreatePipelineLayout(
m_r_context.device, &pipelineLayoutInfo,
nullptr, &m_layout) != VK_SUCCESS) {
1005 throw_error(
"Failed to create fullscreen layout");
1008 VkPipelineDepthStencilStateCreateInfo depthStencil{VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO};
1009 depthStencil.depthTestEnable = VK_FALSE;
1010 depthStencil.depthWriteEnable = VK_FALSE;
1012 std::vector<VkDynamicState> dynamicStates = { VK_DYNAMIC_STATE_VIEWPORT, VK_DYNAMIC_STATE_SCISSOR };
1013 VkPipelineDynamicStateCreateInfo dynamicState{VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO};
1014 dynamicState.dynamicStateCount =
static_cast<uint32_t
>(dynamicStates.size());
1015 dynamicState.pDynamicStates = dynamicStates.data();
1017 VkPipelineRenderingCreateInfo renderingCreateInfo{VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO};
1018 renderingCreateInfo.colorAttachmentCount = 1;
1019 renderingCreateInfo.pColorAttachmentFormats = &
m_r_context.swapchainImageFormat;
1021 VkGraphicsPipelineCreateInfo pipelineInfo{VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO};
1022 pipelineInfo.pNext = &renderingCreateInfo;
1023 pipelineInfo.stageCount = 2;
1024 pipelineInfo.pStages = stages;
1025 pipelineInfo.pVertexInputState = &vertexInputInfo;
1026 pipelineInfo.pInputAssemblyState = &inputAssembly;
1027 pipelineInfo.pViewportState = &viewportState;
1028 pipelineInfo.pRasterizationState = &rasterizer;
1029 pipelineInfo.pMultisampleState = &multisampling;
1030 pipelineInfo.pColorBlendState = &colorBlending;
1031 pipelineInfo.pDepthStencilState = &depthStencil;
1032 pipelineInfo.pDynamicState = &dynamicState;
1033 pipelineInfo.layout = m_layout;
1035 if (vkCreateGraphicsPipelines(
m_r_context.device, VK_NULL_HANDLE, 1, &pipelineInfo,
nullptr, &m_pipeline) != VK_SUCCESS) {
1036 throw_error(
"Failed to create fullscreen pipeline");
1039 vkDestroyShaderModule(
m_r_context.device, vertModule,
nullptr);
1040 vkDestroyShaderModule(
m_r_context.device, fragModule,
nullptr);