xdg: unify initial positioning logic

This commit is contained in:
John Lindgren 2026-02-21 15:36:47 -05:00 committed by Hiroaki Yamamoto
parent 658df83280
commit 3f223fe5b0

View file

@ -121,19 +121,34 @@ set_fullscreen_from_request(struct view *view,
view_set_fullscreen(view, requested->fullscreen); view_set_fullscreen(view, requested->fullscreen);
} }
/* Called from commit handler and updates view->pending.x/y directly */
static void static void
do_late_positioning(struct view *view) set_initial_position(struct view *view)
{ {
if (!view_is_floating(view)) {
return;
}
view_constrain_size_to_that_of_usable_area(view);
struct server *server = view->server; struct server *server = view->server;
if (server->input_mode == LAB_INPUT_STATE_MOVE if (server->input_mode == LAB_INPUT_STATE_MOVE
&& view == server->grabbed_view) { && view == server->grabbed_view) {
/* Reposition the view while anchoring it to cursor */ /* Reposition the view while anchoring it to cursor */
interactive_anchor_to_cursor(server, &view->pending); interactive_anchor_to_cursor(server, &view->pending);
} else {
struct view *parent = xdg_toplevel_view_get_parent(view);
if (parent) {
/* Center relative to parent view */
view_compute_centered_position(view, &parent->pending,
view->pending.width, view->pending.height,
&view->pending.x, &view->pending.y);
} else { } else {
view_compute_position_by_policy(view, &view->pending, view_compute_position_by_policy(view, &view->pending,
/* allow_cursor */ true, rc.placement_policy); /* allow_cursor */ true, rc.placement_policy);
} }
} }
}
static void static void
disable_fullscreen_bg(struct view *view) disable_fullscreen_bg(struct view *view)
@ -247,15 +262,15 @@ handle_commit(struct wl_listener *listener, void *data)
bool update_required = false; bool update_required = false;
/* /*
* If we didn't know the natural size when leaving fullscreen or * The pending size will be empty in two cases:
* unmaximizing, then the pending size will be 0x0. In this case, * (1) when the view is first mapped
* the pending x/y is also unset and we still need to position * (2) when leaving fullscreen or un-maximizing,
* the window. * if natural geometry wasn't known
*/ */
if (wlr_box_empty(&view->pending) && !wlr_box_empty(&size)) { if (wlr_box_empty(&view->pending) && !wlr_box_empty(&size)) {
view->pending.width = size.width; view->pending.width = size.width;
view->pending.height = size.height; view->pending.height = size.height;
do_late_positioning(view); set_initial_position(view);
update_required = true; update_required = true;
} }
@ -789,22 +804,6 @@ xdg_toplevel_view_notify_tiled(struct view *view)
} }
} }
static void
set_initial_position(struct view *view)
{
view_constrain_size_to_that_of_usable_area(view);
struct view *parent = xdg_toplevel_view_get_parent(view);
if (parent) {
/* Child views are center-aligned relative to their parents */
view_center(view, &parent->pending);
return;
}
/* All other views are placed according to a configured strategy */
view_place_by_policy(view, /* allow_cursor */ true, rc.placement_policy);
}
static void static void
handle_map(struct wl_listener *listener, void *data) handle_map(struct wl_listener *listener, void *data)
{ {
@ -821,36 +820,6 @@ handle_map(struct wl_listener *listener, void *data)
} else { } else {
view_set_ssd_mode(view, LAB_SSD_MODE_NONE); view_set_ssd_mode(view, LAB_SSD_MODE_NONE);
} }
/*
* Set initial "pending" dimensions. "Current"
* dimensions remain zero until handle_commit().
*/
if (wlr_box_empty(&view->pending)) {
struct wlr_xdg_surface *xdg_surface =
xdg_surface_from_view(view);
view->pending.width = xdg_surface->geometry.width;
view->pending.height = xdg_surface->geometry.height;
}
/*
* Set initial "pending" position for floating views.
*/
if (view_is_floating(view)) {
set_initial_position(view);
}
/* Disable background fill at map (paranoid?) */
disable_fullscreen_bg(view);
/*
* Set initial "current" position directly before
* calling view_moved() to reduce flicker
*/
view->current.x = view->pending.x;
view->current.y = view->pending.y;
view_moved(view);
} }
view_impl_map(view); view_impl_map(view);