diff options
17 files changed, 121 insertions, 82 deletions
diff --git a/release/scripts/startup/bl_ui/space_view3d.py b/release/scripts/startup/bl_ui/space_view3d.py index 3dff4078e95..c9c8861e9de 100644 --- a/release/scripts/startup/bl_ui/space_view3d.py +++ b/release/scripts/startup/bl_ui/space_view3d.py @@ -3242,6 +3242,9 @@ class VIEW3D_PT_view3d_shading(Panel): if scene.render.use_shading_nodes and view.viewport_shade == 'MATERIAL' : col.prop(view, "use_realistic_mat") + if view.use_realistic_mat: + subcol = col.column(align=True) + subcol.prop(view, "pbr_samples") col.prop(view, "show_backface_culling") diff --git a/source/blender/gpu/GPU_material.h b/source/blender/gpu/GPU_material.h index e058d2e33a8..57a8b7a8346 100644 --- a/source/blender/gpu/GPU_material.h +++ b/source/blender/gpu/GPU_material.h @@ -237,7 +237,8 @@ GPUBlendMode GPU_material_alpha_blend(GPUMaterial *material, float obcol[4]); /* High level functions to create and use GPU materials */ GPUMaterial *GPU_material_world(struct Scene *scene, struct World *wo, bool use_spherical_harmonics); -GPUMaterial *GPU_material_from_blender(struct Scene *scene, struct Material *ma, bool use_opensubdiv, bool use_realistic_preview); +GPUMaterial *GPU_material_from_blender(struct Scene *scene, struct Material *ma, bool use_opensubdiv, + bool use_realistic_preview, int samplecount); GPUMaterial *GPU_material_matcap(struct Scene *scene, struct Material *ma, bool use_opensubdiv); void GPU_material_free(struct ListBase *gpumaterial); @@ -255,6 +256,7 @@ bool GPU_material_bound(GPUMaterial *material); struct Scene *GPU_material_scene(GPUMaterial *material); GPUMatType GPU_material_get_type(GPUMaterial *material); void GPU_material_set_type(GPUMaterial *material, GPUMatType type); +int GPU_material_get_samplecount(GPUMaterial *material); void GPU_material_vertex_attributes(GPUMaterial *material, struct GPUVertexAttribs *attrib); diff --git a/source/blender/gpu/GPU_shader.h b/source/blender/gpu/GPU_shader.h index 0317976f9d0..89bf6c3e31e 100644 --- a/source/blender/gpu/GPU_shader.h +++ b/source/blender/gpu/GPU_shader.h @@ -63,7 +63,8 @@ GPUShader *GPU_shader_create_ex( const char *libcode, const char *defines, int input, int output, int number, - const int flags); + const int flags, + const int samplecount); void GPU_shader_free(GPUShader *shader); void GPU_shader_bind(GPUShader *shader); diff --git a/source/blender/gpu/intern/gpu_codegen.c b/source/blender/gpu/intern/gpu_codegen.c index b2c97764fd3..70bb58b0f66 100644 --- a/source/blender/gpu/intern/gpu_codegen.c +++ b/source/blender/gpu/intern/gpu_codegen.c @@ -1647,7 +1647,8 @@ GPUPass *GPU_generate_pass( GPUVertexAttribs *attribs, int *builtins, const GPUMatType type, const char *UNUSED(name), const bool use_opensubdiv, - const bool use_new_shading) + const bool use_new_shading, + const int samplecount) { GPUShader *shader; GPUPass *pass; @@ -1686,7 +1687,8 @@ GPUPass *GPU_generate_pass( 0, 0, 0, - flags); + flags, + samplecount); /* failed? */ if (!shader) { diff --git a/source/blender/gpu/intern/gpu_codegen.h b/source/blender/gpu/intern/gpu_codegen.h index 0500c82a16d..aa3343eaf4d 100644 --- a/source/blender/gpu/intern/gpu_codegen.h +++ b/source/blender/gpu/intern/gpu_codegen.h @@ -176,7 +176,8 @@ GPUPass *GPU_generate_pass(ListBase *nodes, struct GPUNodeLink *outlink, struct GPUVertexAttribs *attribs, int *builtin, const GPUMatType type, const char *name, const bool use_opensubdiv, - const bool use_new_shading); + const bool use_new_shading, + const int samplecount); struct GPUShader *GPU_pass_shader(GPUPass *pass); diff --git a/source/blender/gpu/intern/gpu_draw.c b/source/blender/gpu/intern/gpu_draw.c index 9688190548b..589a3157d15 100644 --- a/source/blender/gpu/intern/gpu_draw.c +++ b/source/blender/gpu/intern/gpu_draw.c @@ -1677,6 +1677,7 @@ void GPU_begin_object_materials( const bool new_shading_nodes = BKE_scene_use_new_shading_nodes(scene); const bool use_matcap = (v3d->flag2 & V3D_SHOW_SOLID_MATCAP) != 0; /* assumes v3d->defmaterial->preview is set */ bool use_opensubdiv = false; + int pbr_samples = 16 * v3d->pbr_samples; #ifdef WITH_OPENSUBDIV { @@ -1777,7 +1778,7 @@ void GPU_begin_object_materials( if (glsl) { GMS.gmatbuf[0] = &defmaterial; - GPU_material_from_blender(GMS.gscene, &defmaterial, GMS.is_opensubdiv, (v3d->flag3 & V3D_REALISTIC_MAT)); + GPU_material_from_blender(GMS.gscene, &defmaterial, GMS.is_opensubdiv, (v3d->flag3 & V3D_REALISTIC_MAT), pbr_samples); } GMS.alphablend[0] = GPU_BLEND_SOLID; @@ -1791,7 +1792,7 @@ void GPU_begin_object_materials( if (ma == NULL) ma = &defmaterial; /* create glsl material if requested */ - gpumat = glsl ? GPU_material_from_blender(GMS.gscene, ma, GMS.is_opensubdiv, (v3d->flag3 & V3D_REALISTIC_MAT)) : NULL; + gpumat = glsl ? GPU_material_from_blender(GMS.gscene, ma, GMS.is_opensubdiv, (v3d->flag3 & V3D_REALISTIC_MAT), pbr_samples) : NULL; if (gpumat) { /* do glsl only if creating it succeed, else fallback */ @@ -1890,7 +1891,7 @@ int GPU_object_material_bind(int nr, void *attribs) /* unbind glsl material */ if (GMS.gboundmat) { if (GMS.is_alpha_pass) glDepthMask(0); - GPU_material_unbind(GPU_material_from_blender(GMS.gscene, GMS.gboundmat, GMS.is_opensubdiv, false)); + GPU_material_unbind(GPU_material_from_blender(GMS.gscene, GMS.gboundmat, GMS.is_opensubdiv, false, 0)); GMS.gboundmat = NULL; } @@ -1917,7 +1918,7 @@ int GPU_object_material_bind(int nr, void *attribs) float auto_bump_scale; - GPUMaterial *gpumat = GPU_material_from_blender(GMS.gscene, mat, GMS.is_opensubdiv, false); + GPUMaterial *gpumat = GPU_material_from_blender(GMS.gscene, mat, GMS.is_opensubdiv, false, 0); GPU_material_vertex_attributes(gpumat, gattribs); if (GMS.dob) @@ -2015,7 +2016,7 @@ void GPU_object_material_unbind(void) glDisable(GL_CULL_FACE); if (GMS.is_alpha_pass) glDepthMask(0); - GPU_material_unbind(GPU_material_from_blender(GMS.gscene, GMS.gboundmat, GMS.is_opensubdiv, false)); + GPU_material_unbind(GPU_material_from_blender(GMS.gscene, GMS.gboundmat, GMS.is_opensubdiv, false, 0)); GMS.gboundmat = NULL; } else @@ -2313,7 +2314,7 @@ void GPU_draw_update_fvar_offset(DerivedMesh *dm) gpu_material = GPU_material_from_blender(GMS.gscene, material, GMS.is_opensubdiv, - false); + false, 0); GPU_material_update_fvar_offset(gpu_material, dm); } diff --git a/source/blender/gpu/intern/gpu_material.c b/source/blender/gpu/intern/gpu_material.c index ca6087886cb..271a13a2ef9 100644 --- a/source/blender/gpu/intern/gpu_material.c +++ b/source/blender/gpu/intern/gpu_material.c @@ -126,12 +126,14 @@ struct GPUMaterial { bool bound; /* for passing parameters to the world nodetree */ - GPUNodeLink *normalLink; - GPUNodeLink *tangentLink; + GPUNodeLink *norlink; + GPUNodeLink *tanlink; GPUNodeLink *lampNorLink; GPUNodeLink *lampPosLink; GPUNodeLink *lampInLink; GPUBrdfInput *brdf; + + int samplecount; bool is_opensubdiv; }; @@ -242,7 +244,8 @@ static int GPU_material_construct_end(GPUMaterial *material, const char *passnam &material->attribs, &material->builtins, material->type, passname, material->is_opensubdiv, - GPU_material_use_new_shading_nodes(material)); + GPU_material_use_new_shading_nodes(material), + material->samplecount); if (!material->pass) return 0; @@ -491,6 +494,11 @@ void GPU_material_set_type(GPUMaterial *material, GPUMatType type) material->type = type; } +int GPU_material_get_samplecount(GPUMaterial *material) +{ + return material->samplecount; +} + void GPU_material_vertex_attributes(GPUMaterial *material, GPUVertexAttribs *attribs) { *attribs = material->attribs; @@ -514,22 +522,22 @@ GPUNodeLink *GPU_material_get_output_link(GPUMaterial *material) void GPU_material_set_normal_link(GPUMaterial *material, GPUNodeLink *link) { - material->normalLink = link; + material->norlink = link; } GPUNodeLink *GPU_material_get_normal_link(GPUMaterial *material) { - return material->normalLink; + return material->norlink; } void GPU_material_set_tangent_link(GPUMaterial *material, GPUNodeLink *link) { - material->tangentLink = link; + material->tanlink = link; } GPUNodeLink *GPU_material_get_tangent_link(GPUMaterial *material) { - return material->tangentLink; + return material->tanlink; } void GPU_material_set_lamp_normal_link(GPUMaterial *material, GPUNodeLink *link) @@ -1892,29 +1900,28 @@ static void shade_one_brdf_light(GPUBrdfInput *brdf, GPULamp *lamp) GPUNodeLink *lamp_normal, *lamp_position, *lamp_incoming; GPUMatType type = GPU_material_get_type(mat); - if ( !(lamp->type == LA_SUN || lamp->type == LA_HEMI) ) { - GPU_link(mat, "shade_mul_value_v3", dist, lv, &lamp_normal); - } - else { - GPU_link(mat, "set_rgb", lv, &lamp_normal); - } - - if (lamp->type == LA_AREA) { - float vec_z[3] = {0.0, 0.0, -1.0}; - GPU_link(mat, "direction_transform_m4v3", GPU_uniform(&vec_z), GPU_dynamic_uniform((float*)lamp->dynmat, GPU_DYNAMIC_LAMP_DYNMAT, lamp->ob), &lamp_incoming); + /* Position */ + if (lamp->type == LA_SUN || lamp->type == LA_HEMI) { + float zero = 0.0f; + GPU_link(mat, "convert_vec3_to_vec4", lv, GPU_uniform(&zero), &lamp_position); } else { - GPU_link(mat, "set_rgb", lampcoLink, &lampzLink); + float one = 1.0f; + GPU_link(mat, "convert_vec3_to_vec4", GPU_dynamic_uniform(lamp->dynco, GPU_DYNAMIC_LAMP_DYNCO, lamp->ob), GPU_uniform(&one), &lamp_position); } + /* Normal */ if (lamp->type == LA_AREA) { - float vec_z[3] = {0.0, 0.0, -1.0}; - GPU_link(mat, "direction_transform_m4v3", GPU_uniform(&vec_z), GPU_dynamic_uniform((float*)lamp->dynmat, GPU_DYNAMIC_LAMP_DYNMAT, lamp->ob), &lamp_incoming); + float vec_z[3] = {0.0f, 0.0f, -1.0f}; + GPU_link(mat, "direction_transform_m4v3", GPU_uniform(&vec_z), GPU_dynamic_uniform((float*)lamp->dynmat, GPU_DYNAMIC_LAMP_DYNMAT, lamp->ob), &lamp_normal); } else { - GPU_link(mat, "set_rgb", lampcoLink, &lampzLink); + GPU_link(mat, "set_rgb", lv, &lamp_normal); } + /* Incoming */ + GPU_link(mat, "set_rgb", lv, &lamp_incoming); + /* to pass the lamp coordinates to the lamp shadertree */ GPU_material_set_lamp_normal_link(mat, lamp_normal); GPU_material_set_lamp_position_link(mat, lamp_position); @@ -2120,15 +2127,15 @@ static GPUNodeLink *GPU_brdf_sample_world(GPUBrdfInput *brdf) Scene *scene = GPU_material_scene(brdf->mat); GPUMaterial *mat = brdf->mat; World *wo = scene->world; - GPUNodeLink *normalLink, *tangentLink, *env_sample; + GPUNodeLink *norlink, *tanlink, *env_sample; GPUMatType type = GPU_material_get_type(mat); /* XXX : All of this is pretty wonky and need to be replace by sampling a global/local cubemap */ /* First run the normal into the World node tree * The environment texture nodes will save the nodelink of it. */ - GPU_link(mat, "direction_transform_m4v3", brdf->normal, GPU_builtin(GPU_INVERSE_VIEW_MATRIX), &normalLink); /* Send world normal for sampling */ - GPU_material_set_normal_link(mat, normalLink); + GPU_link(mat, "direction_transform_m4v3", brdf->normal, GPU_builtin(GPU_INVERSE_VIEW_MATRIX), &norlink); /* Send world normal for sampling */ + GPU_material_set_normal_link(mat, norlink); GPU_material_set_type(mat, GPU_MATERIAL_TYPE_ENV_NORMAL); ntreeGPUMaterialNodes(wo->nodetree, mat, NODE_NEW_SHADING); GPU_material_empty_output_link(mat); @@ -2136,8 +2143,8 @@ static GPUNodeLink *GPU_brdf_sample_world(GPUBrdfInput *brdf) if (brdf->type == GPU_BRDF_ANISO_GGX) { /* First run the tangent into the World node tree * The environment texture nodes will save the nodelink of it. */ - GPU_link(mat, "direction_transform_m4v3", brdf->aniso_tangent, GPU_builtin(GPU_INVERSE_VIEW_MATRIX), &tangentLink); /* Send world tangent for sampling */ - GPU_material_set_tangent_link(mat, tangentLink); + GPU_link(mat, "direction_transform_m4v3", brdf->aniso_tangent, GPU_builtin(GPU_INVERSE_VIEW_MATRIX), &tanlink); /* Send world tangent for sampling */ + GPU_material_set_tangent_link(mat, tanlink); GPU_material_set_type(mat, GPU_MATERIAL_TYPE_ENV_TANGENT); ntreeGPUMaterialNodes(wo->nodetree, mat, NODE_NEW_SHADING); GPU_material_empty_output_link(mat); @@ -2594,7 +2601,7 @@ GPUMaterial *GPU_material_world(struct Scene *scene, struct World *wo, bool use_ } -GPUMaterial *GPU_material_from_blender(Scene *scene, Material *ma, bool use_opensubdiv, bool use_realistic_preview) +GPUMaterial *GPU_material_from_blender(Scene *scene, Material *ma, bool use_opensubdiv, bool use_realistic_preview, int samplecount) { GPUMaterial *mat; GPUNodeLink *outlink; @@ -2613,6 +2620,7 @@ GPUMaterial *GPU_material_from_blender(Scene *scene, Material *ma, bool use_open mat = GPU_material_construct_begin(ma); mat->scene = scene; mat->type = (use_realistic_preview)? GPU_MATERIAL_TYPE_MESH_REAL_SH : GPU_MATERIAL_TYPE_MESH; + mat->samplecount = samplecount; mat->is_opensubdiv = use_opensubdiv; /* render pipeline option */ @@ -2646,7 +2654,7 @@ GPUMaterial *GPU_material_from_blender(Scene *scene, Material *ma, bool use_open if (mat->outlink) GPU_link(mat, "linearrgb_to_srgb", mat->outlink, &mat->outlink); - //VERY BAD but it works + /* XXX : this is nasty but it works */ mat->type = GPU_MATERIAL_TYPE_MESH; GPU_material_construct_end(mat, ma->id.name); @@ -3171,7 +3179,7 @@ GPUShaderExport *GPU_shader_export(struct Scene *scene, struct Material *ma) int liblen, fraglen; /* TODO(sergey): How to determine whether we need OSD or not here? */ - GPUMaterial *mat = GPU_material_from_blender(scene, ma, false, false); + GPUMaterial *mat = GPU_material_from_blender(scene, ma, false, false, 0); GPUPass *pass = (mat) ? mat->pass : NULL; if (pass && pass->fragmentcode && pass->vertexcode) { diff --git a/source/blender/gpu/intern/gpu_shader.c b/source/blender/gpu/intern/gpu_shader.c index 36b4f60e6cb..e9c029d3587 100644 --- a/source/blender/gpu/intern/gpu_shader.c +++ b/source/blender/gpu/intern/gpu_shader.c @@ -186,7 +186,8 @@ static void gpu_shader_standard_extensions(char defines[MAX_EXT_DEFINE_LENGTH], static void gpu_shader_standard_defines(char defines[MAX_DEFINE_LENGTH], bool use_opensubdiv, - bool use_new_shading) + bool use_new_shading, + int importance_sample_count) { /* some useful defines to detect GPU type */ if (GPU_type_matches(GPU_DEVICE_ATI, GPU_OS_ANY, GPU_DRIVER_ANY)) { @@ -229,6 +230,14 @@ static void gpu_shader_standard_defines(char defines[MAX_DEFINE_LENGTH], strcat(defines, "#define USE_NEW_SHADING\n"); } + if (!importance_sample_count) { + importance_sample_count = 1; + } + + char buffer[32]; + sprintf(buffer, "#define NUM_SAMPLE %du\n", importance_sample_count); + strcat(defines, buffer); + return; } @@ -249,7 +258,8 @@ GPUShader *GPU_shader_create(const char *vertexcode, input, output, number, - GPU_SHADER_FLAGS_NONE); + GPU_SHADER_FLAGS_NONE, + 0); } GPUShader *GPU_shader_create_ex(const char *vertexcode, @@ -260,7 +270,8 @@ GPUShader *GPU_shader_create_ex(const char *vertexcode, int input, int output, int number, - const int flags) + const int flags, + const int samplecount) { #ifdef WITH_OPENSUBDIV /* TODO(sergey): used to add #version 150 to the geometry shader. @@ -305,7 +316,8 @@ GPUShader *GPU_shader_create_ex(const char *vertexcode, gpu_shader_standard_defines(standard_defines, use_opensubdiv, - (flags & GPU_SHADER_FLAGS_NEW_SHADING) != 0); + (flags & GPU_SHADER_FLAGS_NEW_SHADING) != 0, + samplecount); gpu_shader_standard_extensions(standard_extensions, geocode != NULL); if (vertexcode) { diff --git a/source/blender/gpu/shaders/gpu_shader_material.glsl b/source/blender/gpu/shaders/gpu_shader_material.glsl index fd296966744..8256ac1bf72 100644 --- a/source/blender/gpu/shaders/gpu_shader_material.glsl +++ b/source/blender/gpu/shaders/gpu_shader_material.glsl @@ -13,6 +13,11 @@ float convert_rgba_to_float(vec4 color) #endif } +void convert_vec3_to_vec4(vec3 invec, float val, out vec4 outvec) +{ + outvec = vec4(invec, val); +} + float exp_blender(float f) { return pow(2.71828182846, f); @@ -3738,16 +3743,16 @@ void node_geometry(vec3 I, vec3 N, vec3 attr_orco, mat4 toworld, mat4 fromobj, pointiness = 0.5; } -void node_geometry_lamp(vec3 N, vec3 P, vec3 I, mat4 toworld, +void node_geometry_lamp(vec3 N, vec4 P, vec3 I, mat4 toworld, out vec3 position, out vec3 normal, out vec3 tangent, out vec3 true_normal, out vec3 incoming, out vec3 parametric, out float backfacing, out float pointiness) { - position = (toworld*vec4(I-P, 1.0)).xyz; + position = (toworld*P).xyz; normal = normalize(toworld*vec4(N, 0.0)).xyz; tangent = vec3(0.0); true_normal = normal; - incoming = normalize(toworld*vec4(P, 0.0)).xyz; + incoming = normalize(toworld*vec4(I, 0.0)).xyz; parametric = vec3(0.0); backfacing = 0.0; @@ -4198,9 +4203,9 @@ void node_light_path( transmission_depth = 1.0; } -void node_light_falloff(float strength, float tsmooth, vec3 ray, out float quadratic, out float linear, out float constant) +void node_light_falloff(float strength, float tsmooth, vec4 lamppos, vec3 pos, out float quadratic, out float linear, out float constant) { - float ray_length = length(ray); + float ray_length = length(lamppos.xyz - pos); if (tsmooth > 0.0) { float squared = ray_length * ray_length; @@ -4301,10 +4306,6 @@ void env_sampling_refract_sharp(vec3 I, vec3 N, float eta, out vec3 result) result = refract(normalize(I), normalize(N), (gl_FrontFacing) ? 1.0/eta : eta); } -/* Hammersley points set */ -uniform vec4 hammersley32[32] = vec4[32](vec4(0,0,1,0),vec4(0.03125,0.5,-1,1.224646798818428e-16),vec4(0.0625,0.25,0,1),vec4(0.09375,0.75,-1.8369701961596905e-16,-1),vec4(0.125,0.125,0.7071067811865475,0.7071067811865475),vec4(0.15625,0.625,-0.7071067811865476,-0.7071067811865474),vec4(0.1875,0.375,-0.7071067811865474,0.7071067811865476),vec4(0.21875,0.875,0.7071067811865474,-0.7071067811865476),vec4(0.25,0.0625,0.9238795325112867,0.3826834323650898),vec4(0.28125,0.5625,-0.9238795325112867,-0.38268343236508967),vec4(0.3125,0.3125,-0.3826834323650897,0.9238795325112867),vec4(0.34375,0.8125,0.38268343236509006,-0.9238795325112866),vec4(0.375,0.1875,0.3826834323650898,0.9238795325112867),vec4(0.40625,0.6875,-0.38268343236509034,-0.9238795325112865),vec4(0.4375,0.4375,-0.9238795325112867,0.3826834323650898),vec4(0.46875,0.9375,0.9238795325112865,-0.38268343236509034),vec4(0.5,0.03125,0.9807852804032304,0.19509032201612825),vec4(0.53125,0.53125,-0.9807852804032304,-0.19509032201612836),vec4(0.5625,0.28125,-0.1950903220161282,0.9807852804032304),vec4(0.59375,0.78125,0.19509032201612828,-0.9807852804032304),vec4(0.625,0.15625,0.5555702330196022,0.8314696123025452),vec4(0.65625,0.65625,-0.555570233019602,-0.8314696123025453),vec4(0.6875,0.40625,-0.8314696123025453,0.555570233019602),vec4(0.71875,0.90625,0.8314696123025452,-0.5555702330196022),vec4(0.75,0.09375,0.8314696123025452,0.5555702330196022),vec4(0.78125,0.59375,-0.8314696123025455,-0.5555702330196018),vec4(0.8125,0.34375,-0.5555702330196018,0.8314696123025455),vec4(0.84375,0.84375,0.5555702330196017,-0.8314696123025455),vec4(0.875,0.21875,0.19509032201612825,0.9807852804032304),vec4(0.90625,0.71875,-0.19509032201612864,-0.9807852804032304),vec4(0.9375,0.46875,-0.9807852804032303,0.19509032201612844),vec4(0.96875,0.96875,0.9807852804032304,-0.19509032201612864)); -#define NUM_SAMPLE 32u - /* needed for uint type and bitwise operation */ #extension GL_EXT_gpu_shader4: enable diff --git a/source/blender/makesdna/DNA_view3d_types.h b/source/blender/makesdna/DNA_view3d_types.h index 6ea8c816d1e..da5a2b4cbd7 100644 --- a/source/blender/makesdna/DNA_view3d_types.h +++ b/source/blender/makesdna/DNA_view3d_types.h @@ -237,6 +237,10 @@ typedef struct View3D { float stereo3d_convergence_factor; float stereo3d_volume_alpha; float stereo3d_convergence_alpha; + + /* Pbr options */ + int pbr_samples; + int pad5; } View3D; diff --git a/source/blender/makesrna/intern/rna_space.c b/source/blender/makesrna/intern/rna_space.c index e778c535476..345494f63a5 100644 --- a/source/blender/makesrna/intern/rna_space.c +++ b/source/blender/makesrna/intern/rna_space.c @@ -2583,6 +2583,12 @@ static void rna_def_space_view3d(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Realistic Material Preview", "Use a more accurate preview of the shaders in the viewport"); RNA_def_property_update(prop, NC_SPACE | ND_SPACE_VIEW3D, "rna_SpaceView3D_viewport_real_shading_update"); + prop = RNA_def_property(srna, "pbr_samples", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "pbr_samples"); + RNA_def_property_ui_text(prop, "Quality", "Define the quality of brdf sampling."); + RNA_def_property_range(prop, 1, 64); + RNA_def_property_update(prop, NC_SPACE | ND_SPACE_VIEW3D, "rna_SpaceView3D_viewport_real_shading_update"); + prop = RNA_def_property(srna, "use_occlude_geometry", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", V3D_ZBUF_SELECT); RNA_def_property_ui_text(prop, "Occlude Geometry", "Limit selection to visible (clipped with depth buffer)"); diff --git a/source/blender/nodes/shader/nodes/node_shader_geometry.c b/source/blender/nodes/shader/nodes/node_shader_geometry.c index 67c2d15414a..4616d726617 100644 --- a/source/blender/nodes/shader/nodes/node_shader_geometry.c +++ b/source/blender/nodes/shader/nodes/node_shader_geometry.c @@ -45,12 +45,12 @@ static bNodeSocketTemplate sh_node_geometry_out[] = { static int node_shader_gpu_geometry(GPUMaterial *mat, bNode *UNUSED(node), bNodeExecData *UNUSED(execdata), GPUNodeStack *in, GPUNodeStack *out) { if (GPU_material_get_type(mat) == GPU_MATERIAL_TYPE_LAMP) { - GPUNodeLink *lampNorLink = GPU_material_get_lamp_normal_link(mat); - GPUNodeLink *lampPosLink = GPU_material_get_lamp_position_link(mat); - GPUNodeLink *lampInLink = GPU_material_get_lamp_incoming_link(mat); + GPUNodeLink *lamp_normal = GPU_material_get_lamp_normal_link(mat); + GPUNodeLink *lamp_position = GPU_material_get_lamp_position_link(mat); + GPUNodeLink *lamp_incoming = GPU_material_get_lamp_incoming_link(mat); return GPU_stack_link(mat, "node_geometry_lamp", in, out, - lampNorLink, lampPosLink, lampInLink, + lamp_normal, lamp_position, lamp_incoming, GPU_builtin(GPU_INVERSE_VIEW_MATRIX)); } else diff --git a/source/blender/nodes/shader/nodes/node_shader_light_falloff.c b/source/blender/nodes/shader/nodes/node_shader_light_falloff.c index 9b8567d3fcd..e3c30972c70 100644 --- a/source/blender/nodes/shader/nodes/node_shader_light_falloff.c +++ b/source/blender/nodes/shader/nodes/node_shader_light_falloff.c @@ -48,14 +48,16 @@ static bNodeSocketTemplate sh_node_light_falloff_out[] = { static int node_shader_gpu_light_falloff(GPUMaterial *mat, bNode *UNUSED(node), bNodeExecData *UNUSED(execdata), GPUNodeStack *in, GPUNodeStack *out) { if (GPU_material_get_type(mat) == GPU_MATERIAL_TYPE_LAMP) { - GPUNodeLink *lampcoLink = GPU_material_get_lampco_link(mat); - if (lampcoLink) - return GPU_stack_link(mat, "node_light_falloff", in, out, lampcoLink); + GPUNodeLink *lampposlink = GPU_material_get_lamp_position_link(mat); + if (lampposlink) + return GPU_stack_link(mat, "node_light_falloff", in, out, lampposlink, GPU_builtin(GPU_VIEW_POSITION)); else return 0; } - else - return GPU_stack_link(mat, "node_light_falloff", in, out, GPU_builtin(GPU_VIEW_POSITION)); + else { + float lamppos[4] = {0.0f}; + return GPU_stack_link(mat, "node_light_falloff", in, out, GPU_uniform(&lamppos), GPU_builtin(GPU_VIEW_POSITION)); + } } /* node type definition */ diff --git a/source/blender/nodes/shader/nodes/node_shader_tex_coord.c b/source/blender/nodes/shader/nodes/node_shader_tex_coord.c index 7fac7241034..c40be24f08d 100644 --- a/source/blender/nodes/shader/nodes/node_shader_tex_coord.c +++ b/source/blender/nodes/shader/nodes/node_shader_tex_coord.c @@ -47,8 +47,8 @@ static int node_shader_gpu_tex_coord(GPUMaterial *mat, bNode *UNUSED(node), bNod GPUNodeLink *orco = GPU_attribute(CD_ORCO, ""); GPUNodeLink *mtface = GPU_attribute(CD_MTFACE, ""); GPUMatType type = GPU_material_get_type(mat); - GPUNodeLink *normalLink = GPU_material_get_normal_link(mat); - GPUNodeLink *tangentLink = GPU_material_get_tangent_link(mat); + GPUNodeLink *norlink = GPU_material_get_normal_link(mat); + GPUNodeLink *tanlink = GPU_material_get_tangent_link(mat); if (type == GPU_MATERIAL_TYPE_MESH || type == GPU_MATERIAL_TYPE_MESH_REAL_SH) { return GPU_stack_link(mat, "node_tex_coord", in, out, @@ -64,13 +64,13 @@ static int node_shader_gpu_tex_coord(GPUMaterial *mat, bNode *UNUSED(node), bNod } else if (type == GPU_MATERIAL_TYPE_ENV_NORMAL) { return GPU_stack_link(mat, "node_tex_coord_background_sampling_normal", in, out, - GPU_builtin(GPU_VIEW_POSITION), normalLink, + GPU_builtin(GPU_VIEW_POSITION), norlink, GPU_builtin(GPU_VIEW_MATRIX), GPU_builtin(GPU_INVERSE_OBJECT_MATRIX), GPU_builtin(GPU_CAMERA_TEXCO_FACTORS), orco, mtface); } else if (type == GPU_MATERIAL_TYPE_ENV_TANGENT) { return GPU_stack_link(mat, "node_tex_coord_background_sampling_normal", in, out, - GPU_builtin(GPU_VIEW_POSITION), tangentLink, + GPU_builtin(GPU_VIEW_POSITION), tanlink, GPU_builtin(GPU_VIEW_MATRIX), GPU_builtin(GPU_INVERSE_OBJECT_MATRIX), GPU_builtin(GPU_CAMERA_TEXCO_FACTORS), orco, mtface); } diff --git a/source/blender/nodes/shader/nodes/node_shader_tex_environment.c b/source/blender/nodes/shader/nodes/node_shader_tex_environment.c index 787b7e549b7..b7fe7232556 100644 --- a/source/blender/nodes/shader/nodes/node_shader_tex_environment.c +++ b/source/blender/nodes/shader/nodes/node_shader_tex_environment.c @@ -156,16 +156,15 @@ static void SHFilter(ImBuf *ibuf, float *SHCoef) } } -static void get_precalc_lod_factors(Image *ima, ImageUser *iuser, float *maxLod, float *precalcLodFactor, float *sampleNumber) +static void get_precalc_lod_factors(Image *ima, ImageUser *iuser, float *maxLod, float sampleNumber, float *precalcLodFactor) { *maxLod = 0.0f; *precalcLodFactor = 0.0f; - *sampleNumber = 32.0f; /* Hardcoded for now */ ImBuf *ibuf = BKE_image_acquire_ibuf(ima, iuser, NULL); if (ibuf) { *maxLod = log((float)ibuf->y)/log(2); - *precalcLodFactor = 0.5f * log( (float)ibuf->x * (float)ibuf->y / *sampleNumber) / log(2); + *precalcLodFactor = 0.5f * log( (float)ibuf->x * (float)ibuf->y / sampleNumber) / log(2); *precalcLodFactor -= 2.0f; /* Biasing the factor to get more accurate sampling */ } BKE_image_release_ibuf(ima, ibuf, NULL); @@ -276,8 +275,8 @@ static int node_shader_gpu_tex_environment(GPUMaterial *mat, bNode *node, bNodeE } else if (brdf && brdf->type == GPU_BRDF_GLOSSY_GGX) { // REFLECTION GLOSSY - float maxLod, precalcLodFactor, sampleNumber; - get_precalc_lod_factors(ima, iuser, &maxLod, &precalcLodFactor, &sampleNumber); + float maxLod, precalcLodFactor, sampleNumber = GPU_material_get_samplecount(mat); + get_precalc_lod_factors(ima, iuser, &maxLod, sampleNumber, &precalcLodFactor); return GPU_link(mat, "env_sampling_reflect_glossy", in[0].link, normal_transformed, brdf->roughness, GPU_uniform(&precalcLodFactor), GPU_uniform(&maxLod), GPU_builtin(GPU_INVERSE_VIEW_MATRIX), @@ -285,14 +284,13 @@ static int node_shader_gpu_tex_environment(GPUMaterial *mat, bNode *node, bNodeE } else if (brdf && brdf->type == GPU_BRDF_ANISO_GGX) { // REFLECTION ANISO - float maxLod, precalcLodFactor, sampleNumber; - maxLod = 0.0f, precalcLodFactor = 0.0f, sampleNumber = 64.0f; /* Hardcoded for now */ + float maxLod, precalcLodFactor, sampleNumber = GPU_material_get_samplecount(mat); + maxLod = 0.0f, precalcLodFactor = 0.0f, sampleNumber *= 2.0f; ImBuf *ibuf = BKE_image_acquire_ibuf(ima, iuser, NULL); if (ibuf) { maxLod = log((float)ibuf->y)/log(2); precalcLodFactor = 0.5f * log( (float)ibuf->x * (float)ibuf->y / sampleNumber) / log(2); - //precalcLodFactor -= 2.0f; /* Biasing the factor to get more accurate sampling */ } BKE_image_release_ibuf(ima, ibuf, NULL); @@ -303,9 +301,8 @@ static int node_shader_gpu_tex_environment(GPUMaterial *mat, bNode *node, bNodeE } else if (brdf && brdf->type == GPU_BRDF_REFRACT_GGX) { // REFRACTION GLOSSY - float maxLod, precalcLodFactor, sampleNumber; - get_precalc_lod_factors(ima, iuser, &maxLod, &precalcLodFactor, &sampleNumber); - precalcLodFactor += 1.0f; /* Biasing the factor Again */ + float maxLod, precalcLodFactor, sampleNumber = GPU_material_get_samplecount(mat); + get_precalc_lod_factors(ima, iuser, &maxLod, sampleNumber, &precalcLodFactor); return GPU_link(mat, "env_sampling_refract_glossy", in[0].link, normal_transformed, brdf->ior, brdf->roughness, GPU_uniform(&precalcLodFactor), GPU_uniform(&maxLod), GPU_builtin(GPU_INVERSE_VIEW_MATRIX), @@ -313,9 +310,8 @@ static int node_shader_gpu_tex_environment(GPUMaterial *mat, bNode *node, bNodeE } else if (brdf && brdf->type == GPU_BRDF_GLASS_GGX) { // GLASS GLOSSY - float maxLod, precalcLodFactor, sampleNumber; - get_precalc_lod_factors(ima, iuser, &maxLod, &precalcLodFactor, &sampleNumber); - precalcLodFactor += 1.0f; /* Biasing the factor Again */ + float maxLod, precalcLodFactor, sampleNumber = GPU_material_get_samplecount(mat); + get_precalc_lod_factors(ima, iuser, &maxLod, sampleNumber, &precalcLodFactor); return GPU_link(mat, "env_sampling_glass_glossy", in[0].link, normal_transformed, brdf->ior, brdf->roughness, GPU_uniform(&precalcLodFactor), GPU_uniform(&maxLod), GPU_builtin(GPU_INVERSE_VIEW_MATRIX), diff --git a/source/gameengine/Ketsji/BL_BlenderShader.cpp b/source/gameengine/Ketsji/BL_BlenderShader.cpp index 88320e26b7c..0b11332e54b 100644 --- a/source/gameengine/Ketsji/BL_BlenderShader.cpp +++ b/source/gameengine/Ketsji/BL_BlenderShader.cpp @@ -62,7 +62,7 @@ BL_BlenderShader::~BL_BlenderShader() void BL_BlenderShader::ReloadMaterial() { - mGPUMat = (mMat) ? GPU_material_from_blender(mBlenderScene, mMat, false, false) : NULL; + mGPUMat = (mMat) ? GPU_material_from_blender(mBlenderScene, mMat, false, false, 0) : NULL; } void BL_BlenderShader::SetProg(bool enable, double time, RAS_IRasterizer* rasty) diff --git a/source/gameengine/Rasterizer/RAS_OpenGLRasterizer/RAS_OpenGLRasterizer.cpp b/source/gameengine/Rasterizer/RAS_OpenGLRasterizer/RAS_OpenGLRasterizer.cpp index 2a4a712217c..d07c9c95f13 100644 --- a/source/gameengine/Rasterizer/RAS_OpenGLRasterizer/RAS_OpenGLRasterizer.cpp +++ b/source/gameengine/Rasterizer/RAS_OpenGLRasterizer/RAS_OpenGLRasterizer.cpp @@ -806,7 +806,7 @@ void RAS_OpenGLRasterizer::DrawDerivedMesh(class RAS_MeshSlot &ms) Material* blmat = current_polymat->GetBlenderMaterial(); Scene* blscene = current_polymat->GetBlenderScene(); if (!current_wireframe && blscene && blmat) - GPU_material_vertex_attributes(GPU_material_from_blender(blscene, blmat, false, false), ¤t_gpu_attribs); + GPU_material_vertex_attributes(GPU_material_from_blender(blscene, blmat, false, false, 0), ¤t_gpu_attribs); else memset(¤t_gpu_attribs, 0, sizeof(current_gpu_attribs)); // DM draw can mess up blending mode, restore at the end |