Skip to content

Commit

Permalink
implement weighted blended order independent transparency
Browse files Browse the repository at this point in the history
  • Loading branch information
fu5ha committed Jul 10, 2019
1 parent 9b72023 commit 43a858d
Show file tree
Hide file tree
Showing 26 changed files with 684 additions and 272 deletions.
2 changes: 2 additions & 0 deletions src/appleseed.studio/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -365,6 +365,8 @@ set (utility_sources
utility/doubleslider.h
utility/foldablepanelwidget.cpp
utility/foldablepanelwidget.h
utility/gl.cpp
utility/gl.h
utility/inputwidgetproxies.cpp
utility/inputwidgetproxies.h
utility/interop.h
Expand Down
2 changes: 1 addition & 1 deletion src/appleseed.studio/main/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -329,7 +329,7 @@ int main(int argc, char* argv[])
// Set default surface format before creating application instance. This is
// required on macOS in order to use an OpenGL Core profile context.
QSurfaceFormat default_format;
default_format.setVersion(3, 3);
default_format.setVersion(4, 1);
default_format.setProfile(QSurfaceFormat::CoreProfile);
QSurfaceFormat::setDefaultFormat(default_format);

Expand Down
4 changes: 2 additions & 2 deletions src/appleseed.studio/mainwindow/mainwindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -747,12 +747,12 @@ void MainWindow::update_workspace()
m_project_manager.get_project()->get_light_path_recorder().get_light_path_count() > 0)
{
for (const_each<ViewportTabCollection> i = m_viewport_tabs; i; ++i)
i->second->set_light_paths_enabled(true);
i->second->set_light_paths_toggle_enabled(true);
}
else
{
for (const_each<ViewportTabCollection> i = m_viewport_tabs; i; ++i)
i->second->set_light_paths_enabled(false);
i->second->set_light_paths_toggle_enabled(false);
}
}

Expand Down
105 changes: 8 additions & 97 deletions src/appleseed.studio/mainwindow/rendering/glscenelayer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@
#include "glscenelayer.h"

// appleseed.studio headers.
#include "utility/miscellaneous.h"
#include "utility/gl.h"

// appleseed.renderer headers.
#include "renderer/api/camera.h"
Expand All @@ -50,7 +50,7 @@

// Qt headers.
#include <QKeyEvent>
#include <QOpenGLFunctions_3_3_Core>
#include <QOpenGLFunctions_4_1_Core>
#include <QGLFormat>
#include <QSurfaceFormat>
#include <QString>
Expand Down Expand Up @@ -137,7 +137,12 @@ GLSceneLayer::GLSceneLayer(
set_transform(m_camera.transform_sequence().evaluate(time));
}

void GLSceneLayer::set_gl_functions(QOpenGLFunctions_3_3_Core* functions)
GLSceneLayer::~GLSceneLayer()
{
cleanup_gl_data();
}

void GLSceneLayer::set_gl_functions(QOpenGLFunctions_4_1_Core* functions)
{
m_gl = functions;
}
Expand Down Expand Up @@ -364,100 +369,6 @@ void GLSceneLayer::load_scene_data()
load_assembly_instance(assembly_instance, time);
}

