Compare commits

..

2 Commits

Author SHA1 Message Date
burkkyy 9f3ad5f372 Adding tracy command for ease of use 2026-09-30 02:22:55 -07:00
burkkyy 812d50127e Adding in tracy profiler 2026-09-30 02:04:59 -07:00
14 changed files with 74 additions and 4 deletions
+3
View File
@@ -8,3 +8,6 @@
path = third_party/imgui
url = https://github.com/ocornut/imgui.git
branch = docking
[submodule "third_party/tracy"]
path = third_party/tracy
url = https://github.com/wolfpld/tracy.git
+24
View File
@@ -138,6 +138,30 @@ class DevHelper:
qrenderdoc = self._find_qrenderdoc()
self._exec_in_root(qrenderdoc, replace=True)
##
# Builds the Tracy profiler (viewer) from the third_party/tracy submodule,
# then runs it. Building from the submodule keeps the viewer's version in
# sync with the client compiled into the engine.
# dev tracy [--fresh] [args...]
# Configures only when there is no build yet (or --fresh), then builds
# incrementally. Other arguments are passed through to the profiler.
def tracy(self, *args, **kwargs):
fresh = "--fresh" in args
args = [arg for arg in args if arg != "--fresh"]
source_dir = os.path.join("third_party", "tracy", "profiler")
build_dir = os.path.join(source_dir, "build")
if fresh or not os.path.isfile(os.path.join(self._project_root(), build_dir, "CMakeCache.txt")):
configure = ["cmake", "-B", build_dir, "-S", source_dir, "-DCMAKE_BUILD_TYPE=Release"]
if fresh:
configure.append("--fresh")
self._run_in_root(configure)
self._run_in_root(["cmake", "--build", build_dir, "--parallel"])
binary = os.path.join(self._project_root(), build_dir, "tracy-profiler")
print(f"Running: {shlex.join([binary, *args])}")
os.execv(binary, [binary, *args])
def shaders(self, *args, **kwargs):
shaders_dir = os.path.join(self._project_root(), "engine", "src", "shaders")
if not os.path.isdir(shaders_dir):
+1
View File
@@ -30,6 +30,7 @@ target_link_libraries(${ENGINE_NAME} PUBLIC
glm
imgui
entt
Tracy::TracyClient
)
target_link_libraries(${ENGINE_NAME} PRIVATE
+12 -2
View File
@@ -10,6 +10,7 @@
#include <sophia/application.hpp>
#include <sophia/util/logger.hpp>
#include <string>
#include <tracy/Tracy.hpp>
#include <utility>
#include <vector>
#include <vulkan/vulkan.hpp>
@@ -118,7 +119,10 @@ class Application::Impl {
glm::vec2(static_cast<float>(extent.width),
static_cast<float>(extent.height)),
this->application.camera};
this->application.onUpdate(frameInfo);
{
ZoneScopedN("Application::onUpdate");
this->application.onUpdate(frameInfo);
}
this->application.camera.setProjection(
-frameInfo.currentFramebufferExtent.x / 2.f,
frameInfo.currentFramebufferExtent.x / 2.f,
@@ -134,7 +138,10 @@ class Application::Impl {
sceneRenderer.beginFrame(renderContext.getFrameIndex());
panelRegistry.update(frameInfo);
this->application.onRender();
{
ZoneScopedN("Application::onRender");
this->application.onRender();
}
std::vector<ModelRenderSystem::MeshInstance> instances;
instances.reserve(this->meshes.size() + this->drawCalls.size());
@@ -176,6 +183,7 @@ class Application::Impl {
},
[&sceneRenderer, &sceneRegistry, &sceneViewRegistry,
&viewsWithoutCamera, handle](vk::CommandBuffer commandBuffer) {
ZoneScopedN("scene view pass");
const SceneView& view = sceneViewRegistry.peek(handle);
Entity camera =
view.camera ? view.camera
@@ -204,6 +212,7 @@ class Application::Impl {
}
},
[&](vk::CommandBuffer commandBuffer) {
ZoneScopedN("main pass");
modelRenderSystem.render(commandBuffer, instances, frameInfo);
imguiRenderer.endFrame(commandBuffer);
@@ -212,6 +221,7 @@ class Application::Impl {
graph.execute(commandBuffer);
renderContext.endFrame();
FrameMark;
frameIndex++;
}
+4
View File
@@ -5,6 +5,8 @@
#include <imgui_impl_vulkan.h>
#include <imgui_internal.h>
#include <tracy/Tracy.hpp>
#include "resources/render_target.hpp"
namespace sophia {
@@ -79,6 +81,7 @@ ImGuiRenderer::~ImGuiRenderer() {
}
void ImGuiRenderer::beginFrame() {
ZoneScoped;
releaseStaleTextures();
ImGui_ImplVulkan_NewFrame();
@@ -183,6 +186,7 @@ void ImGuiRenderer::applyLayoutIfNeeded(ImGuiID dockspaceId,
}
void ImGuiRenderer::endFrame(vk::CommandBuffer commandBuffer) {
ZoneScoped;
ImGui::Render();
ImDrawData* mainDrawData = ImGui::GetDrawData();
@@ -1,6 +1,7 @@
#include "renderer/model_render_system.hpp"
#include <sophia/util/assert.hpp>
#include <tracy/Tracy.hpp>
#include "shaders/model_render_system.frag.spv.h"
#include "shaders/model_render_system.vert.spv.h"
@@ -44,6 +45,7 @@ ModelRenderSystem::~ModelRenderSystem() {
void ModelRenderSystem::render(vk::CommandBuffer commandBuffer,
std::span<const MeshInstance> instances,
const FrameInfo& frameInfo) {
ZoneScoped;
glm::mat4 viewProjection = frameInfo.camera.getViewProjection();
this->graphicsPipeline->bind(commandBuffer);
+9 -2
View File
@@ -4,6 +4,7 @@
#include <sophia/util/assert.hpp>
#include <sophia/util/logger.hpp>
#include <stdexcept>
#include <tracy/Tracy.hpp>
#include "vulkan/access.hpp"
@@ -18,14 +19,19 @@ RenderContext::RenderContext(Window& window, Device& device)
RenderContext::~RenderContext() { this->device.waitIdle(); }
vk::CommandBuffer RenderContext::beginFrame() {
ZoneScoped;
SOPHIA_ASSERT(!this->isFrameStarted,
"Can't call beginFrame while already in progress");
FrameData& frame = this->frames[this->currentFrameIndex];
vk::Fence inFlightFence = frame.inFlight.get();
vk::Result fenceResult = this->device.get()->waitForFences(
inFlightFence, vk::True, std::numeric_limits<u64>::max());
vk::Result fenceResult;
{
ZoneScopedN("wait for frame fence");
fenceResult = this->device.get()->waitForFences(
inFlightFence, vk::True, std::numeric_limits<u64>::max());
}
if (fenceResult != vk::Result::eSuccess) {
log::error("failed to wait for fence: " + vk::to_string(fenceResult));
@@ -73,6 +79,7 @@ vk::CommandBuffer RenderContext::beginFrame() {
}
void RenderContext::endFrame() {
ZoneScoped;
SOPHIA_ASSERT(this->isFrameStarted,
"Can't call endFrame while no frame is in progress");
+2
View File
@@ -1,6 +1,7 @@
#include "renderer/render_graph.hpp"
#include <sophia/util/assert.hpp>
#include <tracy/Tracy.hpp>
#include <utility>
#include "vulkan/debug_label.hpp"
@@ -24,6 +25,7 @@ void RenderGraph::addPass(std::string name, const SetupFn& setup,
}
void RenderGraph::execute(vk::CommandBuffer commandBuffer) {
ZoneScoped;
for (Pass& pass : this->passes) {
this->recordPass(commandBuffer, pass);
}
+3
View File
@@ -3,6 +3,7 @@
#include <algorithm>
#include <sophia/components.hpp>
#include <sophia/util/assert.hpp>
#include <tracy/Tracy.hpp>
#include <tuple>
namespace sophia {
@@ -15,11 +16,13 @@ SceneRenderer::SceneRenderer(const SceneRegistry& sceneRegistry,
spriteRenderSystem{device, colorFormat, resources} {}
void SceneRenderer::beginFrame(u32 frameIndex) {
ZoneScoped;
this->spriteRenderSystem.beginFrame(frameIndex);
}
void SceneRenderer::render(vk::CommandBuffer commandBuffer,
const SceneView& sceneView, Entity camera) {
ZoneScoped;
SOPHIA_ASSERT(camera.hasComponent<CameraComponent>(),
"camera does not have camera component!");
@@ -2,6 +2,7 @@
#include <sophia/util/assert.hpp>
#include <sophia/util/logger.hpp>
#include <tracy/Tracy.hpp>
#include "shaders/sprite.frag.spv.h"
#include "shaders/sprite.vert.spv.h"
@@ -36,6 +37,7 @@ void SpriteRenderSystem::render(vk::CommandBuffer commandBuffer,
const glm::mat4& viewProjection,
std::span<const Instance> instances,
std::span<const Batch> batches) {
ZoneScoped;
if (instances.empty()) {
return;
}
@@ -1,5 +1,7 @@
#include "resources/pools/render_target_pool.hpp"
#include <tracy/Tracy.hpp>
namespace sophia {
RenderTargetPool::RenderTargetPool(Device& device, vk::Format format)
@@ -16,6 +18,7 @@ void RenderTargetPool::release(RenderTargetHandle handle) {
}
void RenderTargetPool::applyPendingResizes() {
ZoneScoped;
pool.forEach([](RenderTarget& target) { target.applyPendingResize(); });
}
+2
View File
@@ -1,4 +1,5 @@
#include <sophia/ui/panel_registry.hpp>
#include <tracy/Tracy.hpp>
namespace sophia {
@@ -13,6 +14,7 @@ u32 PanelRegistry::visibleCount() const {
}
void PanelRegistry::update(const FrameInfo& frameInfo) {
ZoneScoped;
pool.forEach([&frameInfo](Panel& panel) {
if (panel.isVisible()) {
panel.draw(frameInfo);
+6
View File
@@ -45,6 +45,12 @@ add_library(stb_image STATIC
)
target_include_directories(stb_image PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/stb_image)
# Tracy profiler client (static). Configure with -DTRACY_ENABLE=OFF to compile
# all profiling macros out.
option(TRACY_ENABLE "Enable Tracy profiling" ON)
option(TRACY_ON_DEMAND "Only collect data while the viewer is connected" ON)
add_subdirectory(tracy)
# 5. IMGUI (static)
set(IMGUI_DIR ${CMAKE_CURRENT_SOURCE_DIR}/imgui)
Vendored Submodule
+1
Submodule third_party/tracy added at 30997d5ca6