Commit 03baa419 authored by unknown's avatar unknown
Browse files

Made textures fully bindless

parent 77684cb8
#include <core/numeric/flags.h>
enum class SomeEnum
{
eOne = 1 << 0,
eTwo = 1 << 1,
eThree = 1 << 2,
eFour = 1 << 3,
};
int main(int argc, char* argv[])
{
math::Flags flags;
struct bla
{
int i = 0;
float a = 4;
};
bla x;
bool set = flags & SomeEnum::eOne;
unsigned i = 0;
bool inv = ~flags;
return 0;
}
\ No newline at end of file
......@@ -119,7 +119,7 @@ namespace glare
//initializeScene(m_current_scene_root / "artifact_suzanne_x2_mirror_0r.dae", 1.f);
//initializeScene(m_current_scene_root / "artifact_suzanne_x2_transparent.dae", 1.f);
//initializeScene(m_current_scene_root / "benchmark_stfd_bunny_diff.dae", 1.f);
initializeScene(m_current_scene_root / "some_spheres.dae", 1.f);
initializeScene(m_current_scene_root / "gizmoed.dae", 1.f);
initializeRenderRequirements();
initializeAdvanced();
......
......@@ -111,7 +111,7 @@ namespace glare
else
m_depth_attachment = std::make_shared<texture_depth_type>(m_width, m_height);
putAttachment(attachment, m_depth_attachment->getID());
putAttachment(attachment, m_depth_attachment->id());
break;
default:
{
......@@ -123,7 +123,7 @@ namespace glare
m_color_attachments.emplace(attachment, new_attachment);
putAttachment(attachment, new_attachment->getID());
putAttachment(attachment, new_attachment->id());
} break;
}
}
......
......@@ -9,7 +9,7 @@ namespace math
Flags::operator bool() const
{
return bool(m_flags);
return bool(m_flags) != 0;
}
Flags::operator unsigned() const
......
......@@ -78,19 +78,19 @@ namespace math
template<typename TEnum, enable_flag<TEnum>...>
bool Flags::operator&(TEnum flags) const
{
return (m_flags & unsigned(flags));
return (m_flags & unsigned(flags)) != 0;
}
template<typename TEnum, enable_flag<TEnum>...>
bool Flags::operator|(TEnum flags) const
{
return (m_flags | unsigned(flags));
return (m_flags | unsigned(flags)) != 0;
}
template<typename TEnum, enable_flag<TEnum>...>
bool Flags::operator^(TEnum flags) const
{
return (m_flags ^ unsigned(flags));
return (m_flags ^ unsigned(flags)) != 0;
}
template<typename TEnum, enable_flag<TEnum>...>
......
#include "light.h"
#include <util/messaging.h>
#include "light.h"
#include <util/messaging.h>
#include <core/message_tags.h>
#include <core/rendering/light_manager.h>
namespace glare
{
namespace core
{
LightComponent::LightComponent(color::rgba32f color, Attenuation attenuation, LightParameters data): m_color(color), m_attenuation(attenuation), m_data(data)
{
}
LightComponent::~LightComponent()
{
}
void LightComponent::setParameters(const LightParameters& data)
{
m_data = data;
}
void LightComponent::update()
{
if (!m_shadow_map_renderer && getOwner() && m_data.light_type == LightType::eDirectional) {
m_shadow_map_renderer = std::make_unique<ShadowMap>(2048, 500, getOwner());
}
}
void LightComponent::onTransformChanged()
{
messaging::Handler::getInstance().submit(tags::light, 1);
}
void LightComponent::draw(DrawMode mode)
{
switch (mode) {
case DrawMode::eShaded:
{
buildParameters();
if (m_shadow_map_renderer)
{
m_shadow_map_renderer->build(core::state::graph_root);
}
ShadowMapData shadow_map;
shadow_map.available = m_shadow_map_renderer ? 1 : 0;
shadow_map.map = shadow_map.available ? m_shadow_map_renderer->framebuffer().depthAttachment().getResidentTextureID() : 0;
shadow_map.matrix = shadow_map.available ? m_shadow_map_renderer->matrix() : glm::mat4(1.f);
LightManager::getInstance().registerLightForNextPass({ m_light, shadow_map });
} break;
case DrawMode::eNoColor:
// Don't rebuild shadow maps if a shadow map is currently built to prevent recursive loops.
return;
default:
return;
}
}
}
}
#include <core/rendering/light_manager.h>
namespace glare
{
namespace core
{
LightComponent::LightComponent(color::rgba32f color, Attenuation attenuation, LightParameters data): m_color(color), m_attenuation(attenuation), m_data(data)
{
}
LightComponent::~LightComponent()
{
}
void LightComponent::setParameters(const LightParameters& data)
{
m_data = data;
}
void LightComponent::update()
{
if (!m_shadow_map_renderer && getOwner() && m_data.light_type == LightType::eDirectional) {
m_shadow_map_renderer = std::make_unique<ShadowMap>(2048, 500, getOwner());
}
}
void LightComponent::onTransformChanged()
{
messaging::Handler::getInstance().submit(tags::light, 1);
}
void LightComponent::draw(DrawMode mode)
{
switch (mode) {
case DrawMode::eShaded:
{
buildParameters();
if (m_shadow_map_renderer)
{
m_shadow_map_renderer->build(core::state::graph_root);
}
ShadowMapData shadow_map;
shadow_map.available = m_shadow_map_renderer ? 1 : 0;
shadow_map.map = shadow_map.available ? m_shadow_map_renderer->framebuffer().depthAttachment().residentTextureAddress() : 0;
shadow_map.matrix = shadow_map.available ? m_shadow_map_renderer->matrix() : glm::mat4(1.f);
LightManager::getInstance().registerLightForNextPass({ m_light, shadow_map });
} break;
case DrawMode::eNoColor:
// Don't rebuild shadow maps if a shadow map is currently built to prevent recursive loops.
return;
default:
return;
}
}
}
}
......@@ -12,30 +12,27 @@ namespace glare
{
Skybox::Skybox(std::vector<fs::path> faces)
: m_handle(std::move(gl::TextureTarget::eCubeMap))
{
gl::activeTexture(0);
gl::bindTexture(gl::TextureTarget::eCubeMap, m_handle);
int width; int height;
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eBaseLevel, 0);
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eMaxLevel, 8);
gl::textureParameter(m_handle, gl::TextureParameter::eBaseLevel, 0);
gl::textureParameter(m_handle, gl::TextureParameter::eMaxLevel, 8);
for (GLuint face = 0; face < faces.size(); face++)
{
Log_Debug << "Face No " << face;
auto vec = images::load<unsigned char>(faces[face], width, height, 3);
images::flip(width, height, 3, vec.data());
gl::textureImage2D(gl::TextureImageTarget2D(int(gl::TextureImageTarget2D::eCubeMapPosX) + face), 0, gl::TextureInternalFormat::eRGB, width, height, 0, gl::TextureFormat::eRGB, gl::Type::eUByte, vec.data());
gl::textureImage2D(m_handle, gl::TextureImageTarget2D(int(gl::TextureImageTarget2D::eCubeMapPosX) + face), 0, gl::TextureInternalFormat::eRGB, width, height, 0, gl::TextureFormat::eRGB, gl::Type::eUByte, vec.data());
}
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eMagFilter, gl::TextureFilterMag::eLinear);
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eMinFilter, gl::TextureFilterMin::eLinearMipmapLinear);
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eWrapS, gl::TextureWrapMode::eClampToEdge);
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eWrapT, gl::TextureWrapMode::eClampToEdge);
gl::textureParameter(gl::TextureTarget::eCubeMap, gl::TextureParameter::eWrapR, gl::TextureWrapMode::eClampToEdge);
gl::generateMipmap(gl::TextureTarget::eCubeMap);
gl::bindTexture(gl::TextureTarget::eCubeMap, 0);
gl::textureParameter(m_handle, gl::TextureParameter::eMagFilter, gl::TextureFilterMag::eLinear);
gl::textureParameter(m_handle, gl::TextureParameter::eMinFilter, gl::TextureFilterMin::eLinearMipmapLinear);
gl::textureParameter(m_handle, gl::TextureParameter::eWrapS, gl::TextureWrapMode::eClampToEdge);
gl::textureParameter(m_handle, gl::TextureParameter::eWrapT, gl::TextureWrapMode::eClampToEdge);
gl::textureParameter(m_handle, gl::TextureParameter::eWrapR, gl::TextureWrapMode::eClampToEdge);
gl::generateTextureMipmap(m_handle);
std::vector<math::Vertex> triangle_vertices
{
......@@ -51,6 +48,7 @@ namespace glare
const auto vert = std::make_shared<Shader>(gl::ShaderType::eVertex, files::shader("/cubemap/triangle_skybox.vert"));
const auto frag = std::make_shared<Shader>(gl::ShaderType::eFragment, files::shader("/cubemap/triangle_skybox.frag"));
m_cubemap_shader = std::make_shared<ShaderProgram>(std::vector<std::shared_ptr<Shader>>{ frag, vert });
}
std::vector<fs::path> Skybox::collectFilesFrom(const fs::path &directory)
......@@ -68,15 +66,18 @@ namespace glare
gl::depthMask(false);
gl::cullFace(gl::Face::eFront);
m_cubemap_shader->use();
// if(!gl::isTextureHandleResident(m_resident_address))
/*
gl::activeTexture(0);
gl::bindTexture(gl::TextureTarget::eCubeMap, m_handle);
gl::bindTexture(gl::TextureTarget::eCubeMap, m_handle);*/
m_cubemap_shader->updateUniformInt("u_cube_map", 0);
m_cubemap_shader->updateUniformPointer("u_cube_map", makeResident());
m_cubemap_shader->updateUniformMatrix("u_inv_view_projection", glm::inverse(state::camera->getViewProjection()));
m_cubemap_shader->updateUniformVec3("cam_position", state::camera->getOwner()->c_worldTransform().position);
m_triangle_mesh->draw();
gl::bindTexture(gl::TextureTarget::eCubeMap, 0);
//gl::bindTexture(gl::TextureTarget::eCubeMap, 0);
gl::cullFace(gl::Face::eBack);
gl::depthMask(true);
}
......@@ -96,11 +97,10 @@ namespace glare
return gl::isTextureHandleResident(m_resident_address);
}
uint64_t Skybox::makeResident()
uint64_t Skybox::makeResident() const
{
if (!resident())
{
gl::bindTexture(gl::TextureTarget::eCubeMap, m_handle);
m_resident_address = gl::getTextureHandle(m_handle);
gl::makeTextureHandleResident(m_resident_address);
}
......
#ifndef INCLUDE_SKYBOX_H
#define INCLUDE_SKYBOX_H
#include <filesystem>
#include <memory>
#include <string>
#include <vector>
#ifndef INCLUDE_SKYBOX_H
#define INCLUDE_SKYBOX_H
#include <filesystem>
#include <memory>
#include <string>
#include <vector>
#include <gl/glew.h>
#include <core/base/program.h>
#include "mesh.h"
namespace glare
{
namespace core
{
namespace fs = std::experimental::filesystem;
/**
* \brief A Simple skybox wrapper which draws a cube map with a dedicated shader onto a cube mesh.
*/
class Skybox
{
public:
/**
* \brief Loads the given paths into a cubemap texture and creates the cube mesh, as well as the cubemap shader.
* \param faces The cubemap face image paths in order: posx, negx, posy, negy, posz, negz
*/
explicit Skybox(std::vector<fs::path> faces);
~Skybox() = default;
static std::vector<fs::path> collectFilesFrom(const fs::path &directory);
/**
* \brief Draws the cube map.
*/
void draw() const;
unsigned id() const;
uint64_t residentAddress() const;
bool resident() const;
uint64_t makeResident();
void makeNonResident() const;
private:
gl::handle::texture m_handle;
uint64_t m_resident_address = 0;
std::shared_ptr<ShaderProgram> m_cubemap_shader;
std::shared_ptr<Mesh> m_triangle_mesh;
};
}
}
#endif //INCLUDE_SKYBOX_H
#include <core/base/program.h>
#include "mesh.h"
namespace glare
{
namespace core
{
namespace fs = std::experimental::filesystem;
/**
* \brief A Simple skybox wrapper which draws a cube map with a dedicated shader onto a cube mesh.
*/
class Skybox
{
public:
/**
* \brief Loads the given paths into a cubemap texture and creates the cube mesh, as well as the cubemap shader.
* \param faces The cubemap face image paths in order: posx, negx, posy, negy, posz, negz
*/
explicit Skybox(std::vector<fs::path> faces);
~Skybox() = default;
static std::vector<fs::path> collectFilesFrom(const fs::path &directory);
/**
* \brief Draws the cube map.
*/
void draw() const;
unsigned id() const;
uint64_t residentAddress() const;
bool resident() const;
uint64_t makeResident() const;
void makeNonResident() const;
private:
gl::handle::texture m_handle;
mutable uint64_t m_resident_address = 0;
std::shared_ptr<ShaderProgram> m_cubemap_shader;
std::shared_ptr<Mesh> m_triangle_mesh;
};
}
}
#endif //INCLUDE_SKYBOX_H
#include "GBuffer.h"
#include <core/state.h>
#include <core/numeric/flags.h>
#include <util/log.h>
#include <util/files.h>
#include "GBuffer.h"
#include <core/state.h>
#include <core/numeric/flags.h>
#include <util/log.h>
#include <util/files.h>
#include <core/objects/light.h>
#include <core/rendering/light_manager.h>
namespace glare
{
namespace core
{
GBuffer::GBuffer(unsigned int width, unsigned int height, unsigned samples) : m_width(width), m_height(height)
{
const std::vector<std::shared_ptr<glare::core::Shader>> shaders = {
std::make_shared<glare::core::Shader>(gl::ShaderType::eVertex, files::shader("screenshader/screen_triangle.vert")),
std::make_shared<glare::core::Shader>(gl::ShaderType::eFragment, files::shader("screenshader/gbuffer/gbuffer.frag"))
};
m_texture_renderer = std::make_unique<TextureRenderer>(std::make_shared<glare::core::ShaderProgram>(shaders));
m_gbuffer_framebuffer = std::make_shared<Framebuffer<TextureMultisampled>>(width, height, samples);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor0);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor1);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor2);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor3);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor4);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor5);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor6);
m_gbuffer_framebuffer->attach(gl::Attachment::eDepth);
m_lights_buffer = std::make_unique<Buffer<gl::BufferType::eShaderStorage>>();
}
GBuffer::~GBuffer()
{
}
void GBuffer::record(std::function<void()> render_function) const
{
activate();
render_function();
deactivate();
}
void GBuffer::activate() const
{
m_gbuffer_framebuffer->activate();
gl::clear(gl::ClearBufferBits::eColor | gl::ClearBufferBits::eDepth);
}
void GBuffer::deactivate() const
{
m_gbuffer_framebuffer->deactivate();
}
void GBuffer::draw() const
{
gl::setEnabled(gl::EnableParameter::eDepthTest, false);
m_texture_renderer->shader().use();
m_lights_buffer->upload(LightManager::getInstance().storage(), gl::BufferUsage::eDynamicCopy);
m_texture_renderer->shader().updateStorageBuffer("lightsBuffer", m_lights_buffer);
LightManager::getInstance().clear();
m_texture_renderer->shader().updateUniformMatrix("u_view", state::camera->getView());
m_texture_renderer->shader().updateUniformMatrix("u_projection", state::camera->getProjection());
m_texture_renderer->shader().updateUniformInt("screen.width", m_width);
m_texture_renderer->shader().updateUniformInt("screen.height", m_height);
m_texture_renderer->shader().updateTexture("u_gbuffer.depth", m_gbuffer_framebuffer->depthAttachment());
m_texture_renderer->shader().updateTexture("u_gbuffer.diffuse", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor0));
m_texture_renderer->shader().updateTexture("u_gbuffer.normals", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor1));
m_texture_renderer->shader().updateTexture("u_gbuffer.specular", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor2));
m_texture_renderer->shader().updateTexture("u_gbuffer.id", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor3));
m_texture_renderer->shader().updateTexture("u_gbuffer.position", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor4));
m_texture_renderer->shader().updateTexture("u_gbuffer.position_raw", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor5));
m_texture_renderer->shader().updateTexture("u_gbuffer.lighting", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor6));
m_texture_renderer->shader().updateUniformUInt("u_samples", m_gbuffer_framebuffer->samples());
gl::activeTexture(0);
gl::bindTexture(gl::TextureTarget::eCubeMap, m_skybox->id());
m_texture_renderer->shader().updateUniformInt("environment", 0);
m_texture_renderer->shader().updateUniformVec3("camera_position", glm::vec3(state::camera->getOwner()->absoluteTransform() * glm::vec4(0,0,0,1)));
m_texture_renderer->draw();
gl::bindTexture(gl::TextureTarget::eCubeMap, 0);
gl::setEnabled(gl::EnableParameter::eDepthTest, true);
}
void GBuffer::setSkybox(std::shared_ptr<Skybox> skybox)
{
m_skybox = skybox;
}
const Framebuffer<TextureMultisampled>& GBuffer::framebuffer() const
{
return *m_gbuffer_framebuffer;
}
void GBuffer::updateSize(unsigned width, unsigned height)
{
m_width = width;
m_height = height;
m_gbuffer_framebuffer->resize(width, height, m_gbuffer_framebuffer->samples());
}
}
}
#include <core/rendering/light_manager.h>
namespace glare
{
namespace core
{
GBuffer::GBuffer(unsigned int width, unsigned int height, unsigned samples) : m_width(width), m_height(height)
{
const std::vector<std::shared_ptr<glare::core::Shader>> shaders = {
std::make_shared<glare::core::Shader>(gl::ShaderType::eVertex, files::shader("screenshader/screen_triangle.vert")),
std::make_shared<glare::core::Shader>(gl::ShaderType::eFragment, files::shader("screenshader/gbuffer/gbuffer.frag"))
};
m_texture_renderer = std::make_unique<TextureRenderer>(std::make_shared<glare::core::ShaderProgram>(shaders));
m_gbuffer_framebuffer = std::make_shared<Framebuffer<TextureMultisampled>>(width, height, samples);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor0);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor1);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor2);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor3);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor4);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor5);
m_gbuffer_framebuffer->attach(gl::Attachment::eColor6);
m_gbuffer_framebuffer->attach(gl::Attachment::eDepth);
m_lights_buffer = std::make_unique<Buffer<gl::BufferType::eShaderStorage>>();
}
GBuffer::~GBuffer()
{
}
void GBuffer::record(std::function<void()> render_function) const
{
activate();
render_function();
deactivate();
}
void GBuffer::activate() const
{
m_gbuffer_framebuffer->activate();
gl::clear(gl::ClearBufferBits::eColor | gl::ClearBufferBits::eDepth);
}
void GBuffer::deactivate() const
{
m_gbuffer_framebuffer->deactivate();
}
void GBuffer::draw() const
{
gl::setEnabled(gl::EnableParameter::eDepthTest, false);
m_texture_renderer->shader().use();
m_lights_buffer->upload(LightManager::getInstance().storage(), gl::BufferUsage::eDynamicCopy);
m_texture_renderer->shader().updateStorageBuffer("lightsBuffer", m_lights_buffer);
LightManager::getInstance().clear();
m_texture_renderer->shader().updateUniformMatrix("u_view", state::camera->getView());
m_texture_renderer->shader().updateUniformMatrix("u_projection", state::camera->getProjection());
m_texture_renderer->shader().updateUniformInt("screen.width", m_width);
m_texture_renderer->shader().updateUniformInt("screen.height", m_height);
m_texture_renderer->shader().updateTexture("u_gbuffer.depth", m_gbuffer_framebuffer->depthAttachment());
m_texture_renderer->shader().updateTexture("u_gbuffer.diffuse", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor0));
m_texture_renderer->shader().updateTexture("u_gbuffer.normals", m_gbuffer_framebuffer->colorAttachment(gl::Attachment::eColor1