diff --git a/main.cpp b/main.cpp index 5371d69..59554d5 100644 --- a/main.cpp +++ b/main.cpp @@ -73,7 +73,9 @@ private: const uint32_t WIDTH = 800; const uint32_t HEIGHT = 600; + VkRenderPass renderPass; VkPipelineLayout pipelineLayout; + VkPipeline graphicsPipeline; std::vector dynamicStates = { VK_DYNAMIC_STATE_VIEWPORT, @@ -96,9 +98,44 @@ private: createSwapChain(); createImageViews(); + createRenderPass(); createGraphicsPipeline(); } + void createRenderPass() { + VkAttachmentDescription colorAttachment{}; + colorAttachment.format = swapChainImageFormat; + colorAttachment.samples = VK_SAMPLE_COUNT_1_BIT; + colorAttachment.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR; + colorAttachment.storeOp = VK_ATTACHMENT_STORE_OP_STORE; + colorAttachment.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; + colorAttachment.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; + colorAttachment.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; + colorAttachment.finalLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR; + + VkAttachmentReference colorAttachmentRef{}; + colorAttachmentRef.attachment = 0; + colorAttachmentRef.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; + + VkSubpassDescription subpass{}; + subpass.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS; + subpass.colorAttachmentCount = 1; + subpass.pColorAttachments = &colorAttachmentRef; + + VkRenderPassCreateInfo renderPassInfo{}; + renderPassInfo.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO; + renderPassInfo.attachmentCount = 1; + renderPassInfo.pAttachments = &colorAttachment; + renderPassInfo.subpassCount = 1; + renderPassInfo.pSubpasses = &subpass; + + VkResult result = vkCreateRenderPass(device, &renderPassInfo, nullptr, &renderPass); + if (result != VK_SUCCESS) { + std::cout << "error creating render pass: " << result << std::endl; + throw std::runtime_error("failed to create render pass!"); + } + } + void createGraphicsPipeline() { auto vertShaderCode = readFile("shaders/vert.spv"); auto fragShaderCode = readFile("shaders/frag.spv"); @@ -210,6 +247,28 @@ private: throw std::runtime_error("failed to create pipeline layout!"); } + VkGraphicsPipelineCreateInfo pipelineInfo{}; + pipelineInfo.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO; + pipelineInfo.stageCount = 2; + pipelineInfo.pStages = shaderStages; + pipelineInfo.pVertexInputState = &vertexInputInfo; + pipelineInfo.pInputAssemblyState = &inputAssembly; + pipelineInfo.pViewportState = &viewportState; + pipelineInfo.pRasterizationState = &rasterizer; + pipelineInfo.pMultisampleState = &multisampling; + pipelineInfo.pDepthStencilState = nullptr; // Optional + pipelineInfo.pColorBlendState = &colorBlending; + pipelineInfo.pDynamicState = &dynamicState; + pipelineInfo.layout = pipelineLayout; + pipelineInfo.renderPass = renderPass; + pipelineInfo.subpass = 0; + pipelineInfo.basePipelineHandle = VK_NULL_HANDLE; // Optional + pipelineInfo.basePipelineIndex = -1; // Optional + + if (vkCreateGraphicsPipelines(device, VK_NULL_HANDLE, 1, &pipelineInfo, nullptr, &graphicsPipeline) != VK_SUCCESS) { + throw std::runtime_error("failed to create graphics pipeline!"); + } + vkDestroyShaderModule(device, fragShaderModule, nullptr); vkDestroyShaderModule(device, vertShaderModule, nullptr); } @@ -649,7 +708,9 @@ private: } void cleanup() { + vkDestroyPipeline(device, graphicsPipeline, nullptr); vkDestroyPipelineLayout(device, pipelineLayout, nullptr); + vkDestroyRenderPass(device, renderPass, nullptr); for (auto imageView : swapChainImageViews) { vkDestroyImageView(device, imageView, nullptr); }