mirror of https://github.com/mpv-player/mpv
wayland: make resizing better
Resizing the window while preserving the aspect ratio actually kind of sucked. The window size could make big dramatic changes which was pretty unintuitive with respect to where the mouse was actually located. Instead, let's just do some math to ensure that the window size is always contained inside the width/height reported by handle_toplevel_config while preserving the aspect ratio. Fixes #7426.
This commit is contained in:
parent
cc52a03401
commit
83efdb5a01
|
@ -995,10 +995,13 @@ static void handle_toplevel_config(void *data, struct xdg_toplevel *toplevel,
|
||||||
if (width > 0 && height > 0) {
|
if (width > 0 && height > 0) {
|
||||||
if (!is_fullscreen && !is_maximized) {
|
if (!is_fullscreen && !is_maximized) {
|
||||||
if (wl->vo_opts->keepaspect && wl->vo_opts->keepaspect_window) {
|
if (wl->vo_opts->keepaspect && wl->vo_opts->keepaspect_window) {
|
||||||
if (width > height)
|
if (abs(wl->toplevel_width - old_toplevel_width) > abs(wl->toplevel_height - old_toplevel_height)) {
|
||||||
width = height * wl->aspect_ratio;
|
double scale_factor = (double)width / wl->reduced_width;
|
||||||
else
|
width = wl->reduced_width * scale_factor;
|
||||||
height = width / wl->aspect_ratio;
|
} else {
|
||||||
|
double scale_factor = (double)height / wl->reduced_height;
|
||||||
|
height = wl->reduced_height * scale_factor;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
wl->window_size.x0 = 0;
|
wl->window_size.x0 = 0;
|
||||||
wl->window_size.y0 = 0;
|
wl->window_size.y0 = 0;
|
||||||
|
@ -1270,6 +1273,25 @@ static struct vo_wayland_output *find_output(struct vo_wayland_state *wl, int in
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void greatest_common_divisor(struct vo_wayland_state *wl, int a, int b) {
|
||||||
|
// euclidean algorithm
|
||||||
|
int larger;
|
||||||
|
int smaller;
|
||||||
|
if (a > b) {
|
||||||
|
larger = a;
|
||||||
|
smaller = b;
|
||||||
|
} else {
|
||||||
|
larger = b;
|
||||||
|
smaller = a;
|
||||||
|
}
|
||||||
|
int remainder = larger - smaller * floor(larger/smaller);
|
||||||
|
if (remainder == 0) {
|
||||||
|
wl->gcd = smaller;
|
||||||
|
} else {
|
||||||
|
greatest_common_divisor(wl, smaller, remainder);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int vo_wayland_reconfig(struct vo *vo)
|
int vo_wayland_reconfig(struct vo *vo)
|
||||||
{
|
{
|
||||||
struct vo_wayland_state *wl = vo->wl;
|
struct vo_wayland_state *wl = vo->wl;
|
||||||
|
@ -1309,7 +1331,9 @@ int vo_wayland_reconfig(struct vo *vo)
|
||||||
wl->window_size = wl->geometry;
|
wl->window_size = wl->geometry;
|
||||||
}
|
}
|
||||||
|
|
||||||
wl->aspect_ratio = vo->dwidth / (float)vo->dheight;
|
greatest_common_divisor(wl, vo->dwidth, vo->dheight);
|
||||||
|
wl->reduced_width = vo->dwidth / wl->gcd;
|
||||||
|
wl->reduced_height = vo->dheight / wl->gcd;
|
||||||
|
|
||||||
if (wl->vo_opts->fullscreen) {
|
if (wl->vo_opts->fullscreen) {
|
||||||
/* If already fullscreen, fix resolution for the frame size change */
|
/* If already fullscreen, fix resolution for the frame size change */
|
||||||
|
|
|
@ -70,7 +70,9 @@ struct vo_wayland_state {
|
||||||
/* State */
|
/* State */
|
||||||
struct mp_rect geometry;
|
struct mp_rect geometry;
|
||||||
struct mp_rect window_size;
|
struct mp_rect window_size;
|
||||||
float aspect_ratio;
|
int gcd;
|
||||||
|
int reduced_width;
|
||||||
|
int reduced_height;
|
||||||
bool configured;
|
bool configured;
|
||||||
bool frame_wait;
|
bool frame_wait;
|
||||||
bool hidden;
|
bool hidden;
|
||||||
|
|
Loading…
Reference in New Issue