namespace {
const string shader_kind_to_string(const GLint shader_kind)
{
switch (shader_kind) {
case GL_VERTEX_SHADER:
return "Vertex";
case GL_FRAGMENT_SHADER:
return "Fragment";
default:
return "Unknown Kind";
}
}

void compile_shader(
QOpenGLFunctions_3_3_Core* f,
const GLuint shader,
const GLsizei count,
const GLchar** src_string,
const GLint* length)
{
f->glShaderSource(shader, count, src_string, length);
f->glCompileShader(shader);
GLint success;
f->glGetShaderiv(shader, GL_COMPILE_STATUS, &success);

if (!success)
{
char info_log[1024];
f->glGetShaderInfoLog(shader, 1024, NULL, info_log);

GLint shader_kind;
f->glGetShaderiv(shader, GL_SHADER_TYPE, &shader_kind);
string shader_kind_string = shader_kind_to_string(shader_kind);

RENDERER_LOG_ERROR("opengl: %s shader compilation failed:\n%s", shader_kind_string.c_str(), info_log);
}
}

void link_shader_program(
QOpenGLFunctions_3_3_Core* f,
const GLuint program,
const GLuint vert,
const GLuint frag)
{
f->glAttachShader(program, vert);

if (frag != 0)
f->glAttachShader(program, frag);

f->glLinkProgram(program);

GLint success;
f->glGetProgramiv(program, GL_LINK_STATUS, &success);

if (!success)
{
char info_log[1024];
f->glGetProgramInfoLog(program, 1024, NULL, info_log);
RENDERER_LOG_ERROR("opengl: shader program linking failed:\n%s", info_log);
}
}

void create_shader_program(
QOpenGLFunctions_3_3_Core* f,
GLuint& program,
const QByteArray* vert_source,
const QByteArray* frag_source)
{
bool has_frag_shader = frag_source != nullptr;

GLuint vert = f->glCreateShader(GL_VERTEX_SHADER);
GLuint frag = has_frag_shader ? f->glCreateShader(GL_FRAGMENT_SHADER) : 0;

auto gl_vert_source = static_cast<const GLchar*>(vert_source->constData());
auto gl_vert_source_length = static_cast<const GLint>(vert_source->size());

compile_shader(f, vert, 1, &gl_vert_source, &gl_vert_source_length);

if (has_frag_shader)
{
auto gl_frag_source = static_cast<const GLchar*>(frag_source->constData());
auto gl_frag_source_length = static_cast<const GLint>(frag_source->size());
compile_shader(f, frag, 1, &gl_frag_source, &gl_frag_source_length);
}

program = f->glCreateProgram();
link_shader_program(f, program, vert, frag);

f->glDeleteShader(vert);
if (has_frag_shader)
f->glDeleteShader(frag);
}
}

void GLSceneLayer::init_gl(QSurfaceFormat format)
{
// If there was already previous data, clean up
Expand Down
9 changes: 5 additions & 4 deletions src/appleseed.studio/mainwindow/rendering/glscenelayer.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ namespace renderer { class ObjectInstance; }
namespace renderer { class Project; }
class QKeyEvent;
class QImage;
class QOpenGLFunctions_3_3_Core;
class QOpenGLFunctions_4_1_Core;
class QSurfaceFormat;

namespace appleseed {
Expand All @@ -79,14 +79,16 @@ class GLSceneLayer
const size_t width,
const size_t height);

~GLSceneLayer();

void init_gl(
QSurfaceFormat format);

void set_transform(
const foundation::Transformd& transform);

void set_gl_functions(
QOpenGLFunctions_3_3_Core* functions);
QOpenGLFunctions_4_1_Core* functions);

void draw();
void draw_depth_only();
Expand All @@ -103,7 +105,7 @@ class GLSceneLayer

bool m_backface_culling_enabled;

QOpenGLFunctions_3_3_Core* m_gl;
QOpenGLFunctions_4_1_Core* m_gl;

std::vector<GLuint> m_scene_object_data_vbos;
std::vector<GLsizei> m_scene_object_data_index_counts;
Expand All @@ -125,7 +127,6 @@ class GLSceneLayer
bool m_initialized;

void render_scene();

void cleanup_gl_data();
void load_scene_data();

Expand Down
101 changes: 5 additions & 96 deletions src/appleseed.studio/mainwindow/rendering/lightpathslayer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@
#include "lightpathslayer.h"

// appleseed.studio headers.
#include "utility/miscellaneous.h"
#include "utility/gl.h"

// appleseed.renderer headers.
#include "renderer/api/camera.h"
Expand All @@ -50,7 +50,7 @@

// Qt headers.
#include <QKeyEvent>
#include <QOpenGLFunctions_3_3_Core>
#include <QOpenGLFunctions_4_1_Core>
#include <QSurfaceFormat>
#include <QString>

Expand Down Expand Up @@ -105,7 +105,7 @@ void LightPathsLayer::resize(const size_t width, const size_t height)
m_height = height;
}

void LightPathsLayer::set_gl_functions(QOpenGLFunctions_3_3_Core* functions)
void LightPathsLayer::set_gl_functions(QOpenGLFunctions_4_1_Core* functions)
{
m_gl = functions;
}
Expand Down Expand Up @@ -341,91 +341,6 @@ void LightPathsLayer::load_light_paths_data()
}
}

