Skip to content

Commit

Permalink
new light path drawing using antialisased billboarded quads
Browse files Browse the repository at this point in the history
  • Loading branch information
fu5ha committed Jul 2, 2019
1 parent bf27aaf commit 9b72023
Show file tree
Hide file tree
Showing 12 changed files with 403 additions and 118 deletions.
351 changes: 254 additions & 97 deletions src/appleseed.studio/mainwindow/rendering/lightpathslayer.cpp

Large diffs are not rendered by default.

22 changes: 17 additions & 5 deletions src/appleseed.studio/mainwindow/rendering/lightpathslayer.h
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ class LightPathsLayer: public QObject
const size_t width,
const size_t height);

void resize(const size_t width, const size_t height);

void update_render_camera_transform();

Expand Down Expand Up @@ -120,15 +121,26 @@ class LightPathsLayer: public QObject

renderer::LightPathArray m_light_paths;
int m_selected_light_path_index; // -1 == display all paths
float m_max_luminance;
float m_max_thickness;
float m_min_thickness;
size_t m_width;
size_t m_height;

QOpenGLFunctions_3_3_Core* m_gl;

GLuint m_light_paths_vbo;
std::vector<GLsizei> m_light_paths_index_offsets;
GLuint m_positions_vbo;
GLuint m_others_vbo;
GLuint m_indices_ebo;
std::vector<GLsizei> m_index_offsets;
GLuint m_light_paths_vao;
GLuint m_light_paths_shader_program;
GLint m_light_paths_view_mat_location;
GLint m_light_paths_proj_mat_location;
GLuint m_shader_program;
GLint m_view_mat_loc;
GLint m_proj_mat_loc;
GLint m_res_loc;
GLint m_max_luminance_loc;
GLint m_min_thickness_loc;
GLint m_max_thickness_loc;
foundation::Matrix4f m_gl_render_view_matrix;
foundation::Matrix4f m_gl_view_matrix;
foundation::Matrix4f m_gl_proj_matrix;
Expand Down
12 changes: 10 additions & 2 deletions src/appleseed.studio/mainwindow/rendering/viewportwidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -174,10 +174,18 @@ void ViewportWidget::initializeGL() {
}

void ViewportWidget::resize(
const size_t width,
const size_t height)
const size_t width,
const size_t height)
{
m_render_layer->resize(width, height);
m_light_paths_layer->resize(width, height);
}

void ViewportWidget::resizeGL(
int width,
int height)
{
m_light_paths_layer->resize(width, height);
}

void ViewportWidget::set_draw_light_paths_enabled(const bool enabled)
Expand Down
1 change: 1 addition & 0 deletions src/appleseed.studio/mainwindow/rendering/viewportwidget.h
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,7 @@ class ViewportWidget
void create_render_layer(OCIO::ConstConfigRcPtr ocio_config);

void initializeGL() override;
void resizeGL(int width, int height) override;
void paintGL() override;
void dragEnterEvent(QDragEnterEvent* event) override;
void dragMoveEvent(QDragMoveEvent* event) override;
Expand Down
13 changes: 11 additions & 2 deletions src/appleseed.studio/resources/shaders/lightpaths.frag
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,20 @@
#version 330
#extension GL_ARB_separate_shader_objects : enable

layout(location = 0) in vec3 v_color;
flat in vec3 f_color;
in float f_aa_norm;
flat in float f_thickness;
flat in float f_total_thickness;
flat in float f_aspect_expansion_len;

uniform vec2 u_res;

out vec4 Target0;

void main()
{
Target0 = vec4(v_color, 1.0);
float dist = abs(f_aa_norm) * f_total_thickness - 0.5 / f_aspect_expansion_len;
float eps = fwidth(dist);
float a = 1.0 - smoothstep(f_thickness - eps, f_thickness + eps, dist);
Target0 = vec4(f_color, a);
}
84 changes: 75 additions & 9 deletions src/appleseed.studio/resources/shaders/lightpaths.vert
Original file line number Diff line number Diff line change
Expand Up @@ -26,18 +26,84 @@
//

#version 330
#extension GL_ARB_separate_shader_objects : enable

layout(location = 0) in vec3 a_pos;
layout(location = 1) in vec3 a_color;
const float AA_BUFFER_SIZE = 1.0;

