You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
260 lines
10 KiB
260 lines
10 KiB
/*
|
|
* Copyright (c) 2014-2021, NVIDIA CORPORATION. All rights reserved.
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*
|
|
* SPDX-FileCopyrightText: Copyright (c) 2014-2021 NVIDIA CORPORATION
|
|
* SPDX-License-Identifier: Apache-2.0
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
// Not strictly needed for this header, but some samples got used to having
|
|
// them available by just including appbase_vkpp.hpp
|
|
#include "imgui.h"
|
|
#include "imgui/imgui_helper.h"
|
|
#include "imgui/imgui_camera_widget.h"
|
|
|
|
#include <vulkan/vulkan.hpp>
|
|
|
|
#include "nvh/timesampler.hpp"
|
|
#include "nvh/cameramanipulator.hpp"
|
|
|
|
#include "nvvk/swapchain_vk.hpp"
|
|
#include "imgui/backends/imgui_impl_vulkan.h"
|
|
|
|
#include "GLFW/glfw3.h"
|
|
|
|
#include <set>
|
|
#include <vector>
|
|
|
|
namespace nvvkhl {
|
|
|
|
/**
|
|
\class nvvkhl::AppBase
|
|
|
|
nvvkhl::AppBaseVk is the same as nvvkhl::AppBaseVk but makes use of the Vulkan C++ API (`vulkan.hpp`).
|
|
|
|
*/
|
|
|
|
class AppBase
|
|
{
|
|
public:
|
|
AppBase() = default;
|
|
virtual ~AppBase() = default;
|
|
|
|
virtual void onResize(int /*w*/, int /*h*/);
|
|
; // To implement when the size of the window change
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Setup the low level Vulkan for various operations
|
|
//
|
|
virtual void setup(const vk::Instance& instance, const vk::Device& device, const vk::PhysicalDevice& physicalDevice, uint32_t graphicsQueueIndex);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// To call on exit
|
|
//
|
|
virtual void destroy();
|
|
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Return the surface "screen" for the display
|
|
//
|
|
VkSurfaceKHR getVkSurface(const vk::Instance& instance, GLFWwindow* window);
|
|
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Creating the surface for rendering
|
|
//
|
|
virtual void createSwapchain(const vk::SurfaceKHR& surface,
|
|
uint32_t width,
|
|
uint32_t height,
|
|
vk::Format colorFormat = vk::Format::eB8G8R8A8Unorm,
|
|
vk::Format depthFormat = vk::Format::eUndefined,
|
|
bool vsync = false);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Create the framebuffers in which the image will be rendered
|
|
// - Swapchain need to be created before calling this
|
|
//
|
|
virtual void createFrameBuffers();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Creating a default render pass, very simple one.
|
|
// Other examples will mostly override this one.
|
|
//
|
|
virtual void createRenderPass();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Creating an image to be used as depth buffer
|
|
//
|
|
virtual void createDepthBuffer();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Convenient function to call before rendering
|
|
//
|
|
void prepareFrame();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Convenient function to call for submitting the rendering command
|
|
//
|
|
virtual void submitFrame();
|
|
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// When the pipeline is set for using dynamic, this becomes useful
|
|
//
|
|
void setViewport(const vk::CommandBuffer& cmdBuf);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when the it is resized
|
|
// - Destroy allocated frames, then rebuild them with the new size
|
|
// - Call onResize() of the derived class
|
|
//
|
|
virtual void onFramebufferSize(int w, int h);
|
|
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when the mouse move
|
|
// - Handling ImGui and a default camera
|
|
//
|
|
virtual void onMouseMotion(int x, int y);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when a special key gets hit
|
|
// - Handling ImGui and a default camera
|
|
//
|
|
virtual void onKeyboard(int key, int /*scancode*/, int action, int mods);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when a key gets hit
|
|
//
|
|
virtual void onKeyboardChar(unsigned char key);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when the mouse button is pressed
|
|
// - Handling ImGui and a default camera
|
|
//
|
|
virtual void onMouseButton(int button, int action, int mods);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Window callback when the mouse wheel is modified
|
|
// - Handling ImGui and a default camera
|
|
//
|
|
virtual void onMouseWheel(int delta);
|
|
|
|
virtual void onFileDrop(const char* filename);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Initialization of the GUI
|
|
// - Need to be call after the device creation
|
|
//
|
|
void initGUI(uint32_t subpassID = 0);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Fit the camera to the Bounding box
|
|
//
|
|
void fitCamera(const nvmath::vec3f& boxMin, const nvmath::vec3f& boxMax, bool instantFit = true);
|
|
|
|
// Return true if the window is minimized
|
|
bool isMinimized(bool doSleeping = true);
|
|
|
|
void setTitle(const std::string& title);
|
|
|
|
// GLFW Callback setup
|
|
void setupGlfwCallbacks(GLFWwindow* window);
|
|
static void framebuffersize_cb(GLFWwindow* window, int w, int h);
|
|
static void mousebutton_cb(GLFWwindow* window, int button, int action, int mods);
|
|
static void cursorpos_cb(GLFWwindow* window, double x, double y);
|
|
static void scroll_cb(GLFWwindow* window, double x, double y);
|
|
static void key_cb(GLFWwindow* window, int key, int scancode, int action, int mods);
|
|
static void char_cb(GLFWwindow* window, unsigned int key);
|
|
static void drop_cb(GLFWwindow* window, int count, const char** paths);
|
|
// GLFW Callback end
|
|
|
|
// Set if Nvlink will be used
|
|
void useNvlink(bool useNvlink);
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Getters
|
|
vk::Instance getInstance();
|
|
vk::Device getDevice();
|
|
vk::PhysicalDevice getPhysicalDevice();
|
|
vk::Queue getQueue();
|
|
uint32_t getQueueFamily();
|
|
vk::CommandPool getCommandPool();
|
|
vk::RenderPass getRenderPass();
|
|
vk::Extent2D getSize();
|
|
vk::PipelineCache getPipelineCache();
|
|
vk::SurfaceKHR getSurface();
|
|
const std::vector<vk::Framebuffer>& getFramebuffers();
|
|
const std::vector<vk::CommandBuffer>& getCommandBuffers();
|
|
uint32_t getCurFrame() const;
|
|
vk::Format getColorFormat() const;
|
|
vk::Format getDepthFormat() const;
|
|
bool showGui();
|
|
|
|
protected:
|
|
uint32_t getMemoryType(uint32_t typeBits, const vk::MemoryPropertyFlags& properties) const;
|
|
|
|
// Showing help
|
|
void uiDisplayHelp();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
// Called every frame to translate currently pressed keys into camera movement
|
|
//
|
|
void updateCamera();
|
|
|
|
//--------------------------------------------------------------------------------------------------
|
|
|
|
// Vulkan low level
|
|
vk::Instance m_instance;
|
|
vk::Device m_device;
|
|
vk::SurfaceKHR m_surface;
|
|
vk::PhysicalDevice m_physicalDevice;
|
|
vk::Queue m_queue;
|
|
uint32_t m_graphicsQueueIndex{VK_QUEUE_FAMILY_IGNORED};
|
|
vk::CommandPool m_cmdPool;
|
|
vk::DescriptorPool m_imguiDescPool;
|
|
|
|
// Drawing/Surface
|
|
nvvk::SwapChain m_swapChain;
|
|
std::vector<vk::Framebuffer> m_framebuffers; // All framebuffers, correspond to the Swapchain
|
|
std::vector<vk::CommandBuffer> m_commandBuffers; // Command buffer per nb element in Swapchain
|
|
std::vector<vk::Fence> m_waitFences; // Fences per nb element in Swapchain
|
|
vk::Image m_depthImage; // Depth/Stencil
|
|
vk::DeviceMemory m_depthMemory; // Depth/Stencil
|
|
vk::ImageView m_depthView; // Depth/Stencil
|
|
vk::RenderPass m_renderPass; // Base render pass
|
|
vk::Extent2D m_size{0, 0}; // Size of the window
|
|
vk::PipelineCache m_pipelineCache; // Cache for pipeline/shaders
|
|
bool m_vsync{false}; // Swapchain with vsync
|
|
bool m_useNvlink{false}; // NVLINK usage
|
|
GLFWwindow* m_window{nullptr}; // GLFW Window
|
|
|
|
// Surface buffer formats
|
|
vk::Format m_colorFormat{vk::Format::eB8G8R8A8Unorm};
|
|
vk::Format m_depthFormat{vk::Format::eUndefined};
|
|
|
|
// Camera manipulators
|
|
nvh::CameraManipulator::Inputs m_inputs; // Mouse button pressed
|
|
std::set<int> m_keys; // Keyboard pressed
|
|
|
|
nvh::Stopwatch m_timer; // measure time from frame to frame to base camera movement on
|
|
|
|
// Other
|
|
bool m_showHelp{false}; // Show help, pressing
|
|
bool m_show_gui{true};
|
|
};
|
|
|
|
} // namespace nvvk
|
|
|