gpu: Optimize box-shadow shader
Like in the border shader, don't draw the (potentially large for the window's shadow) inside part that is transparent.
This commit is contained in:
@@ -37,6 +37,24 @@ gsk_gpu_box_shadow_op_print (GskGpuOp *op,
|
||||
gsk_gpu_print_newline (string);
|
||||
}
|
||||
|
||||
#ifdef GDK_RENDERING_VULKAN
|
||||
static GskGpuOp *
|
||||
gsk_gpu_box_shadow_op_vk_command (GskGpuOp *op,
|
||||
GskGpuFrame *frame,
|
||||
GskVulkanCommandState *state)
|
||||
{
|
||||
return gsk_gpu_shader_op_vk_command_n (op, frame, state, 8);
|
||||
}
|
||||
#endif
|
||||
|
||||
static GskGpuOp *
|
||||
gsk_gpu_box_shadow_op_gl_command (GskGpuOp *op,
|
||||
GskGpuFrame *frame,
|
||||
GskGLCommandState *state)
|
||||
{
|
||||
return gsk_gpu_shader_op_gl_command_n (op, frame, state, 8);
|
||||
}
|
||||
|
||||
static const GskGpuShaderOpClass GSK_GPU_BOX_SHADOW_OP_CLASS = {
|
||||
{
|
||||
GSK_GPU_OP_SIZE (GskGpuBoxShadowOp),
|
||||
@@ -44,9 +62,9 @@ static const GskGpuShaderOpClass GSK_GPU_BOX_SHADOW_OP_CLASS = {
|
||||
gsk_gpu_shader_op_finish,
|
||||
gsk_gpu_box_shadow_op_print,
|
||||
#ifdef GDK_RENDERING_VULKAN
|
||||
gsk_gpu_shader_op_vk_command,
|
||||
gsk_gpu_box_shadow_op_vk_command,
|
||||
#endif
|
||||
gsk_gpu_shader_op_gl_command
|
||||
gsk_gpu_box_shadow_op_gl_command
|
||||
},
|
||||
"gskgpuboxshadow",
|
||||
sizeof (GskGpuBoxshadowInstance),
|
||||
|
||||
@@ -19,20 +19,37 @@ IN(6) float in_shadow_spread;
|
||||
IN(7) float in_blur_radius;
|
||||
IN(8) uint in_inset;
|
||||
|
||||
#define GAUSSIAN_SCALE_FACTOR ((3.0 * sqrt(2.0 * PI) / 4.0))
|
||||
|
||||
void
|
||||
run (out vec2 pos)
|
||||
{
|
||||
Rect bounds = rect_from_gsk (in_bounds);
|
||||
RoundedRect outside = rounded_rect_from_rect (bounds);
|
||||
RoundedRect outline = rounded_rect_from_gsk (in_outline);
|
||||
vec2 spread = GSK_GLOBAL_SCALE * in_shadow_spread;
|
||||
|
||||
pos = rect_get_position (rect_from_gsk (in_bounds));
|
||||
_clip_outline = outline;
|
||||
|
||||
RoundedRect inside;
|
||||
if (in_inset == 0u)
|
||||
{
|
||||
inside = outline;
|
||||
spread = -spread;
|
||||
outline = rounded_rect_shrink (outline, spread.yxyx);
|
||||
rounded_rect_offset (outline, GSK_GLOBAL_SCALE * in_shadow_offset);
|
||||
}
|
||||
else
|
||||
{
|
||||
outline = rounded_rect_shrink (outline, spread.yxyx);
|
||||
rounded_rect_offset (outline, GSK_GLOBAL_SCALE * in_shadow_offset);
|
||||
inside = outline;
|
||||
inside = rounded_rect_shrink (inside, (in_blur_radius * GAUSSIAN_SCALE_FACTOR * GSK_GLOBAL_SCALE).yxyx);
|
||||
}
|
||||
|
||||
pos = border_get_position (outside, inside);
|
||||
|
||||
_pos = pos;
|
||||
_clip_outline = outline;
|
||||
vec2 spread = GSK_GLOBAL_SCALE * in_shadow_spread;
|
||||
if (in_inset == 0u)
|
||||
spread = -spread;
|
||||
outline = rounded_rect_shrink (outline, spread.yxyx);
|
||||
rounded_rect_offset (outline, GSK_GLOBAL_SCALE * in_shadow_offset);
|
||||
_shadow_outline = outline;
|
||||
_color = in_color;
|
||||
_sigma = GSK_GLOBAL_SCALE * 0.5 * in_blur_radius;
|
||||
|
||||
@@ -11,6 +11,12 @@ struct RoundedRect
|
||||
vec4 corner_heights;
|
||||
};
|
||||
|
||||
RoundedRect
|
||||
rounded_rect_from_rect (Rect r)
|
||||
{
|
||||
return RoundedRect (r.bounds, vec4 (0.0), vec4 (0.0));
|
||||
}
|
||||
|
||||
RoundedRect
|
||||
rounded_rect_from_gsk (mat3x4 gsk_rounded_rect)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user