86 const std::string &modelPath,
87 const std::string &textureManifestPath,
88 const std::string &textureBasePath,
101 const std::string &textureManifestPath,
102 const std::string &textureBasePath,
103 [[maybe_unused]]
float scale = 1.0f);
111 void setShaders(
VK_Window *window,
const std::string &vertSpv,
const std::string &fragSpv);
137 [[nodiscard]]
bool updatePrimaryTexture(
const void *pixels,
int width,
int height,
int pitch = 0);
146 [[nodiscard]]
bool updatePrimaryTextureCuda(
const cv::cuda::GpuMat &rgba, cv::cuda::Stream &stream);
155 void render(VkCommandBuffer cmd, uint32_t imageIndex,
bool wireframe =
false)
const;
169 bool wireframe =
false);
192 [[nodiscard]]
bool isLoaded()
const {
return obj.indexCount() > 0 && vertexBufferReady(); }
207 struct TextureEntry {
208 VkImage image = VK_NULL_HANDLE;
209 VkDeviceMemory memory = VK_NULL_HANDLE;
210 VkImageView view = VK_NULL_HANDLE;
214 VkDeviceSize cudaExportMemorySize = 0;
215 cudaExternalMemory_t cudaExternalMemory =
nullptr;
216 cudaMipmappedArray_t cudaMipmappedArray =
nullptr;
217 cudaArray_t cudaArray =
nullptr;
218 bool cudaInteropEnabled =
false;
219 bool cudaInteropUnavailableLogged =
false;
220 bool cudaUploadLogged =
false;
221 bool cudaWriteTransitionLogged =
false;
222 bool cudaShaderTransitionLogged =
false;
223 VkImageLayout cudaImageLayout = VK_IMAGE_LAYOUT_UNDEFINED;
228 std::vector<TextureEntry> textures{};
230 VkDescriptorSetLayout descriptorSetLayout = VK_NULL_HANDLE;
231 VkDescriptorPool descriptorPool = VK_NULL_HANDLE;
232 uint32_t descriptorPoolSetCapacity = 0;
233 std::vector<VkDescriptorSet> descriptorSets{};
235 VkPipelineLayout pipelineLayout = VK_NULL_HANDLE;
236 VkPipeline pipelineFill = VK_NULL_HANDLE;
237 VkPipeline pipelineWireframe = VK_NULL_HANDLE;
238 VkSampler textureSampler = VK_NULL_HANDLE;
240 std::vector<VkBuffer> uniformBuffers{};
241 std::vector<VkDeviceMemory> uniformBufferMemory{};
242 std::vector<void *> uniformBuffersMapped{};
243 std::vector<VkBuffer> fragmentUniformBuffers{};
244 std::vector<VkDeviceMemory> fragmentUniformBufferMemory{};
245 std::vector<void *> fragmentUniformBuffersMapped{};
247 glm::vec3 modelCenterOffsetValue{0.0f, 0.0f, 0.0f};
248 float modelRenderScaleValue = 1.0f;
249 glm::vec3 modelAxisExtentValue{1.0f, 1.0f, 1.0f};
251 std::string vertexShaderPath{};
252 std::string fragmentShaderPath{};
253 bool backfaceCullingEnabled =
false;
254 bool alphaBlendingEnabled =
false;
255 ModelFragmentPushConstants fragmentPushConstants{};
256 bool extendedFragmentUniformsEnabled =
false;
258 VK_Window *windowPtr =
nullptr;
260 [[nodiscard]]
bool vertexBufferReady()
const {
return obj.vertexBuffer() != VK_NULL_HANDLE && obj.indexBuffer() != VK_NULL_HANDLE; }
262 void computeBoundsAndScale();
263 void loadTextures(
const std::string &textureManifestPath,
const std::string &textureBasePath);
264 void loadTexturesFromMTL(
const std::string &textureBasePath);
265 void createFallbackTexture();
267 void createBuffer(VkDeviceSize size, VkBufferUsageFlags usage,
268 VkMemoryPropertyFlags properties, VkBuffer &buffer,
269 VkDeviceMemory &bufferMemory)
const;
270 [[nodiscard]] uint32_t findMemoryType(uint32_t typeFilter, VkMemoryPropertyFlags properties)
const;
271 [[nodiscard]] VkCommandBuffer beginSingleTimeCommands()
const;
272 void endSingleTimeCommands(VkCommandBuffer commandBuffer)
const;
273 void createImage(uint32_t width, uint32_t height, VkFormat format,
274 VkImageTiling tiling, VkImageUsageFlags usage,
275 VkMemoryPropertyFlags properties, VkImage &image,
276 VkDeviceMemory &memory)
const;
277 void createTextureImage(uint32_t width, uint32_t height, TextureEntry &texture)
const;
279 void createCudaExportableImage(uint32_t width, uint32_t height, TextureEntry &texture)
const;
280 void destroyTextureCudaInterop(TextureEntry &texture)
const;
281 [[nodiscard]]
bool ensureTextureCudaInterop(TextureEntry &texture)
const;
282 [[nodiscard]]
bool transitionTextureForCudaWrite(TextureEntry &texture)
const;
283 [[nodiscard]]
bool transitionTextureForShaderRead(TextureEntry &texture)
const;
284 [[nodiscard]]
bool updatePrimaryTextureCudaHost(TextureEntry &texture,
const void *pixels,
285 uint32_t width, uint32_t height, uint32_t pitch)
const;
286 void recreatePrimaryTextureForCuda(TextureEntry &texture, uint32_t width, uint32_t height);
288 [[nodiscard]] VkImageView createImageView(VkImage image, VkFormat format, VkImageAspectFlags aspectFlags)
const;
289 void transitionImageLayout(VkImage image, VkFormat format, VkImageLayout oldLayout, VkImageLayout newLayout)
const;
290 void copyBufferToImage(VkBuffer buffer, VkImage image, uint32_t width, uint32_t height)
const;
292 void createTextureSampler();
293 void createDescriptorSetLayout();
294 void createUniformBuffers();
295 void destroyUniformBuffers();
296 void createDescriptorPool();
297 void createDescriptorSets();
298 void createPipelines();
300 void destroyPipelines();
301 void destroyDescriptors();
302 void destroyTextures();