diff --git a/include/labwc.h b/include/labwc.h index d8303e42..2747aa9e 100644 --- a/include/labwc.h +++ b/include/labwc.h @@ -144,7 +144,6 @@ struct server { double grab_x, grab_y; struct wlr_box grab_box; uint32_t resize_edges; - struct wlr_texture *osd; struct wl_list outputs; struct wl_listener new_output; @@ -154,7 +153,6 @@ struct server { struct wlr_output_manager_v1 *output_manager; struct wl_listener output_manager_apply; struct wlr_output_configuration_v1 *pending_output_config; - float greatest_scale; struct wlr_foreign_toplevel_manager_v1 *foreign_toplevel_manager; @@ -177,6 +175,7 @@ struct output { struct wlr_output_damage *damage; struct wl_list layers[4]; struct wlr_box usable_area; + struct wlr_texture *osd; struct wl_listener destroy; struct wl_listener damage_frame; diff --git a/src/osd.c b/src/osd.c index f95ec1dc..f2a54967 100644 --- a/src/osd.c +++ b/src/osd.c @@ -79,115 +79,118 @@ osd_update(struct server *server) struct wlr_renderer *renderer = server->renderer; struct theme *theme = server->theme; - float scale = server->greatest_scale; - int w = (OSD_ITEM_WIDTH + (2 * OSD_BORDER_WIDTH)) * scale; - int h = get_osd_height(&server->views) * scale; + struct output *output; + wl_list_for_each(output, &server->outputs, link) { + float scale = output->wlr_output->scale; + int w = (OSD_ITEM_WIDTH + (2 * OSD_BORDER_WIDTH)) * scale; + int h = get_osd_height(&server->views) * scale; - cairo_surface_t *surf = - cairo_image_surface_create(CAIRO_FORMAT_ARGB32, w, h); - cairo_surface_set_device_scale(surf, scale, scale); - cairo_t *cairo = cairo_create(surf); + cairo_surface_t *surf = + cairo_image_surface_create(CAIRO_FORMAT_ARGB32, w, h); + cairo_surface_set_device_scale(surf, scale, scale); + cairo_t *cairo = cairo_create(surf); - /* background */ - set_source(cairo, theme->osd_bg_color); - cairo_rectangle(cairo, 0, 0, w, h); - cairo_fill(cairo); + /* background */ + set_source(cairo, theme->osd_bg_color); + cairo_rectangle(cairo, 0, 0, w, h); + cairo_fill(cairo); - /* border */ - set_source(cairo, theme->osd_label_text_color); - cairo_rectangle(cairo, 0, 0, w, h); - cairo_stroke(cairo); + /* border */ + set_source(cairo, theme->osd_label_text_color); + cairo_rectangle(cairo, 0, 0, w, h); + cairo_stroke(cairo); - /* highlight current window */ - int y = OSD_BORDER_WIDTH; - struct view *view; - wl_list_for_each(view, &server->views, link) { - if (!isfocusable(view)) { - continue; + /* highlight current window */ + int y = OSD_BORDER_WIDTH; + struct view *view; + wl_list_for_each(view, &server->views, link) { + if (!isfocusable(view)) { + continue; + } + if (view == server->cycle_view) { + set_source(cairo, theme->osd_label_text_color); + cairo_rectangle(cairo, OSD_BORDER_WIDTH, y, + OSD_ITEM_WIDTH, OSD_ITEM_HEIGHT); + cairo_stroke(cairo); + break; + } + y += OSD_ITEM_HEIGHT; } - if (view == server->cycle_view) { - set_source(cairo, theme->osd_label_text_color); - cairo_rectangle(cairo, OSD_BORDER_WIDTH, y, - OSD_ITEM_WIDTH, OSD_ITEM_HEIGHT); - cairo_stroke(cairo); - break; - } - y += OSD_ITEM_HEIGHT; - } - /* text */ - set_source(cairo, theme->osd_label_text_color); - PangoLayout *layout = pango_cairo_create_layout(cairo); - pango_layout_set_width(layout, w * PANGO_SCALE); - pango_layout_set_ellipsize(layout, PANGO_ELLIPSIZE_END); + /* text */ + set_source(cairo, theme->osd_label_text_color); + PangoLayout *layout = pango_cairo_create_layout(cairo); + pango_layout_set_width(layout, w * PANGO_SCALE); + pango_layout_set_ellipsize(layout, PANGO_ELLIPSIZE_END); - struct font font = { - .name = rc.font_name_osd, - .size = rc.font_size_osd, - }; - PangoFontDescription *desc = pango_font_description_new(); - pango_font_description_set_family(desc, font.name); - pango_font_description_set_size(desc, font.size * PANGO_SCALE); - pango_layout_set_font_description(layout, desc); - pango_font_description_free(desc); + struct font font = { + .name = rc.font_name_osd, + .size = rc.font_size_osd, + }; + PangoFontDescription *desc = pango_font_description_new(); + pango_font_description_set_family(desc, font.name); + pango_font_description_set_size(desc, font.size * PANGO_SCALE); + pango_layout_set_font_description(layout, desc); + pango_font_description_free(desc); - PangoTabArray *tabs = pango_tab_array_new_with_positions(2, TRUE, - PANGO_TAB_LEFT, OSD_TAB1, PANGO_TAB_LEFT, OSD_TAB2); - pango_layout_set_tabs(layout, tabs); - pango_tab_array_free(tabs); + PangoTabArray *tabs = pango_tab_array_new_with_positions(2, TRUE, + PANGO_TAB_LEFT, OSD_TAB1, PANGO_TAB_LEFT, OSD_TAB2); + pango_layout_set_tabs(layout, tabs); + pango_tab_array_free(tabs); - pango_cairo_update_layout(cairo, layout); + pango_cairo_update_layout(cairo, layout); - struct buf buf; - buf_init(&buf); - y = OSD_BORDER_WIDTH; + struct buf buf; + buf_init(&buf); + y = OSD_BORDER_WIDTH; - y += (OSD_ITEM_HEIGHT - font_height(&font)) / 2; + y += (OSD_ITEM_HEIGHT - font_height(&font)) / 2; - wl_list_for_each(view, &server->views, link) { - if (!isfocusable(view)) { - continue; - } - buf.len = 0; - cairo_move_to(cairo, OSD_BORDER_WIDTH + OSD_ITEM_PADDING, y); + wl_list_for_each(view, &server->views, link) { + if (!isfocusable(view)) { + continue; + } + buf.len = 0; + cairo_move_to(cairo, OSD_BORDER_WIDTH + OSD_ITEM_PADDING, y); - switch (view->type) { - case LAB_XDG_SHELL_VIEW: - buf_add(&buf, "[xdg-shell]\t"); - buf_add(&buf, get_formatted_app_id(view)); - buf_add(&buf, "\t"); - break; + switch (view->type) { + case LAB_XDG_SHELL_VIEW: + buf_add(&buf, "[xdg-shell]\t"); + buf_add(&buf, get_formatted_app_id(view)); + buf_add(&buf, "\t"); + break; #if HAVE_XWAYLAND - case LAB_XWAYLAND_VIEW: - buf_add(&buf, "[xwayland]\t"); - buf_add(&buf, view_get_string_prop(view, "class")); - buf_add(&buf, "\t"); - break; + case LAB_XWAYLAND_VIEW: + buf_add(&buf, "[xwayland]\t"); + buf_add(&buf, view_get_string_prop(view, "class")); + buf_add(&buf, "\t"); + break; #endif + } + + if (is_title_different(view)) { + buf_add(&buf, view_get_string_prop(view, "title")); + } + + pango_layout_set_text(layout, buf.buf, -1); + pango_cairo_show_layout(cairo, layout); + y += OSD_ITEM_HEIGHT; } - if (is_title_different(view)) { - buf_add(&buf, view_get_string_prop(view, "title")); + g_object_unref(layout); + + /* convert to wlr_texture */ + cairo_surface_flush(surf); + unsigned char *data = cairo_image_surface_get_data(surf); + struct wlr_texture *texture = wlr_texture_from_pixels(renderer, + DRM_FORMAT_ARGB8888, cairo_image_surface_get_stride(surf), + w, h, data); + + cairo_destroy(cairo); + cairo_surface_destroy(surf); + if (output->osd) { + wlr_texture_destroy(output->osd); } - - pango_layout_set_text(layout, buf.buf, -1); - pango_cairo_show_layout(cairo, layout); - y += OSD_ITEM_HEIGHT; + output->osd = texture; } - - g_object_unref(layout); - - /* convert to wlr_texture */ - cairo_surface_flush(surf); - unsigned char *data = cairo_image_surface_get_data(surf); - struct wlr_texture *texture = wlr_texture_from_pixels(renderer, - DRM_FORMAT_ARGB8888, cairo_image_surface_get_stride(surf), - w, h, data); - - cairo_destroy(cairo); - cairo_surface_destroy(surf); - if (server->osd) { - wlr_texture_destroy(server->osd); - } - server->osd = texture; } diff --git a/src/output.c b/src/output.c index a9356cf8..5d472b19 100644 --- a/src/output.c +++ b/src/output.c @@ -516,10 +516,6 @@ static void render_osd(struct output *output, pixman_region32_t *damage, struct server *server) { - if (!server->osd) { - return; - } - /* show on screen display (osd) on all outputs */ struct output *o; struct wlr_output_layout *layout = server->output_layout; @@ -530,15 +526,16 @@ render_osd(struct output *output, pixman_region32_t *damage, continue; } + if (!output->osd) { + continue; + } struct wlr_box box = { .x = ol_output->x + o->wlr_output->width / 2, .y = ol_output->y + o->wlr_output->height / 2, - .width = server->osd->width * o->wlr_output->scale - / server->greatest_scale, - .height = server->osd->height * o->wlr_output->scale - / server->greatest_scale, + .width = output->osd->width, + .height = output->osd->height, }; box.x -= box.width / 2; box.y -= box.height / 2; @@ -551,7 +548,7 @@ render_osd(struct output *output, pixman_region32_t *damage, float matrix[9]; wlr_matrix_project_box(matrix, &box, WL_OUTPUT_TRANSFORM_NORMAL, 0, output->wlr_output->transform_matrix); - render_texture(o->wlr_output, damage, server->osd, NULL, &box, + render_texture(o->wlr_output, damage, output->osd, NULL, &box, matrix); } } @@ -1046,6 +1043,9 @@ new_output_notify(struct wl_listener *listener, void *data) wlr_output->name); wlr_output_enable_adaptive_sync(wlr_output, true); } + + output->osd = NULL; + wlr_output_layout_add_auto(server->output_layout, wlr_output); } @@ -1071,8 +1071,6 @@ output_init(struct server *server) wl_list_init(&server->outputs); - server->greatest_scale = 1; - output_manager_init(server); } @@ -1167,11 +1165,7 @@ handle_output_manager_apply(struct wl_listener *listener, void *data) } wlr_output_configuration_v1_destroy(config); struct output *output; - server->greatest_scale = 0; wl_list_for_each(output, &server->outputs, link) { - if (output->wlr_output->scale > server->greatest_scale) { - server->greatest_scale = output->wlr_output->scale; - } wlr_xcursor_manager_load(server->seat.xcursor_manager, output->wlr_output->scale); }