namespace {
const string shader_kind_to_string(const GLint shader_kind)
{
switch (shader_kind) {
case GL_VERTEX_SHADER:
return "Vertex";
case GL_FRAGMENT_SHADER:
return "Fragment";
default:
return "Unknown Kind";
}
}

void compile_shader(
QOpenGLFunctions_3_3_Core* f,
const GLuint shader,
const GLsizei count,
const GLchar** src_string,
const GLint* length)
{
f->glShaderSource(shader, count, src_string, length);
f->glCompileShader(shader);
GLint success;
f->glGetShaderiv(shader, GL_COMPILE_STATUS, &success);

if (!success)
{
char info_log[1024];
f->glGetShaderInfoLog(shader, 1024, NULL, info_log);

GLint shader_kind;
f->glGetShaderiv(shader, GL_SHADER_TYPE, &shader_kind);
string shader_kind_string = shader_kind_to_string(shader_kind);

RENDERER_LOG_ERROR("opengl: %s shader compilation failed:\n%s", shader_kind_string.c_str(), info_log);
}
}

void link_shader_program(
QOpenGLFunctions_3_3_Core* f,
const GLuint program,
const GLuint vert,
const GLuint frag)
{
f->glAttachShader(program, vert);
f->glAttachShader(program, frag);
f->glLinkProgram(program);

GLint success;
f->glGetProgramiv(program, GL_LINK_STATUS, &success);

if (!success)
{
char info_log[1024];
f->glGetProgramInfoLog(program, 1024, NULL, info_log);
RENDERER_LOG_ERROR("opengl: shader program linking failed:\n%s", info_log);
}
}

void create_shader_program(
QOpenGLFunctions_3_3_Core* f,
GLuint& program,
const QByteArray& vert_source,
const QByteArray& frag_source)
{
GLuint vert = f->glCreateShader(GL_VERTEX_SHADER);
GLuint frag = f->glCreateShader(GL_FRAGMENT_SHADER);

auto gl_vert_source = static_cast<const GLchar*>(vert_source.constData());
auto gl_vert_source_length = static_cast<const GLint>(vert_source.size());

auto gl_frag_source = static_cast<const GLchar*>(frag_source.constData());
auto gl_frag_source_length = static_cast<const GLint>(frag_source.size());

compile_shader(f, vert, 1, &gl_vert_source, &gl_vert_source_length);
compile_shader(f, frag, 1, &gl_frag_source, &gl_frag_source_length);

program = f->glCreateProgram();
link_shader_program(f, program, vert, frag);

f->glDeleteShader(vert);
f->glDeleteShader(frag);
}
}

void LightPathsLayer::init_gl(QSurfaceFormat format)
{
// If there was already previous data, clean up
Expand All @@ -441,8 +356,8 @@ void LightPathsLayer::init_gl(QSurfaceFormat format)
create_shader_program(
m_gl,
m_shader_program,
vertex_shader,
fragment_shader);
&vertex_shader,
&fragment_shader);

m_view_mat_loc = m_gl->glGetUniformLocation(m_shader_program, "u_view");
m_proj_mat_loc = m_gl->glGetUniformLocation(m_shader_program, "u_proj");
Expand Down Expand Up @@ -586,20 +501,14 @@ void LightPathsLayer::draw_render_camera() const
{
auto gl_view_matrix = const_cast<const GLfloat*>(&m_gl_render_view_matrix[0]);

m_gl->glEnable(GL_BLEND);
m_gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
render_scene(gl_view_matrix);
m_gl->glDisable(GL_BLEND);
}

void LightPathsLayer::draw() const
{
auto gl_view_matrix = const_cast<const GLfloat*>(&m_gl_view_matrix[0]);

m_gl->glEnable(GL_BLEND);
m_gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
render_scene(gl_view_matrix);
m_gl->glDisable(GL_BLEND);
}

void LightPathsLayer::render_scene(const GLfloat* gl_view_matrix) const
Expand Down
6 changes: 3 additions & 3 deletions src/appleseed.studio/mainwindow/rendering/lightpathslayer.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ namespace renderer { class ObjectInstance; }
namespace renderer { class Project; }
class QKeyEvent;
class QImage;
class QOpenGLFunctions_3_3_Core;
class QOpenGLFunctions_4_1_Core;

namespace appleseed {
namespace studio {
Expand Down Expand Up @@ -91,7 +91,7 @@ class LightPathsLayer: public QObject
const int selected_light_path_index);

void set_gl_functions(
QOpenGLFunctions_3_3_Core* functions);
QOpenGLFunctions_4_1_Core* functions);

void init_gl(QSurfaceFormat format);

Expand Down Expand Up @@ -127,7 +127,7 @@ class LightPathsLayer: public QObject
size_t m_width;
size_t m_height;

QOpenGLFunctions_3_3_Core* m_gl;
QOpenGLFunctions_4_1_Core* m_gl;

GLuint m_positions_vbo;
GLuint m_others_vbo;
Expand Down
Loading

0 comments on commit 43a858d

Please sign in to comment.