diff options
Diffstat (limited to 'source')
13 files changed, 320 insertions, 182 deletions
diff --git a/source/blender/draw/CMakeLists.txt b/source/blender/draw/CMakeLists.txt index 9036ca9cd50..63405e5fa75 100644 --- a/source/blender/draw/CMakeLists.txt +++ b/source/blender/draw/CMakeLists.txt @@ -499,7 +499,10 @@ set(GLSL_SRC engines/overlay/shaders/motion_path_point_vert.glsl engines/overlay/shaders/outline_detect_frag.glsl engines/overlay/shaders/outline_prepass_frag.glsl + engines/overlay/shaders/outline_prepass_gpencil_frag.glsl engines/overlay/shaders/outline_prepass_geom.glsl + engines/overlay/shaders/outline_prepass_gpencil_vert.glsl + engines/overlay/shaders/outline_prepass_pointcloud_vert.glsl engines/overlay/shaders/outline_prepass_vert.glsl engines/overlay/shaders/paint_face_vert.glsl engines/overlay/shaders/paint_point_vert.glsl diff --git a/source/blender/draw/engines/overlay/overlay_outline.c b/source/blender/draw/engines/overlay/overlay_outline.c index 47d9d19cad2..eea9a1a1bef 100644 --- a/source/blender/draw/engines/overlay/overlay_outline.c +++ b/source/blender/draw/engines/overlay/overlay_outline.c @@ -132,7 +132,7 @@ void OVERLAY_outline_cache_init(OVERLAY_Data *vedata) pd->outlines_gpencil_grp = grp = DRW_shgroup_create(sh_gpencil, psl->outlines_prepass_ps); DRW_shgroup_uniform_bool_copy(grp, "isTransform", (G.moving & G_TRANSFORM_OBJ) != 0); - DRW_shgroup_uniform_float_copy(grp, "strokeIndexOffset", 0.0); + DRW_shgroup_uniform_float_copy(grp, "gpStrokeIndexOffset", 0.0); } /* outlines_prepass_ps is still needed for selection of probes. */ @@ -186,12 +186,10 @@ static void gpencil_layer_cache_populate(bGPDlayer *gpl, float thickness_scale = (is_screenspace) ? -1.0f : (gpd->pixfactor / 2000.0f); DRWShadingGroup *grp = iter->stroke_grp = DRW_shgroup_create_sub(iter->stroke_grp); - DRW_shgroup_uniform_bool_copy(grp, "strokeOrder3d", is_stroke_order_3d); - DRW_shgroup_uniform_vec2_copy(grp, "sizeViewportInv", DRW_viewport_invert_size_get()); - DRW_shgroup_uniform_vec2_copy(grp, "sizeViewport", DRW_viewport_size_get()); - DRW_shgroup_uniform_float_copy(grp, "thicknessScale", object_scale); - DRW_shgroup_uniform_float_copy(grp, "thicknessOffset", (float)gpl->line_change); - DRW_shgroup_uniform_float_copy(grp, "thicknessWorldScale", thickness_scale); + DRW_shgroup_uniform_bool_copy(grp, "gpStrokeOrder3d", is_stroke_order_3d); + DRW_shgroup_uniform_float_copy(grp, "gpThicknessScale", object_scale); + DRW_shgroup_uniform_float_copy(grp, "gpThicknessOffset", (float)gpl->line_change); + DRW_shgroup_uniform_float_copy(grp, "gpThicknessWorldScale", thickness_scale); DRW_shgroup_uniform_vec4_copy(grp, "gpDepthPlane", iter->plane); } diff --git a/source/blender/draw/engines/overlay/overlay_shader.c b/source/blender/draw/engines/overlay/overlay_shader.c index 0288dc12be8..c04a3218461 100644 --- a/source/blender/draw/engines/overlay/overlay_shader.c +++ b/source/blender/draw/engines/overlay/overlay_shader.c @@ -829,33 +829,16 @@ GPUShader *OVERLAY_shader_motion_path_vert(void) GPUShader *OVERLAY_shader_outline_prepass(bool use_wire) { const DRWContextState *draw_ctx = DRW_context_state_get(); - const GPUShaderConfigData *sh_cfg = &GPU_shader_cfg_data[draw_ctx->sh_cfg]; OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg]; if (use_wire && !sh_data->outline_prepass_wire) { - sh_data->outline_prepass_wire = GPU_shader_create_from_arrays({ - .vert = (const char *[]){sh_cfg->lib, - datatoc_common_view_lib_glsl, - datatoc_gpu_shader_common_obinfos_lib_glsl, - datatoc_outline_prepass_vert_glsl, - NULL}, - .geom = (const char *[]){sh_cfg->lib, - datatoc_common_view_lib_glsl, - datatoc_outline_prepass_geom_glsl, - NULL}, - .frag = (const char *[]){datatoc_outline_prepass_frag_glsl, NULL}, - .defs = (const char *[]){sh_cfg->def, "#define USE_GEOM\n", NULL}, - }); + sh_data->outline_prepass_wire = GPU_shader_create_from_info_name( + draw_ctx->sh_cfg ? "overlay_outline_prepass_wire_clipped" : + "overlay_outline_prepass_wire"); } else if (!sh_data->outline_prepass) { - sh_data->outline_prepass = GPU_shader_create_from_arrays({ - .vert = (const char *[]){sh_cfg->lib, - datatoc_common_view_lib_glsl, - datatoc_gpu_shader_common_obinfos_lib_glsl, - datatoc_outline_prepass_vert_glsl, - NULL}, - .frag = (const char *[]){datatoc_outline_prepass_frag_glsl, NULL}, - .defs = (const char *[]){sh_cfg->def, NULL}, - }); + sh_data->outline_prepass = GPU_shader_create_from_info_name( + draw_ctx->sh_cfg ? "overlay_outline_prepass_mesh_clipped" : + "overlay_outline_prepass_mesh"); } return use_wire ? sh_data->outline_prepass_wire : sh_data->outline_prepass; } @@ -863,25 +846,11 @@ GPUShader *OVERLAY_shader_outline_prepass(bool use_wire) GPUShader *OVERLAY_shader_outline_prepass_gpencil(void) { const DRWContextState *draw_ctx = DRW_context_state_get(); - const GPUShaderConfigData *sh_cfg = &GPU_shader_cfg_data[draw_ctx->sh_cfg]; OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg]; if (!sh_data->outline_prepass_gpencil) { - sh_data->outline_prepass_gpencil = GPU_shader_create_from_arrays({ - .vert = (const char *[]){sh_cfg->lib, - datatoc_common_view_lib_glsl, - datatoc_gpencil_common_lib_glsl, - datatoc_gpu_shader_common_obinfos_lib_glsl, - datatoc_outline_prepass_vert_glsl, - NULL}, - .frag = (const char *[]){datatoc_common_view_lib_glsl, - datatoc_gpencil_common_lib_glsl, - datatoc_outline_prepass_frag_glsl, - NULL}, - .defs = (const char *[]){sh_cfg->def, - "#define USE_GPENCIL\n", - "#define UNIFORM_RESOURCE_ID\n", - NULL}, - }); + sh_data->outline_prepass_gpencil = GPU_shader_create_from_info_name( + draw_ctx->sh_cfg ? "overlay_outline_prepass_gpencil_clipped" : + "overlay_outline_prepass_gpencil"); } return sh_data->outline_prepass_gpencil; } @@ -889,26 +858,11 @@ GPUShader *OVERLAY_shader_outline_prepass_gpencil(void) GPUShader *OVERLAY_shader_outline_prepass_pointcloud(void) { const DRWContextState *draw_ctx = DRW_context_state_get(); - const GPUShaderConfigData *sh_cfg = &GPU_shader_cfg_data[draw_ctx->sh_cfg]; OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg]; if (!sh_data->outline_prepass_pointcloud) { - sh_data->outline_prepass_pointcloud = GPU_shader_create_from_arrays({ - .vert = (const char *[]){sh_cfg->lib, - datatoc_common_view_lib_glsl, - datatoc_common_pointcloud_lib_glsl, - datatoc_gpu_shader_common_obinfos_lib_glsl, - datatoc_outline_prepass_vert_glsl, - NULL}, - .frag = (const char *[]){datatoc_common_view_lib_glsl, - datatoc_gpencil_common_lib_glsl, - datatoc_outline_prepass_frag_glsl, - NULL}, - .defs = (const char *[]){sh_cfg->def, - "#define POINTCLOUD\n", - "#define INSTANCED_ATTR\n", - "#define UNIFORM_RESOURCE_ID\n", - NULL}, - }); + sh_data->outline_prepass_pointcloud = GPU_shader_create_from_info_name( + draw_ctx->sh_cfg ? "overlay_outline_prepass_pointcloud_clipped" : + "overlay_outline_prepass_pointcloud"); } return sh_data->outline_prepass_pointcloud; } @@ -917,13 +871,7 @@ GPUShader *OVERLAY_shader_outline_detect(void) { OVERLAY_Shaders *sh_data = &e_data.sh_data[0]; if (!sh_data->outline_detect) { - sh_data->outline_detect = GPU_shader_create_from_arrays({ - .vert = (const char *[]){datatoc_common_fullscreen_vert_glsl, NULL}, - .frag = (const char *[]){datatoc_common_view_lib_glsl, - datatoc_common_globals_lib_glsl, - datatoc_outline_detect_frag_glsl, - NULL}, - }); + sh_data->outline_detect = GPU_shader_create_from_info_name("overlay_outline_detect"); } return sh_data->outline_detect; } diff --git a/source/blender/draw/engines/overlay/shaders/infos/outline_info.hh b/source/blender/draw/engines/overlay/shaders/infos/outline_info.hh new file mode 100644 index 00000000000..dbc08384680 --- /dev/null +++ b/source/blender/draw/engines/overlay/shaders/infos/outline_info.hh @@ -0,0 +1,100 @@ +/* SPDX-License-Identifier: GPL-2.0-or-later */ + +#include "gpu_shader_create_info.hh" + +/* -------------------------------------------------------------------- */ +/** \name Outline Prepass + * \{ */ + +GPU_SHADER_INTERFACE_INFO(overlay_outline_prepass_iface, "interp").flat(Type::UINT, "ob_id"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass) + .push_constant(Type::BOOL, "isTransform") + .vertex_out(overlay_outline_prepass_iface) + /* Using uint because 16bit uint can contain more ids than int. */ + .fragment_out(0, Type::UINT, "out_object_id") + .fragment_source("outline_prepass_frag.glsl") + .additional_info("draw_resource_handle"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_mesh) + .do_static_compilation(true) + .vertex_in(0, Type::VEC3, "pos") + .vertex_source("outline_prepass_vert.glsl") + .additional_info("draw_mesh", "overlay_outline_prepass") + .additional_info("draw_object_infos"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_mesh_clipped) + .do_static_compilation(true) + .additional_info("overlay_outline_prepass_mesh", "drw_clipped"); + +GPU_SHADER_INTERFACE_INFO(overlay_outline_prepass_wire_iface, "vert").flat(Type::VEC3, "pos"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_wire) + .do_static_compilation(true) + .define("USE_GEOM") + .vertex_in(0, Type::VEC3, "pos") + .vertex_out(overlay_outline_prepass_wire_iface) + .geometry_layout(PrimitiveIn::LINES_ADJACENCY, PrimitiveOut::LINE_STRIP, 2) + .geometry_out(overlay_outline_prepass_iface) + .vertex_source("outline_prepass_vert.glsl") + .additional_info("draw_mesh", "overlay_outline_prepass") + .additional_info("draw_object_infos"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_wire_clipped) + .do_static_compilation(true) + .additional_info("overlay_outline_prepass_wire", "drw_clipped"); + +GPU_SHADER_INTERFACE_INFO(overlay_outline_prepass_gpencil_iface, "gp_interp") + .no_perspective(Type::VEC2, "thickness") + .no_perspective(Type::FLOAT, "hardness") + .flat(Type::VEC2, "aspect") + .flat(Type::VEC4, "sspos"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_gpencil) + .do_static_compilation(true) + .push_constant(Type::BOOL, "isTransform") + .vertex_out(overlay_outline_prepass_iface) + .vertex_out(overlay_outline_prepass_gpencil_iface) + .vertex_source("outline_prepass_gpencil_vert.glsl") + .push_constant(Type::BOOL, "gpStrokeOrder3d") /* TODO(fclem): Move to a GPencil object UBO. */ + .push_constant(Type::VEC4, "gpDepthPlane") /* TODO(fclem): Move to a GPencil object UBO. */ + /* Using uint because 16bit uint can contain more ids than int. */ + .fragment_out(0, Type::UINT, "out_object_id") + .fragment_source("outline_prepass_gpencil_frag.glsl") + .additional_info("draw_gpencil", "draw_resource_handle"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_gpencil_clipped) + .do_static_compilation(true) + .additional_info("overlay_outline_prepass_gpencil", "drw_clipped"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_pointcloud) + .do_static_compilation(true) + .vertex_source("outline_prepass_pointcloud_vert.glsl") + .additional_info("draw_pointcloud", "overlay_outline_prepass") + .additional_info("draw_object_infos"); + +GPU_SHADER_CREATE_INFO(overlay_outline_prepass_pointcloud_clipped) + .do_static_compilation(true) + .additional_info("overlay_outline_prepass_pointcloud", "drw_clipped"); + +/** \} */ + +/* -------------------------------------------------------------------- */ +/** \name Outline Rendering + * \{ */ + +GPU_SHADER_CREATE_INFO(overlay_outline_detect) + .do_static_compilation(true) + .push_constant(Type::FLOAT, "alphaOcclu") + .push_constant(Type::BOOL, "isXrayWires") + .push_constant(Type::BOOL, "doAntiAliasing") + .push_constant(Type::BOOL, "doThickOutlines") + .sampler(0, ImageType::UINT_2D, "outlineId") + .sampler(1, ImageType::DEPTH_2D, "outlineDepth") + .sampler(2, ImageType::DEPTH_2D, "sceneDepth") + .fragment_out(0, Type::VEC4, "fragColor") + .fragment_out(1, Type::VEC4, "lineOutput") + .fragment_source("outline_detect_frag.glsl") + .additional_info("draw_fullscreen", "draw_view", "draw_globals"); + +/** \} */ diff --git a/source/blender/draw/engines/overlay/shaders/outline_detect_frag.glsl b/source/blender/draw/engines/overlay/shaders/outline_detect_frag.glsl index ba0a4c0da81..c33bb474d96 100644 --- a/source/blender/draw/engines/overlay/shaders/outline_detect_frag.glsl +++ b/source/blender/draw/engines/overlay/shaders/outline_detect_frag.glsl @@ -1,16 +1,5 @@ -uniform float alphaOcclu; -uniform bool isXrayWires; -uniform bool doAntiAliasing; -uniform bool doThickOutlines; -uniform usampler2D outlineId; -uniform sampler2D outlineDepth; -uniform sampler2D sceneDepth; - -in vec4 uvcoordsvar; - -layout(location = 0) out vec4 fragColor; -layout(location = 1) out vec4 lineOutput; +#pragma BLENDER_REQUIRE(common_view_lib.glsl) #define XPOS (1 << 0) #define XNEG (1 << 1) @@ -47,7 +36,7 @@ bvec4 gather_edges(vec2 uv, uint ref) #ifdef GPU_ARB_texture_gather ids = textureGather(outlineId, uv); #else - vec3 ofs = vec3(0.5, 0.5, -0.5) * sizeViewportInv.xyy; + vec3 ofs = vec3(0.5, 0.5, -0.5) * drw_view.viewport_size_inversey; ids.x = textureLod(outlineId, uv - ofs.xz, 0.0).r; ids.y = textureLod(outlineId, uv + ofs.xy, 0.0).r; ids.z = textureLod(outlineId, uv + ofs.xz, 0.0).r; @@ -172,8 +161,8 @@ void main() uint ref = textureLod(outlineId, uvcoordsvar.xy, 0.0).r; uint ref_col = ref; - vec2 uvs = gl_FragCoord.xy * sizeViewportInv.xy; - vec3 ofs = vec3(1.0, 1.0, 0.0) * sizeViewportInv.xyy; + vec2 uvs = gl_FragCoord.xy * drw_view.viewport_size_inverse; + vec3 ofs = vec3(drw_view.viewport_size_inverse.xy, 0.0); vec2 depth_uv = uvs; @@ -280,13 +269,13 @@ void main() switch (edge_case) { /* Straight lines. */ case YPOS: - extra_edges = gather_edges(uvs + sizeViewportInv.xy * vec2(2.5, 0.5), ref); - extra_edges2 = gather_edges(uvs + sizeViewportInv.xy * vec2(-2.5, 0.5), ref); + extra_edges = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(2.5, 0.5), ref); + extra_edges2 = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(-2.5, 0.5), ref); straight_line_dir(extra_edges, extra_edges2, line_start, line_end); break; case YNEG: - extra_edges = gather_edges(uvs + sizeViewportInv.xy * vec2(-2.5, -0.5), ref); - extra_edges2 = gather_edges(uvs + sizeViewportInv.xy * vec2(2.5, -0.5), ref); + extra_edges = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(-2.5, -0.5), ref); + extra_edges2 = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(2.5, -0.5), ref); extra_edges = rotate_180(extra_edges); extra_edges2 = rotate_180(extra_edges2); straight_line_dir(extra_edges, extra_edges2, line_start, line_end); @@ -294,8 +283,8 @@ void main() line_end = rotate_180(line_end); break; case XPOS: - extra_edges = gather_edges(uvs + sizeViewportInv.xy * vec2(0.5, 2.5), ref); - extra_edges2 = gather_edges(uvs + sizeViewportInv.xy * vec2(0.5, -2.5), ref); + extra_edges = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(0.5, 2.5), ref); + extra_edges2 = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(0.5, -2.5), ref); extra_edges = rotate_90(extra_edges); extra_edges2 = rotate_90(extra_edges2); straight_line_dir(extra_edges, extra_edges2, line_start, line_end); @@ -303,8 +292,8 @@ void main() line_end = rotate_90(line_end); break; case XNEG: - extra_edges = gather_edges(uvs + sizeViewportInv.xy * vec2(-0.5, 2.5), ref); - extra_edges2 = gather_edges(uvs + sizeViewportInv.xy * vec2(-0.5, -2.5), ref); + extra_edges = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(-0.5, 2.5), ref); + extra_edges2 = gather_edges(uvs + drw_view.viewport_size_inverse * vec2(-0.5, -2.5), ref); extra_edges = rotate_270(extra_edges); extra_edges2 = rotate_270(extra_edges2); straight_line_dir(extra_edges, extra_edges2, line_start, line_end); diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_frag.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_frag.glsl index 85f79e94263..d1abd74a7b3 100644 --- a/source/blender/draw/engines/overlay/shaders/outline_prepass_frag.glsl +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_frag.glsl @@ -1,46 +1,5 @@ -uniform vec4 gpDepthPlane; - -flat in uint objectId; - -/* using uint because 16bit uint can contain more ids than int. */ -out uint outId; - -vec3 ray_plane_intersection(vec3 ray_ori, vec3 ray_dir, vec4 plane) -{ - float d = dot(plane.xyz, ray_dir); - vec3 plane_co = plane.xyz * (-plane.w / dot(plane.xyz, plane.xyz)); - vec3 h = ray_ori - plane_co; - float lambda = -dot(plane.xyz, h) / ((abs(d) < 1e-8) ? 1e-8 : d); - return ray_ori + ray_dir * lambda; -} - void main() { -#ifdef USE_GPENCIL - if (stroke_round_cap_mask(strokePt1, strokePt2, strokeAspect, strokeThickness, strokeHardeness) < - 0.001) { - discard; - } - - if (depth != -1.0) { - /* Stroke order 2D. */ - bool is_persp = ProjectionMatrix[3][3] == 0.0; - vec2 uvs = vec2(gl_FragCoord.xy) * sizeViewportInv; - vec3 pos_ndc = vec3(uvs, gl_FragCoord.z) * 2.0 - 1.0; - vec4 pos_world = ViewProjectionMatrixInverse * vec4(pos_ndc, 1.0); - vec3 pos = pos_world.xyz / pos_world.w; - - vec3 ray_ori = pos; - vec3 ray_dir = (is_persp) ? (ViewMatrixInverse[3].xyz - pos) : ViewMatrixInverse[2].xyz; - vec3 isect = ray_plane_intersection(ray_ori, ray_dir, gpDepthPlane); - vec4 ndc = point_world_to_ndc(isect); - gl_FragDepth = (ndc.z / ndc.w) * 0.5 + 0.5; - } - else { - gl_FragDepth = gl_FragCoord.z; - } -#endif - - outId = uint(objectId); + out_object_id = interp.ob_id; } diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_geom.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_geom.glsl index b89cd821b37..0c7fafbf6b0 100644 --- a/source/blender/draw/engines/overlay/shaders/outline_prepass_geom.glsl +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_geom.glsl @@ -1,16 +1,16 @@ -layout(lines_adjacency) in; -layout(line_strip, max_vertices = 2) out; +#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl) +#pragma BLENDER_REQUIRE(common_view_lib.glsl) -in vec3 vPos[]; -in uint objectId_g[]; +in vec3 vert[]; +.pos -flat out uint objectId; + flat out uint objectId; void vert_from_gl_in(int v) { gl_Position = gl_in[v].gl_Position; - objectId = objectId_g[v]; + interp_out.ob_id = interp_in[v].ob_id; #ifdef USE_WORLD_CLIP_PLANES world_clip_planes_set_clip_distance(gl_in[v].gl_ClipDistance); #endif @@ -20,11 +20,11 @@ void main() { bool is_persp = (ProjectionMatrix[3][3] == 0.0); - vec3 view_vec = (is_persp) ? normalize(vPos[1]) : vec3(0.0, 0.0, -1.0); + vec3 view_vec = (is_persp) ? normalize(vert[1].pos) : vec3(0.0, 0.0, -1.0); - vec3 v10 = vPos[0] - vPos[1]; - vec3 v12 = vPos[2] - vPos[1]; - vec3 v13 = vPos[3] - vPos[1]; + vec3 v10 = vert[0].pos - vert[1].pos; + vec3 v12 = vert[2].pos - vert[1].pos; + vec3 v13 = vert[3].pos - vert[1].pos; vec3 n0 = cross(v12, v10); vec3 n3 = cross(v13, v12); diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_frag.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_frag.glsl new file mode 100644 index 00000000000..b6d5cd96c12 --- /dev/null +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_frag.glsl @@ -0,0 +1,42 @@ + +#pragma BLENDER_REQUIRE(common_gpencil_lib.glsl) + +vec3 ray_plane_intersection(vec3 ray_ori, vec3 ray_dir, vec4 plane) +{ + float d = dot(plane.xyz, ray_dir); + vec3 plane_co = plane.xyz * (-plane.w / dot(plane.xyz, plane.xyz)); + vec3 h = ray_ori - plane_co; + float lambda = -dot(plane.xyz, h) / ((abs(d) < 1e-8) ? 1e-8 : d); + return ray_ori + ray_dir * lambda; +} + +void main() +{ + if (gpencil_stroke_round_cap_mask(gp_interp.sspos.xy, + gp_interp.sspos.zw, + gp_interp.aspect, + gp_interp.thickness.x, + gp_interp.hardness) < 0.001) { + discard; + } + + if (!gpStrokeOrder3d) { + /* Stroke order 2D. Project to gpDepthPlane. */ + bool is_persp = ProjectionMatrix[3][3] == 0.0; + vec2 uvs = vec2(gl_FragCoord.xy) * drw_view.viewport_size_inverse; + vec3 pos_ndc = vec3(uvs, gl_FragCoord.z) * 2.0 - 1.0; + vec4 pos_world = ViewProjectionMatrixInverse * vec4(pos_ndc, 1.0); + vec3 pos = pos_world.xyz / pos_world.w; + + vec3 ray_ori = pos; + vec3 ray_dir = (is_persp) ? (ViewMatrixInverse[3].xyz - pos) : ViewMatrixInverse[2].xyz; + vec3 isect = ray_plane_intersection(ray_ori, ray_dir, gpDepthPlane); + vec4 ndc = point_world_to_ndc(isect); + gl_FragDepth = (ndc.z / ndc.w) * 0.5 + 0.5; + } + else { + gl_FragDepth = gl_FragCoord.z; + } + + out_object_id = interp.ob_id; +} diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_vert.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_vert.glsl new file mode 100644 index 00000000000..4b1470e5723 --- /dev/null +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_gpencil_vert.glsl @@ -0,0 +1,74 @@ + +#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl) +#pragma BLENDER_REQUIRE(common_view_lib.glsl) +#pragma BLENDER_REQUIRE(common_gpencil_lib.glsl) + +uint outline_colorid_get(void) +{ + int flag = int(abs(ObjectInfo.w)); + bool is_active = (flag & DRW_BASE_ACTIVE) != 0; + + if (isTransform) { + return 0u; /* colorTransform */ + } + else if (is_active) { + return 3u; /* colorActive */ + } + else { + return 1u; /* colorSelect */ + } + + return 0u; +} + +/* Replace top 2 bits (of the 16bit output) by outlineId. + * This leaves 16K different IDs to create outlines between objects. + * SHIFT = (32 - (16 - 2)) */ +#define SHIFT 18u + +void main() +{ + vec3 world_pos; + vec3 unused_N; + vec4 unused_color; + float unused_strength; + vec2 unused_uv; + + gl_Position = gpencil_vertex(ma, + ma1, + ma2, + ma3, + pos, + pos1, + pos2, + pos3, + uv1, + uv2, + col1, + col2, + fcol1, + vec4(drw_view.viewport_size, drw_view.viewport_size_inverse), + world_pos, + unused_N, + unused_color, + unused_strength, + unused_uv, + gp_interp.sspos, + gp_interp.aspect, + gp_interp.thickness, + gp_interp.hardness); + + /* Small bias to always be on top of the geom. */ + gl_Position.z -= 1e-3; + + /* ID 0 is nothing (background) */ + interp.ob_id = uint(resource_handle + 1); + + /* Should be 2 bits only [0..3]. */ + uint outline_id = outline_colorid_get(); + + /* Combine for 16bit uint target. */ + interp.ob_id = (outline_id << 14u) | ((interp.ob_id << SHIFT) >> SHIFT); + + view_clipping_distances(world_pos); +} diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_pointcloud_vert.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_pointcloud_vert.glsl new file mode 100644 index 00000000000..371ff628c59 --- /dev/null +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_pointcloud_vert.glsl @@ -0,0 +1,48 @@ + +#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl) +#pragma BLENDER_REQUIRE(common_view_lib.glsl) +#pragma BLENDER_REQUIRE(common_pointcloud_lib.glsl) + +uint outline_colorid_get(void) +{ + int flag = int(abs(ObjectInfo.w)); + bool is_active = (flag & DRW_BASE_ACTIVE) != 0; + + if (isTransform) { + return 0u; /* colorTransform */ + } + else if (is_active) { + return 3u; /* colorActive */ + } + else { + return 1u; /* colorSelect */ + } + + return 0u; +} + +/* Replace top 2 bits (of the 16bit output) by outlineId. + * This leaves 16K different IDs to create outlines between objects. + * SHIFT = (32 - (16 - 2)) */ +#define SHIFT 18u + +void main() +{ + vec3 world_pos = pointcloud_get_pos(); + + gl_Position = point_world_to_ndc(world_pos); + + /* Small bias to always be on top of the geom. */ + gl_Position.z -= 1e-3; + + /* ID 0 is nothing (background) */ + interp.ob_id = uint(resource_handle + 1); + + /* Should be 2 bits only [0..3]. */ + uint outline_id = outline_colorid_get(); + + /* Combine for 16bit uint target. */ + interp.ob_id = (outline_id << 14u) | ((interp.ob_id << SHIFT) >> SHIFT); + + view_clipping_distances(world_pos); +} diff --git a/source/blender/draw/engines/overlay/shaders/outline_prepass_vert.glsl b/source/blender/draw/engines/overlay/shaders/outline_prepass_vert.glsl index 701760dac18..1d0b08f51b2 100644 --- a/source/blender/draw/engines/overlay/shaders/outline_prepass_vert.glsl +++ b/source/blender/draw/engines/overlay/shaders/outline_prepass_vert.glsl @@ -1,18 +1,6 @@ -uniform bool isTransform; - -#if !defined(USE_GPENCIL) && !defined(POINTCLOUD) -in vec3 pos; -#endif - -#ifdef USE_GEOM -out vec3 vPos; -out uint objectId_g; -# define objectId objectId_g -#else - -flat out uint objectId; -#endif +#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl) +#pragma BLENDER_REQUIRE(common_view_lib.glsl) uint outline_colorid_get(void) { @@ -39,36 +27,24 @@ uint outline_colorid_get(void) void main() { -#ifdef USE_GPENCIL - gpencil_vertex(); -# ifdef USE_WORLD_CLIP_PLANES - vec3 world_pos = point_object_to_world(pos1.xyz); -# endif - -#else -# ifdef POINTCLOUD - vec3 world_pos = pointcloud_get_pos(); -# else vec3 world_pos = point_object_to_world(pos); -# endif + gl_Position = point_world_to_ndc(world_pos); -# ifdef USE_GEOM - vPos = point_world_to_view(world_pos); -# endif +#ifdef USE_GEOM + vert.pos = point_world_to_view(world_pos); #endif + /* Small bias to always be on top of the geom. */ gl_Position.z -= 1e-3; /* ID 0 is nothing (background) */ - objectId = uint(resource_handle + 1); + interp.ob_id = uint(resource_handle + 1); /* Should be 2 bits only [0..3]. */ uint outline_id = outline_colorid_get(); /* Combine for 16bit uint target. */ - objectId = (outline_id << 14u) | ((objectId << SHIFT) >> SHIFT); + interp.ob_id = (outline_id << 14u) | ((interp.ob_id << SHIFT) >> SHIFT); -#ifdef USE_WORLD_CLIP_PLANES - world_clip_planes_calc_clip_distance(world_pos); -#endif + view_clipping_distances(world_pos); } diff --git a/source/blender/draw/intern/shaders/common_gpencil_lib.glsl b/source/blender/draw/intern/shaders/common_gpencil_lib.glsl index 0610bc4e57d..d63b9917973 100644 --- a/source/blender/draw/intern/shaders/common_gpencil_lib.glsl +++ b/source/blender/draw/intern/shaders/common_gpencil_lib.glsl @@ -393,7 +393,7 @@ vec4 gpencil_vertex(ivec4 ma, col2, fcol1, viewport_size, - GP_STROKE_ALIGNMENT_OBJECT, + 0, vec2(1.0, 0.0), out_P, out_N, diff --git a/source/blender/gpu/CMakeLists.txt b/source/blender/gpu/CMakeLists.txt index f03de5288d6..34690e01e43 100644 --- a/source/blender/gpu/CMakeLists.txt +++ b/source/blender/gpu/CMakeLists.txt @@ -445,9 +445,10 @@ set(SRC_SHADER_CREATE_INFOS ../draw/engines/gpencil/shaders/infos/gpencil_vfx_info.hh ../draw/engines/overlay/shaders/infos/antialiasing_info.hh ../draw/engines/overlay/shaders/infos/armature_info.hh + ../draw/engines/overlay/shaders/infos/edit_mode_info.hh ../draw/engines/overlay/shaders/infos/extra_info.hh ../draw/engines/overlay/shaders/infos/grid_info.hh - ../draw/engines/overlay/shaders/infos/edit_mode_info.hh + ../draw/engines/overlay/shaders/infos/outline_info.hh ../draw/engines/overlay/shaders/infos/paint_info.hh ../draw/engines/overlay/shaders/infos/volume_info.hh ../draw/engines/select/shaders/infos/select_id_info.hh |