vulkan游戏引擎的pipeline管道实现

1.vulkan_pipeline.h

#pragma once

#include "vulkan_types.inl"

b8 vulkan_graphics_pipeline_create(

vulkan_context* context,

vulkan_renderpass* renderpass,

u32 attribute_count,

VkVertexInputAttributeDescription* attributes,

u32 descriptor_set_layout_count,

VkDescriptorSetLayout* descriptor_set_layouts,

u32 stage_count,

VkPipelineShaderStageCreateInfo* stages,

VkViewport viewport,

VkRect2D scissor,

b8 is_wireframe,

vulkan_pipeline* out_pipeline

);

void vulkan_pipeline_destroy(vulkan_context* context,vulkan_pipeline* pipeline);

void vulkan_pipeline_bind(vulkan_command_buffer* command_buffer,VkPipelineBindPoint bind_point,vulkan_pipeline* pipeline);

2.vulkan_pipeline.c

#include "vulkan_pipeline.h"

#include "vulkan_utils.h"

#include "core/kmemory.h"

#include "core/logger.h"

#include "math/math_types.h"

b8 vulkan_graphics_pipeline_create(

vulkan_context* context,

vulkan_renderpass* renderpass,

u32 attribute_count,

VkVertexInputAttributeDescription* attributes,

u32 descriptor_set_layout_count,

VkDescriptorSetLayout* descriptor_set_layouts,

u32 stage_count,

VkPipelineShaderStageCreateInfo* stages,

VkViewport viewport,

VkRect2D scissor,

b8 is_wireframe,

vulkan_pipeline* out_pipeline

)

{

//viewport state

VkPipelineViewportStateCreateInfo viewport_state = {VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO};

viewport_state.viewportCount = 1;

viewport_state.pViewports = &viewport;

viewport_state.scissorCount = 1;

viewport_state.pScissors=&scissor;

//Rasterizer

VkPipelineRasterizationStateCreateInfo rasterizer_create_info = {VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO};

rasterizer_create_info.depthClampEnable = VK_FALSE;

rasterizer_create_info.rasterizerDiscardEnable = VK_FALSE;

rasterizer_create_info.polygonMode = is_wireframe ? VK_POLYGON_MODE_LINE : VK_POLYGON_MODE_FILL;

rasterizer_create_info.lineWidth = 1.0f;

rasterizer_create_info.cullMode = VK_CULL_MODE_BACK_BIT;

rasterizer_create_info.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE;

rasterizer_create_info.depthBiasEnable = VK_FALSE;

rasterizer_create_info.depthBiasConstantFactor = 0.0f;

rasterizer_create_info.depthBiasClamp = 0.0f;

rasterizer_create_info.depthBiasSlopeFactor = 0.0f;

//Multisampling

VkPipelineMultisampleStateCreateInfo multisampling_create_info = {VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO};

multisampling_create_info.sampleShadingEnable = VK_FALSE;

multisampling_create_info.rasterizationSamples = VK_SAMPLE_COUNT_1_BIT;

multisampling_create_info.minSampleShading = 1.0f;

multisampling_create_info.pSampleMask = 0;

multisampling_create_info.alphaToCoverageEnable = VK_FALSE;

multisampling_create_info.alphaToOneEnable = VK_FALSE;

//Depth and stencil testing

VkPipelineDepthStencilStateCreateInfo depth_stencil = {VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO};

depth_stencil.depthTestEnable = VK_TRUE;

depth_stencil.depthWriteEnable = VK_TRUE;

depth_stencil.depthCompareOp = VK_COMPARE_OP_LESS;

depth_stencil.depthBoundsTestEnable = VK_FALSE;

depth_stencil.stencilTestEnable = VK_FALSE;

VkPipelineColorBlendAttachmentState color_blend_attachment_state;

kzero_memory(&color_blend_attachment_state,sizeof(VkPipelineColorBlendAttachmentState));

color_blend_attachment_state.blendEnable = VK_TRUE;

color_blend_attachment_state.srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;

color_blend_attachment_state.dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;

color_blend_attachment_state.colorBlendOp = VK_BLEND_OP_ADD;

color_blend_attachment_state.srcAlphaBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA;

color_blend_attachment_state.dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA;

color_blend_attachment_state.alphaBlendOp = VK_BLEND_OP_ADD;

color_blend_attachment_state.colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT |

VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT;

VkPipelineColorBlendStateCreateInfo color_blend_state_create_info = {VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO};

color_blend_state_create_info.logicOpEnable = VK_FALSE;

color_blend_state_create_info.logicOp = VK_LOGIC_OP_COPY;

color_blend_state_create_info.attachmentCount = 1;

color_blend_state_create_info.pAttachments = &color_blend_attachment_state;

//Dynamic state

const u32 dynamic_state_count = 3;

VkDynamicState dynamic_states[dynamic_state_count] = {

VK_DYNAMIC_STATE_VIEWPORT,

VK_DYNAMIC_STATE_SCISSOR,

VK_DYNAMIC_STATE_LINE_WIDTH

};

VkPipelineDynamicStateCreateInfo dynamic_state_create_info = {VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO};

dynamic_state_create_info.dynamicStateCount = dynamic_state_count;

dynamic_state_create_info.pDynamicStates = dynamic_states;

//Vertex input

VkVertexInputBindingDescription binding_description;

binding_description.binding = 0;

binding_description.stride = sizeof(vertex_3d);

binding_description.inputRate = VK_VERTEX_INPUT_RATE_VERTEX;

//Atrributes

VkPipelineVertexInputStateCreateInfo vertex_input_info = {VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO};

vertex_input_info.vertexBindingDescriptionCount = 1;

vertex_input_info.pVertexBindingDescriptions = &binding_description;

vertex_input_info.vertexAttributeDescriptionCount = attribute_count;

vertex_input_info.pVertexAttributeDescriptions = attributes;

//Input assembly

VkPipelineInputAssemblyStateCreateInfo input_assembly = {VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO};

input_assembly.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;

input_assembly.primitiveRestartEnable = VK_FALSE;

//Pipeline layout

VkPipelineLayoutCreateInfo pipeline_layout_create_info = {VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO};

//Push constants

VkPushConstantRange push_constant;

push_constant.stageFlags = VK_SHADER_STAGE_VERTEX_BIT;

push_constant.offset = sizeof(mat4) * 0;

push_constant.size = sizeof(mat4) * 2;

pipeline_layout_create_info.pushConstantRangeCount = 1;

pipeline_layout_create_info.pPushConstantRanges = &push_constant;

pipeline_layout_create_info.setLayoutCount = descriptor_set_layout_count;

pipeline_layout_create_info.pSetLayouts = descriptor_set_layouts;

//Create the pipeline layout

VK_CHECK(vkCreatePipelineLayout(

context->device.logical_device,

&pipeline_layout_create_info,

context->allocator,

&out_pipeline->pipeline_layout

));

//Pipeline create

VkGraphicsPipelineCreateInfo pipeline_create_info = {VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO};

pipeline_create_info.stageCount = stage_count;

pipeline_create_info.pStages = stages;

pipeline_create_info.pVertexInputState = &vertex_input_info;

pipeline_create_info.pInputAssemblyState = &input_assembly;

pipeline_create_info.pViewportState = &viewport_state;

pipeline_create_info.pRasterizationState = &rasterizer_create_info;

pipeline_create_info.pMultisampleState = &multisampling_create_info;

pipeline_create_info.pDepthStencilState = &depth_stencil;

pipeline_create_info.pColorBlendState = &color_blend_state_create_info;

pipeline_create_info.pDynamicState = &dynamic_state_create_info;

pipeline_create_info.pTessellationState = 0;

pipeline_create_info.layout = out_pipeline->pipeline_layout;

pipeline_create_info.renderPass = renderpass->handle;

pipeline_create_info.subpass = 0;

pipeline_create_info.basePipelineHandle = VK_NULL_HANDLE;

pipeline_create_info.basePipelineIndex = -1;

VkResult result = vkCreateGraphicsPipelines(

context->device.logical_device,

VK_NULL_HANDLE,

1,

&pipeline_create_info,

context->allocator,

&out_pipeline->handle

);

if(vulkan_result_is_success(result))

{

KDEBUG("Graphics pipeline created!");

return true;

}

KERROR("vkCreateGraphicsPipelines failed with %s.",vulkan_result_string(result,true));

return false;

}

