From ffe1b798816c3dfbe040ae14fe4c0b61076a477c Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 12 Jan 2022 13:34:37 +0000 Subject: [PATCH 1/6] backend: add new property: BORDER_COLOR Signed-off-by: Yuxuan Shui --- src/backend/backend.c | 9 +++++++++ src/backend/backend.h | 3 +++ src/backend/backend_common.c | 1 + src/backend/backend_common.h | 1 + 4 files changed, 14 insertions(+) diff --git a/src/backend/backend.c b/src/backend/backend.c index bbc8bd6d..36c5fec1 100644 --- a/src/backend/backend.c +++ b/src/backend/backend.c @@ -342,6 +342,15 @@ void paint_all_new(session_t *ps, struct managed_win *t, bool ignore_damage) { ps->backend_data->ops->set_image_property( ps->backend_data, IMAGE_PROPERTY_CORNER_RADIUS, w->win_image, (double[]){w->corner_radius}); + if (w->corner_radius) { + struct color border_color; + ps->backend_data->ops->read_pixel( + ps->backend_data, w->win_image, 0, w->heightb, + &border_color); + ps->backend_data->ops->set_image_property( + ps->backend_data, IMAGE_PROPERTY_BORDER_COLOR, + w->win_image, &border_color); + } } if (w->opacity * MAX_ALPHA < 1) { diff --git a/src/backend/backend.h b/src/backend/backend.h index 613073a5..721b1974 100644 --- a/src/backend/backend.h +++ b/src/backend/backend.h @@ -58,6 +58,9 @@ enum image_properties { // Gives the image a rounded corner. // 1 double, default: 0 IMAGE_PROPERTY_CORNER_RADIUS, + // Border color + // 1 struct color, default: black + IMAGE_PROPERTY_BORDER_COLOR, }; enum image_operations { diff --git a/src/backend/backend_common.c b/src/backend/backend_common.c index b0145efb..d5dd7057 100644 --- a/src/backend/backend_common.c +++ b/src/backend/backend_common.c @@ -451,6 +451,7 @@ bool default_set_image_property(backend_t *base attr_unused, enum image_properti break; case IMAGE_PROPERTY_CORNER_RADIUS: tex->corner_radius = dargs[0]; break; case IMAGE_PROPERTY_MAX_BRIGHTNESS: tex->max_brightness = dargs[0]; break; + case IMAGE_PROPERTY_BORDER_COLOR: tex->border_color = *(struct color *)arg; break; } return true; diff --git a/src/backend/backend_common.h b/src/backend/backend_common.h index 1aaf1337..6d967b56 100644 --- a/src/backend/backend_common.h +++ b/src/backend/backend_common.h @@ -41,6 +41,7 @@ struct backend_image { // Effective size of the image int ewidth, eheight; bool color_inverted; + struct color border_color; }; bool build_shadow(xcb_connection_t *, xcb_drawable_t, double opacity, int width, From b7df820ff246e4202b1233ffe74e7decfb2653e4 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Thu, 13 Jan 2022 11:31:31 +0000 Subject: [PATCH 2/6] backend: add new property: BORDER_WIDTH Signed-off-by: Yuxuan Shui --- src/backend/backend.c | 11 +++++++++++ src/backend/backend.h | 3 +++ src/backend/backend_common.c | 1 + src/backend/backend_common.h | 1 + src/utils.h | 1 + 5 files changed, 17 insertions(+) diff --git a/src/backend/backend.c b/src/backend/backend.c index 36c5fec1..842a233c 100644 --- a/src/backend/backend.c +++ b/src/backend/backend.c @@ -350,6 +350,17 @@ void paint_all_new(session_t *ps, struct managed_win *t, bool ignore_damage) { ps->backend_data->ops->set_image_property( ps->backend_data, IMAGE_PROPERTY_BORDER_COLOR, w->win_image, &border_color); + + int border_width = w->g.border_width; + if (border_width == 0) { + // Some WM has borders implemented as WM frames + border_width = min3(w->frame_extents.left, + w->frame_extents.right, + w->frame_extents.bottom); + } + ps->backend_data->ops->set_image_property( + ps->backend_data, IMAGE_PROPERTY_BORDER_WIDTH, + w->win_image, &border_width); } } diff --git a/src/backend/backend.h b/src/backend/backend.h index 721b1974..607752d7 100644 --- a/src/backend/backend.h +++ b/src/backend/backend.h @@ -61,6 +61,9 @@ enum image_properties { // Border color // 1 struct color, default: black IMAGE_PROPERTY_BORDER_COLOR, + // Border width + // 1 int, default: 0 + IMAGE_PROPERTY_BORDER_WIDTH, }; enum image_operations { diff --git a/src/backend/backend_common.c b/src/backend/backend_common.c index d5dd7057..30a56920 100644 --- a/src/backend/backend_common.c +++ b/src/backend/backend_common.c @@ -452,6 +452,7 @@ bool default_set_image_property(backend_t *base attr_unused, enum image_properti case IMAGE_PROPERTY_CORNER_RADIUS: tex->corner_radius = dargs[0]; break; case IMAGE_PROPERTY_MAX_BRIGHTNESS: tex->max_brightness = dargs[0]; break; case IMAGE_PROPERTY_BORDER_COLOR: tex->border_color = *(struct color *)arg; break; + case IMAGE_PROPERTY_BORDER_WIDTH: tex->border_width = *(int *)arg; break; } return true; diff --git a/src/backend/backend_common.h b/src/backend/backend_common.h index 6d967b56..335eace2 100644 --- a/src/backend/backend_common.h +++ b/src/backend/backend_common.h @@ -42,6 +42,7 @@ struct backend_image { int ewidth, eheight; bool color_inverted; struct color border_color; + int border_width; }; bool build_shadow(xcb_connection_t *, xcb_drawable_t, double opacity, int width, diff --git a/src/utils.h b/src/utils.h index c5098936..23a5abb1 100644 --- a/src/utils.h +++ b/src/utils.h @@ -134,6 +134,7 @@ static inline int attr_const normalize_i_range(int i, int min, int max) { #define min2(a, b) ((a) > (b) ? (b) : (a)) #define max2(a, b) ((a) > (b) ? (a) : (b)) +#define min3(a, b, c) min2(a, min2(b, c)) /// clamp `val` into interval [min, max] #define clamp(val, min, max) max2(min2(val, max), min) From b6c14989e13cadb8e91800ee4bf3033ead32fbc5 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Thu, 13 Jan 2022 11:43:40 +0000 Subject: [PATCH 3/6] backend: gl: trivial refactoring * unifm -> uniform * add macro for storing uniform locations Signed-off-by: Yuxuan Shui --- src/backend/gl/gl_common.c | 86 ++++++++++++++++---------------------- src/backend/gl/gl_common.h | 31 ++++++++++---- 2 files changed, 57 insertions(+), 60 deletions(-) diff --git a/src/backend/gl/gl_common.c b/src/backend/gl/gl_common.c index c0480fce..d4770cbf 100644 --- a/src/backend/gl/gl_common.c +++ b/src/backend/gl/gl_common.c @@ -57,16 +57,6 @@ struct gl_blur_context { int npasses; }; -static GLint glGetUniformLocationChecked(GLuint p, const char *name) { - auto ret = glGetUniformLocation(p, name); - if (ret < 0) { - log_info("Failed to get location of uniform '%s'. This is normal when " - "using custom shaders.", - name); - } - return ret; -} - GLuint gl_create_shader(GLenum shader_type, const char *shader_str) { log_trace("===\n%s\n===", shader_str); @@ -383,26 +373,26 @@ static void _gl_compose(backend_t *base, struct backend_image *img, GLuint targe assert(gd->win_shader.prog); glUseProgram(gd->win_shader.prog); - if (gd->win_shader.unifm_opacity >= 0) { - glUniform1f(gd->win_shader.unifm_opacity, (float)img->opacity); + if (gd->win_shader.uniform_opacity >= 0) { + glUniform1f(gd->win_shader.uniform_opacity, (float)img->opacity); } - if (gd->win_shader.unifm_invert_color >= 0) { - glUniform1i(gd->win_shader.unifm_invert_color, img->color_inverted); + if (gd->win_shader.uniform_invert_color >= 0) { + glUniform1i(gd->win_shader.uniform_invert_color, img->color_inverted); } - if (gd->win_shader.unifm_tex >= 0) { - glUniform1i(gd->win_shader.unifm_tex, 0); + if (gd->win_shader.uniform_tex >= 0) { + glUniform1i(gd->win_shader.uniform_tex, 0); } - if (gd->win_shader.unifm_dim >= 0) { - glUniform1f(gd->win_shader.unifm_dim, (float)img->dim); + if (gd->win_shader.uniform_dim >= 0) { + glUniform1f(gd->win_shader.uniform_dim, (float)img->dim); } - if (gd->win_shader.unifm_brightness >= 0) { - glUniform1i(gd->win_shader.unifm_brightness, 1); + if (gd->win_shader.uniform_brightness >= 0) { + glUniform1i(gd->win_shader.uniform_brightness, 1); } - if (gd->win_shader.unifm_max_brightness >= 0) { - glUniform1f(gd->win_shader.unifm_max_brightness, (float)img->max_brightness); + if (gd->win_shader.uniform_max_brightness >= 0) { + glUniform1f(gd->win_shader.uniform_max_brightness, (float)img->max_brightness); } - if (gd->win_shader.unifm_corner_radius >= 0) { - glUniform1f(gd->win_shader.unifm_corner_radius, (float)img->corner_radius); + if (gd->win_shader.uniform_corner_radius >= 0) { + glUniform1f(gd->win_shader.uniform_corner_radius, (float)img->corner_radius); } // log_trace("Draw: %d, %d, %d, %d -> %d, %d (%d, %d) z %d\n", @@ -586,7 +576,7 @@ bool gl_kernel_blur(backend_t *base, double opacity, void *ctx, const rect_t *ex glBindTexture(GL_TEXTURE_2D, src_texture); glUseProgram(p->prog); - glUniform2f(p->unifm_pixel_norm, 1.0f / (GLfloat)tex_width, + glUniform2f(p->uniform_pixel_norm, 1.0f / (GLfloat)tex_width, 1.0f / (GLfloat)tex_height); // The number of indices in the selected vertex array @@ -608,7 +598,7 @@ bool gl_kernel_blur(backend_t *base, double opacity, void *ctx, const rect_t *ex return false; } - glUniform1f(p->unifm_opacity, 1.0); + glUniform1f(p->uniform_opacity, 1.0); } else { // last pass, draw directly into the back buffer, with origin // regions @@ -616,7 +606,7 @@ bool gl_kernel_blur(backend_t *base, double opacity, void *ctx, const rect_t *ex nelems = vao_nelems[0]; glBindFramebuffer(GL_FRAMEBUFFER, gd->back_fbo); - glUniform1f(p->unifm_opacity, (float)opacity); + glUniform1f(p->uniform_opacity, (float)opacity); } glUniform2f(p->texorig_loc, (GLfloat)texorig_x, (GLfloat)texorig_y); @@ -679,7 +669,7 @@ bool gl_dual_kawase_blur(backend_t *base, double opacity, void *ctx, const rect_ glUniform1f(down_pass->scale_loc, (GLfloat)scale_factor); - glUniform2f(down_pass->unifm_pixel_norm, 1.0f / (GLfloat)tex_width, + glUniform2f(down_pass->uniform_pixel_norm, 1.0f / (GLfloat)tex_width, 1.0f / (GLfloat)tex_height); glDrawElements(GL_TRIANGLES, nelems, GL_UNSIGNED_INT, NULL); @@ -717,18 +707,18 @@ bool gl_dual_kawase_blur(backend_t *base, double opacity, void *ctx, const rect_ glBindFramebuffer(GL_DRAW_FRAMEBUFFER, bctx->blur_fbos[i - 1]); glDrawBuffer(GL_COLOR_ATTACHMENT0); - glUniform1f(up_pass->unifm_opacity, (GLfloat)1); + glUniform1f(up_pass->uniform_opacity, (GLfloat)1); } else { // last pass, draw directly into the back buffer glBindVertexArray(vao[0]); nelems = vao_nelems[0]; glBindFramebuffer(GL_FRAMEBUFFER, gd->back_fbo); - glUniform1f(up_pass->unifm_opacity, (GLfloat)opacity); + glUniform1f(up_pass->uniform_opacity, (GLfloat)opacity); } glUniform1f(up_pass->scale_loc, (GLfloat)scale_factor); - glUniform2f(up_pass->unifm_pixel_norm, 1.0f / (GLfloat)tex_width, + glUniform2f(up_pass->uniform_pixel_norm, 1.0f / (GLfloat)tex_width, 1.0f / (GLfloat)tex_height); glDrawElements(GL_TRIANGLES, nelems, GL_UNSIGNED_INT, NULL); @@ -896,15 +886,13 @@ static int gl_win_shader_from_string(const char *vshader_str, const char *fshade } // Get uniform addresses - ret->unifm_opacity = glGetUniformLocationChecked(ret->prog, "opacity"); - ret->unifm_invert_color = glGetUniformLocationChecked(ret->prog, "invert_color"); - ret->unifm_tex = glGetUniformLocationChecked(ret->prog, "tex"); - ret->unifm_dim = glGetUniformLocationChecked(ret->prog, "dim"); - ret->unifm_brightness = glGetUniformLocationChecked(ret->prog, "brightness"); - ret->unifm_max_brightness = - glGetUniformLocationChecked(ret->prog, "max_brightness"); - ret->unifm_corner_radius = - glGetUniformLocationChecked(ret->prog, "corner_radius"); + bind_uniform(ret, opacity); + bind_uniform(ret, invert_color); + bind_uniform(ret, tex); + bind_uniform(ret, dim); + bind_uniform(ret, brightness); + bind_uniform(ret, max_brightness); + bind_uniform(ret, corner_radius); gl_check_err(); @@ -1251,9 +1239,8 @@ bool gl_create_kernel_blur_context(void *blur_context, GLfloat *projection, glBindFragDataLocation(pass->prog, 0, "out_color"); // Get uniform addresses - pass->unifm_pixel_norm = - glGetUniformLocationChecked(pass->prog, "pixel_norm"); - pass->unifm_opacity = glGetUniformLocationChecked(pass->prog, "opacity"); + bind_uniform(pass, pixel_norm); + bind_uniform(pass, opacity); pass->texorig_loc = glGetUniformLocationChecked(pass->prog, "texorig"); // Setup projection matrix @@ -1271,8 +1258,8 @@ bool gl_create_kernel_blur_context(void *blur_context, GLfloat *projection, // the single pass case auto pass = &ctx->blur_shader[1]; pass->prog = gl_create_program_from_str(vertex_shader, dummy_frag); - pass->unifm_pixel_norm = -1; - pass->unifm_opacity = -1; + pass->uniform_pixel_norm = -1; + pass->uniform_opacity = -1; pass->texorig_loc = glGetUniformLocationChecked(pass->prog, "texorig"); // Setup projection matrix @@ -1371,8 +1358,7 @@ bool gl_create_dual_kawase_blur_context(void *blur_context, GLfloat *projection, glBindFragDataLocation(down_pass->prog, 0, "out_color"); // Get uniform addresses - down_pass->unifm_pixel_norm = - glGetUniformLocationChecked(down_pass->prog, "pixel_norm"); + bind_uniform(down_pass, pixel_norm); down_pass->texorig_loc = glGetUniformLocationChecked(down_pass->prog, "texorig"); down_pass->scale_loc = @@ -1432,10 +1418,8 @@ bool gl_create_dual_kawase_blur_context(void *blur_context, GLfloat *projection, glBindFragDataLocation(up_pass->prog, 0, "out_color"); // Get uniform addresses - up_pass->unifm_pixel_norm = - glGetUniformLocationChecked(up_pass->prog, "pixel_norm"); - up_pass->unifm_opacity = - glGetUniformLocationChecked(up_pass->prog, "opacity"); + bind_uniform(up_pass, pixel_norm); + bind_uniform(up_pass, opacity); up_pass->texorig_loc = glGetUniformLocationChecked(up_pass->prog, "texorig"); up_pass->scale_loc = glGetUniformLocationChecked(up_pass->prog, "scale"); diff --git a/src/backend/gl/gl_common.h b/src/backend/gl/gl_common.h index 3daf7460..c1ae506c 100644 --- a/src/backend/gl/gl_common.h +++ b/src/backend/gl/gl_common.h @@ -13,16 +13,29 @@ #define CASESTRRET(s) \ case s: return #s +static inline GLint glGetUniformLocationChecked(GLuint p, const char *name) { + auto ret = glGetUniformLocation(p, name); + if (ret < 0) { + log_info("Failed to get location of uniform '%s'. This is normal when " + "using custom shaders.", + name); + } + return ret; +} + +#define bind_uniform(shader, uniform) \ + (shader)->uniform_##uniform = glGetUniformLocationChecked((shader)->prog, #uniform) + // Program and uniforms for window shader typedef struct { GLuint prog; - GLint unifm_opacity; - GLint unifm_invert_color; - GLint unifm_tex; - GLint unifm_dim; - GLint unifm_brightness; - GLint unifm_max_brightness; - GLint unifm_corner_radius; + GLint uniform_opacity; + GLint uniform_invert_color; + GLint uniform_tex; + GLint uniform_dim; + GLint uniform_brightness; + GLint uniform_max_brightness; + GLint uniform_corner_radius; } gl_win_shader_t; // Program and uniforms for brightness shader @@ -33,8 +46,8 @@ typedef struct { // Program and uniforms for blur shader typedef struct { GLuint prog; - GLint unifm_pixel_norm; - GLint unifm_opacity; + GLint uniform_pixel_norm; + GLint uniform_opacity; GLint texorig_loc; GLint scale_loc; } gl_blur_shader_t; From 4aac801a12da7df938d0bf59193744656a121ad2 Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 19 Jan 2022 10:25:01 +0000 Subject: [PATCH 4/6] backend: gl: draw border for rounded windows Signed-off-by: Yuxuan Shui --- src/backend/gl/gl_common.c | 18 +++++++++++++++++- src/backend/gl/gl_common.h | 2 ++ 2 files changed, 19 insertions(+), 1 deletion(-) diff --git a/src/backend/gl/gl_common.c b/src/backend/gl/gl_common.c index d4770cbf..f36e8347 100644 --- a/src/backend/gl/gl_common.c +++ b/src/backend/gl/gl_common.c @@ -394,6 +394,13 @@ static void _gl_compose(backend_t *base, struct backend_image *img, GLuint targe if (gd->win_shader.uniform_corner_radius >= 0) { glUniform1f(gd->win_shader.uniform_corner_radius, (float)img->corner_radius); } + if (gd->win_shader.uniform_border_width >= 0) { + glUniform1f(gd->win_shader.uniform_border_width, (float)img->border_width); + } + if (gd->win_shader.uniform_border_color >= 0) { + glUniform3f(gd->win_shader.uniform_border_color, (float)img->border_color.red, + (float)img->border_color.green, (float)img->border_color.blue); + } // log_trace("Draw: %d, %d, %d, %d -> %d, %d (%d, %d) z %d\n", // x, y, width, height, dx, dy, ptex->width, ptex->height, z); @@ -893,6 +900,8 @@ static int gl_win_shader_from_string(const char *vshader_str, const char *fshade bind_uniform(ret, brightness); bind_uniform(ret, max_brightness); bind_uniform(ret, corner_radius); + bind_uniform(ret, border_width); + bind_uniform(ret, border_color); gl_check_err(); @@ -1524,6 +1533,8 @@ const char *win_shader_glsl = GLSL(330, uniform float opacity; uniform float dim; uniform float corner_radius; + uniform float border_width; + uniform vec3 border_color; uniform bool invert_color; in vec2 texcoord; uniform sampler2D tex; @@ -1555,7 +1566,12 @@ const char *win_shader_glsl = GLSL(330, vec2 inner_size = outer_size - vec2(corner_radius) * 2.0f; float rect_distance = rectangle_sdf(texcoord - outer_size / 2.0f, inner_size / 2.0f) - corner_radius; - c *= 1.0f - clamp(rect_distance, 0.0f, 1.0f); + if (rect_distance > 0.0f) { + c = (1.0f - clamp(rect_distance, 0.0f, 1.0f)) * vec4(border_color, 1.0); + } else { + float factor = clamp(rect_distance + border_width, 0.0f, 1.0f); + c = (1.0f - factor) * c + factor * vec4(border_color, 1.0); + } gl_FragColor = c; } diff --git a/src/backend/gl/gl_common.h b/src/backend/gl/gl_common.h index c1ae506c..fcc0e40a 100644 --- a/src/backend/gl/gl_common.h +++ b/src/backend/gl/gl_common.h @@ -36,6 +36,8 @@ typedef struct { GLint uniform_brightness; GLint uniform_max_brightness; GLint uniform_corner_radius; + GLint uniform_border_width; + GLint uniform_border_color; } gl_win_shader_t; // Program and uniforms for brightness shader From ef73668eb974a0d7940f3f808c8fd52b4cdf55db Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Wed, 19 Jan 2022 17:47:55 +0000 Subject: [PATCH 5/6] backend: gl: fix read_pixel Signed-off-by: Yuxuan Shui --- src/backend/gl/gl_common.c | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/backend/gl/gl_common.c b/src/backend/gl/gl_common.c index f36e8347..87b71bfd 100644 --- a/src/backend/gl/gl_common.c +++ b/src/backend/gl/gl_common.c @@ -1918,6 +1918,12 @@ bool gl_read_pixel(backend_t *base attr_unused, void *image_data, int x, int y, struct color *output) { struct backend_image *tex = image_data; auto inner = (struct gl_texture *)tex->inner; + GLuint fbo; + glGenFramebuffers(1, &fbo); + glBindFramebuffer(GL_READ_FRAMEBUFFER, fbo); + glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, + inner->texture, 0); + glReadBuffer(GL_COLOR_ATTACHMENT0); GLfloat color[4]; glReadPixels(x, inner->y_inverted ? inner->height - y : y, 1, 1, GL_RGBA, GL_FLOAT, color); @@ -1926,6 +1932,9 @@ bool gl_read_pixel(backend_t *base attr_unused, void *image_data, int x, int y, output->green = color[1]; output->blue = color[2]; + glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0); + glDeleteFramebuffers(1, &fbo); + bool ret = glGetError() == GL_NO_ERROR; gl_clear_err(); return ret; From e50be3173f0a9d6717917d01f70705c49217cb4c Mon Sep 17 00:00:00 2001 From: Yuxuan Shui Date: Mon, 24 Jan 2022 17:13:37 +0000 Subject: [PATCH 6/6] backend: remove the read_pixel interface. Sample the border color in the shader instead. Signed-off-by: Yuxuan Shui --- src/backend/backend.c | 8 -------- src/backend/backend.h | 17 ---------------- src/backend/backend_common.c | 1 - src/backend/backend_common.h | 1 - src/backend/gl/gl_common.c | 37 +++-------------------------------- src/backend/gl/gl_common.h | 1 - src/backend/gl/glx.c | 1 - src/backend/xrender/xrender.c | 25 ----------------------- 8 files changed, 3 insertions(+), 88 deletions(-) diff --git a/src/backend/backend.c b/src/backend/backend.c index 842a233c..a9cea7c9 100644 --- a/src/backend/backend.c +++ b/src/backend/backend.c @@ -343,14 +343,6 @@ void paint_all_new(session_t *ps, struct managed_win *t, bool ignore_damage) { ps->backend_data, IMAGE_PROPERTY_CORNER_RADIUS, w->win_image, (double[]){w->corner_radius}); if (w->corner_radius) { - struct color border_color; - ps->backend_data->ops->read_pixel( - ps->backend_data, w->win_image, 0, w->heightb, - &border_color); - ps->backend_data->ops->set_image_property( - ps->backend_data, IMAGE_PROPERTY_BORDER_COLOR, - w->win_image, &border_color); - int border_width = w->g.border_width; if (border_width == 0) { // Some WM has borders implemented as WM frames diff --git a/src/backend/backend.h b/src/backend/backend.h index 607752d7..ed66442c 100644 --- a/src/backend/backend.h +++ b/src/backend/backend.h @@ -58,9 +58,6 @@ enum image_properties { // Gives the image a rounded corner. // 1 double, default: 0 IMAGE_PROPERTY_CORNER_RADIUS, - // Border color - // 1 struct color, default: black - IMAGE_PROPERTY_BORDER_COLOR, // Border width // 1 int, default: 0 IMAGE_PROPERTY_BORDER_WIDTH, @@ -251,20 +248,6 @@ struct backend_operations { bool (*image_op)(backend_t *backend_data, enum image_operations op, void *image_data, const region_t *reg_op, const region_t *reg_visible, void *args); - /** - * Read the color of the pixel at given position of the given image. Image - * properties have no effect. - * - * @param backend_data backend_data - * @param image_data an image data structure previously returned by the - * backend. the image to read pixel from. - * @param x, y coordinate of the pixel to read - * @param[out] color the color of the pixel - * @return whether the operation is successful - */ - bool (*read_pixel)(backend_t *backend_data, void *image_data, int x, int y, - struct color *output); - /// Create another instance of the `image_data`. All `image_op` and /// `set_image_property` calls on the returned image should not affect the /// original image diff --git a/src/backend/backend_common.c b/src/backend/backend_common.c index 30a56920..5bd75e21 100644 --- a/src/backend/backend_common.c +++ b/src/backend/backend_common.c @@ -451,7 +451,6 @@ bool default_set_image_property(backend_t *base attr_unused, enum image_properti break; case IMAGE_PROPERTY_CORNER_RADIUS: tex->corner_radius = dargs[0]; break; case IMAGE_PROPERTY_MAX_BRIGHTNESS: tex->max_brightness = dargs[0]; break; - case IMAGE_PROPERTY_BORDER_COLOR: tex->border_color = *(struct color *)arg; break; case IMAGE_PROPERTY_BORDER_WIDTH: tex->border_width = *(int *)arg; break; } diff --git a/src/backend/backend_common.h b/src/backend/backend_common.h index 335eace2..cf77ce8b 100644 --- a/src/backend/backend_common.h +++ b/src/backend/backend_common.h @@ -41,7 +41,6 @@ struct backend_image { // Effective size of the image int ewidth, eheight; bool color_inverted; - struct color border_color; int border_width; }; diff --git a/src/backend/gl/gl_common.c b/src/backend/gl/gl_common.c index 87b71bfd..0ed973bf 100644 --- a/src/backend/gl/gl_common.c +++ b/src/backend/gl/gl_common.c @@ -397,10 +397,6 @@ static void _gl_compose(backend_t *base, struct backend_image *img, GLuint targe if (gd->win_shader.uniform_border_width >= 0) { glUniform1f(gd->win_shader.uniform_border_width, (float)img->border_width); } - if (gd->win_shader.uniform_border_color >= 0) { - glUniform3f(gd->win_shader.uniform_border_color, (float)img->border_color.red, - (float)img->border_color.green, (float)img->border_color.blue); - } // log_trace("Draw: %d, %d, %d, %d -> %d, %d (%d, %d) z %d\n", // x, y, width, height, dx, dy, ptex->width, ptex->height, z); @@ -901,7 +897,6 @@ static int gl_win_shader_from_string(const char *vshader_str, const char *fshade bind_uniform(ret, max_brightness); bind_uniform(ret, corner_radius); bind_uniform(ret, border_width); - bind_uniform(ret, border_color); gl_check_err(); @@ -1534,7 +1529,6 @@ const char *win_shader_glsl = GLSL(330, uniform float dim; uniform float corner_radius; uniform float border_width; - uniform vec3 border_color; uniform bool invert_color; in vec2 texcoord; uniform sampler2D tex; @@ -1549,6 +1543,7 @@ const char *win_shader_glsl = GLSL(330, void main() { vec4 c = texelFetch(tex, ivec2(texcoord), 0); + vec4 border_color = texture(tex, vec2(0.0, 0.5)); if (invert_color) { c = vec4(c.aaa - c.rgb, c.a); } @@ -1567,10 +1562,10 @@ const char *win_shader_glsl = GLSL(330, float rect_distance = rectangle_sdf(texcoord - outer_size / 2.0f, inner_size / 2.0f) - corner_radius; if (rect_distance > 0.0f) { - c = (1.0f - clamp(rect_distance, 0.0f, 1.0f)) * vec4(border_color, 1.0); + c = (1.0f - clamp(rect_distance, 0.0f, 1.0f)) * border_color; } else { float factor = clamp(rect_distance + border_width, 0.0f, 1.0f); - c = (1.0f - factor) * c + factor * vec4(border_color, 1.0); + c = (1.0f - factor) * c + factor * border_color; } gl_FragColor = c; @@ -1913,29 +1908,3 @@ bool gl_image_op(backend_t *base, enum image_operations op, void *image_data, return true; } - -bool gl_read_pixel(backend_t *base attr_unused, void *image_data, int x, int y, - struct color *output) { - struct backend_image *tex = image_data; - auto inner = (struct gl_texture *)tex->inner; - GLuint fbo; - glGenFramebuffers(1, &fbo); - glBindFramebuffer(GL_READ_FRAMEBUFFER, fbo); - glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, - inner->texture, 0); - glReadBuffer(GL_COLOR_ATTACHMENT0); - GLfloat color[4]; - glReadPixels(x, inner->y_inverted ? inner->height - y : y, 1, 1, GL_RGBA, - GL_FLOAT, color); - output->alpha = color[3]; - output->red = color[0]; - output->green = color[1]; - output->blue = color[2]; - - glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0); - glDeleteFramebuffers(1, &fbo); - - bool ret = glGetError() == GL_NO_ERROR; - gl_clear_err(); - return ret; -} diff --git a/src/backend/gl/gl_common.h b/src/backend/gl/gl_common.h index fcc0e40a..9bea831d 100644 --- a/src/backend/gl/gl_common.h +++ b/src/backend/gl/gl_common.h @@ -37,7 +37,6 @@ typedef struct { GLint uniform_max_brightness; GLint uniform_corner_radius; GLint uniform_border_width; - GLint uniform_border_color; } gl_win_shader_t; // Program and uniforms for brightness shader diff --git a/src/backend/gl/glx.c b/src/backend/gl/glx.c index 1397d193..54d1114f 100644 --- a/src/backend/gl/glx.c +++ b/src/backend/gl/glx.c @@ -530,7 +530,6 @@ struct backend_operations glx_ops = { .compose = gl_compose, .image_op = gl_image_op, .set_image_property = default_set_image_property, - .read_pixel = gl_read_pixel, .clone_image = default_clone_image, .blur = gl_blur, .is_image_transparent = default_is_image_transparent, diff --git a/src/backend/xrender/xrender.c b/src/backend/xrender/xrender.c index c6c3c8c0..9e2236b5 100644 --- a/src/backend/xrender/xrender.c +++ b/src/backend/xrender/xrender.c @@ -745,30 +745,6 @@ static void get_blur_size(void *blur_context, int *width, int *height) { *height = ctx->resize_height; } -static bool -read_pixel(backend_t *backend_data, void *image_data, int x, int y, struct color *output) { - auto xd = (struct _xrender_data *)backend_data; - auto img = (struct backend_image *)image_data; - auto inner = (struct _xrender_image_data_inner *)img->inner; - - auto r = XCB_AWAIT(xcb_get_image, xd->base.c, XCB_IMAGE_FORMAT_XY_PIXMAP, inner->pixmap, - to_i16_checked(x), to_i16_checked(y), 1, 1, (uint32_t)-1L); - - if (!r) { - return false; - } - - // Color format seems to be BGRA8888, see glamor_format_for_pixmap from the - // Xserver codebase. - uint8_t *pixels = xcb_get_image_data(r); - output->blue = pixels[0] / 255.0; - output->green = pixels[1] / 255.0; - output->red = pixels[2] / 255.0; - output->alpha = pixels[3] / 255.0; - - return true; -} - static backend_t *backend_xrender_init(session_t *ps) { auto xd = ccalloc(1, struct _xrender_data); init_backend_base(&xd->base, ps); @@ -888,7 +864,6 @@ struct backend_operations xrender_ops = { .max_buffer_age = 2, .image_op = image_op, - .read_pixel = read_pixel, .clone_image = clone_image, .set_image_property = set_image_property, .create_blur_context = create_blur_context,