Canta is a Tolkien elvish word meaning shape/framework. This library acts as a framework for creating vulkan applications.
- Device creation.
- Resource management.
- Indexed ("bindless") resources.
- Automatic frame synchronisation.
- Render graph.
- Pipeline/Shader management.
- Included ImGui backend.
Simple graphics device creation.
auto device = canta::Device::create({
.applicationName = "hello world",
.enableMeshShading = false,
// ... enable other feature flags
});Includes a render graph to help with synchronisation dependencies between shader passes.
// Create graph
auto renderGraph = canta::RenderGraph::create({
.device = device.get(),
.name = "graph"
});
// Create graph resources
auto objectBuffer = renderGraph.addBuffer({
.size = sizeof(Object) * numObjects,
.name = "object_buffer"
});
auto backbuffer = renderGraph.addImage({
.width = 1920,
.height = 1080,
.format = canta::Format::RGBA8_SRGB,
.name = "backbuffer"
});
// Create graph passes
renderGraph.addPass({
.name = "run_objects",
.type = canta::PassType::COMPUTE
})
.addStorageBufferWrite(objectBuffer, canta::PipelineStage::COMPUTE_SHADER) // add write dependency
.setPipeline(runPipeline)
.pushConstants(objectBuffer)
.dispatch(x, y);
renderGraph.addPass({
.name = "main_draw"
.type = canta::PassType::COMPUTE
})
.addStorageBufferRead(objectBuffer, canta::PipelineStage::COMPUTE_SHADER) // reads output from "run_objects" pass
.addStorageImageWrite(backbuffer, canta::PipelineStage::COMPUTE_SHADER)
.setPipeline(drawPipeline)
.pushConstants(backbuffer, objectBuffer)
.dispatch(x, y);
// Set output target
renderGraph.setBackbuffer(backbuffer);
// Compile and run
renderGraph.compile();
renderGraph.execute({}, {}); // First arg is semaphores to wait on and second is semaphores to signal for use with frame sync
Includes a pipeline manager which facilitates the creation and management of shaders and pipeline objects. Shaders/Pipelines are cached after the first use so passing the same arguments to getShader/getPipeline will return the same object.
auto pipelineManager = canta::PipelineManager::create({
.device = device.get();
.rootPath = "assets/shaders"
});
// Create and cache shader object
auto shader = pipelineManager.getShader({
.path = "path/to/shader",
.stage = canta::ShaderStage::COMPUTE,
.name = "compute_shader"
});
// Create and cache pipeline.
auto pipeline = pipelineManager.getPipeline({
.vertex = {
.module = pipelineManager.getShader({
.path = "path/to/vertex/shader",
.stage = canta::ShaderStage::VERTEX
.name = "vertex_shader"
}),
.entryPoint = "main"
},
.fragment = {
.module = pipelineManager.getShader({
.path - "path/to/fragment/shader",
.stage = canta::ShaderStage::FRAGMENT,
.name = "fragment_shader"
}),
.entryPoint = "fragmentMain"
},
.name = "raster_pipeline"
});
- SDL2
- Vulkan
- spdlog
- Ende
- volk
- VulkanMemoryAllocator
- Tessil/robin-map
- SPIRV-Cross
- slang
- imgui
- rapidjson
- imnodes