mirror of
https://github.com/labwc/labwc.git
synced 2026-03-27 07:58:31 -04:00
theme: add circle button hover effect (#2127)
This commit is contained in:
parent
dcd9b47e5b
commit
9395348c55
4 changed files with 59 additions and 19 deletions
|
|
@ -132,6 +132,10 @@ labwc-config(5).
|
||||||
Space between titlebar buttons, in pixels.
|
Space between titlebar buttons, in pixels.
|
||||||
Default is 0.
|
Default is 0.
|
||||||
|
|
||||||
|
*window.button.hover.bg.shape*
|
||||||
|
The shape of the hover effect of a titlebar button: "rectangle" or "circle".
|
||||||
|
Default is "rectangle".
|
||||||
|
|
||||||
*window.active.button.unpressed.image.color*
|
*window.active.button.unpressed.image.color*
|
||||||
Color of the images in titlebar buttons in their default, unpressed,
|
Color of the images in titlebar buttons in their default, unpressed,
|
||||||
state. This element is for the focused window.
|
state. This element is for the focused window.
|
||||||
|
|
|
||||||
|
|
@ -34,6 +34,9 @@ window.label.text.justify: center
|
||||||
window.button.width: 26
|
window.button.width: 26
|
||||||
window.button.spacing: 0
|
window.button.spacing: 0
|
||||||
|
|
||||||
|
# window button hover effect
|
||||||
|
window.button.hover.bg.shape: rectangle
|
||||||
|
|
||||||
# window buttons
|
# window buttons
|
||||||
window.active.button.unpressed.image.color: #000000
|
window.active.button.unpressed.image.color: #000000
|
||||||
window.inactive.button.unpressed.image.color: #000000
|
window.inactive.button.unpressed.image.color: #000000
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,11 @@ enum lab_justification {
|
||||||
LAB_JUSTIFY_RIGHT,
|
LAB_JUSTIFY_RIGHT,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum lab_shape {
|
||||||
|
LAB_RECTANGLE,
|
||||||
|
LAB_CIRCLE,
|
||||||
|
};
|
||||||
|
|
||||||
struct theme_snapping_overlay {
|
struct theme_snapping_overlay {
|
||||||
bool bg_enabled;
|
bool bg_enabled;
|
||||||
bool border_enabled;
|
bool border_enabled;
|
||||||
|
|
@ -57,6 +62,8 @@ struct theme {
|
||||||
int window_button_width;
|
int window_button_width;
|
||||||
/* the space between buttons */
|
/* the space between buttons */
|
||||||
int window_button_spacing;
|
int window_button_spacing;
|
||||||
|
/* the shape of the hover effect */
|
||||||
|
enum lab_shape window_button_hover_bg_shape;
|
||||||
|
|
||||||
/* button colors */
|
/* button colors */
|
||||||
float window_active_button_menu_unpressed_image_color[4];
|
float window_active_button_menu_unpressed_image_color[4];
|
||||||
|
|
|
||||||
64
src/theme.c
64
src/theme.c
|
|
@ -70,6 +70,9 @@ struct rounded_corner_ctx {
|
||||||
|
|
||||||
static struct lab_data_buffer *rounded_rect(struct rounded_corner_ctx *ctx);
|
static struct lab_data_buffer *rounded_rect(struct rounded_corner_ctx *ctx);
|
||||||
|
|
||||||
|
/* 1 degree in radians (=2π/360) */
|
||||||
|
static const double deg = 0.017453292519943295;
|
||||||
|
|
||||||
static void
|
static void
|
||||||
zdrop(struct lab_data_buffer **buffer)
|
zdrop(struct lab_data_buffer **buffer)
|
||||||
{
|
{
|
||||||
|
|
@ -162,26 +165,36 @@ create_hover_fallback(struct theme *theme, const char *icon_name,
|
||||||
|
|
||||||
/* Overlay (pre-multiplied alpha) */
|
/* Overlay (pre-multiplied alpha) */
|
||||||
float overlay_color[4] = { 0.15f, 0.15f, 0.15f, 0.3f};
|
float overlay_color[4] = { 0.15f, 0.15f, 0.15f, 0.3f};
|
||||||
|
int radius = MIN(width, height) / 2;
|
||||||
enum corner corner = corner_from_icon_name(icon_name);
|
enum corner corner = corner_from_icon_name(icon_name);
|
||||||
|
|
||||||
if (corner == LAB_CORNER_UNKNOWN) {
|
switch (theme->window_button_hover_bg_shape) {
|
||||||
|
case LAB_CIRCLE:
|
||||||
set_cairo_color(cairo, overlay_color);
|
set_cairo_color(cairo, overlay_color);
|
||||||
cairo_rectangle(cairo, 0, 0, width, height);
|
cairo_arc(cairo, width / 2, height / 2, radius, 0 * deg, 360 * deg);
|
||||||
cairo_fill(cairo);
|
cairo_fill(cairo);
|
||||||
} else {
|
break;
|
||||||
struct rounded_corner_ctx rounded_ctx = {
|
case LAB_RECTANGLE:
|
||||||
.box = &(struct wlr_box) { .width = width, .height = height },
|
if (corner == LAB_CORNER_UNKNOWN) {
|
||||||
.radius = rc.corner_radius,
|
set_cairo_color(cairo, overlay_color);
|
||||||
.line_width = theme->border_width,
|
cairo_rectangle(cairo, 0, 0, width, height);
|
||||||
.fill_color = overlay_color,
|
cairo_fill(cairo);
|
||||||
.border_color = overlay_color,
|
} else {
|
||||||
.corner = corner
|
struct rounded_corner_ctx rounded_ctx = {
|
||||||
};
|
.box = &(struct wlr_box){.width = width, .height = height},
|
||||||
struct lab_data_buffer *overlay_buffer = rounded_rect(&rounded_ctx);
|
.radius = rc.corner_radius,
|
||||||
cairo_set_source_surface(cairo,
|
.line_width = theme->border_width,
|
||||||
cairo_get_target(overlay_buffer->cairo), 0, 0);
|
.fill_color = overlay_color,
|
||||||
cairo_paint(cairo);
|
.border_color = overlay_color,
|
||||||
wlr_buffer_drop(&overlay_buffer->base);
|
.corner = corner};
|
||||||
|
struct lab_data_buffer *overlay_buffer =
|
||||||
|
rounded_rect(&rounded_ctx);
|
||||||
|
cairo_set_source_surface(cairo,
|
||||||
|
cairo_get_target(overlay_buffer->cairo), 0, 0);
|
||||||
|
cairo_paint(cairo);
|
||||||
|
wlr_buffer_drop(&overlay_buffer->base);
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
cairo_surface_flush(surf);
|
cairo_surface_flush(surf);
|
||||||
|
|
||||||
|
|
@ -532,6 +545,18 @@ parse_justification(const char *str)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static enum lab_shape
|
||||||
|
parse_shape(const char *str)
|
||||||
|
{
|
||||||
|
if (!strcasecmp(str, "Rectangle")) {
|
||||||
|
return LAB_RECTANGLE;
|
||||||
|
} else if (!strcasecmp(str, "Circle")) {
|
||||||
|
return LAB_CIRCLE;
|
||||||
|
} else {
|
||||||
|
return LAB_RECTANGLE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* We generally use Openbox defaults, but if no theme file can be found it's
|
* We generally use Openbox defaults, but if no theme file can be found it's
|
||||||
* better to populate the theme variables with some sane values as no-one
|
* better to populate the theme variables with some sane values as no-one
|
||||||
|
|
@ -569,6 +594,7 @@ theme_builtin(struct theme *theme, struct server *server)
|
||||||
theme->padding_width = 0;
|
theme->padding_width = 0;
|
||||||
theme->window_button_width = 26;
|
theme->window_button_width = 26;
|
||||||
theme->window_button_spacing = 0;
|
theme->window_button_spacing = 0;
|
||||||
|
theme->window_button_hover_bg_shape = LAB_RECTANGLE;
|
||||||
|
|
||||||
parse_hexstr("#000000",
|
parse_hexstr("#000000",
|
||||||
theme->window_active_button_menu_unpressed_image_color);
|
theme->window_active_button_menu_unpressed_image_color);
|
||||||
|
|
@ -774,6 +800,9 @@ entry(struct theme *theme, const char *key, const char *value)
|
||||||
theme->window_button_spacing = get_int_if_positive(
|
theme->window_button_spacing = get_int_if_positive(
|
||||||
value, "window.button.spacing");
|
value, "window.button.spacing");
|
||||||
}
|
}
|
||||||
|
if (match_glob(key, "window.button.hover.bg.shape")) {
|
||||||
|
theme->window_button_hover_bg_shape = parse_shape(value);
|
||||||
|
}
|
||||||
|
|
||||||
/* universal button */
|
/* universal button */
|
||||||
if (match_glob(key, "window.active.button.unpressed.image.color")) {
|
if (match_glob(key, "window.active.button.unpressed.image.color")) {
|
||||||
|
|
@ -1077,9 +1106,6 @@ theme_read(struct theme *theme, struct wl_list *paths)
|
||||||
static struct lab_data_buffer *
|
static struct lab_data_buffer *
|
||||||
rounded_rect(struct rounded_corner_ctx *ctx)
|
rounded_rect(struct rounded_corner_ctx *ctx)
|
||||||
{
|
{
|
||||||
/* 1 degree in radians (=2π/360) */
|
|
||||||
double deg = 0.017453292519943295;
|
|
||||||
|
|
||||||
if (ctx->corner == LAB_CORNER_UNKNOWN) {
|
if (ctx->corner == LAB_CORNER_UNKNOWN) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue