diff options
author | rathnor <rathnor> | 2003-09-29 14:58:15 (GMT) |
---|---|---|
committer | rathnor <rathnor> | 2003-09-29 14:58:15 (GMT) |
commit | 81378f9494db4ab1d033947532d7fac968095ecd (patch) | |
tree | 0980a0ed9e2ebcbb2d7b7c88d6fbe1d98ab06dd2 | |
parent | 15dfe811124e3f1be7d9a802290372427dae5afb (diff) | |
download | fluxbox_paul-81378f9494db4ab1d033947532d7fac968095ecd.zip fluxbox_paul-81378f9494db4ab1d033947532d7fac968095ecd.tar.bz2 |
fix handling of base_Width/height hints in wm_normal_hints
- fixes abiword resize issues
-rw-r--r-- | ChangeLog | 3 | ||||
-rw-r--r-- | src/WinClient.cc | 72 | ||||
-rw-r--r-- | src/WinClient.hh | 12 | ||||
-rw-r--r-- | src/Window.cc | 59 | ||||
-rw-r--r-- | src/Window.hh | 5 |
5 files changed, 95 insertions, 56 deletions
@@ -1,6 +1,9 @@ | |||
1 | (Format: Year/Month/Day) | 1 | (Format: Year/Month/Day) |
2 | Changes for 0.9.6: | 2 | Changes for 0.9.6: |
3 | *03/09/29: | 3 | *03/09/29: |
4 | * Fix resize calculations, particularly wrt base_width/height (Simon) | ||
5 | - fixes abiword resize issues | ||
6 | Window.hh/cc WinClient.hh/cc | ||
4 | * Nearest-quadrant resizing (Thanks Mathias Gumz) | 7 | * Nearest-quadrant resizing (Thanks Mathias Gumz) |
5 | Window.hh/cc Screen.hh/cc FbWinFrameTheme.hh/cc | 8 | Window.hh/cc Screen.hh/cc FbWinFrameTheme.hh/cc |
6 | * Update from Han | 9 | * Update from Han |
diff --git a/src/WinClient.cc b/src/WinClient.cc index 614b7a4..e032304 100644 --- a/src/WinClient.cc +++ b/src/WinClient.cc | |||
@@ -19,7 +19,7 @@ | |||
19 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER | 19 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
20 | // DEALINGS IN THE SOFTWARE. | 20 | // DEALINGS IN THE SOFTWARE. |
21 | 21 | ||
22 | // $Id: WinClient.cc,v 1.27 2003/09/24 14:02:25 rathnor Exp $ | 22 | // $Id: WinClient.cc,v 1.28 2003/09/29 14:58:15 rathnor Exp $ |
23 | 23 | ||
24 | #include "WinClient.hh" | 24 | #include "WinClient.hh" |
25 | 25 | ||
@@ -43,7 +43,7 @@ WinClient::WinClient(Window win, BScreen &screen, FluxboxWindow *fbwin):FbTk::Fb | |||
43 | window_group(0), | 43 | window_group(0), |
44 | x(0), y(0), old_bw(0), | 44 | x(0), y(0), old_bw(0), |
45 | min_width(1), min_height(1), | 45 | min_width(1), min_height(1), |
46 | max_width(1), max_height(1), | 46 | max_width(0), max_height(0), |
47 | width_inc(1), height_inc(1), | 47 | width_inc(1), height_inc(1), |
48 | min_aspect_x(1), min_aspect_y(1), | 48 | min_aspect_x(1), min_aspect_y(1), |
49 | max_aspect_x(1), max_aspect_y(1), | 49 | max_aspect_x(1), max_aspect_y(1), |
@@ -434,8 +434,23 @@ void WinClient::updateWMNormalHints() { | |||
434 | if (sizehint.flags & PMinSize) { | 434 | if (sizehint.flags & PMinSize) { |
435 | min_width = sizehint.min_width; | 435 | min_width = sizehint.min_width; |
436 | min_height = sizehint.min_height; | 436 | min_height = sizehint.min_height; |
437 | } else | 437 | if (!(sizehint.flags & PBaseSize)) { |
438 | base_width = min_width; | ||
439 | base_height = min_height; | ||
440 | } | ||
441 | } else { | ||
438 | min_width = min_height = 1; | 442 | min_width = min_height = 1; |
443 | base_width = base_height = 0; | ||
444 | } | ||
445 | |||
446 | if (sizehint.flags & PBaseSize) { | ||
447 | base_width = sizehint.base_width; | ||
448 | base_height = sizehint.base_height; | ||
449 | if (!(sizehint.flags & PMinSize)) { | ||
450 | min_width = base_width; | ||
451 | min_height = base_height; | ||
452 | } | ||
453 | } // default set in PMinSize | ||
439 | 454 | ||
440 | if (sizehint.flags & PMaxSize) { | 455 | if (sizehint.flags & PMaxSize) { |
441 | max_width = sizehint.max_width; | 456 | max_width = sizehint.max_width; |
@@ -460,12 +475,6 @@ void WinClient::updateWMNormalHints() { | |||
460 | min_aspect_x = min_aspect_y = | 475 | min_aspect_x = min_aspect_y = |
461 | max_aspect_x = max_aspect_y = 1; | 476 | max_aspect_x = max_aspect_y = 1; |
462 | 477 | ||
463 | if (sizehint.flags & PBaseSize) { | ||
464 | base_width = sizehint.base_width; | ||
465 | base_height = sizehint.base_height; | ||
466 | } else | ||
467 | base_width = base_height = 0; | ||
468 | |||
469 | if (sizehint.flags & PWinGravity) | 478 | if (sizehint.flags & PWinGravity) |
470 | m_win_gravity = sizehint.win_gravity; | 479 | m_win_gravity = sizehint.win_gravity; |
471 | else | 480 | else |
@@ -605,3 +614,48 @@ void WinClient::updateWMProtocols() { | |||
605 | } | 614 | } |
606 | 615 | ||
607 | } | 616 | } |
617 | |||
618 | |||
619 | /** | ||
620 | * Changes width and height to the nearest (lower) value | ||
621 | * that conforms to it's size hints. | ||
622 | * | ||
623 | * display_* give the values that would be displayed | ||
624 | * to the user when resizing. | ||
625 | * We use pointers for display_* since they are optional. | ||
626 | * | ||
627 | * See ICCCM section 4.1.2.3 | ||
628 | */ | ||
629 | void WinClient::applySizeHints(int &width, int &height, | ||
630 | int *display_width, int *display_height) { | ||
631 | |||
632 | int i = width, j = height; | ||
633 | |||
634 | // Check minimum size | ||
635 | if (width < 0 || width < min_width) | ||
636 | width = min_width; | ||
637 | |||
638 | if (height < 0 || height < min_height) | ||
639 | height = min_height; | ||
640 | |||
641 | // Check maximum size | ||
642 | if (max_width > 0 && width > max_width) | ||
643 | width = max_width; | ||
644 | |||
645 | if (max_height > 0 && height > max_height) | ||
646 | height = max_height; | ||
647 | |||
648 | // enforce incremental size limits, wrt base size | ||
649 | // only calculate this if we really need to | ||
650 | i = (width - base_width) / width_inc; | ||
651 | width = i*width_inc + base_width; | ||
652 | |||
653 | j = (height - base_height) / height_inc; | ||
654 | height = j*height_inc + base_height; | ||
655 | |||
656 | if (display_width) | ||
657 | *display_width = i; | ||
658 | |||
659 | if (display_height) | ||
660 | *display_height = j; | ||
661 | } | ||
diff --git a/src/WinClient.hh b/src/WinClient.hh index 6bdfe3f..c93a76d 100644 --- a/src/WinClient.hh +++ b/src/WinClient.hh | |||
@@ -19,7 +19,7 @@ | |||
19 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER | 19 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
20 | // DEALINGS IN THE SOFTWARE. | 20 | // DEALINGS IN THE SOFTWARE. |
21 | 21 | ||
22 | // $Id: WinClient.hh,v 1.14 2003/09/21 12:49:48 rathnor Exp $ | 22 | // $Id: WinClient.hh,v 1.15 2003/09/29 14:58:15 rathnor Exp $ |
23 | 23 | ||
24 | #ifndef WINCLIENT_HH | 24 | #ifndef WINCLIENT_HH |
25 | #define WINCLIENT_HH | 25 | #define WINCLIENT_HH |
@@ -102,6 +102,16 @@ public: | |||
102 | void updateWMHints(); | 102 | void updateWMHints(); |
103 | void updateWMNormalHints(); | 103 | void updateWMNormalHints(); |
104 | 104 | ||
105 | /** | ||
106 | * Changes width and height to the nearest (lower) value | ||
107 | * that conforms to it's size hints. | ||
108 | * | ||
109 | * display_* give the values that would be displayed | ||
110 | * to the user when resizing. | ||
111 | * We use pointers for display_* since they are optional. | ||
112 | */ | ||
113 | void applySizeHints(int &width, int &height, int *display_width = 0, int *display_height = 0); | ||
114 | |||
105 | // grouping is tracked by remembering the window to the left in the group | 115 | // grouping is tracked by remembering the window to the left in the group |
106 | Window getGroupLeftWindow() const; | 116 | Window getGroupLeftWindow() const; |
107 | void setGroupLeftWindow(Window win); | 117 | void setGroupLeftWindow(Window win); |
diff --git a/src/Window.cc b/src/Window.cc index 193f689..e6ff0c6 100644 --- a/src/Window.cc +++ b/src/Window.cc | |||
@@ -22,7 +22,7 @@ | |||
22 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER | 22 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
23 | // DEALINGS IN THE SOFTWARE. | 23 | // DEALINGS IN THE SOFTWARE. |
24 | 24 | ||
25 | // $Id: Window.cc,v 1.235 2003/09/29 12:53:58 rathnor Exp $ | 25 | // $Id: Window.cc,v 1.236 2003/09/29 14:58:15 rathnor Exp $ |
26 | 26 | ||
27 | #include "Window.hh" | 27 | #include "Window.hh" |
28 | 28 | ||
@@ -2437,11 +2437,11 @@ void FluxboxWindow::motionNotifyEvent(XMotionEvent &me) { | |||
2437 | 2437 | ||
2438 | fixsize(&gx, &gy); | 2438 | fixsize(&gx, &gy); |
2439 | 2439 | ||
2440 | // draw resize rectangle | 2440 | // draw resize rectangle |
2441 | parent().drawRectangle(screen().rootTheme().opGC(), | 2441 | parent().drawRectangle(screen().rootTheme().opGC(), |
2442 | m_last_resize_x, m_last_resize_y, | 2442 | m_last_resize_x, m_last_resize_y, |
2443 | m_last_resize_w - 1 + 2 * frame().window().borderWidth(), | 2443 | m_last_resize_w - 1 + 2 * frame().window().borderWidth(), |
2444 | m_last_resize_h - 1 + 2 * frame().window().borderWidth()); | 2444 | m_last_resize_h - 1 + 2 * frame().window().borderWidth()); |
2445 | 2445 | ||
2446 | if (screen().doShowWindowPos()) | 2446 | if (screen().doShowWindowPos()) |
2447 | screen().showGeometry(gx, gy); | 2447 | screen().showGeometry(gx, gy); |
@@ -3166,7 +3166,7 @@ void FluxboxWindow::downsize() { | |||
3166 | } | 3166 | } |
3167 | 3167 | ||
3168 | 3168 | ||
3169 | void FluxboxWindow::fixsize(int *gx, int *gy) { | 3169 | void FluxboxWindow::fixsize(int *user_w, int *user_h) { |
3170 | int titlebar_height = (decorations.titlebar ? | 3170 | int titlebar_height = (decorations.titlebar ? |
3171 | frame().titlebar().height() + | 3171 | frame().titlebar().height() + |
3172 | frame().titlebar().borderWidth() : 0); | 3172 | frame().titlebar().borderWidth() : 0); |
@@ -3177,49 +3177,20 @@ void FluxboxWindow::fixsize(int *gx, int *gy) { | |||
3177 | 3177 | ||
3178 | // dx is new width = current width + difference between new and old x values | 3178 | // dx is new width = current width + difference between new and old x values |
3179 | //int dx = frame().width() + frame().x() - m_last_resize_x; | 3179 | //int dx = frame().width() + frame().x() - m_last_resize_x; |
3180 | int dx = m_last_resize_w - m_client->base_width; | 3180 | int dw = m_last_resize_w; |
3181 | 3181 | ||
3182 | // dy = new height (w/o decorations), similarly | 3182 | // dy = new height (w/o decorations), similarly |
3183 | int dy = m_last_resize_h - m_client->base_height - decoration_height; | 3183 | int dh = m_last_resize_h - decoration_height; |
3184 | 3184 | ||
3185 | // check minimum size | 3185 | m_client->applySizeHints(dw, dh, user_w, user_h); |
3186 | if (dx < static_cast<signed int>(m_client->min_width)) | ||
3187 | dx = m_client->min_width; | ||
3188 | if (dy < static_cast<signed int>(m_client->min_height)) | ||
3189 | dy = m_client->min_height; | ||
3190 | |||
3191 | // check maximum size | ||
3192 | if (m_client->max_width > 0 && dx > static_cast<signed int>(m_client->max_width)) | ||
3193 | dx = m_client->max_width; | ||
3194 | if (m_client->max_height > 0 && dy > static_cast<signed int>(m_client->max_height)) | ||
3195 | dy = m_client->max_height; | ||
3196 | |||
3197 | // make sure we have valid increment | ||
3198 | if (m_client->width_inc == 0) | ||
3199 | m_client->width_inc = 1; | ||
3200 | if (m_client->height_inc == 0) | ||
3201 | m_client->height_inc = 1; | ||
3202 | |||
3203 | // set snapping | ||
3204 | dx /= m_client->width_inc; | ||
3205 | dy /= m_client->height_inc; | ||
3206 | |||
3207 | // set return values | ||
3208 | if (gx != 0) | ||
3209 | *gx = dx; | ||
3210 | if (gy != 0) | ||
3211 | *gy = dy; | ||
3212 | |||
3213 | // snapping | ||
3214 | dx = dx * m_client->width_inc + m_client->base_width; | ||
3215 | dy = dy * m_client->height_inc + m_client->base_height + decoration_height; | ||
3216 | 3186 | ||
3217 | // update last resize | 3187 | // update last resize |
3218 | m_last_resize_w = dx; | 3188 | m_last_resize_w = dw; |
3219 | m_last_resize_h = dy; | 3189 | m_last_resize_h = dh + decoration_height; |
3220 | 3190 | ||
3191 | // move X if necessary | ||
3221 | if (m_resize_corner == LEFTTOP || m_resize_corner == LEFTBOTTOM) { | 3192 | if (m_resize_corner == LEFTTOP || m_resize_corner == LEFTBOTTOM) { |
3222 | m_last_resize_x = frame().x() + frame().width() - m_last_resize_w; | 3193 | m_last_resize_x = frame().x() + frame().width() - m_last_resize_w; |
3223 | } | 3194 | } |
3224 | 3195 | ||
3225 | if (m_resize_corner == LEFTTOP || m_resize_corner == RIGHTTOP) { | 3196 | if (m_resize_corner == LEFTTOP || m_resize_corner == RIGHTTOP) { |
diff --git a/src/Window.hh b/src/Window.hh index e023253..9d94166 100644 --- a/src/Window.hh +++ b/src/Window.hh | |||
@@ -22,7 +22,7 @@ | |||
22 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER | 22 | // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
23 | // DEALINGS IN THE SOFTWARE. | 23 | // DEALINGS IN THE SOFTWARE. |
24 | 24 | ||
25 | // $Id: Window.hh,v 1.96 2003/09/29 12:53:58 rathnor Exp $ | 25 | // $Id: Window.hh,v 1.97 2003/09/29 14:58:15 rathnor Exp $ |
26 | 26 | ||
27 | #ifndef WINDOW_HH | 27 | #ifndef WINDOW_HH |
28 | #define WINDOW_HH | 28 | #define WINDOW_HH |
@@ -398,7 +398,8 @@ private: | |||
398 | 398 | ||
399 | // modifies left and top if snap is necessary | 399 | // modifies left and top if snap is necessary |
400 | void doSnapping(int &left, int &top); | 400 | void doSnapping(int &left, int &top); |
401 | void fixsize(int *x = 0, int *y = 0); | 401 | // user_w/h return the values that should be shown to the user |
402 | void fixsize(int *user_w = 0, int *user_h = 0); | ||
402 | void resizeClient(WinClient &client, unsigned int width, unsigned int height); | 403 | void resizeClient(WinClient &client, unsigned int width, unsigned int height); |
403 | /// sends configurenotify to all clients | 404 | /// sends configurenotify to all clients |
404 | void sendConfigureNotify(bool send_to_netizens = true); | 405 | void sendConfigureNotify(bool send_to_netizens = true); |