layout(location = 0) in vec3 v_previous;
layout(location = 1) in vec3 v_position;
layout(location = 2) in vec3 v_next;
layout(location = 3) in float v_luminance;
layout(location = 4) in int v_direction_start_end;
layout(location = 5) in vec3 v_color;
layout(location = 6) in vec3 v_surface_normal;

uniform mat4 u_view;
uniform mat4 u_proj;
uniform mat4 u_view;
uniform vec2 u_res;
uniform float u_max_luminance;
uniform float u_max_thickness;
uniform float u_min_thickness;

flat out vec3 f_color;
out float f_aa_norm;
flat out float f_thickness;
flat out float f_total_thickness;
flat out float f_aspect_expansion_len;

void main() {
float aspect = u_res.x / u_res.y;
vec2 aspect_vec = vec2(aspect, 1.0);
mat4 vp = u_proj * u_view;
vec4 prev_proj = vp * vec4(v_previous, 1.0);
vec4 curr_proj = vp * vec4(v_position, 1.0);
vec4 next_proj = vp * vec4(v_next, 1.0);

//get 2D screen space with W divide and aspect correction
vec2 curr_screen = curr_proj.xy / curr_proj.w * aspect_vec;
vec2 prev_screen = prev_proj.xy / prev_proj.w * aspect_vec;
vec2 next_screen = next_proj.xy / next_proj.w * aspect_vec;

float orientation = 1.0;
if ((v_direction_start_end & 1) == 1)
{
orientation = -1.0;
}

vec2 dir = vec2(0.0);
if ((v_direction_start_end & 2) == 2)
{
//starting point uses (next - current)
dir = normalize(next_screen - curr_screen);
}
else if ((v_direction_start_end & 4) == 4)
{
//ending point uses (current - v_previous)
dir = normalize(curr_screen - prev_screen);
}
vec2 perp_dir = vec2(-dir.y, dir.x);

vec4 normal_clip = vp * vec4(v_surface_normal, 0.0);
normal_clip.xy *= aspect_vec;
normal_clip = normalize(normal_clip);
vec2 tang_clip = vec2(-normal_clip.y, normal_clip.x);

float tdp = dot(tang_clip, perp_dir);
vec2 expansion = perp_dir;
if (tdp > 0.05)
expansion = tang_clip / tdp;

vec2 norm_exp = normalize(expansion);
vec2 res_exp_dir = vec2(norm_exp.x * u_res.x, norm_exp.y * u_res.y);
f_aspect_expansion_len = length(res_exp_dir);

f_thickness = (max(max(min(v_luminance / u_max_luminance, 1.0), 0.0) * u_max_thickness, u_min_thickness) / 2.0) / f_aspect_expansion_len;

f_total_thickness = f_thickness + AA_BUFFER_SIZE / f_aspect_expansion_len;

layout(location = 0) out vec3 v_color;
expansion *= f_total_thickness;
expansion *= orientation;

void main()
{
v_color = a_color;
gl_Position = u_proj * u_view * vec4(a_pos, 1.0);
gl_Position = vec4((curr_screen + expansion) / aspect_vec, curr_proj.z / curr_proj.w, 1.0);
f_aa_norm = orientation;
f_color = v_color;
}
Original file line number Diff line number Diff line change
Expand Up @@ -466,6 +466,7 @@ void DirectLightingIntegrator::add_emitting_shape_sample_contribution(
light_path_stream->sampled_emitting_shape(
*sample.m_shape,
sample.m_point,
sample.m_geometric_normal,
material_value.m_beauty,
edf_value);
}
Expand Down Expand Up @@ -541,6 +542,7 @@ void DirectLightingIntegrator::add_non_physical_light_sample_contribution(
light_path_stream->sampled_non_physical_light(
*light,
emission_position,
m_material_sampler.get_shading_point().get_geometric_normal(),
material_value.m_beauty,
light_value);
}
Expand Down
4 changes: 4 additions & 0 deletions src/appleseed/renderer/kernel/lighting/lightpathrecorder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -276,6 +276,10 @@ void LightPathRecorder::get_light_path_vertex(
result.m_radiance[0] = source_vertex.m_radiance[0];
result.m_radiance[1] = source_vertex.m_radiance[1];
result.m_radiance[2] = source_vertex.m_radiance[2];

result.m_surface_normal[0] = source_vertex.m_surface_normal[0];
result.m_surface_normal[1] = source_vertex.m_surface_normal[1];
result.m_surface_normal[2] = source_vertex.m_surface_normal[2];
}

bool LightPathRecorder::write(const char* filename) const
Expand Down
1 change: 1 addition & 0 deletions src/appleseed/renderer/kernel/lighting/lightpathrecorder.h
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ struct LightPathVertex
const Entity* m_entity;
float m_position[3];
float m_radiance[3];
float m_surface_normal[3];
};


