1#ifndef LIBSBX_GRAPHICS_PIPELINE_SHADER_HPP_
2#define LIBSBX_GRAPHICS_PIPELINE_SHADER_HPP_
6#include <unordered_map>
9#include <spirv_cross/spirv_cross.hpp>
11#include <vulkan/vulkan.hpp>
13#include <libsbx/utility/noncopyable.hpp>
15#include <libsbx/containers/static_vector.hpp>
17namespace sbx::graphics {
23 enum class data_type : std::uint8_t {
62 explicit uniform(std::uint32_t set, std::uint32_t binding, std::uint32_t offset, std::uint32_t size, data_type type,
bool is_readonly,
bool is_writeonly, VkShaderStageFlags stage_flags)
68 _is_readonly{is_readonly},
69 _is_writeonly{is_writeonly},
70 _stage_flags{stage_flags} { }
72 auto set()
const noexcept -> std::uint32_t {
76 auto binding()
const noexcept -> std::uint32_t {
80 auto offset()
const noexcept -> std::uint32_t {
84 auto size()
const noexcept -> std::uint32_t {
88 auto type()
const noexcept -> data_type {
92 auto is_readonly()
const noexcept ->
bool {
96 auto is_writeonly()
const noexcept ->
bool {
100 auto stage_flags()
const noexcept -> VkShaderStageFlags {
104 auto add_stage_flag(VkShaderStageFlags stage)
noexcept ->
void {
105 _stage_flags |= stage;
108 auto operator==(
const uniform& other)
const noexcept ->
bool {
109 return _set == other._set && _binding == other._binding && _offset == other._offset && _size == other._size && _type == other._type && _is_readonly == other._is_readonly && _is_writeonly == other._is_writeonly && _stage_flags == other._stage_flags;
114 std::uint32_t _set{};
115 std::uint32_t _binding{};
116 std::uint32_t _offset{};
117 std::uint32_t _size{};
120 bool _is_writeonly{};
121 VkShaderStageFlags _stage_flags{};
129 enum class type : std::uint8_t {
135 explicit uniform_block(std::uint32_t set, std::uint32_t binding, std::uint32_t size, VkShaderStageFlags stage_flags, type type, std::map<std::string, uniform> uniforms = {})
139 _stage_flags{stage_flags},
141 _uniforms{std::move(uniforms)} { }
143 auto set()
const noexcept -> std::uint32_t {
147 auto binding()
const noexcept -> std::uint32_t {
151 auto size()
const noexcept -> std::uint32_t {
155 auto stage_flags()
const noexcept -> VkShaderStageFlags {
159 auto add_stage_flag(VkShaderStageFlags stage)
noexcept ->
void {
160 _stage_flags |= stage;
163 auto buffer_type()
const noexcept -> type {
167 auto uniforms()
const noexcept ->
const std::map<std::string, uniform>& {
171 auto find_uniform(
const std::string& name)
const noexcept -> std::optional<uniform> {
172 if (
auto entry = _uniforms.find(name); entry != _uniforms.end()) {
173 return entry->second;
179 auto operator==(
const uniform_block& other)
const noexcept ->
bool {
180 return _set == other._set && _binding == other._binding && _size == other._size && _stage_flags == other._stage_flags && _type == other._type && _uniforms == other._uniforms;
185 std::uint32_t _set{};
186 std::uint32_t _binding{};
187 std::uint32_t _size{};
188 VkShaderStageFlags _stage_flags{};
190 std::map<std::string, uniform> _uniforms{};
198 explicit attribute(std::uint32_t binding, std::uint32_t size, VkShaderStageFlags stage_flags, data_type type)
201 _stage_flags{stage_flags},
204 auto binding()
const noexcept -> std::uint32_t {
208 auto size()
const noexcept -> std::uint32_t {
212 auto stage_flags()
const noexcept -> VkShaderStageFlags {
216 auto type()
const noexcept -> data_type {
220 auto operator==(
const attribute& other)
const noexcept ->
bool {
221 return _binding == other._binding && _size == other._size && _stage_flags == other._stage_flags && _type == other._type;
226 std::uint32_t _binding{};
227 std::uint32_t _size{};
228 VkShaderStageFlags _stage_flags{};
238 using handle_type = VkShaderModule;
244 auto handle() const noexcept -> handle_type;
246 operator handle_type() const noexcept;
248 auto stage() const noexcept -> VkShaderStageFlagBits;
250 auto set_uniforms() const noexcept -> const std::vector<std::unordered_map<std::
string, uniform>>& {
251 return _set_uniforms;
254 auto set_uniform_blocks() const noexcept -> const std::vector<std::unordered_map<std::
string, uniform_block>>& {
255 return _set_uniform_blocks;
258 auto uniforms(std::uint32_t set)
const noexcept ->
const std::unordered_map<std::string, uniform>& {
259 return _set_uniforms[set];
262 auto uniform_blocks(std::uint32_t set)
const noexcept ->
const std::unordered_map<std::string, uniform_block>& {
263 return _set_uniform_blocks[set];
268 auto _create_reflection(
const spirv_cross::Compiler& compiler) -> void;
270 auto _get_data_type(
const spirv_cross::SPIRType& type) -> data_type;
272 auto _data_type_to_string(data_type type) -> std::string;
274 std::vector<std::unordered_map<std::string, uniform>> _set_uniforms{};
275 std::vector<std::unordered_map<std::string, uniform_block>> _set_uniform_blocks{};
277 VkShaderStageFlagBits _stage{};
278 handle_type _handle{};
static_vector implementation inspired by https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p08...
Definition: static_vector.hpp:24
Definition: separate_image2d_array.hpp:15
Definition: separate_sampler.hpp:8
Definition: shader.hpp:194
Definition: shader.hpp:19
Definition: shader.hpp:233
Definition: noncopyable.hpp:6