Commit: ddb33a3181cb9f61c5708fce0a06253401ae24d8
Author: Antony Riakiotakis
Date: Wed Oct 22 19:27:43 2014 +0200
Branches: viewport_experiments
https://developer.blender.org/rBddb33a3181cb9f61c5708fce0a06253401ae24d8
SSAO introduce quality settings
Basically change the way SSAO samples the screen by using a circular
filter instead. This is inspired by HBAO though we still don't use this.
The quality settings change the number and density of samples. We can
definitely improve things here though.
We also jitter the sampling locations per pixel. Generally this adds a
kind of noise. Some banding is, unfortunately still apparent and small
distances will introduce noise. This can be fixed but I will have to see
if it can be done without much of a cost.
===================================================================
M release/scripts/startup/bl_ui/space_view3d.py
M source/blender/gpu/GPU_extensions.h
M source/blender/gpu/intern/gpu_compositing.c
M source/blender/gpu/intern/gpu_extensions.c
M source/blender/gpu/shaders/gpu_shader_fx_frag.glsl
M source/blender/makesdna/DNA_view3d_types.h
M source/blender/makesrna/intern/rna_space.c
===================================================================
diff --git a/release/scripts/startup/bl_ui/space_view3d.py
b/release/scripts/startup/bl_ui/space_view3d.py
index 32d8709..db169e1 100644
--- a/release/scripts/startup/bl_ui/space_view3d.py
+++ b/release/scripts/startup/bl_ui/space_view3d.py
@@ -2903,6 +2903,7 @@ class VIEW3D_PT_view3d_shading(Panel):
subcol.prop(view, "ssao_darkening")
subcol.prop(view, "ssao_distance_max")
subcol.prop(view, "ssao_attenuation")
+ subcol.prop(view, "ssao_ray_sample_mode")
subcol.prop(view, "ssao_color")
diff --git a/source/blender/gpu/GPU_extensions.h
b/source/blender/gpu/GPU_extensions.h
index b8bec84..7e45e13 100644
--- a/source/blender/gpu/GPU_extensions.h
+++ b/source/blender/gpu/GPU_extensions.h
@@ -112,6 +112,7 @@ GPUTexture *GPU_texture_create_2D(int w, int h, float
*pixels, char err_out[256]
GPUTexture *GPU_texture_create_3D(int w, int h, int depth, int channels, float
*fpixels);
GPUTexture *GPU_texture_create_depth(int w, int h, char err_out[256]);
GPUTexture *GPU_texture_create_vsm_shadow_map(int size, char err_out[256]);
+GPUTexture *GPU_texture_create_2D_procedural(int w, int h, float *pixels, char
err_out[256]);
GPUTexture *GPU_texture_from_blender(struct Image *ima,
struct ImageUser *iuser, bool is_data, double time, int mipmap);
GPUTexture *GPU_texture_from_preview(struct PreviewImage *prv, int mipmap);
diff --git a/source/blender/gpu/intern/gpu_compositing.c
b/source/blender/gpu/intern/gpu_compositing.c
index e475713..5c675b9 100644
--- a/source/blender/gpu/intern/gpu_compositing.c
+++ b/source/blender/gpu/intern/gpu_compositing.c
@@ -34,6 +34,7 @@
#include "BLI_sys_types.h"
#include "BLI_rect.h"
#include "BLI_math.h"
+#include "BLI_rand.h"
#include "DNA_vec_types.h"
#include "DNA_view3d_types.h"
@@ -48,6 +49,9 @@
static const float fullscreencos[4][2] = {{-1.0f, -1.0f}, {1.0f, -1.0f},
{1.0f, 1.0f}, {-1.0f, 1.0f}};
static const float fullscreenuvs[4][2] = {{0.0f, 0.0f}, {1.0f, 0.0f}, {1.0f,
1.0f}, {0.0f, 1.0f}};
+static float ssao_sample_directions[16][2];
+static bool init = false;
+
struct GPUFX {
/* we borrow the term gbuffer from deferred rendering however this is
just a regular
* depth/color framebuffer. Could be extended later though */
@@ -58,7 +62,10 @@ struct GPUFX {
/* texture bound to the depth attachment of the gbuffer */
GPUTexture *depth_buffer;
-
+
+ /* texture used for jittering for various effects */
+ GPUTexture *jitter_buffer;
+
/* dimensions of the gbuffer */
int gbuffer_dim[2];
@@ -89,6 +96,11 @@ static void cleanup_fx_gl_data(GPUFX *fx, bool do_fbo)
fx->depth_buffer = NULL;
}
+ if (fx->jitter_buffer && do_fbo) {
+ GPU_texture_free(fx->jitter_buffer);
+ fx->jitter_buffer = NULL;
+ }
+
if (fx->gbuffer && do_fbo) {
GPU_framebuffer_free(fx->gbuffer);
fx->gbuffer = NULL;
@@ -102,8 +114,49 @@ void GPU_destroy_fx_compositor(GPUFX *fx)
MEM_freeN(fx);
}
+static GPUTexture * create_jitter_texture (void)
+{
+ float jitter [64 * 64][2];
+ int i;
+ for (i = 0; i < 64 * 64; i++) {
+ jitter[i][0] = BLI_frand();
+ jitter[i][1] = BLI_frand();
+ normalize_v2(jitter[i]);
+ }
+
+ return GPU_texture_create_2D_procedural(64, 64, &jitter[0][0], NULL);
+}
+
+static void create_sample_directions(void)
+{
+ int i;
+ float dir[4][2] = {{1.0f, 0.0f},
+ {0.0f, 1.0f},
+ {-1.0f, 0.0f},
+ {0.0f, -1.0f}};
+
+ for (i = 0; i < 4; i++) {
+ copy_v2_v2(ssao_sample_directions[i], dir[i]);
+ }
+
+ for (i = 0; i < 4; i++) {
+ float mat[2][2];
+ rotate_m2(mat, M_PI/4.0);
+
+ copy_v2_v2(ssao_sample_directions[i + 4],
ssao_sample_directions[i]);
+ mul_m2v2(mat, ssao_sample_directions[i + 4]);
+ }
+
+ for (i = 0; i < 8; i++) {
+ float mat[2][2];
+ rotate_m2(mat, M_PI/8.0);
+ copy_v2_v2(ssao_sample_directions[i + 8],
ssao_sample_directions[i]);
+ mul_m2v2(mat, ssao_sample_directions[i + 8]);
+ }
+ init = true;
+}
bool GPU_initialize_fx_passes(GPUFX *fx, rcti *rect, rcti *scissor_rect, int
fxflags)
{
@@ -111,10 +164,19 @@ bool GPU_initialize_fx_passes(GPUFX *fx, rcti *rect, rcti
*scissor_rect, int fxf
char err_out[256];
fx->effects = 0;
+
+ if (!fxflags) {
+ cleanup_fx_gl_data(fx, true);
+ return false;
+ }
if (!fx->gbuffer)
fx->gbuffer = GPU_framebuffer_create();
+ /* try creating the jitter texture */
+ if (!fx->jitter_buffer)
+ fx->jitter_buffer = create_jitter_texture();
+
if (!fx->gbuffer)
return false;
@@ -195,15 +257,20 @@ bool GPU_fx_do_composite_pass(GPUFX *fx, struct View3D
*v3d, struct RegionView3D
};
int i;
int screendim_uniform, color_uniform, depth_uniform,
dof_uniform, blurred_uniform;
- int ssao_uniform, ssao_color_uniform, ssao_viewvecs_uniform;
+ int ssao_uniform, ssao_color_uniform, ssao_viewvecs_uniform,
ssao_sample_params_uniform;
+ int ssao_jitter_uniform, ssao_direction_uniform;
float fac = v3d->dof_fstop * v3d->dof_aperture;
float dof_params[2] = {v3d->dof_aperture * fabs(fac /
(v3d->dof_focal_distance - fac)),
v3d->dof_focal_distance};
float ssao_params[4] = {v3d->ssao_distance_max,
v3d->ssao_darkening, v3d->ssao_attenuation, 0.0f};
float screen_dim[2] = {fx->gbuffer_dim[0], fx->gbuffer_dim[1]};
-
+ float sample_params[4] = {fx->gbuffer_dim[0],
fx->gbuffer_dim[1]};
+
float invproj[4][4];
+ if (!init)
+ create_sample_directions();
+
/* invert the view matrix */
invert_m4_m4(invproj, rv3d->winmat);
@@ -220,15 +287,38 @@ bool GPU_fx_do_composite_pass(GPUFX *fx, struct View3D
*v3d, struct RegionView3D
ssao_viewvecs[1][0] -= ssao_viewvecs[0][0];
ssao_viewvecs[1][1] = ssao_viewvecs[2][1] - ssao_viewvecs[0][1];
+ switch (v3d->ssao_ray_sample_mode) {
+ case 0:
+ sample_params[0] = 4;
+ sample_params[1] = 4;
+ break;
+ case 1:
+ sample_params[0] = 8;
+ sample_params[1] = 5;
+ break;
+ case 2:
+ sample_params[0] = 16;
+ sample_params[1] = 6;
+ break;
+ }
+
+ /* multiplier so we tile the random texture on screen */
+ sample_params[2] = fx->gbuffer_dim[0] / 64.0;
+ sample_params[3] = fx->gbuffer_dim[1] / 64.0;
+
dof_uniform = GPU_shader_get_uniform(fx_shader, "dof_params");
- ssao_uniform = GPU_shader_get_uniform(fx_shader, "ssao_params");
- ssao_color_uniform = GPU_shader_get_uniform(fx_shader,
"ssao_color");
blurred_uniform = GPU_shader_get_uniform(fx_shader,
"blurredcolorbuffer");
screendim_uniform = GPU_shader_get_uniform(fx_shader,
"screendim");
+
+ ssao_uniform = GPU_shader_get_uniform(fx_shader, "ssao_params");
+ ssao_color_uniform = GPU_shader_get_uniform(fx_shader,
"ssao_color");
color_uniform = GPU_shader_get_uniform(fx_shader,
"colorbuffer");
depth_uniform = GPU_shader_get_uniform(fx_shader,
"depthbuffer");
ssao_viewvecs_uniform = GPU_shader_get_uniform(fx_shader,
"ssao_viewvecs");
-
+ ssao_sample_params_uniform = GPU_shader_get_uniform(fx_shader,
"ssao_sample_params");
+ ssao_jitter_uniform = GPU_shader_get_uniform(fx_shader,
"jitter_tex");
+ ssao_direction_uniform = GPU_shader_get_uniform(fx_shader,
"sample_directions");
+
GPU_shader_bind(fx_shader);
GPU_shader_uniform_vector(fx_shader, screendim_uniform, 2, 1,
screen_dim);
@@ -236,6 +326,8 @@ bool GPU_fx_do_composite_pass(GPUFX *fx, struct View3D
*v3d, struct RegionView3D
GPU_shader_uniform_vector(fx_shader, ssao_uniform, 4, 1,
ssao_params);
GPU_shader_uniform_vector(fx_shader, ssao_color_uniform, 4, 1,
v3d->ssao_color);
GPU_shader_uniform_vector(fx_shader, ssao_viewvecs_uniform, 4,
3, ssao_viewvecs[0]);
+ GPU_shader_uniform_vector(fx_shader,
ssao_sample_params_uniform, 4, 1, sample_params);
+ GPU_shader_uniform_vector(fx_shader, ssao_direction_uniform, 2,
16, ssao_sample_directions[0]);
GPU_texture_bind(fx->color_buffer, numslots++);
GPU_shader_uniform_texture(fx_shader, blurred_uniform,
fx->color_buffer);
@@ -250,6 +342,9 @@ bool GPU_fx_do_composite_pass(GPUFX *fx, struct View3D
*v3d, struct RegionView3D
GPU_texture_bind(fx->depth_buffer, numslots++);
GPU_depth_texture_mode(fx->depth_buffer, false);
GPU_shader_uniform_texture(fx_shader, depth_uniform,
fx->depth_buffer);
+
+ GPU_texture_bind(fx->jitter_buffer, numslots++);
+ GPU_shader_uniform_texture(fx_shader, ssao_jitter_uniform,
fx->jitter_buffer);
}
/* set up quad buffer */
glVertexPointer(2, GL_FLOAT, 0, fullscreencos);
diff --git a/source/blender/gpu/intern/gpu_extensions.c
b/source/blender/gpu/intern/gpu_extensions.c
index c6270b8..b85efe6 100644
--- a/source/blender/gpu/intern/gpu_extensions.c
+++ b/source/blender/gpu/intern/gpu_extensions.c
@@ -699,6 +699,22 @@ GPUTexture *GPU_texture_create_vsm_shadow_map(int size,
char err_out[256])
return tex;
}
+GPUTexture *GPU_texture_create_2D_procedural(int w, int h, float *pixels, char
err_out[256])
+{
+ GPUTexture *tex = GPU_texture_create_nD(w, h, 2, NULL, 0, err_out);
+
+ if (tex) {
+ /* Now we tweak some of the settings */
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
+ glTexImage2D(GL_TEXTURE_2D, 0, GL_RG16F, w, h, 0, GL_RG,
GL_FLOAT, pixels);
+
+ GPU_texture_unbind(tex);
+ }
+
+ return tex;
+}
+
void GPU_invalid_tex_init(void)
{
float color[4] = {1.0f, 0.0f, 1.0f, 1.0};
diff --git a/source/blender/gpu/shaders/gpu_shader_fx_frag.glsl
b/source/blender/gpu/shaders/gpu_shader_fx_frag.glsl
index 31b7361..1232acc 100644
--- a/source/blender/gpu/shaders/gpu_shader_fx_frag.glsl
+++ b/source/blender/gpu/shaders/gpu_shader_fx_frag.glsl
@@ -5,6 +5,9 @@ uniform sampler2D colorbuffer;
//blurred color buffer for DOF effect
uniform sampler2D blurredcolorbuffer;
+// jitter texture for ssao
+uniform sampler2D jitter_tex;
+
// depth buffer
uniform sampler2D depthbuffer;
// coordinates on framebuffer in normalized (0.0-1.0) uv space
@@ -16,14 +19,14 @@ uniform vec2 dof_params;
/* ssao_params.x : pixel scale for the ssao radious */
/* ssao_params.y : factor for the ssao darkening */
uniform vec4 ssao_params;
+uniform vec4 ssao_sample_params;
uniform vec4 ssao_color;
+uniform vec2 sample_directions[16];
/* store the view space vectors for the corners of the view frustum here. It
@@ Diff output truncated at 10240 characters. @@
_______________________________________________
Bf-blender-cvs mailing list
[email protected]
http://lists.blender.org/mailman/listinfo/bf-blender-cvs