void vulkan_pipeline_destroy(vulkan_context* context,vulkan_pipeline* pipeline)

{

if(pipeline){

//Destroy pipeline

if(pipeline->handle)

{

vkDestroyPipeline(context->device.logical_device,pipeline->handle,context->allocator);

pipeline->handle=0;

}

//Destroy layout

if(pipeline->pipeline_layout)

{

vkDestroyPipelineLayout(context->device.logical_device,pipeline->pipeline_layout,context->allocator);

pipeline->pipeline_layout = 0;

}

}

}

void vulkan_pipeline_bind(vulkan_command_buffer* command_buffer,VkPipelineBindPoint bind_point,vulkan_pipeline* pipeline)

{

vkCmdBindPipeline(command_buffer->handle,bind_point,pipeline->handle);

}

相关推荐
C语言小火车5 分钟前
C语言酒店管理系统:完整源码与深度解析
c语言·开发语言
guwei66666625 分钟前
多模态能解决什么样的业务场景?
java
伊成28 分钟前
Java面试高频面试题【2025最新版】
java·开发语言·面试
风象南41 分钟前
SpringBoot的4种数据水平分片策略
java·spring boot·后端
~贝母~44 分钟前
猿人学js逆向比赛第一届第九题
开发语言·javascript·爬虫·ecmascript
琢磨先生David44 分钟前
常见的 AI 自动编程工具:开启高效编程新时代
java·人工智能·python
jackson凌1 小时前
【Java学习笔记】线程基础
java·笔记·学习
@ chen1 小时前
Spring Boot自动装配原理解析
java·spring boot·后端
guygg881 小时前
Linux 内核源码分析---proc 文件系统
java·linux·服务器
YuTaoShao1 小时前
Java八股文——数据结构「排序算法篇」
java·数据结构·算法·面试·排序算法·八股文