#include "simple_render_system.hpp" // libs #define GLM_FORCE_RADIANS #define GLM_FORCE_DEPTH_ZERO_TO_ONE #include #include // std #include #include #include namespace lve { struct SimplePushConstantData { glm::mat4 transform{1.f}; glm::mat4 normalMatrix{1.f}; }; SimpleRenderSystem::SimpleRenderSystem(LveDevice& device, VkRenderPass renderPass) : lveDevice{device} { createPipelineLayout(); createPipeline(renderPass); } SimpleRenderSystem::~SimpleRenderSystem() { vkDestroyPipelineLayout(lveDevice.device(), pipelineLayout, nullptr); } void SimpleRenderSystem::createPipelineLayout() { VkPushConstantRange pushConstantRange{}; pushConstantRange.stageFlags = VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT; pushConstantRange.offset = 0; pushConstantRange.size = sizeof(SimplePushConstantData); VkPipelineLayoutCreateInfo pipelineLayoutInfo{}; pipelineLayoutInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO; pipelineLayoutInfo.setLayoutCount = 0; pipelineLayoutInfo.pSetLayouts = nullptr; pipelineLayoutInfo.pushConstantRangeCount = 1; pipelineLayoutInfo.pPushConstantRanges = &pushConstantRange; if (vkCreatePipelineLayout(lveDevice.device(), &pipelineLayoutInfo, nullptr, &pipelineLayout) != VK_SUCCESS) { throw std::runtime_error("failed to create pipeline layout!"); } } void SimpleRenderSystem::createPipeline(VkRenderPass renderPass) { assert(pipelineLayout != nullptr && "Cannot create pipeline before pipeline layout"); PipelineConfigInfo pipelineConfig{}; LvePipeline::defaultPipelineConfigInfo(pipelineConfig); pipelineConfig.renderPass = renderPass; pipelineConfig.pipelineLayout = pipelineLayout; lvePipeline = std::make_unique( lveDevice, "shaders/simple_shader.vert.spv", "shaders/simple_shader.frag.spv", pipelineConfig); } void SimpleRenderSystem::renderGameObjects( VkCommandBuffer commandBuffer, std::vector& gameObjects, const LveCamera& camera) { lvePipeline->bind(commandBuffer); auto projectionView = camera.getProjection() * camera.getView(); for (auto& obj : gameObjects) { SimplePushConstantData push{}; auto modelMatrix = obj.transform.mat4(); push.transform = projectionView * modelMatrix; push.normalMatrix = obj.transform.normalMatrix(); vkCmdPushConstants( commandBuffer, pipelineLayout, VK_SHADER_STAGE_VERTEX_BIT | VK_SHADER_STAGE_FRAGMENT_BIT, 0, sizeof(SimplePushConstantData), &push); obj.model->bind(commandBuffer); obj.model->draw(commandBuffer); } } } // namespace lve