From 092c80a53735b23b2c211e361bb4a2cff8e590e0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20L=C3=BCbking?= Date: Thu, 31 Jan 2013 23:58:53 +0100 Subject: [PATCH] constrain maximization/restorage for fixed ratio when eg. vertically maximizing a cinemascope video in mplayer it would horizontally exceed the (16:9) screen, so this case is translated to a full maximization (effectively binding the window into screen dimensions) also, when restoring such video from a horizontal maximization the restore would usually keep the height (thus breaking the window aspect) so pass geom_restore -> restore through adjustedSize() REVIEW: 108702 --- geometry.cpp | 33 +++++++++++++++++++++++++++------ 1 file changed, 27 insertions(+), 6 deletions(-) diff --git a/geometry.cpp b/geometry.cpp index 7eb7e94d28..64b7e01a9f 100644 --- a/geometry.cpp +++ b/geometry.cpp @@ -2109,6 +2109,12 @@ void Client::changeMaximize(bool vertical, bool horizontal, bool adjust) return; } + QRect clientArea; + if (isElectricBorderMaximizing()) + clientArea = workspace()->clientArea(MaximizeArea, cursorPos(), desktop()); + else + clientArea = workspace()->clientArea(MaximizeArea, this); + MaximizeMode old_mode = max_mode; // 'adjust == true' means to update the size only, e.g. after changing workspace size if (!adjust) { @@ -2118,6 +2124,24 @@ void Client::changeMaximize(bool vertical, bool horizontal, bool adjust) max_mode = MaximizeMode(max_mode ^ MaximizeHorizontal); } + // if the client insist on a fix aspect ratio, we check whether the maximizing will get us + // out of screen bounds and take that as a "full maximization with aspect check" then + if ((xSizeHint.flags & PAspect) && // fixed aspect + (max_mode == MaximizeVertical || max_mode == MaximizeHorizontal) && // ondimensional maximization + rules()->checkStrictGeometry(true)) { // obey aspect + if (max_mode == MaximizeVertical || (old_mode & MaximizeVertical)) { + const double fx = xSizeHint.min_aspect.x; // use doubles, because the values can be MAX_INT + const double fy = xSizeHint.max_aspect.y; // use doubles, because the values can be MAX_INT + if (fx*clientArea.height()/fy > clientArea.width()) // too big + max_mode = old_mode & MaximizeHorizontal ? MaximizeRestore : MaximizeFull; + } else { // max_mode == MaximizeHorizontal + const double fx = xSizeHint.max_aspect.x; + const double fy = xSizeHint.min_aspect.y; + if (fy*clientArea.width()/fx > clientArea.height()) // too big + max_mode = old_mode & MaximizeVertical ? MaximizeRestore : MaximizeFull; + } + } + max_mode = rules()->checkMaximize(max_mode); if (!adjust && max_mode == old_mode) return; @@ -2133,12 +2157,6 @@ void Client::changeMaximize(bool vertical, bool horizontal, bool adjust) changeMaximize(false, false, false); // restore } - QRect clientArea; - if (isElectricBorderMaximizing()) - clientArea = workspace()->clientArea(MaximizeArea, cursorPos(), desktop()); - else - clientArea = workspace()->clientArea(MaximizeArea, this); - // save sizes for restoring, if maximalizing QSize sz; if (isShade()) @@ -2257,6 +2275,9 @@ void Client::changeMaximize(bool vertical, bool horizontal, bool adjust) restore.moveTop(geom_restore.y()); geom_restore = restore; // relevant for mouse pos calculation, bug #298646 } + if (xSizeHint.flags & PAspect) { + restore.setSize(adjustedSize(restore.size(), SizemodeAny)); + } setGeometry(restore, geom_mode); if (!clientArea.contains(geom_restore.center())) // Not restoring to the same screen Placement::self()->place(this, clientArea);