Files
sophia/engine/include/sophia/application.hpp
T
burkkyy 5e1caabde6 Add offscreen render targets and rename AssetRegistry to ResourceRegistry
Add a RenderTarget resource so the scene can render offscreen instead of
straight to the swapchain. The editor uses it to show the scene inside the
Viewport panel.

- Rename AssetRegistry to ResourceRegistry (AssetTraits -> ResourceTraits,
  assets() -> resources()) and move the pools from engine/src/assets to
  engine/src/resources. It now covers non-asset GPU resources as well.
- Replace loadMesh() with create<T>(...), and add create<RenderTarget>(),
  requestResize(), getExtent() and isAlive().
- Add RenderTarget and RenderTargetPool with RenderTargetHandle.
  Resizes are deferred and applied at the start of the next frame, when the
  GPU is idle.
- Add Application::setSceneTarget(). With no target set, the scene still
  renders to the swapchain. With a target set, the scene renders offscreen
  and the swapchain receives only the UI. Frame extent and camera projection
  follow the target's size.
- Add sophia::UI (Application::ui()) with image() and getTextureId() to draw
  a render target in an ImGui window, sizing the target to the available
  space. ImGuiRenderer now registers the target textures for this.
- ViewportPanel takes the UI and a target, and draws the scene image in place
  of the flat background fill.
- Update the testbed, the boids example, and the glossary for the rename.
2026-09-20 16:21:22 -07:00

99 lines
2.6 KiB
C++

#pragma once
#include <cstdlib>
#include <iostream>
#include <memory>
#include <sophia/camera_2d.hpp>
#include <sophia/canvas.hpp>
#include <sophia/console/console_command_registry.hpp>
#include <sophia/frame_info.hpp>
#include <sophia/resource_registry.hpp>
#include <sophia/types.hpp>
#include <sophia/ui/debug_ui.hpp>
#include <sophia/ui/panel_registry.hpp>
#include <sophia/ui/ui.hpp>
#include <string>
#include <vector>
#define GLM_FORCE_RADIANS
#define GLM_FORCE_DEPTH_ZERO_TO_ONE
#include <glm/glm.hpp>
namespace sophia {
class Application {
public:
struct Config {
int width;
int height;
std::string name;
};
Application(const Application&) = delete;
Application& operator=(const Application&) = delete;
explicit Application(const Config& config);
virtual ~Application();
void run();
static void setCommandLineArgs(int argc, const char* const* argv);
protected:
virtual void onCreate() {}
virtual void onUpdate(const FrameInfo& frameInfo) { (void)frameInfo; }
virtual void onRender() {}
virtual void onDestroy() {}
ResourceRegistry& resources() { return this->resourceRegistry; }
PanelRegistry& panels() { return this->panelRegistry; }
UI& ui() { return this->_ui; }
DebugUI& debugUI() { return this->_debugUI; }
Canvas canvas;
Camera2D camera;
std::vector<std::string> args;
ConsoleCommandRegistry consoleCommandRegistry;
void drawMesh(MeshHandle handle, const glm::mat4& transform);
/**
* Chooses where the scene is rendered. An invalid handle (the default) means
* the swapchain; a target created with
* ResourceRegistry::create<RenderTarget>() redirects it offscreen, and the
* swapchain then only receives the UI. FrameInfo::currentFramebufferExtent
* and the camera projection follow the target's size.
*/
void setSceneTarget(RenderTargetHandle handle);
private:
friend class Canvas;
void pushMesh(std::vector<CanvasVertex> vertices, std::vector<u32> indices);
void clearMeshes();
class Impl;
std::unique_ptr<Impl> impl;
ResourceRegistry resourceRegistry;
PanelRegistry panelRegistry;
UI _ui;
DebugUI _debugUI;
};
} // namespace sophia
#define SOPHIA_MAIN(AppType) \
int main(int argc, const char** argv) { \
std::cout << __FILE__ << "::" << __LINE__ << '\n'; \
\
sophia::Application::setCommandLineArgs(argc, argv); \
AppType app; \
app.run(); \
\
return EXIT_SUCCESS; \
}