From 693854a8d56090c283ad60fbe3dc3bf46ab4c1cf Mon Sep 17 00:00:00 2001 From: gambas Date: Wed, 24 Feb 2021 16:21:41 +0100 Subject: [PATCH] Fix management of default minimum size of modal and utility windows. [GB.GTK] * BUG: Fix management of default minimum size of modal and utility windows. [GB.GTK3] * BUG: Fix management of default minimum size of modal and utility windows. [GB.QT4] * BUG: Fix management of default minimum size of modal and utility windows. [GB.QT5] * BUG: Fix management of default minimum size of modal and utility windows. --- gb.gtk/src/gmainwindow.cpp | 31 ++++-- gb.gtk/src/gmainwindow.h | 5 +- gb.qt4/src/CWidget.cpp | 203 ++++--------------------------------- gb.qt4/src/CWindow.cpp | 63 +++++++++++- gb.qt4/src/CWindow.h | 12 ++- 5 files changed, 114 insertions(+), 200 deletions(-) diff --git a/gb.gtk/src/gmainwindow.cpp b/gb.gtk/src/gmainwindow.cpp index 7ff1527e1..b8ac31f24 100644 --- a/gb.gtk/src/gmainwindow.cpp +++ b/gb.gtk/src/gmainwindow.cpp @@ -172,7 +172,7 @@ static gboolean cb_configure(GtkWidget *widget, GdkEventConfigure *event, gMainW } #ifdef DEBUG_RESIZE - fprintf(stderr, "cb_configure: %s: (%d %d %d %d) -> (%d/%d %d/%d %d %d) window = %p resized = %d send_event = %d\n", data->name(), data->bufX, data->bufY, data->bufW, data->bufH, x, event->x, y, event->y, event->width, event->height, event->window, data->_resized, event->send_event); + fprintf(stderr, "cb_configure: %s: (%d %d %d %d) -> (%d/%d %d/%d %d %d) window = %p resized = %d send_event = %d\n", data->name(), data->bufX, data->bufY, data->bufW, data->bufH, x, event->x, y, event->y, event->width, event->height, event->window, data->_event_resized, event->send_event); #endif if (x != data->bufX || y != data->bufY) @@ -191,9 +191,9 @@ static gboolean cb_configure(GtkWidget *widget, GdkEventConfigure *event, gMainW w = event->width; h = event->height; - if ((w != data->bufW) || (h != data->bufH) || (data->_resized) || !event->window) + if ((w != data->bufW) || (h != data->bufH) || (data->_event_resized) || !event->window) { - data->_resized = false; + data->_event_resized = false; data->bufW = w; data->bufH = h; #ifdef DEBUG_RESIZE @@ -224,13 +224,13 @@ static void cb_resize(GtkWidget *wid, GdkRectangle *a, gMainWindow *data) w -= data->_csd_w; h -= data->_csd_h; - if (w != data->bufW || h != data->bufH || data->_resized) + if (w != data->bufW || h != data->bufH || data->_event_resized) { #ifdef DEBUG_RESIZE fprintf(stderr, "cb_resize: %s: %d %d\n", data->name(), w, h); #endif - data->_resized = false; + data->_event_resized = false; data->bufW = w; data->bufH = h; data->emitResize(); // later @@ -249,13 +249,13 @@ static void cb_resize_layout(GtkWidget *wid, GdkRectangle *a, gMainWindow *data) data->calcCsdSize(); - if (w != data->bufW || h != data->bufH || data->_resized) + if (w != data->bufW || h != data->bufH || data->_event_resized) { #ifdef DEBUG_RESIZE - fprintf(stderr, "cb_resize_layout: %s: %d x %d / resize = %d\n", data->name(), w, h, data->_resized); + fprintf(stderr, "cb_resize_layout: %s: %d x %d / resize = %d\n", data->name(), w, h, data->_event_resized); #endif - data->_resized = false; + data->_event_resized = false; data->bufW = w; data->bufH = h; data->emitResize(); // later @@ -389,7 +389,7 @@ void gMainWindow::initialize() _title = NULL; _current = NULL; _resize_last_w = _resize_last_h = -1; - _min_w = _min_h = 0; + _min_w = _min_h = _default_min_w = _default_min_h = 0; _csd_w = _csd_h = -1; _opened = false; @@ -398,6 +398,7 @@ void gMainWindow::initialize() _mask = false; _masked = false; _resized = false; + _event_resized = false; _top_only = false; _closing = false; _closed = false; @@ -695,10 +696,18 @@ bool gMainWindow::resize(int w, int h) bufW = w < 0 ? 0 : w; bufH = h < 0 ? 0 : h; + // we check for _resized to ignore the first resize() + if (_resized && _default_min_w <= 0 && _default_min_h <= 0) + { + _default_min_w = w; + _default_min_h = h; + } + updateSize(); } _resized = true; + _event_resized = true; return false; } @@ -1911,8 +1920,8 @@ void gMainWindow::setGeometryHints() { if (!min_w && !min_h) { - min_w = width(); - min_h = height(); + min_w = _default_min_w; + min_h = _default_min_h; } } diff --git a/gb.gtk/src/gmainwindow.h b/gb.gtk/src/gmainwindow.h index ee6c3aaa9..731df0af3 100644 --- a/gb.gtk/src/gmainwindow.h +++ b/gb.gtk/src/gmainwindow.h @@ -183,13 +183,14 @@ public: int _min_w; int _min_h; + int _default_min_w; + int _default_min_h; int _csd_w; int _csd_h; unsigned _mask : 1; unsigned _top_only : 1; - unsigned _resized : 1; unsigned _persistent : 1; unsigned _sticky : 1; unsigned _opened : 1; @@ -211,6 +212,8 @@ public: unsigned _transparent : 1; unsigned _no_take_focus : 1; unsigned _moved : 1; + unsigned _resized : 1; + unsigned _event_resized : 1; unsigned _resizable : 1; unsigned _unmap : 1; unsigned _initMenuBar : 1; diff --git a/gb.qt4/src/CWidget.cpp b/gb.qt4/src/CWidget.cpp index 4d3f73521..6bfa2cac3 100644 --- a/gb.qt4/src/CWidget.cpp +++ b/gb.qt4/src/CWidget.cpp @@ -534,36 +534,7 @@ void CWIDGET_destroy(CWIDGET *_object) //#define WIDGET_SIZE(_c) ((WIDGET->isA("MyMainWindow")) ? ((CWINDOW *)_object)->_c : WIDGET->pos()._c()) //#endif -#if 0 -static QWidget *get_widget(void *_object) -{ - QWidget *w = THIS->widget; - //if (w->isVisible() && CWIDGET_test_flag(THIS, WF_PARENT_GEOMETRY)) - // w = w->parentWidget(); - - if (WIDGET->isA("MyMainWindow")) - { - CWINDOW *win = (CWINDOW *)THIS; - if (win->toplevel && win->embedded) - { - QWidget *p = w->parentWidget(); - if (p && p->isA("QWorkspaceChild")) - w = p; - } - } - - return w; -} - -static QWidget *get_widget_resize(void *_object) -{ - QWidget *w = THIS->widget; - return w; -} -#endif - #define get_widget(_object) QWIDGET(_object) -#define get_widget_resize(_object) QWIDGET(_object) static void arrange_parent(CWIDGET *_object) { @@ -599,178 +570,46 @@ static void CWIDGET_after_geometry_change(void *_object, bool arrange) arrange_parent(THIS); } -void CWIDGET_move(void *_object, int x, int y) -{ - QWidget *wid = get_widget(THIS); - - if (GB.Is(THIS, CLASS_Window)) - { - CWINDOW *win = (CWINDOW *)_object; - win->x = x; - win->y = y; - if (!win->moved && (x || y)) - win->moved = true; - } - - if (wid) - { - if (x == wid->x() && y == wid->y()) - return; - - wid->move(x, y); - } - - CWIDGET_after_geometry_change(THIS, false); -} - -/* -void CWIDGET_move_cached(void *_object, int x, int y) -{ - if (GB.Is(THIS, CLASS_Window)) - { - ((CWINDOW *)_object)->x = x; - ((CWINDOW *)_object)->y = y; - } - - CWIDGET_after_geometry_change(THIS, false); -} -*/ - -void CWIDGET_resize(void *_object, int w, int h) -{ - QWidget *wid = get_widget_resize(THIS); - bool window, toplevel; - bool resizable = true; - bool decide_w, decide_h; - - if (!wid) - return; - - window = GB.Is(THIS, CLASS_Window); - toplevel = wid->isTopLevel(); - - if (w < 0 && h < 0) - return; - - CWIDGET_check_visibility(THIS); - - CCONTAINER_decide(THIS, &decide_w, &decide_h); - - if (w < 0 || decide_w) - w = wid->width(); - - if (h < 0 || decide_h) - h = wid->height(); - - if (w == wid->width() && h == wid->height()) - return; - - if (window) - { - MyMainWindow *win = (MyMainWindow *)wid; - - if (toplevel) - { - resizable = win->isResizable(); - if (!resizable) - win->setResizable(true); - } - - wid->resize(qMax(0, w), qMax(0, h)); - - ((CWINDOW *)_object)->w = w; - ((CWINDOW *)_object)->h = h; - win->configure(); - - if (toplevel) - ((MyMainWindow *)wid)->setResizable(resizable); - } - else - wid->resize(qMax(0, w), qMax(0, h)); - - CWIDGET_after_geometry_change(THIS, true); -} - - void CWIDGET_move_resize(void *_object, int x, int y, int w, int h) { - QWidget *wid = get_widget(THIS); - bool window, toplevel; + QWidget *wid = WIDGET; - if (wid) + if (GB.Is(THIS, CLASS_Window)) + { + CWINDOW_move_resize(THIS, x, y, w, h); + } + else { if (w < 0) w = wid->width(); if (h < 0) h = wid->height(); - } - - window = GB.Is(THIS, CLASS_Window); - toplevel = wid->isTopLevel(); - - if (window) - { - CWINDOW *win = (CWINDOW *)_object; - win->x = x; - win->y = y; - win->w = w; - win->h = h; - - if (!win->moved && (x || y)) - win->moved = true; - } - - CWIDGET_check_visibility(THIS); - - if (wid) - { - if (w < 0) // || decide_w) - w = wid->width(); - - if (h < 0) // || decide_h) - h = wid->height(); if (x == wid->x() && y == wid->y() && w == wid->width() && h == wid->height()) return; - - if (window) - { - MyMainWindow *win = (MyMainWindow *)wid; - bool resize = w != wid->width() || h != wid->height(); - bool resizable = true; - if (x != wid->x() || y != wid->y()) - wid->move(x, y); - - if (resize) - { - if (toplevel) - { - resizable = win->isResizable(); - if (!resizable) - win->setResizable(true); - } - - wid->resize(qMax(0, w), qMax(0, h)); - - if (toplevel) - win->setResizable(resizable); - - win->configure(); - } - } - else - wid->setGeometry(x, y, qMax(0, w), qMax(0, h)); + wid->setGeometry(x, y, w, h); } + CWIDGET_check_visibility(THIS); CWIDGET_after_geometry_change(THIS, true); } +void CWIDGET_move(void *_object, int x, int y) +{ + CWIDGET_move_resize(THIS, x, y, -1, -1); +} + +void CWIDGET_resize(void *_object, int w, int h) +{ + CWIDGET_move_resize(THIS, COORD(x), COORD(y), w, h); +} + #if 0 void CWIDGET_move_resize(void *_object, int x, int y, int w, int h) { - QWidget *wid = get_widget(THIS); + QWidget *wid = WIDGET; if (wid) { @@ -915,7 +754,7 @@ END_PROPERTY BEGIN_PROPERTY(Control_Width) if (READ_PROPERTY) - GB.ReturnInteger(get_widget_resize(THIS)->width()); + GB.ReturnInteger(WIDGET->width()); else CWIDGET_resize(_object, VPROP(GB_INTEGER), -1); @@ -925,7 +764,7 @@ END_PROPERTY BEGIN_PROPERTY(Control_Height) if (READ_PROPERTY) - GB.ReturnInteger(get_widget_resize(THIS)->height()); + GB.ReturnInteger(WIDGET->height()); else CWIDGET_resize(_object, -1, VPROP(GB_INTEGER)); diff --git a/gb.qt4/src/CWindow.cpp b/gb.qt4/src/CWindow.cpp index e585158fe..ea743ba1b 100644 --- a/gb.qt4/src/CWindow.cpp +++ b/gb.qt4/src/CWindow.cpp @@ -315,8 +315,6 @@ void CWINDOW_ensure_active_window() } -//-- Window --------------------------------------------------------------- - static void show_later(CWINDOW *_object) { /* If the user has explicitely hidden the window since the posting of this routines @@ -332,6 +330,63 @@ static void show_later(CWINDOW *_object) GB.Unref(POINTER(&_object)); } + +void CWINDOW_move_resize(void *_object, int x, int y, int w, int h) +{ + bool move, resize; + + move = x != THIS->x || y != THIS->y || !THIS->moved; + + if (w < 0) + w = THIS->w; + + if (h < 0) + h = THIS->h; + + resize = w != THIS->w || h != THIS->h || !THIS->resized; + + if (!move && !resize) + return; + + THIS->x = x; + THIS->y = y; + THIS->w = w; + THIS->h = h; + + if (!THIS->moved && (x || y)) + THIS->moved = TRUE; + + if (move) + WINDOW->move(x, y); + + if (resize) + { + bool resizable = false; + + if (WINDOW->isTopLevel() && !WINDOW->isResizable()) + { + resizable = true; + WINDOW->setResizable(true); + } + + WINDOW->resize(w, h); + + THIS->resized = TRUE; + if (THIS->default_minw <= 0 && THIS->default_minh <= 0) + { + THIS->default_minw = w; + THIS->default_minh = h; + } + + if (resizable) + WINDOW->setResizable(false); + + WINDOW->configure(); + } +} + +//-- Window --------------------------------------------------------------- + BEGIN_METHOD(Window_new, GB_OBJECT parent) MyMainWindow *win = 0; @@ -1712,8 +1767,8 @@ void MyMainWindow::setGeometryHints() { if (!minw && !minh) { - minw = width(); - minh = height(); + minw = THIS->default_minw; + minh = THIS->default_minh; } } setMinimumSize(minw, minh); diff --git a/gb.qt4/src/CWindow.h b/gb.qt4/src/CWindow.h index 3416c6485..5fbfeb64b 100644 --- a/gb.qt4/src/CWindow.h +++ b/gb.qt4/src/CWindow.h @@ -52,21 +52,25 @@ typedef MyContainer *container; CARRANGEMENT arrangement; QMenuBar *menuBar; - int ret; CPICTURE *icon; CPICTURE *picture; CWIDGET *focus; QPushButton *defaultButton; QPushButton *cancelButton; + int ret; int loopLevel; + int x; int y; int w; int h; int minw; int minh; + int default_minw; + int default_minh; int last_resize_w; int last_resize_h; + unsigned toplevel : 1; unsigned persistent : 1; unsigned closed : 1; @@ -74,6 +78,7 @@ typedef unsigned xembed : 1; unsigned stacking : 2; unsigned skipTaskbar : 1; + unsigned masked : 1; unsigned reallyMasked : 1; unsigned opened : 1; @@ -82,13 +87,16 @@ typedef unsigned minsize : 1; unsigned title : 1; unsigned stateChange : 1; + unsigned closing : 1; unsigned hideMenuBar : 1; unsigned showMenuBar : 1; unsigned sticky : 1; unsigned noTakeFocus : 1; unsigned moved : 1; + unsigned resized : 1; unsigned popup : 1; + unsigned modal : 1; } CWINDOW; @@ -273,6 +281,6 @@ void CWINDOW_ensure_active_window(); bool CWINDOW_must_quit(); bool CWINDOW_close_all(bool main); void CWINDOW_delete_all(bool main); -//void CWINDOW_fix_menubar(CWINDOW *window); +void CWINDOW_move_resize(void *_object, int x, int y, int w, int h); #endif