From d1a8285f818eb7e5c3d6a05709ea21a808490b8c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=B6rg=20Frings-F=C3=BCrst?= Date: Mon, 19 Mar 2018 19:55:58 +0100 Subject: New upstream version 5.1.0 --- app/wlib/gtklib/window.c | 268 ++++++++++++++++++++++++++++++++++++----------- 1 file changed, 209 insertions(+), 59 deletions(-) (limited to 'app/wlib/gtklib/window.c') diff --git a/app/wlib/gtklib/window.c b/app/wlib/gtklib/window.c index 489f35e..65706fd 100644 --- a/app/wlib/gtklib/window.c +++ b/app/wlib/gtklib/window.c @@ -48,6 +48,7 @@ extern wBool_t listHelpStrings; static wControl_p firstWin = NULL, lastWin; static int keyState; static wBool_t gtkBlockEnabled = TRUE; +static wBool_t maximize_at_next_show = FALSE; /* ***************************************************************************** @@ -57,6 +58,44 @@ static wBool_t gtkBlockEnabled = TRUE; ***************************************************************************** */ +/** + * Get the "monitor" size for the window (strictly the nearest or most used monitor) + * Note in OSX there is one giant virtual monitor so this doesn't work to force resize down... + * + */ + +static GdkRectangle getMonitorDimensions(GtkWidget * widget) { + + GdkRectangle monitor_dimensions; + + GdkScreen *screen = NULL; + + int monitor; + + GtkWidget * toplevel = gtk_widget_get_toplevel(widget); + + if (gtk_widget_is_toplevel(GTK_WIDGET(toplevel)) && + gtk_widget_get_parent_window(GTK_WIDGET(toplevel))) { + + GdkWindow * window = GDK_WINDOW(gtk_widget_get_parent_window(GTK_WIDGET(toplevel))); + + screen = gdk_window_get_screen(GDK_WINDOW(window)); + + monitor = gdk_screen_get_monitor_at_window(screen,GDK_WINDOW(window)); + + } else { + + screen = gdk_screen_get_default(); + + monitor = gdk_screen_get_primary_monitor(screen); + + } + + gdk_screen_get_monitor_geometry(screen,monitor,&monitor_dimensions); + + return monitor_dimensions; +} + /** * Get the window size from the resource (.rc) file. The size is saved under the key * SECTIONWINDOWSIZE.window name @@ -71,6 +110,16 @@ static void getWinSize(wWin_p win, const char * nameStr) const char *cp; char *cp1, *cp2; + /* + * Clamp window to be no bigger than one monitor size (to start - the user can always maximize) + */ + + GdkRectangle monitor_dimensions = getMonitorDimensions(GTK_WIDGET(win->gtkwin)); + + wPos_t maxDisplayWidth = monitor_dimensions.width-5; + wPos_t maxDisplayHeight = monitor_dimensions.height-25; + + if ((win->option&F_RESIZE) && (win->option&F_RECALLPOS) && (cp = wPrefGetString(SECTIONWINDOWSIZE, nameStr)) && @@ -84,6 +133,9 @@ static void getWinSize(wWin_p win, const char * nameStr) h = 10; } + if (w > maxDisplayWidth) w = maxDisplayWidth; + if (h > maxDisplayHeight) h = maxDisplayHeight; + win->w = win->origX = w; win->h = win->origY = h; win->option &= ~F_AUTOSIZE; @@ -103,7 +155,7 @@ static void saveSize(wWin_p win) if ((win->option&F_RESIZE) && (win->option&F_RECALLPOS) && gtk_widget_get_visible(GTK_WIDGET(win->gtkwin))) { - char pos_s[20]; + char pos_s[20]; sprintf(pos_s, "%d %d", win->w, win->h-(BORDERSIZE + ((win->option&F_MENUBAR)?MENUH:0))); @@ -121,14 +173,13 @@ static void saveSize(wWin_p win) static void getPos(wWin_p win) { char *cp1, *cp2; - wPos_t gtkDisplayWidth = gdk_screen_width(); - wPos_t gtkDisplayHeight = gdk_screen_height(); + GdkRectangle monitor_dimensions = getMonitorDimensions(GTK_WIDGET(win->gtkwin)); if ((win->option&F_RECALLPOS) && (!win->shown)) { - const char *cp; + const char *cp; if ((cp = wPrefGetString(SECTIONWINDOWPOS, win->nameStr))) { - int x, y; + int x, y; x = strtod(cp, &cp1); @@ -142,12 +193,12 @@ static void getPos(wWin_p win) return; } - if (y > gtkDisplayHeight-win->h) { - y = gtkDisplayHeight-win->h; + if (y > monitor_dimensions.height+monitor_dimensions.y-win->h) { + y = monitor_dimensions.height+monitor_dimensions.y-win->h; } - if (x > gtkDisplayWidth-win->w) { - x = gtkDisplayWidth-win->w; + if (x > monitor_dimensions.width+monitor_dimensions.x-win->w) { + x = monitor_dimensions.width+monitor_dimensions.x-win->w; } if (x <= 0) { @@ -176,7 +227,7 @@ static void savePos(wWin_p win) int x, y; if ((win->option&F_RECALLPOS)) { - char pos_s[20]; + char pos_s[20]; gdk_window_get_position(gtk_widget_get_window(GTK_WIDGET(win->gtkwin)), &x, &y); x -= 5; @@ -216,7 +267,7 @@ void wWinGetSize( } *width = w; - *height = h - BORDERSIZE - ((win->option&F_MENUBAR)?MENUH:0); + *height = h - BORDERSIZE - ((win->option&F_MENUBAR)?win->menu_height:0); } /** @@ -234,8 +285,8 @@ void wWinSetSize( { win->busy = TRUE; win->w = width; - win->h = height + BORDERSIZE + ((win->option&F_MENUBAR)?MENUH:0); - gtk_widget_set_size_request(win->gtkwin, win->w, win->h); + win->h = height + BORDERSIZE + ((win->option&F_MENUBAR)?win->menu_height:0); + //gtk_widget_set_size_request(win->gtkwin, win->w, win->h); gtk_widget_set_size_request(win->widget, win->w, win->h); win->busy = FALSE; } @@ -271,11 +322,15 @@ void wWinShow( gtk_widget_size_request(win->gtkwin, &requisition); if (requisition.width != win->w || requisition.height != win->h) { - gtk_widget_set_size_request(win->gtkwin, win->w, win->h); - gtk_widget_set_size_request(win->widget, win->w, win->h); + //gtk_window_resize(GTK_WINDOW(win->gtkwin), win->w, win->h); + gtk_widget_set_size_request(win->gtkwin, win->w, win->h); + gtk_widget_set_size_request(win->widget, win->w-20, win->h); if (win->option&F_MENUBAR) { - gtk_widget_set_size_request(win->menubar, win->w, MENUH); + gtk_widget_set_size_request(win->menubar, win->w-20, MENUH); + GtkAllocation allocation; + gtk_widget_get_allocation(win->menubar, &allocation); + win->menu_height = allocation.height; } } } @@ -299,6 +354,10 @@ void wWinShow( } else { wlibDoModal(win, TRUE); } + if (maximize_at_next_show) { + gtk_window_maximize(GTK_WINDOW(win->gtkwin)); + maximize_at_next_show = FALSE; + } } else { wFlush(); saveSize(win); @@ -339,6 +398,18 @@ wBool_t wWinIsVisible( return win->shown; } +/** + * Returns whether the window is maximized. + * + * \param win IN window + * \return TRUE if maximized, FALSE otherwise + */ + +wBool_t wWinIsMaximized(wWin_p win) +{ + return win->maximize_initially; +} + /** * Sets the title of to . * @@ -480,6 +551,25 @@ void wWinDoCancel( ****************************************************************************** */ +static int window_redraw( + wWin_p win, + wBool_t doWinProc) +{ + wControl_p b; + + if (win==NULL) { + return FALSE; + } + + for (b=win->first; b != NULL; b = b->next) { + if (b->repaintProc) { + b->repaintProc(b); + } + } + + return FALSE; +} + static gint window_delete_event( GtkWidget *widget, GdkEvent *event, @@ -511,25 +601,6 @@ static gint window_delete_event( return (TRUE); } -static int window_redraw( - wWin_p win, - wBool_t doWinProc) -{ - wControl_p b; - - if (win==NULL) { - return FALSE; - } - - for (b=win->first; b != NULL; b = b->next) { - if (b->repaintProc) { - b->repaintProc(b); - } - } - - return FALSE; -} - static int fixed_expose_event( GtkWidget * widget, GdkEventExpose * event, @@ -542,27 +613,37 @@ static int fixed_expose_event( } } +static int resizeTime(wWin_p win) { + + if (win->resizeW == win->w && win->resizeH == win->h) { // If hasn't changed since last + win->resizeTimer = 0; + return FALSE; //Stop Timer and don't resize + } + if (win->busy==FALSE && win->winProc) { //Always drive once + win->winProc(win, wResize_e, win->data); + win->resizeW = win->w; //Remember this one + win->resizeH = win->h; + } + return TRUE; //Will redrive after another timer interval +} + static int window_configure_event( GtkWidget * widget, GdkEventConfigure * event, wWin_p win) { -// wPos_t h; if (win==NULL) { return FALSE; } - //h = event->height - BORDERSIZE; - - //if (win->option&F_MENUBAR) { - //h -= MENUH; - //} - if (win->option&F_RESIZE) { if (event->width < 10 || event->height < 10) { return TRUE; } + int w = win->w; + int h = win->h; + if (win->w != event->width || win->h != event->height) { win->w = event->width; @@ -577,11 +658,18 @@ static int window_configure_event( } if (win->option&F_MENUBAR) { - gtk_widget_set_size_request(win->menubar, win->w, MENUH); + GtkAllocation allocation; + gtk_widget_get_allocation(win->menubar, &allocation); + win->menu_height= allocation.height; + gtk_widget_set_size_request(win->menubar, win->w-20, win->menu_height); } - - if (win->busy==FALSE && win->winProc) { - win->winProc(win, wResize_e, win->data); + if (win->resizeTimer) { // Already have a timer + return FALSE; + } else { + win->resizeW = w; //Remember where this started + win->resizeH = h; + win->resizeTimer = g_timeout_add(200,(GSourceFunc)resizeTime,win); // 200ms delay + return FALSE; } } } @@ -589,6 +677,38 @@ static int window_configure_event( return FALSE; } +/** + * Event handler for window state changes (maximize) + * Handles maximize event by storing the new state in the internal structure and + * calling the event handler + * + * \param widget gtk widget + * \param event event information + * \param win the wlib internal window data + * \return TRUE if win is valid, + */ + +gboolean window_state_event( + GtkWidget *widget, + GdkEventWindowState *event, + wWin_p win) +{ + if (!win) { + return (FALSE); + } + + win->maximize_initially = FALSE; + + if (event->new_window_state & GDK_WINDOW_STATE_MAXIMIZED) { + win->maximize_initially = TRUE; + } + + if (win->busy==FALSE && win->winProc) { + win->winProc(win, wState_e, win->data); + } + + return TRUE; +} /** * Get current state of shift, ctrl or alt keys. * @@ -680,19 +800,22 @@ static gint window_char_event( ******************************************************************************* */ + /** - * Create a window + * Create a window. + * Default width and height are replaced by values stored in the configuration + * file (.rc) * * \param parent IN parent window * \param winType IN type of window - * \param x IN x position - * \param y IN y position + * \param x IN default width + * \param y IN default height * \param labelStr IN window title - * \param nameStr IN - * \param option IN + * \param nameStr IN name of window + * \param option IN misc options for placement and sizing of window * \param winProc IN window procedure * \param data IN additional data to pass to the window procedure - * \return describe the return value + * \return the newly created window */ static wWin_p wWinCommonCreate( @@ -711,7 +834,9 @@ static wWin_p wWinCommonCreate( w = wlibAlloc(NULL, winType, x, y, labelStr, sizeof *w, data); w->busy = TRUE; w->option = option; - getWinSize(w, nameStr); + w->resizeTimer = 0; + + h = BORDERSIZE; if (w->option&F_MENUBAR) { @@ -728,6 +853,9 @@ static wWin_p wWinCommonCreate( GTK_WINDOW(gtkMainW->gtkwin)); } } + if (winType != W_MAIN) { + getWinSize(w, nameStr); + } if (option & F_HIDE) { gtk_widget_hide(w->gtkwin); @@ -738,6 +866,7 @@ static wWin_p wWinCommonCreate( gtk_window_set_position(GTK_WINDOW(w->gtkwin), GTK_WIN_POS_CENTER_ON_PARENT); } + w->widget = gtk_fixed_new(); if (w->widget == 0) { @@ -748,7 +877,10 @@ static wWin_p wWinCommonCreate( w->menubar = gtk_menu_bar_new(); gtk_container_add(GTK_CONTAINER(w->widget), w->menubar); gtk_widget_show(w->menubar); - gtk_widget_set_size_request(w->menubar, -1, MENUH); + GtkAllocation allocation; + gtk_widget_get_allocation(w->menubar, &allocation); + w->menu_height = allocation.height; + gtk_widget_set_size_request(w->menubar, -1, w->menu_height); } gtk_container_add(GTK_CONTAINER(w->gtkwin), w->widget); @@ -758,14 +890,14 @@ static wWin_p wWinCommonCreate( w->w = 0; w->realY = h; w->h = 0; - } else { + } else if (w->origX != 0){ w->w = w->realX = w->origX; w->h = w->realY = w->origY+h; - gtk_widget_set_size_request(w->gtkwin, w->w, w->h); - gtk_widget_set_size_request(w->widget, w->w, w->h); + gtk_window_set_default_size(GTK_WINDOW(w->gtkwin), w->w, w->h); + //gtk_widget_set_size_request(w->widget, w->w-20, w->h); if (w->option&F_MENUBAR) { - gtk_widget_set_size_request(w->menubar, w->w, MENUH); + gtk_widget_set_size_request(w->menubar, w->w-20, MENUH); } } @@ -777,6 +909,8 @@ static wWin_p wWinCommonCreate( G_CALLBACK(fixed_expose_event), w); g_signal_connect(GTK_OBJECT(w->gtkwin), "configure_event", G_CALLBACK(window_configure_event), w); + g_signal_connect(GTK_OBJECT(w->gtkwin), "window-state-event", + G_CALLBACK(window_state_event), w); g_signal_connect(GTK_OBJECT(w->gtkwin), "key_press_event", G_CALLBACK(window_char_event), w); g_signal_connect(GTK_OBJECT(w->gtkwin), "key_release_event", @@ -813,7 +947,16 @@ static wWin_p wWinCommonCreate( lastWin = (wControl_p)w; gtk_widget_show(w->widget); gtk_widget_realize(w->gtkwin); + GtkAllocation allocation; + gtk_widget_get_allocation(w->gtkwin, &allocation); + w->menu_height = allocation.height; + w->busy = FALSE; + + if (option&F_MAXIMIZE) { + maximize_at_next_show = TRUE; + } + return w; } @@ -846,8 +989,11 @@ wWin_p wWinMainCreate( void * data) /* User context */ { char *pos; + long isMaximized; - if (pos = strchr(name, ';')) { + pos = strchr(name, ';'); + + if (pos) { /* if found, split application name and configuration name */ strcpy(wConfigName, pos + 1); } else { @@ -855,8 +1001,12 @@ wWin_p wWinMainCreate( strcpy(wConfigName, name); } + wPrefGetInteger("draw", "maximized", &isMaximized, 0); + option = option | (isMaximized?F_MAXIMIZE:0); + gtkMainW = wWinCommonCreate(NULL, W_MAIN, x, y, labelStr, nameStr, option, winProc, data); + wDrawColorWhite = wDrawFindColor(0xFFFFFF); wDrawColorBlack = wDrawFindColor(0x000000); return gtkMainW; -- cgit v1.2.3