Add framework for compute shaders
This commit is contained in:
parent
bcac561a1e
commit
41ef1c33f5
10 changed files with 65 additions and 4 deletions
|
@ -42,7 +42,8 @@ public:
|
||||||
|
|
||||||
// pipeline operations
|
// pipeline operations
|
||||||
GFXPipeline* create_graphics_pipeline(const GFXGraphicsPipelineCreateInfo& info) override;
|
GFXPipeline* create_graphics_pipeline(const GFXGraphicsPipelineCreateInfo& info) override;
|
||||||
|
GFXPipeline* create_compute_pipeline(const GFXComputePipelineCreateInfo& info) override;
|
||||||
|
|
||||||
GFXCommandBuffer* acquire_command_buffer() override;
|
GFXCommandBuffer* acquire_command_buffer() override;
|
||||||
|
|
||||||
void submit(GFXCommandBuffer* command_buffer, const int window = -1) override;
|
void submit(GFXCommandBuffer* command_buffer, const int window = -1) override;
|
||||||
|
|
|
@ -641,6 +641,43 @@ GFXPipeline* GFXMetal::create_graphics_pipeline(const GFXGraphicsPipelineCreateI
|
||||||
return pipeline;
|
return pipeline;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
GFXPipeline* GFXMetal::create_compute_pipeline(const GFXComputePipelineCreateInfo& info) {
|
||||||
|
GFXMetalPipeline* pipeline = new GFXMetalPipeline();
|
||||||
|
|
||||||
|
NSError* error = nil;
|
||||||
|
|
||||||
|
// vertex
|
||||||
|
id<MTLLibrary> computeLibrary;
|
||||||
|
{
|
||||||
|
std::string compute_src;
|
||||||
|
if(info.shaders.compute_path.empty()) {
|
||||||
|
compute_src = info.shaders.compute_src.as_string();
|
||||||
|
} else {
|
||||||
|
const auto compute_path = utility::format("{}.msl", info.shaders.compute_path);
|
||||||
|
|
||||||
|
auto file = file::open(file::internal_domain / compute_path);
|
||||||
|
if(file != std::nullopt) {
|
||||||
|
compute_src = file->read_as_string();
|
||||||
|
} else {
|
||||||
|
console::error(System::GFX, "Failed to load compute shader from {}!", compute_path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
computeLibrary = [device newLibraryWithSource:[NSString stringWithFormat:@"%s", compute_src.c_str()] options:nil error:&error];
|
||||||
|
if(!computeLibrary)
|
||||||
|
NSLog(@"%@", error.debugDescription);
|
||||||
|
}
|
||||||
|
|
||||||
|
id<MTLFunction> computeFunc = [computeLibrary newFunctionWithName:@"main0"];
|
||||||
|
|
||||||
|
MTLComputePipelineDescriptor* pipelineDescriptor = [MTLComputePipelineDescriptor new];
|
||||||
|
pipelineDescriptor.computeFunction = computeFunc;
|
||||||
|
|
||||||
|
[computeLibrary release];
|
||||||
|
|
||||||
|
return pipeline;
|
||||||
|
}
|
||||||
|
|
||||||
GFXCommandBuffer* GFXMetal::acquire_command_buffer() {
|
GFXCommandBuffer* GFXMetal::acquire_command_buffer() {
|
||||||
GFXCommandBuffer* cmdbuf = nullptr;
|
GFXCommandBuffer* cmdbuf = nullptr;
|
||||||
while(cmdbuf == nullptr) {
|
while(cmdbuf == nullptr) {
|
||||||
|
|
|
@ -199,6 +199,7 @@ struct GFXComputePipelineCreateInfo {
|
||||||
|
|
||||||
struct Shaders {
|
struct Shaders {
|
||||||
std::string_view compute_path;
|
std::string_view compute_path;
|
||||||
|
ShaderSource compute_src;
|
||||||
} shaders;
|
} shaders;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -78,4 +78,5 @@ add_shader(TARGET Renderer
|
||||||
shaders/rendering.nocompile.glsl
|
shaders/rendering.nocompile.glsl
|
||||||
shaders/common.nocompile.glsl
|
shaders/common.nocompile.glsl
|
||||||
shaders/dof.vert.glsl
|
shaders/dof.vert.glsl
|
||||||
shaders/dof.frag.glsl)
|
shaders/dof.frag.glsl
|
||||||
|
shaders/histogram.comp.glsl)
|
||||||
|
|
|
@ -139,6 +139,7 @@ private:
|
||||||
void createUIPipeline();
|
void createUIPipeline();
|
||||||
void createGaussianResources();
|
void createGaussianResources();
|
||||||
void createBRDF();
|
void createBRDF();
|
||||||
|
void create_histogram_resources();
|
||||||
|
|
||||||
GFX* gfx = nullptr;
|
GFX* gfx = nullptr;
|
||||||
prism::Extent extent;
|
prism::Extent extent;
|
||||||
|
@ -176,6 +177,9 @@ private:
|
||||||
|
|
||||||
// general ui
|
// general ui
|
||||||
GFXPipeline* generalPipeline, *worldGeneralPipeline = nullptr;
|
GFXPipeline* generalPipeline, *worldGeneralPipeline = nullptr;
|
||||||
|
|
||||||
|
// histogram compute
|
||||||
|
GFXPipeline* histogram_pipeline = nullptr;
|
||||||
|
|
||||||
std::unique_ptr<SMAAPass> smaaPass;
|
std::unique_ptr<SMAAPass> smaaPass;
|
||||||
std::unique_ptr<GaussianHelper> gHelper;
|
std::unique_ptr<GaussianHelper> gHelper;
|
||||||
|
|
|
@ -87,6 +87,7 @@ Renderer::Renderer(GFX* gfx, const bool enable_imgui) : gfx(gfx) {
|
||||||
shader_compiler.set_include_path(file::get_domain_path(file::Domain::Internal).string());
|
shader_compiler.set_include_path(file::get_domain_path(file::Domain::Internal).string());
|
||||||
|
|
||||||
createDummyTexture();
|
createDummyTexture();
|
||||||
|
create_histogram_resources();
|
||||||
|
|
||||||
shadow_pass = std::make_unique<ShadowPass>(gfx);
|
shadow_pass = std::make_unique<ShadowPass>(gfx);
|
||||||
scene_capture = std::make_unique<SceneCapture>(gfx);
|
scene_capture = std::make_unique<SceneCapture>(gfx);
|
||||||
|
@ -994,3 +995,10 @@ void Renderer::createBRDF() {
|
||||||
|
|
||||||
gfx->submit(command_buffer);
|
gfx->submit(command_buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Renderer::create_histogram_resources() {
|
||||||
|
GFXComputePipelineCreateInfo create_info = {};
|
||||||
|
create_info.shaders.compute_path = "histogram.comp";
|
||||||
|
|
||||||
|
histogram_pipeline = gfx->create_compute_pipeline(create_info);
|
||||||
|
}
|
||||||
|
|
|
@ -9,7 +9,8 @@
|
||||||
/// The shader stage that the shader is written in.
|
/// The shader stage that the shader is written in.
|
||||||
enum class ShaderStage {
|
enum class ShaderStage {
|
||||||
Vertex,
|
Vertex,
|
||||||
Fragment
|
Fragment,
|
||||||
|
Compute
|
||||||
};
|
};
|
||||||
|
|
||||||
/// The shader language that the shader is written in.
|
/// The shader language that the shader is written in.
|
||||||
|
|
|
@ -89,6 +89,9 @@ std::optional<ShaderSource> ShaderCompiler::compile(const ShaderLanguage from_la
|
||||||
case ShaderStage::Fragment:
|
case ShaderStage::Fragment:
|
||||||
lang = EShLangFragment;
|
lang = EShLangFragment;
|
||||||
break;
|
break;
|
||||||
|
case ShaderStage::Compute:
|
||||||
|
lang = EShLangCompute;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto spirv = compile_glsl_to_spv(shader_source.as_string(), lang, options);
|
auto spirv = compile_glsl_to_spv(shader_source.as_string(), lang, options);
|
||||||
|
|
3
shaders/histogram.comp.glsl
Executable file
3
shaders/histogram.comp.glsl
Executable file
|
@ -0,0 +1,3 @@
|
||||||
|
void main() {
|
||||||
|
|
||||||
|
}
|
|
@ -41,8 +41,10 @@ int main(int argc, char* argv[]) {
|
||||||
ShaderStage stage;
|
ShaderStage stage;
|
||||||
if(has_extension(source_path, ".vert"))
|
if(has_extension(source_path, ".vert"))
|
||||||
stage = ShaderStage::Vertex;
|
stage = ShaderStage::Vertex;
|
||||||
else
|
else if(has_extension(source_path, ".frag"))
|
||||||
stage = ShaderStage::Fragment;
|
stage = ShaderStage::Fragment;
|
||||||
|
else if(has_extension(source_path, ".comp"))
|
||||||
|
stage = ShaderStage::Compute;
|
||||||
|
|
||||||
ShaderLanguage language;
|
ShaderLanguage language;
|
||||||
CompileOptions options;
|
CompileOptions options;
|
||||||
|
|
Reference in a new issue