Expand Down
19 changes: 18 additions & 1 deletion src/appleseed/renderer/kernel/lighting/lightpathstream.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,8 @@ void LightPathStream::clear()
void LightPathStream::begin_path(
const PixelContext& pixel_context,
const Camera* camera,
const Vector3d& camera_vertex_position)
const Vector3d& camera_vertex_position,
const Vector3d& camera_vertex_normal)
{
assert(m_events.empty());
assert(m_hit_reflector_data.empty());
Expand All @@ -90,6 +91,7 @@ void LightPathStream::begin_path(

m_camera = camera;
m_camera_vertex_position = Vector3f(camera_vertex_position);
m_camera_vertex_normal = Vector3f(camera_vertex_normal);
m_pixel_coords = pixel_context.get_pixel_coords();
m_sample_position = Vector2f(pixel_context.get_sample_position());
}
Expand All @@ -107,6 +109,7 @@ void LightPathStream::hit_reflector(const PathVertex& vertex)
HitReflectorData data;
data.m_object_instance = &vertex.m_shading_point->get_object_instance();
data.m_vertex_position = Vector3f(vertex.get_point());
data.m_surface_normal = Vector3f(vertex.get_geometric_normal());
data.m_path_throughput = vertex.m_throughput.to_rgb(g_std_lighting_conditions);
m_hit_reflector_data.push_back(data);
}
Expand All @@ -126,6 +129,7 @@ void LightPathStream::hit_emitter(
HitEmitterData data;
data.m_object_instance = &vertex.m_shading_point->get_object_instance();
data.m_vertex_position = Vector3f(vertex.get_point());
data.m_surface_normal = Vector3f(vertex.get_geometric_normal());
data.m_path_throughput = vertex.m_throughput.to_rgb(g_std_lighting_conditions);
data.m_emitted_radiance = emitted_radiance.to_rgb(g_std_lighting_conditions);
m_hit_emitter_data.push_back(data);
Expand All @@ -134,6 +138,7 @@ void LightPathStream::hit_emitter(
void LightPathStream::sampled_emitting_shape(
const EmittingShape& shape,
const Vector3d& emission_position,
const Vector3d& emission_normal,
const Spectrum& material_value,
const Spectrum& emitted_radiance)
{
Expand All @@ -147,6 +152,7 @@ void LightPathStream::sampled_emitting_shape(
shape.get_assembly_instance()->get_assembly().object_instances().get_by_index(
shape.get_object_instance_index());
data.m_vertex_position = Vector3f(emission_position);
data.m_surface_normal = Vector3f(emission_normal);
data.m_material_value = material_value.to_rgb(g_std_lighting_conditions);
data.m_emitted_radiance = emitted_radiance.to_rgb(g_std_lighting_conditions);
m_sampled_emitter_data.push_back(data);
Expand All @@ -155,6 +161,7 @@ void LightPathStream::sampled_emitting_shape(
void LightPathStream::sampled_non_physical_light(
const Light& light,
const Vector3d& emission_position,
const Vector3d& emission_normal,
const Spectrum& material_value,
const Spectrum& emitted_radiance)
{
Expand All @@ -166,6 +173,7 @@ void LightPathStream::sampled_non_physical_light(
SampledEmitterData data;
data.m_entity = &light;
data.m_vertex_position = Vector3f(emission_position);
data.m_surface_normal = Vector3f(emission_normal);
data.m_material_value = material_value.to_rgb(g_std_lighting_conditions);
data.m_emitted_radiance = emitted_radiance.to_rgb(g_std_lighting_conditions);
m_sampled_emitter_data.push_back(data);
Expand Down Expand Up @@ -244,6 +252,7 @@ void LightPathStream::create_path_from_hit_emitter(const size_t emitter_event_in
StoredPathVertex emitter_vertex;
emitter_vertex.m_entity = hit_emitter_data.m_object_instance;
emitter_vertex.m_position = hit_emitter_data.m_vertex_position;
emitter_vertex.m_surface_normal = hit_emitter_data.m_surface_normal;
emitter_vertex.m_radiance = hit_emitter_data.m_emitted_radiance;
m_vertices.push_back(emitter_vertex);

Expand All @@ -264,6 +273,7 @@ void LightPathStream::create_path_from_hit_emitter(const size_t emitter_event_in
StoredPathVertex reflector_vertex;
reflector_vertex.m_entity = event_data.m_object_instance;
reflector_vertex.m_position = event_data.m_vertex_position;
reflector_vertex.m_surface_normal = event_data.m_surface_normal;
reflector_vertex.m_radiance = current_radiance;
m_vertices.push_back(reflector_vertex);

Expand All @@ -288,6 +298,7 @@ void LightPathStream::create_path_from_hit_emitter(const size_t emitter_event_in
StoredPathVertex camera_vertex;
camera_vertex.m_entity = m_camera;
camera_vertex.m_position = m_camera_vertex_position;
camera_vertex.m_surface_normal = m_camera_vertex_normal;
camera_vertex.m_radiance = current_radiance;
m_vertices.push_back(camera_vertex);

Expand Down Expand Up @@ -319,6 +330,7 @@ void LightPathStream::create_path_from_sampled_emitter(const size_t emitter_even
StoredPathVertex emitter_vertex;
emitter_vertex.m_entity = sampled_emitter_data.m_entity;
emitter_vertex.m_position = sampled_emitter_data.m_vertex_position;
emitter_vertex.m_surface_normal = sampled_emitter_data.m_surface_normal;
emitter_vertex.m_radiance = sampled_emitter_data.m_emitted_radiance;
m_vertices.push_back(emitter_vertex);

Expand All @@ -339,6 +351,7 @@ void LightPathStream::create_path_from_sampled_emitter(const size_t emitter_even
StoredPathVertex reflector_vertex;
reflector_vertex.m_entity = event_data.m_object_instance;
reflector_vertex.m_position = event_data.m_vertex_position;
reflector_vertex.m_surface_normal = event_data.m_surface_normal;
reflector_vertex.m_radiance = current_radiance;
m_vertices.push_back(reflector_vertex);

Expand All @@ -363,6 +376,7 @@ void LightPathStream::create_path_from_sampled_emitter(const size_t emitter_even
StoredPathVertex camera_vertex;
camera_vertex.m_entity = m_camera;
camera_vertex.m_position = m_camera_vertex_position;
camera_vertex.m_surface_normal = m_camera_vertex_normal;
camera_vertex.m_radiance = current_radiance;
m_vertices.push_back(camera_vertex);

Expand Down Expand Up @@ -394,6 +408,7 @@ void LightPathStream::create_path_from_sampled_environment(const size_t env_even
StoredPathVertex emitter_vertex;
emitter_vertex.m_entity = sampled_env_data.m_environment_edf;
emitter_vertex.m_position = last_reflector_data.m_vertex_position + m_scene_diameter * sampled_env_data.m_emission_direction;
emitter_vertex.m_surface_normal = -sampled_env_data.m_emission_direction;
emitter_vertex.m_radiance = sampled_env_data.m_emitted_radiance;
m_vertices.push_back(emitter_vertex);

Expand All @@ -414,6 +429,7 @@ void LightPathStream::create_path_from_sampled_environment(const size_t env_even
StoredPathVertex reflector_vertex;
reflector_vertex.m_entity = event_data.m_object_instance;
reflector_vertex.m_position = event_data.m_vertex_position;
reflector_vertex.m_surface_normal = event_data.m_surface_normal;
reflector_vertex.m_radiance = current_radiance;
m_vertices.push_back(reflector_vertex);

Expand All @@ -438,6 +454,7 @@ void LightPathStream::create_path_from_sampled_environment(const size_t env_even
StoredPathVertex camera_vertex;
camera_vertex.m_entity = m_camera;
camera_vertex.m_position = m_camera_vertex_position;
camera_vertex.m_surface_normal = m_camera_vertex_normal;
camera_vertex.m_radiance = current_radiance;
m_vertices.push_back(camera_vertex);

Expand Down
Loading

0 comments on commit 9b72023

Please sign in to comment.