#ifndef _WX_GTK_FRAME_H_
#define _WX_GTK_FRAME_H_
-//-----------------------------------------------------------------------------
-// classes
-//-----------------------------------------------------------------------------
-
-class WXDLLIMPEXP_FWD_CORE wxMDIChildFrame;
-class WXDLLIMPEXP_FWD_CORE wxMDIClientWindow;
-class WXDLLIMPEXP_FWD_CORE wxMenu;
-class WXDLLIMPEXP_FWD_CORE wxMenuBar;
-class WXDLLIMPEXP_FWD_CORE wxToolBar;
-class WXDLLIMPEXP_FWD_CORE wxStatusBar;
-
//-----------------------------------------------------------------------------
// wxFrame
//-----------------------------------------------------------------------------
// --------------------------
// GTK callbacks
- virtual void GtkOnSize();
virtual void OnInternalIdle();
- bool m_menuBarDetached;
- int m_menuBarHeight;
- bool m_toolBarDetached;
-
protected:
// common part of all ctors
void Init();
#if wxUSE_MENUS_NATIVE
virtual void DetachMenuBar();
virtual void AttachMenuBar(wxMenuBar *menubar);
- // Whether frame has a menubar showing
- // (needed to deal with perverted MDI menubar handling)
- virtual bool HasVisibleMenubar() const;
-
-public:
- // Menu size is dynamic now, call this whenever it might change.
- void UpdateMenuBarSize();
#endif // wxUSE_MENUS_NATIVE
private:
#include "wx/frame.h"
+class WXDLLIMPEXP_FWD_CORE wxMDIChildFrame;
+class WXDLLIMPEXP_FWD_CORE wxMDIClientWindow;
+
//-----------------------------------------------------------------------------
// wxMDIParentFrame
//-----------------------------------------------------------------------------
wxMDIClientWindow *m_clientWindow;
bool m_justInserted;
- virtual void GtkOnSize();
virtual void OnInternalIdle();
protected:
void Init();
- virtual bool HasVisibleMenubar() const;
+ virtual void DoGetClientSize(int* width, int* height) const;
private:
friend class wxMDIChildFrame;
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
-#ifndef __GTKMINIFRAMEH__
-#define __GTKMINIFRAMEH__
+#ifndef _WX_GTK_MINIFRAME_H_
+#define _WX_GTK_MINIFRAME_H_
-#include "wx/defs.h"
-
-#if wxUSE_MINIFRAME
-
-#include "wx/object.h"
#include "wx/bitmap.h"
#include "wx/frame.h"
-//-----------------------------------------------------------------------------
-// classes
-//-----------------------------------------------------------------------------
-
-class WXDLLIMPEXP_FWD_CORE wxMiniFrame;
-
//-----------------------------------------------------------------------------
// wxMiniFrame
//-----------------------------------------------------------------------------
const wxString& name = wxFrameNameStr);
virtual void SetTitle( const wxString &title );
+
+protected:
+ virtual void DoGetClientSize(int* width, int* height) const;
+
// implementation
-
+public:
bool m_isDragging;
int m_oldX,m_oldY;
int m_diffX,m_diffY;
wxBitmap m_closeButton;
+ int m_miniEdge;
+ int m_miniTitle;
};
-#endif
-
-#endif
- // __GTKMINIFRAMEH__
+#endif // _WX_GTK_MINIFRAME_H_
{ (void)Create(parent, flags); }
bool Create(wxWindow *parent, int flags = wxBORDER_NONE);
- virtual bool Show( bool show = TRUE );
+ virtual bool Show(bool show = true);
// implementation
// --------------
- virtual void OnInternalIdle();
-
// GTK time when connecting to button_press signal
wxUint32 m_time;
-
protected:
- void GtkOnSize();
-
virtual void DoSetSize(int x, int y,
int width, int height,
int sizeFlags = wxSIZE_AUTO);
virtual void DoMoveWindow(int x, int y, int width, int height);
private:
- bool m_sizeSet;
-
+#ifdef __WXUNIVERSAL__
DECLARE_EVENT_TABLE()
+#endif
DECLARE_DYNAMIC_CLASS(wxPopupWindow)
};
// --------------------------
// GTK callbacks
- virtual void GtkOnSize();
virtual void OnInternalIdle();
// do *not* call this to iconize the frame, this is a private function!
void SetIconizeState(bool iconic);
- int m_miniEdge,
- m_miniTitle;
GtkWidget *m_mainWidget;
bool m_fsIsShowing; /* full screen */
int m_gdkFunc,
m_gdkDecor;
- bool m_sizeSet;
-
// private gtk_timeout_add result for mimicing wxUSER_ATTENTION_INFO and
// wxUSER_ATTENTION_ERROR difference, -2 for no hint, -1 for ERROR hint, rest for GtkTimeout handle.
int m_urgency_hint;
// return the size of the window without WM decorations
void GTKDoGetSize(int *width, int *height) const;
- void GtkUpdateSize() { m_sizeSet = false; }
-
// whether frame extents are accurate
virtual bool IsDecorCacheable() const;
// string shown in the title bar
wxString m_title;
+private:
// is the frame currently iconized?
bool m_isIconized;
virtual bool IsRetained() const;
virtual void SetFocus();
-
+
// hint from wx to native GTK+ tab traversal code
virtual void SetCanFocus(bool canFocus);
// return true if the window is of a standard (i.e. not wxWidgets') class
bool IsOfStandardClass() const { return m_wxwindow == NULL; }
-
+
// this widget will be queried for GTK's focus events
GtkWidget *m_focusWidget;
// find the direction of the given scrollbar (must be one of ours)
ScrollDir ScrollDirFromRange(GtkRange *range) const;
-
// extra (wxGTK-specific) flags
bool m_noExpose:1; // wxGLCanvas has its own redrawing
bool m_nativeSizeEvent:1; // wxGLCanvas sends wxSizeEvent upon "alloc_size"
bool m_hasScrolling:1;
bool m_hasVMT:1;
- bool m_resizing:1;
bool m_hasFocus:1; // true if == FindFocus()
bool m_isScrolling:1; // dragging scrollbar thumb?
bool m_clipPaintRegion:1; // true after ScrollWindow()
#include "wx/panel.h"
#include "wx/gtk/private.h"
-#include "wx/gtk/win_gtk.h"
-
-#include <gtk/gtkexpander.h>
// ============================================================================
// implementation
// when the expander is collapsed!)
gtk_window_set_resizable (GTK_WINDOW (top->m_widget), p->IsExpanded());
- // 4) set size hints: note that this code has been taken and adapted
- // from src/gtk/toplevel.cpp
- GdkGeometry geom;
-
- geom.min_width = sz.x;
- geom.min_height = sz.y;
-
- gtk_window_set_geometry_hints( GTK_WINDOW(top->m_widget),
- (GtkWidget*) NULL,
- &geom,
- GDK_HINT_MIN_SIZE );
-
- // 5) set size: also this code has been adapted from src/gtk/toplevel.cpp
- // to do the size changes immediately and not delaying them in the idle
- // time
- top->m_width = sz.x;
- top->m_height = sz.y;
-
- int client_x = top->m_miniEdge;
- int client_y = top->m_miniEdge + top->m_miniTitle;
- int client_w = top->m_width - 2*top->m_miniEdge;
- int client_h = top->m_height - 2*top->m_miniEdge - top->m_miniTitle;
- if (client_w < 0)
- client_w = 0;
- if (client_h < 0)
- client_h = 0;
-
- gtk_pizza_set_size( GTK_PIZZA(top->m_mainWidget),
- top->m_wxwindow,
- client_x, client_y, client_w, client_h );
-
- gtk_widget_set_size_request( top->m_wxwindow, sz.x, sz.y );
+ // 4) set size hints
+ top->SetSizeHints(sz.x, sz.y);
+ // 5) set size
+ top->SetClientSize(sz);
}
}
#include "wx/dialog.h"
#ifndef WX_PRECOMP
- #include "wx/app.h"
- #include "wx/frame.h"
#include "wx/cursor.h"
#endif // WX_PRECOMP
#include "wx/evtloop.h"
-#include <gdk/gdk.h>
#include <gtk/gtk.h>
-#include <gdk/gdkkeysyms.h>
-
-#include "wx/gtk/win_gtk.h"
//-----------------------------------------------------------------------------
// global data
void wxDialog::Init()
{
m_returnCode = 0;
- m_sizeSet = false;
m_modalShowing = false;
m_themeEnabled = true;
}
EndModal( wxID_CANCEL );
}
- if (show && !m_sizeSet)
- {
- /* by calling GtkOnSize here, we don't have to call
- either after showing the frame, which would entail
- much ugly flicker nor from within the size_allocate
- handler, because GTK 1.1.X forbids that. */
-
- GtkOnSize();
- }
-
bool ret = wxWindow::Show( show );
if (show) InitDialog();
#endif // WX_PRECOMP
#include <gtk/gtk.h>
-#include "wx/gtk/win_gtk.h"
-
-// ----------------------------------------------------------------------------
-// constants
-// ----------------------------------------------------------------------------
-
-static const int wxSTATUS_HEIGHT = 25;
-static const int wxPLACE_HOLDER = 0;
// ----------------------------------------------------------------------------
// event tables
// implementation
// ============================================================================
-// ----------------------------------------------------------------------------
-// GTK callbacks
-// ----------------------------------------------------------------------------
-
-#if wxUSE_MENUS_NATIVE
-
-//-----------------------------------------------------------------------------
-// "child_attached" of menu bar
-//-----------------------------------------------------------------------------
-
-extern "C" {
-static void gtk_menu_attached_callback( GtkWidget *WXUNUSED(widget), GtkWidget *WXUNUSED(child), wxFrame *win )
-{
- if (!win->m_hasVMT) return;
-
- win->m_menuBarDetached = false;
- win->GtkUpdateSize();
-}
-}
-
-//-----------------------------------------------------------------------------
-// "child_detached" of menu bar
-//-----------------------------------------------------------------------------
-
-extern "C" {
-static void gtk_menu_detached_callback( GtkWidget *WXUNUSED(widget), GtkWidget *WXUNUSED(child), wxFrame *win )
-{
- if (!win->m_hasVMT) return;
-
- // Raise the client area area
- gdk_window_raise( win->m_wxwindow->window );
-
- win->m_menuBarDetached = true;
- win->GtkUpdateSize();
-}
-}
-
-#endif // wxUSE_MENUS_NATIVE
-
-#if wxUSE_TOOLBAR
-//-----------------------------------------------------------------------------
-// "child_attached" of tool bar
-//-----------------------------------------------------------------------------
-
-extern "C" {
-static void gtk_toolbar_attached_callback( GtkWidget *WXUNUSED(widget), GtkWidget *WXUNUSED(child), wxFrame *win )
-{
- if (!win->m_hasVMT) return;
-
- win->m_toolBarDetached = false;
- win->GtkUpdateSize();
-}
-}
-
-//-----------------------------------------------------------------------------
-// "child_detached" of tool bar
-//-----------------------------------------------------------------------------
-
-extern "C" {
-static void gtk_toolbar_detached_callback( GtkWidget *WXUNUSED(widget), GtkWidget *WXUNUSED(child), wxFrame *win )
-{
- if (!win->m_hasVMT) return;
-
- // Raise the client area area
- gdk_window_raise( win->m_wxwindow->window );
-
- win->m_toolBarDetached = true;
- win->GtkUpdateSize();
-}
-}
-#endif // wxUSE_TOOLBAR
-
// ----------------------------------------------------------------------------
// wxFrame creation
// ----------------------------------------------------------------------------
void wxFrame::Init()
{
- m_menuBarDetached = false;
- m_toolBarDetached = false;
- m_menuBarHeight = 2;
m_fsSaveFlag = 0;
}
{
#if wxUSE_MENUS_NATIVE
// menu bar
- if (HasVisibleMenubar() && !m_menuBarDetached)
+ if (m_frameMenuBar && m_frameMenuBar->IsShown())
{
- *height -= m_menuBarHeight;
+ GtkRequisition req;
+ gtk_widget_size_request(m_frameMenuBar->m_widget, &req);
+ *height -= req.height;
}
#endif // wxUSE_MENUS_NATIVE
#if wxUSE_STATUSBAR
// status bar
- if (m_frameStatusBar && GTK_WIDGET_VISIBLE(m_frameStatusBar->m_widget))
- *height -= wxSTATUS_HEIGHT;
+ if (m_frameStatusBar && m_frameStatusBar->IsShown())
+ *height -= m_frameStatusBar->m_height;
#endif // wxUSE_STATUSBAR
}
#if wxUSE_TOOLBAR
// tool bar
- if (m_frameToolBar &&
- GTK_WIDGET_VISIBLE(m_frameToolBar->m_widget) && !m_toolBarDetached)
+ if (m_frameToolBar && m_frameToolBar->IsShown())
{
+ GtkRequisition req;
+ gtk_widget_size_request(m_frameToolBar->m_widget, &req);
if (m_frameToolBar->IsVertical())
{
if (width)
- *width -= m_frameToolBar->GetSize().x;
+ *width -= req.width;
}
else
{
if (height)
- *height -= m_frameToolBar->GetSize().y;
+ *height -= req.height;
}
}
#endif // wxUSE_TOOLBAR
return true;
}
-void wxFrame::GtkOnSize()
-{
- // avoid recursions
- if (m_resizing) return;
- m_resizing = true;
-
- // this shouldn't happen: wxFrame, wxMDIParentFrame and wxMDIChildFrame have m_wxwindow
- wxASSERT_MSG( (m_wxwindow != NULL), wxT("invalid frame") );
-
- // space occupied by m_frameToolBar and m_frameMenuBar
- int client_area_x_offset = 0,
- client_area_y_offset = 0;
-
- /* wxMDIChildFrame derives from wxFrame but it _is_ a wxWindow as it uses
- wxWindow::Create to create it's GTK equivalent. m_mainWidget is only
- set in wxFrame::Create so it is used to check what kind of frame we
- have here. if m_mainWidget is NULL it is a wxMDIChildFrame and so we
- skip the part which handles m_frameMenuBar, m_frameToolBar and (most
- importantly) m_mainWidget */
-
- ConstrainSize();
-
- int width, height;
- GTKDoGetSize(&width, &height);
-
- if (m_mainWidget)
- {
- // TODO
- // Rewrite this terrible code to using GtkVBox
-
- // m_mainWidget holds the menubar, the toolbar and the client
- // area, which is represented by m_wxwindow.
-
-#if wxUSE_MENUS_NATIVE
- int menubarHeight = 0;
-#endif
-
-#if wxUSE_MENUS_NATIVE
- if (HasVisibleMenubar())
- {
- int xx = m_miniEdge;
- int yy = m_miniEdge + m_miniTitle;
- int ww = width - 2*m_miniEdge;
- if (ww < 0)
- ww = 0;
- menubarHeight = m_menuBarHeight;
- if (m_menuBarDetached) menubarHeight = wxPLACE_HOLDER;
- m_frameMenuBar->m_x = xx;
- m_frameMenuBar->m_y = yy;
- m_frameMenuBar->m_width = ww;
- m_frameMenuBar->m_height = menubarHeight;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- m_frameMenuBar->m_widget,
- xx, yy, ww, menubarHeight);
- client_area_y_offset += menubarHeight;
- }
-#endif // wxUSE_MENUS_NATIVE
-
-#if wxUSE_TOOLBAR
- if ((m_frameToolBar) && m_frameToolBar->IsShown() &&
- (m_frameToolBar->m_widget->parent == m_mainWidget))
- {
- int xx = m_miniEdge;
- int yy = m_miniEdge + m_miniTitle
-#if wxUSE_MENUS_NATIVE
- + menubarHeight
-#endif
- ;
-
- m_frameToolBar->m_x = xx;
- m_frameToolBar->m_y = yy;
-
- // don't change the toolbar's reported height/width
- int ww, hh;
- if ( m_frameToolBar->GetWindowStyle() & wxTB_VERTICAL )
- {
- ww = m_toolBarDetached ? wxPLACE_HOLDER
- : m_frameToolBar->m_width;
- hh = height - 2*m_miniEdge;
-
- client_area_x_offset += ww;
- }
- else if( m_frameToolBar->HasFlag(wxTB_RIGHT) )
- {
- yy += 2;
- ww = m_toolBarDetached ? wxPLACE_HOLDER
- : m_frameToolBar->m_width;
- xx = GetClientSize().x - 1;
- hh = height - 2*m_miniEdge;
- if( hh < 0 )
- hh = 0;
-
- }
- else if( m_frameToolBar->GetWindowStyle() & wxTB_BOTTOM )
- {
- xx = m_miniEdge;
- yy = GetClientSize().y;
-#if wxUSE_MENUS_NATIVE
- yy += m_menuBarHeight;
-#endif // wxUSE_MENUS_NATIVE
- m_frameToolBar->m_x = xx;
- m_frameToolBar->m_y = yy;
- ww = width - 2*m_miniEdge;
- hh = m_toolBarDetached ? wxPLACE_HOLDER
- : m_frameToolBar->m_height;
- }
- else
- {
- ww = width - 2*m_miniEdge;
- hh = m_toolBarDetached ? wxPLACE_HOLDER
- : m_frameToolBar->m_height;
-
- client_area_y_offset += hh;
- }
-
- if (ww < 0)
- ww = 0;
- if (hh < 0)
- hh = 0;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- m_frameToolBar->m_widget,
- xx, yy, ww, hh );
- }
-#endif // wxUSE_TOOLBAR
-
- int client_x = client_area_x_offset + m_miniEdge;
- int client_y = client_area_y_offset + m_miniEdge + m_miniTitle;
- int client_w = width - client_area_x_offset - 2*m_miniEdge;
- int client_h = height - client_area_y_offset- 2*m_miniEdge - m_miniTitle;
- if (client_w < 0)
- client_w = 0;
- if (client_h < 0)
- client_h = 0;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- m_wxwindow,
- client_x, client_y, client_w, client_h );
- }
- else
- {
- // If there is no m_mainWidget between m_widget and m_wxwindow there
- // is no need to set the size or position of m_wxwindow.
- }
-
-#if wxUSE_STATUSBAR
- if (m_frameStatusBar && m_frameStatusBar->IsShown())
- {
- int xx = 0 + m_miniEdge;
- int yy = height - wxSTATUS_HEIGHT - m_miniEdge - client_area_y_offset;
- int ww = width - 2*m_miniEdge;
- if (ww < 0)
- ww = 0;
- int hh = wxSTATUS_HEIGHT;
- m_frameStatusBar->m_x = xx;
- m_frameStatusBar->m_y = yy;
- m_frameStatusBar->m_width = ww;
- m_frameStatusBar->m_height = hh;
- gtk_pizza_set_size( GTK_PIZZA(m_wxwindow),
- m_frameStatusBar->m_widget,
- xx, yy, ww, hh );
- }
-#endif // wxUSE_STATUSBAR
-
- m_sizeSet = true;
-
- // send size event to frame
- wxSizeEvent event( wxSize(m_width,m_height), GetId() );
- event.SetEventObject( this );
- GetEventHandler()->ProcessEvent( event );
-
-#if wxUSE_STATUSBAR
- // send size event to status bar
- if (m_frameStatusBar)
- {
- wxSizeEvent event2( wxSize(m_frameStatusBar->m_width,m_frameStatusBar->m_height), m_frameStatusBar->GetId() );
- event2.SetEventObject( m_frameStatusBar );
- m_frameStatusBar->GetEventHandler()->ProcessEvent( event2 );
- }
-#endif // wxUSE_STATUSBAR
-
- m_resizing = false;
-}
-
void wxFrame::OnInternalIdle()
{
wxFrameBase::OnInternalIdle();
{
m_frameMenuBar->UnsetInvokingWindow( this );
- if (m_frameMenuBar->GetWindowStyle() & wxMB_DOCKABLE)
- {
- g_signal_handlers_disconnect_by_func (m_frameMenuBar->m_widget,
- (gpointer) gtk_menu_attached_callback,
- this);
-
- g_signal_handlers_disconnect_by_func (m_frameMenuBar->m_widget,
- (gpointer) gtk_menu_detached_callback,
- this);
- }
-
gtk_widget_ref( m_frameMenuBar->m_widget );
gtk_container_remove( GTK_CONTAINER(m_mainWidget), m_frameMenuBar->m_widget );
}
wxFrameBase::DetachMenuBar();
+
+ // make sure next size_allocate causes a wxSizeEvent
+ m_oldClientWidth = 0;
}
void wxFrame::AttachMenuBar( wxMenuBar *menuBar )
m_frameMenuBar->SetInvokingWindow( this );
m_frameMenuBar->SetParent(this);
- gtk_pizza_put( GTK_PIZZA(m_mainWidget),
- m_frameMenuBar->m_widget,
- m_frameMenuBar->m_x,
- m_frameMenuBar->m_y,
- m_frameMenuBar->m_width,
- m_frameMenuBar->m_height );
-
- if (menuBar->GetWindowStyle() & wxMB_DOCKABLE)
- {
- g_signal_connect (menuBar->m_widget, "child_attached",
- G_CALLBACK (gtk_menu_attached_callback),
- this);
- g_signal_connect (menuBar->m_widget, "child_detached",
- G_CALLBACK (gtk_menu_detached_callback),
- this);
- }
- gtk_widget_show( m_frameMenuBar->m_widget );
+ // menubar goes into top of vbox (m_mainWidget)
+ gtk_box_pack_start(
+ GTK_BOX(m_mainWidget), menuBar->m_widget, false, false, 0);
+ gtk_box_reorder_child(GTK_BOX(m_mainWidget), menuBar->m_widget, 0);
- UpdateMenuBarSize();
- }
- else
- {
- m_menuBarHeight = 2;
- GtkUpdateSize(); // resize window in OnInternalIdle
- }
-}
+ // disconnect wxWindowGTK "size_request" handler,
+ // it interferes with sizing of detached GtkHandleBox
+ gulong handler_id = g_signal_handler_find(
+ menuBar->m_widget,
+ GSignalMatchType(G_SIGNAL_MATCH_ID | G_SIGNAL_MATCH_DATA),
+ g_signal_lookup("size_request", GTK_TYPE_WIDGET),
+ 0, NULL, NULL, menuBar);
+ if (handler_id != 0)
+ g_signal_handler_disconnect(menuBar->m_widget, handler_id);
-void wxFrame::UpdateMenuBarSize()
-{
- m_menuBarHeight = 2;
+ // reset size request to allow native sizing to work
+ gtk_widget_set_size_request(menuBar->m_widget, -1, -1);
- // this is called after Remove with a NULL m_frameMenuBar
- if ( m_frameMenuBar )
- {
- GtkRequisition req;
- gtk_widget_ensure_style(m_frameMenuBar->m_widget);
- // have to call class method directly because
- // "size_request" signal is overridden by wx
- GTK_WIDGET_GET_CLASS(m_frameMenuBar->m_widget)->size_request(
- m_frameMenuBar->m_widget, &req);
-
- m_menuBarHeight = req.height;
+ gtk_widget_show( m_frameMenuBar->m_widget );
}
-
- // resize window in OnInternalIdle
- GtkUpdateSize();
-}
-
-bool wxFrame::HasVisibleMenubar() const
-{
- return m_frameMenuBar && m_frameMenuBar->IsShown();
+ // make sure next size_allocate causes a wxSizeEvent
+ m_oldClientWidth = 0;
}
#endif // wxUSE_MENUS_NATIVE
void wxFrame::SetToolBar(wxToolBar *toolbar)
{
- wxFrameBase::SetToolBar(toolbar);
-
- if ( m_frameToolBar )
+ m_frameToolBar = toolbar;
+ if (toolbar)
{
- // insert into toolbar area if not already there
- if ((m_frameToolBar->m_widget->parent) &&
- (m_frameToolBar->m_widget->parent != m_mainWidget))
+ if (toolbar->IsVertical())
{
- GetChildren().DeleteObject( m_frameToolBar );
-
- gtk_widget_reparent( m_frameToolBar->m_widget, m_mainWidget );
+ // Vertical toolbar and m_wxwindow go into an hbox, inside the
+ // vbox (m_mainWidget). hbox is created on demand.
+ GtkWidget* hbox = m_wxwindow->parent;
+ if (!GTK_IS_HBOX(hbox))
+ {
+ hbox = gtk_hbox_new(false, 0);
+ gtk_widget_show(hbox);
+ gtk_container_add(GTK_CONTAINER(m_mainWidget), hbox);
+ gtk_widget_reparent(m_wxwindow, hbox);
+ }
+ gtk_widget_reparent(toolbar->m_widget, hbox);
+ gtk_box_set_child_packing(GTK_BOX(hbox),
+ toolbar->m_widget, false, false, 0, GTK_PACK_START);
+
+ int pos = 0; // left
+ if (toolbar->HasFlag(wxTB_RIGHT))
+ pos = 1; // right
+ gtk_box_reorder_child(GTK_BOX(hbox), toolbar->m_widget, pos);
}
-#if wxUSE_TOOLBAR_NATIVE
- if (m_frameToolBar->HasFlag(wxTB_DOCKABLE))
+ else
{
- g_signal_connect(m_frameToolBar->m_widget, "child_attached",
- G_CALLBACK(gtk_toolbar_attached_callback), this);
- g_signal_connect(m_frameToolBar->m_widget, "child_detached",
- G_CALLBACK(gtk_toolbar_detached_callback), this);
+ // Horizontal toolbar goes into vbox (m_mainWidget)
+ gtk_widget_reparent(toolbar->m_widget, m_mainWidget);
+ gtk_box_set_child_packing(GTK_BOX(m_mainWidget),
+ toolbar->m_widget, false, false, 0, GTK_PACK_START);
+
+ int pos = 0; // top
+ if (m_frameMenuBar)
+ pos = 1; // below menubar
+ if (toolbar->HasFlag(wxTB_BOTTOM))
+ pos += 2; // below client area (m_wxwindow)
+ gtk_box_reorder_child(
+ GTK_BOX(m_mainWidget), toolbar->m_widget, pos);
}
-#endif // wxUSE_TOOLBAR_NATIVE
- }
- GtkUpdateSize();
+ // disconnect wxWindowGTK "size_request" handler,
+ // it interferes with sizing of detached GtkHandleBox
+ gulong handler_id = g_signal_handler_find(
+ toolbar->m_widget,
+ GSignalMatchType(G_SIGNAL_MATCH_ID | G_SIGNAL_MATCH_DATA),
+ g_signal_lookup("size_request", GTK_TYPE_WIDGET),
+ 0, NULL, NULL, toolbar);
+ if (handler_id != 0)
+ g_signal_handler_disconnect(toolbar->m_widget, handler_id);
+
+ // reset size request to allow native sizing to work
+ gtk_widget_set_size_request(toolbar->m_widget, -1, -1);
+ }
+ // make sure next size_allocate causes a wxSizeEvent
+ m_oldClientWidth = 0;
}
#endif // wxUSE_TOOLBAR
void wxFrame::SetStatusBar(wxStatusBar *statbar)
{
- wxFrameBase::SetStatusBar(statbar);
- GtkUpdateSize();
+ m_frameStatusBar = statbar;
+ if (statbar)
+ {
+ // statusbar goes into bottom of vbox (m_mainWidget)
+ gtk_widget_reparent(statbar->m_widget, m_mainWidget);
+ gtk_box_set_child_packing(GTK_BOX(m_mainWidget),
+ statbar->m_widget, false, false, 0, GTK_PACK_END);
+ // make sure next size_allocate on statusbar causes a size event
+ statbar->m_oldClientWidth = 0;
+ }
+ // make sure next size_allocate causes a wxSizeEvent
+ m_oldClientWidth = 0;
}
#endif // wxUSE_STATUSBAR
#ifndef WX_PRECOMP
#include "wx/intl.h"
#include "wx/menu.h"
- #include "wx/dialog.h"
#endif
-#include "wx/notebook.h"
#include "wx/gtk/private.h"
-#include <gtk/gtk.h>
-#include "wx/gtk/win_gtk.h"
-
-//-----------------------------------------------------------------------------
-// constants
-//-----------------------------------------------------------------------------
-
-const int wxMENU_HEIGHT = 27;
-
-//-----------------------------------------------------------------------------
-// globals
-//-----------------------------------------------------------------------------
-
//-----------------------------------------------------------------------------
// "switch_page"
//-----------------------------------------------------------------------------
return true;
}
-void wxMDIParentFrame::GtkOnSize()
-{
- wxFrame::GtkOnSize();
-
- wxMDIChildFrame *child_frame = GetActiveChild();
- if (!child_frame) return;
-
- wxMenuBar *menu_bar = child_frame->m_menuBar;
- if (!menu_bar) return;
- if (!menu_bar->m_widget) return;
-
- menu_bar->m_x = 0;
- menu_bar->m_y = 0;
- GTKDoGetSize(&menu_bar->m_width, NULL);
- menu_bar->m_height = wxMENU_HEIGHT;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- menu_bar->m_widget,
- 0, 0, menu_bar->m_width, menu_bar->m_height);
-}
-
void wxMDIParentFrame::OnInternalIdle()
{
/* if a an MDI child window has just been inserted
wxMenuBar *menu_bar = active_child_frame->m_menuBar;
if (menu_bar)
{
- GTKDoGetSize(&menu_bar->m_width, NULL);
- menu_bar->m_height = wxMENU_HEIGHT;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- menu_bar->m_widget,
- 0, 0, menu_bar->m_width, menu_bar->m_height);
menu_bar->SetInvokingWindow(active_child_frame);
}
}
{
if (menu_bar->Show(true))
{
- GTKDoGetSize(&menu_bar->m_width, NULL);
- menu_bar->m_height = wxMENU_HEIGHT;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- menu_bar->m_widget,
- 0, 0, menu_bar->m_width, menu_bar->m_height);
menu_bar->SetInvokingWindow( child_frame );
}
visible_child_menu = true;
{
m_frameMenuBar->Show( true );
m_frameMenuBar->SetInvokingWindow( this );
+ }
+ }
+}
- GTKDoGetSize(&m_frameMenuBar->m_width, NULL);
- m_frameMenuBar->m_height = wxMENU_HEIGHT;
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- m_frameMenuBar->m_widget,
- 0, 0, m_frameMenuBar->m_width, m_frameMenuBar->m_height);
+void wxMDIParentFrame::DoGetClientSize(int* width, int* height) const
+{
+ wxFrame::DoGetClientSize(width, height);
+
+ if (height)
+ {
+ wxMDIChildFrame* active_child_frame = GetActiveChild();
+ if (active_child_frame)
+ {
+ wxMenuBar* menubar = active_child_frame->m_menuBar;
+ if (menubar && menubar->IsShown())
+ {
+ GtkRequisition req;
+ gtk_widget_size_request(menubar->m_widget, &req);
+ *height -= req.height;
+ if (*height < 0) *height = 0;
+ }
}
}
}
gtk_notebook_prev_page( GTK_NOTEBOOK(m_clientWindow->m_widget) );
}
-bool wxMDIParentFrame::HasVisibleMenubar() const
-{
- if (wxFrame::HasVisibleMenubar())
- return true;
-
- wxMDIChildFrame* active_child_frame = GetActiveChild();
- wxMenuBar* menubar = NULL;
- if (active_child_frame)
- menubar = active_child_frame->m_menuBar;
- return menubar && menubar->IsShown();
-}
-
//-----------------------------------------------------------------------------
// wxMDIChildFrame
//-----------------------------------------------------------------------------
m_menuBar->SetParent( mdi_frame );
/* insert the invisible menu bar into the _parent_ mdi frame */
- int w;
- mdi_frame->GTKDoGetSize(&w, NULL);
- gtk_pizza_put( GTK_PIZZA(mdi_frame->m_mainWidget),
- m_menuBar->m_widget,
- 0, 0, w, wxMENU_HEIGHT);
+ m_menuBar->Show(false);
+ gtk_box_pack_start(GTK_BOX(mdi_frame->m_mainWidget), m_menuBar->m_widget, false, false, 0);
+ gtk_box_reorder_child(GTK_BOX(mdi_frame->m_mainWidget), m_menuBar->m_widget, 0);
+
+ gulong handler_id = g_signal_handler_find(
+ m_menuBar->m_widget,
+ GSignalMatchType(G_SIGNAL_MATCH_ID | G_SIGNAL_MATCH_DATA),
+ g_signal_lookup("size_request", GTK_TYPE_WIDGET),
+ 0, NULL, NULL, m_menuBar);
+ if (handler_id != 0)
+ g_signal_handler_disconnect(m_menuBar->m_widget, handler_id);
+ gtk_widget_set_size_request(m_menuBar->m_widget, -1, -1);
}
}
gtk_notebook_set_tab_label_text(notebook, m_widget, wxGTK_CONV( title ) );
}
-//-----------------------------------------------------------------------------
-// "size_allocate"
-//-----------------------------------------------------------------------------
-
-extern "C" {
-static void gtk_page_size_callback( GtkWidget *WXUNUSED(widget), GtkAllocation* alloc, wxMDIChildFrame *win )
-{
- if ((win->m_x == alloc->x) &&
- (win->m_y == alloc->y) &&
- (win->m_width == alloc->width) &&
- (win->m_height == alloc->height) &&
- (win->m_sizeSet))
- {
- return;
- }
-
- win->SetSize( alloc->x, alloc->y, alloc->width, alloc->height );
-}
-}
-
//-----------------------------------------------------------------------------
// InsertChild callback for wxMDIClientWindow
//-----------------------------------------------------------------------------
GtkWidget *label_widget = gtk_label_new( s.mbc_str() );
gtk_misc_set_alignment( GTK_MISC(label_widget), 0.0, 0.5 );
- g_signal_connect (child->m_widget, "size_allocate",
- G_CALLBACK (gtk_page_size_callback), child);
-
GtkNotebook *notebook = GTK_NOTEBOOK(parent->m_widget);
gtk_notebook_append_page( notebook, child->m_widget, label_widget );
#include "wx/stockitem.h"
#include "wx/gtk/private.h"
-#ifdef __WXGTK20__
-#include <gdk/gdktypes.h>
-#endif
-
// FIXME: is this right? somehow I don't think so (VZ)
#define gtk_accel_group_attach(g, o) gtk_window_add_accel_group((o), (g))
// m_invokingWindow is set after wxFrame::SetMenuBar(). This call enables
// addings menu later on.
if (m_invokingWindow)
- {
wxMenubarSetInvokingWindow( menu, m_invokingWindow );
- // OPTIMISE ME: we should probably cache this, or pass it
- // directly, but for now this is a minimal
- // change to validate the new dynamic sizing.
- // see (and refactor :) similar code in Remove
- // below.
-
- wxFrame *frame = wxDynamicCast( m_invokingWindow, wxFrame );
-
- if( frame )
- frame->UpdateMenuBarSize();
- }
-
return true;
}
menu->m_owner = NULL;
if (m_invokingWindow)
- {
- // OPTIMISE ME: see comment in GtkAppend
- wxFrame *frame = wxDynamicCast( m_invokingWindow, wxFrame );
-
- if( frame )
- frame->UpdateMenuBarSize();
-
wxMenubarUnsetInvokingWindow( menu, m_invokingWindow );
- }
-
return menu;
}
#include "wx/image.h"
#endif
-#include "wx/gtk/win_gtk.h"
-#include "wx/gtk/private.h"
+#include <gtk/gtk.h>
//-----------------------------------------------------------------------------
// data
extern bool g_blockEventsOnDrag;
extern bool g_blockEventsOnScroll;
-extern GtkWidget *wxGetRootWindow();
//-----------------------------------------------------------------------------
// "expose_event" of m_mainWidget
if (!win->m_hasVMT || gdk_event->count > 0)
return false;
- GtkPizza *pizza = GTK_PIZZA(widget);
-
gtk_paint_shadow (widget->style,
- pizza->bin_window,
+ widget->window,
GTK_STATE_NORMAL,
GTK_SHADOW_OUT,
NULL, NULL, NULL, // FIXME: No clipping?
int style = win->GetWindowStyle();
wxClientDC dc(win);
-
+
#if wxUSE_NEW_DC
wxImplDC *impl = dc.GetImpl();
wxGTKClientImplDC *client_impl = wxDynamicCast( impl, wxGTKClientImplDC );
// Hack alert
- client_impl->m_window = pizza->bin_window;
+ client_impl->m_window = widget->window;
#else
// Hack alert
- dc.m_window = pizza->bin_window;
+ dc.m_window = widget->window;
#endif
if (style & wxRESIZE_BORDER)
if (win->m_isDragging) return TRUE;
- GtkPizza *pizza = GTK_PIZZA(widget);
- if (gdk_event->window != pizza->bin_window) return TRUE;
-
int style = win->GetWindowStyle();
int y = (int)gdk_event->y;
{
GtkWidget *ancestor = gtk_widget_get_toplevel( widget );
- GdkWindow *source = GTK_PIZZA(widget)->bin_window;
+ GdkWindow *source = widget->window;
int org_x = 0;
int org_y = 0;
win->m_y = y;
gtk_window_move( GTK_WINDOW(win->m_widget), x, y );
-
return TRUE;
}
}
+//-----------------------------------------------------------------------------
+// "size_allocate" from GtkFixed, parent of m_mainWidget
+//-----------------------------------------------------------------------------
+
+extern "C" {
+static void size_allocate(GtkWidget*, GtkAllocation* alloc, wxMiniFrame* win)
+{
+ // place m_mainWidget inside of decorations drawn on the GtkFixed
+ GtkAllocation alloc2 = win->m_mainWidget->allocation;
+ alloc2.width = alloc->width - 2 * win->m_miniEdge;
+ alloc2.height = alloc->height - win->m_miniTitle - 2 * win->m_miniEdge;
+ gtk_widget_size_allocate(win->m_mainWidget, &alloc2);
+}
+}
+
//-----------------------------------------------------------------------------
// wxMiniFrame
//-----------------------------------------------------------------------------
wxFrame::Create( parent, id, title, pos, size, style, name );
+ // borders and title are on a GtkFixed between m_widget and m_mainWidget
+ GtkWidget* fixed = gtk_fixed_new();
+ gtk_fixed_set_has_window((GtkFixed*)fixed, true);
+ gtk_widget_add_events(fixed,
+ GDK_POINTER_MOTION_MASK |
+ GDK_POINTER_MOTION_HINT_MASK |
+ GDK_BUTTON_MOTION_MASK |
+ GDK_BUTTON_PRESS_MASK |
+ GDK_BUTTON_RELEASE_MASK |
+ GDK_LEAVE_NOTIFY_MASK);
+ gtk_widget_show(fixed);
+ gtk_widget_reparent(m_mainWidget, fixed);
+ gtk_container_add((GtkContainer*)m_widget, fixed);
+ gtk_fixed_move((GtkFixed*)fixed, m_mainWidget, m_miniEdge, m_miniTitle + m_miniEdge);
+ g_signal_connect(fixed, "size_allocate", G_CALLBACK(size_allocate), this);
+
+ m_gdkDecor = 0;
+ m_gdkFunc = 0;
+ if (style & wxRESIZE_BORDER)
+ m_gdkFunc = GDK_FUNC_RESIZE;
+
if (m_parent && (GTK_IS_WINDOW(m_parent->m_widget)))
{
gtk_window_set_transient_for( GTK_WINDOW(m_widget), GTK_WINDOW(m_parent->m_widget) );
}
/* these are called when the borders are drawn */
- g_signal_connect (m_mainWidget, "expose_event",
+ g_signal_connect_after(fixed, "expose_event",
G_CALLBACK (gtk_window_own_expose_callback), this );
/* these are required for dragging the mini frame around */
- g_signal_connect (m_mainWidget, "button_press_event",
+ g_signal_connect (fixed, "button_press_event",
G_CALLBACK (gtk_window_button_press_callback), this);
- g_signal_connect (m_mainWidget, "button_release_event",
+ g_signal_connect (fixed, "button_release_event",
G_CALLBACK (gtk_window_button_release_callback), this);
- g_signal_connect (m_mainWidget, "motion_notify_event",
+ g_signal_connect (fixed, "motion_notify_event",
G_CALLBACK (gtk_window_motion_notify_callback), this);
- g_signal_connect (m_mainWidget, "leave_notify_event",
+ g_signal_connect (fixed, "leave_notify_event",
G_CALLBACK (gtk_window_leave_callback), this);
return true;
}
+void wxMiniFrame::DoGetClientSize(int* width, int* height) const
+{
+ wxFrame::DoGetClientSize(width, height);
+ if (width)
+ {
+ *width -= 2 * m_miniEdge;
+ if (*width < 0) *width = 0;
+ }
+ if (height)
+ {
+ *height -= m_miniTitle + 2 * m_miniEdge;
+ if (*height < 0) *height = 0;
+ }
+}
+
void wxMiniFrame::SetTitle( const wxString &title )
{
wxFrame::SetTitle( title );
- if (GTK_PIZZA(m_mainWidget)->bin_window)
- gdk_window_invalidate_rect( GTK_PIZZA(m_mainWidget)->bin_window, NULL, true );
+ GtkWidget* fixed = GTK_BIN(m_widget)->child;
+ if (fixed->window)
+ gdk_window_invalidate_rect(fixed->window, NULL, false);
}
#endif // wxUSE_MINIFRAME
#include "wx/popupwin.h"
#ifndef WX_PRECOMP
- #include "wx/app.h"
- #include "wx/frame.h"
- #include "wx/cursor.h"
#endif // WX_PRECOMP
#include <gtk/gtk.h>
// wxPopupWindow
//-----------------------------------------------------------------------------
-BEGIN_EVENT_TABLE(wxPopupWindow,wxPopupWindowBase)
#ifdef __WXUNIVERSAL__
+BEGIN_EVENT_TABLE(wxPopupWindow,wxPopupWindowBase)
EVT_SIZE(wxPopupWindow::OnSize)
-#endif
END_EVENT_TABLE()
+#endif
wxPopupWindow::~wxPopupWindow()
{
bool wxPopupWindow::Create( wxWindow *parent, int style )
{
- m_sizeSet = false;
-
if (!PreCreation( parent, wxDefaultPosition, wxDefaultSize ) ||
!CreateBase( parent, -1, wxDefaultPosition, wxDefaultSize, style, wxDefaultValidator, wxT("popup") ))
{
wxASSERT_MSG( (m_widget != NULL), wxT("invalid dialog") );
wxASSERT_MSG( (m_wxwindow != NULL), wxT("invalid dialog") );
- if (m_resizing) return; /* I don't like recursions */
- m_resizing = true;
-
int old_x = m_x;
int old_y = m_y;
int old_width = m_width;
int old_height = m_height;
- if ((sizeFlags & wxSIZE_ALLOW_MINUS_ONE) == 0)
- {
- if (x != -1) m_x = x;
- if (y != -1) m_y = y;
- if (width != -1) m_width = width;
- if (height != -1) m_height = height;
- }
- else
- {
+ if (x != -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
m_x = x;
+ if (y != -1 || (sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
m_y = y;
+ if (width != -1)
m_width = width;
+ if (height != -1)
m_height = height;
- }
-
-/*
- if ((sizeFlags & wxSIZE_AUTO_WIDTH) == wxSIZE_AUTO_WIDTH)
- {
- if (width == -1) m_width = 80;
- }
-
- if ((sizeFlags & wxSIZE_AUTO_HEIGHT) == wxSIZE_AUTO_HEIGHT)
- {
- if (height == -1) m_height = 26;
- }
-*/
ConstrainSize();
{
if ((m_x != old_x) || (m_y != old_y))
{
- /* we set the position here and when showing the dialog
- for the first time in idle time */
- // Where does that happen in idle time? I do not see it anywhere - MR
gtk_window_move( GTK_WINDOW(m_widget), m_x, m_y );
}
}
if ((m_width != old_width) || (m_height != old_height))
{
+ // gtk_window_resize does not work for GTK_WINDOW_POPUP
gtk_widget_set_size_request( m_widget, m_width, m_height );
-
- /* actual resizing is deferred to GtkOnSize in idle time and
- when showing the dialog */
- m_sizeSet = false;
-
+ wxSizeEvent event(GetSize(), GetId());
+ event.SetEventObject(this);
+ GetEventHandler()->ProcessEvent(event);
}
-
- m_resizing = false;
-}
-
-void wxPopupWindow::GtkOnSize()
-{
- if (m_sizeSet) return;
- if (!m_wxwindow) return;
-
- /* FIXME: is this a hack? */
- /* Since for some reason GTK will revert to using maximum size ever set
- for this window, we have to set geometry hints maxsize to match size
- given. Also set the to that minsize since resizing isn't possible
- anyway. */
-
- /* set size hints */
- gint flag = GDK_HINT_MAX_SIZE | GDK_HINT_MIN_SIZE; // GDK_HINT_POS;
- GdkGeometry geom;
- geom.min_width = m_width;
- geom.min_height = m_height;
- geom.max_width = m_width;
- geom.max_height = m_height;
- gtk_window_set_geometry_hints( GTK_WINDOW(m_widget),
- (GtkWidget*) NULL,
- &geom,
- (GdkWindowHints) flag );
-
-
- m_sizeSet = true;
-
- wxSizeEvent event( wxSize(m_width,m_height), GetId() );
- event.SetEventObject( this );
- GetEventHandler()->ProcessEvent( event );
-}
-
-void wxPopupWindow::OnInternalIdle()
-{
- if (!m_sizeSet && GTK_WIDGET_REALIZED(m_wxwindow))
- GtkOnSize();
-
- wxWindow::OnInternalIdle();
}
bool wxPopupWindow::Show( bool show )
{
- if (show && !m_sizeSet)
+ if (show && !IsShown())
{
- /* by calling GtkOnSize here, we don't have to call
- either after showing the frame, which would entail
- much ugly flicker nor from within the size_allocate
- handler, because GTK 1.1.X forbids that. */
-
- GtkOnSize();
+ wxSizeEvent event(GetSize(), GetId());
+ event.SetEventObject(this);
+ GetEventHandler()->ProcessEvent(event);
}
bool ret = wxWindow::Show( show );
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
-// ============================================================================
-// declarations
-// ============================================================================
-
-// ----------------------------------------------------------------------------
-// headers
-// ----------------------------------------------------------------------------
-
// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"
}
}
+//-----------------------------------------------------------------------------
+// "size_request" from m_toolbar
+//-----------------------------------------------------------------------------
+
+extern "C" {
+static void
+size_request(GtkWidget*, GtkRequisition* req, wxToolBar* win)
+{
+ const wxSize margins = win->GetMargins();
+ req->width += margins.x;
+ req->height += 2 * margins.y;
+}
+}
+
//-----------------------------------------------------------------------------
// InsertChild callback for wxToolBar
//-----------------------------------------------------------------------------
PostCreation(size);
+ g_signal_connect_after(m_toolbar, "size_request",
+ G_CALLBACK(size_request), this);
+
return true;
}
break;
}
- GtkRequisition req;
- (* GTK_WIDGET_CLASS( GTK_OBJECT_GET_CLASS(m_widget) )->size_request )
- (m_widget, &req );
- m_width = req.width + m_xMargin;
- m_height = req.height + 2*m_yMargin;
InvalidateBestSize();
return true;
}
//-----------------------------------------------------------------------------
-// "size_allocate"
+// "size_allocate" from m_wxwindow
//-----------------------------------------------------------------------------
extern "C" {
-static void gtk_frame_size_callback( GtkWidget *WXUNUSED(widget), GtkAllocation* alloc, wxTopLevelWindowGTK *win )
+static void
+size_allocate(GtkWidget*, GtkAllocation* alloc, wxTopLevelWindowGTK* win)
{
- if (!win->m_hasVMT)
- return;
-
- wxSize sizeDecor;
- if (!win->IsFullScreen())
- sizeDecor = GetDecorSize(win->m_gdkDecor);
- const int w = alloc->width + sizeDecor.x;
- const int h = alloc->height + sizeDecor.y;
-
- if (win->m_width != w || win->m_height != h)
+ if (win->m_oldClientWidth != alloc->width ||
+ win->m_oldClientHeight != alloc->height)
{
- win->m_width = w;
- win->m_height = h;
-
- win->GtkUpdateSize();
+ win->m_oldClientWidth = alloc->width;
+ win->m_oldClientHeight = alloc->height;
+ wxSize sizeDecor;
+ if (!win->IsFullScreen())
+ sizeDecor = GetDecorSize(win->m_gdkDecor);
+ win->m_width = win->m_widget->allocation.width + sizeDecor.x;
+ win->m_height = win->m_widget->allocation.height + sizeDecor.y;
+ if (!win->IsIconized())
+ {
+ wxSizeEvent event(win->GetSize(), win->GetId());
+ event.SetEventObject(win);
+ win->GetEventHandler()->ProcessEvent(event);
+ }
+ // else the window is currently unmapped, don't generate size events
}
}
}
// Update window size and frame extents cache
win->m_width = rect.width;
win->m_height = rect.height;
- win->GtkUpdateSize();
decorSize = size;
+ wxSizeEvent event(win->GetSize(), win->GetId());
+ event.SetEventObject(win);
+ win->GetEventHandler()->ProcessEvent(event);
}
}
win->m_height += size.y - decorSize.y;
if (win->m_width < 0) win->m_width = 0;
if (win->m_height < 0) win->m_height = 0;
- win->GtkUpdateSize();
decorSize = size;
+ wxSizeEvent event(win->GetSize(), win->GetId());
+ event.SetEventObject(win);
+ win->GetEventHandler()->ProcessEvent(event);
}
}
if (data)
void wxTopLevelWindowGTK::Init()
{
- m_sizeSet = false;
- m_miniEdge = 0;
- m_miniTitle = 0;
m_mainWidget = (GtkWidget*) NULL;
m_isIconized = false;
m_fsIsShowing = false;
// e.g. in wxTaskBarIconAreaGTK
if (m_widget == NULL)
{
+ m_widget = gtk_window_new(GTK_WINDOW_TOPLEVEL);
if (GetExtraStyle() & wxTOPLEVEL_EX_DIALOG)
{
- m_widget = gtk_window_new(GTK_WINDOW_TOPLEVEL);
// Tell WM that this is a dialog window and make it center
// on parent by default (this is what GtkDialog ctor does):
gtk_window_set_type_hint(GTK_WINDOW(m_widget),
}
else
{
- m_widget = gtk_window_new(GTK_WINDOW_TOPLEVEL);
#if GTK_CHECK_VERSION(2,1,0)
if (!gtk_check_version(2,1,0))
{
g_signal_connect (m_widget, "delete_event",
G_CALLBACK (gtk_frame_delete_callback), this);
- // m_mainWidget holds the toolbar, the menubar and the client area
- m_mainWidget = gtk_pizza_new();
+ // m_mainWidget is a GtkVBox, holding the bars and client area (m_wxwindow)
+ m_mainWidget = gtk_vbox_new(false, 0);
gtk_widget_show( m_mainWidget );
GTK_WIDGET_UNSET_FLAGS( m_mainWidget, GTK_CAN_FOCUS );
gtk_container_add( GTK_CONTAINER(m_widget), m_mainWidget );
- // m_wxwindow only represents the client area without toolbar and menubar
- m_wxwindow = gtk_pizza_new();
+ // m_wxwindow is the client area
+ m_wxwindow = gtk_pizza_new_no_scroll();
gtk_widget_show( m_wxwindow );
gtk_container_add( GTK_CONTAINER(m_mainWidget), m_wxwindow );
if (m_parent) m_parent->AddChild( this );
- // the user resized the frame by dragging etc.
- g_signal_connect (m_widget, "size_allocate",
- G_CALLBACK (gtk_frame_size_callback), this);
+ g_signal_connect(m_wxwindow, "size_allocate",
+ G_CALLBACK(size_allocate), this);
g_signal_connect (m_widget, "size_request",
G_CALLBACK (wxgtk_tlw_size_request_callback), this);
m_gdkFunc = 0;
}
else
- if (m_miniEdge > 0)
- {
- m_gdkDecor = 0;
- m_gdkFunc = 0;
-
- if ((style & wxRESIZE_BORDER) != 0)
- m_gdkFunc |= GDK_FUNC_RESIZE;
- }
- else
{
m_gdkDecor = GDK_DECOR_BORDER;
m_gdkFunc = GDK_FUNC_MOVE;
{
wxASSERT_MSG( (m_widget != NULL), wxT("invalid frame") );
- if (show == IsShown())
- return false;
-
- if (show && !m_sizeSet)
+ if (show && !IsShown())
{
- /* by calling GtkOnSize here, we don't have to call
- either after showing the frame, which would entail
- much ugly flicker or from within the size_allocate
- handler, because GTK 1.1.X forbids that. */
-
- GtkOnSize();
+ // size_allocate signals occur in reverse order (bottom to top).
+ // Things work better if the initial wxSizeEvents are sent (from the
+ // top down), before the initial size_allocate signals occur.
+ wxSizeEvent event(GetSize(), GetId());
+ event.SetEventObject(this);
+ GetEventHandler()->ProcessEvent(event);
}
- wxTopLevelWindowBase::Show(show);
+ bool change = wxTopLevelWindowBase::Show(show);
- if (!show)
+ if (change && !show)
{
// make sure window has a non-default position, so when it is shown
// again, it won't be repositioned by WM as if it were a new window
gtk_window_move((GtkWindow*)m_widget, m_x, m_y);
}
- return true;
+ return change;
}
void wxTopLevelWindowGTK::Raise()
gtk_window_move( GTK_WINDOW(m_widget), m_x, m_y );
}
- m_resizing = true;
-
const wxSize oldSize(m_width, m_height);
if (width >= 0)
m_width = width;
int w, h;
GTKDoGetSize(&w, &h);
gtk_window_resize(GTK_WINDOW(m_widget), w, h);
- GtkUpdateSize();
+
+ GetClientSize(&m_oldClientWidth, &m_oldClientHeight);
+ wxSizeEvent event(GetSize(), GetId());
+ event.SetEventObject(this);
+ GetEventHandler()->ProcessEvent(event);
}
- m_resizing = false;
}
void wxTopLevelWindowGTK::DoGetClientSize( int *width, int *height ) const
{
+ wxASSERT_MSG(m_widget, wxT("invalid frame"));
+
if ( IsIconized() )
{
// for consistency with wxMSW, client area is supposed to be empty for
*width = 0;
if ( height )
*height = 0;
-
- return;
}
-
- wxASSERT_MSG( (m_widget != NULL), wxT("invalid frame") );
-
- int w, h;
- GTKDoGetSize(&w, &h);
- if (width)
- {
- *width = w - 2 * m_miniEdge;
- if (*width < 0)
- *width = 0;
- }
- if (height)
+ else
{
- *height = h - 2 * m_miniEdge - m_miniTitle;
- if (*height < 0)
- *height = 0;
+ GTKDoGetSize(width, height);
}
}
(GtkWindow*)m_widget, NULL, &hints, (GdkWindowHints)hints_mask);
}
-void wxTopLevelWindowGTK::GtkOnSize()
-{
- // avoid recursions
- if (m_resizing) return;
- m_resizing = true;
-
- if ( m_wxwindow == NULL ) return;
-
- ConstrainSize();
-
- if (m_mainWidget)
- {
- int w, h;
- GTKDoGetSize(&w, &h);
- gtk_pizza_set_size( GTK_PIZZA(m_mainWidget),
- m_wxwindow,
- 0, 0, w, h);
- }
-
- m_sizeSet = true;
-
- // send size event to frame
- wxSizeEvent event( wxSize(m_width,m_height), GetId() );
- event.SetEventObject( this );
- GetEventHandler()->ProcessEvent( event );
-
- m_resizing = false;
-}
-
bool wxTopLevelWindowGTK::IsDecorCacheable() const
{
return true;
void wxTopLevelWindowGTK::OnInternalIdle()
{
- if (!m_sizeSet && GTK_WIDGET_REALIZED(m_wxwindow))
- {
- GtkOnSize();
-
- // we'll come back later
- return;
- }
-
// set the focus if not done yet and if we can already do it
if ( GTK_WIDGET_REALIZED(m_wxwindow) )
{
#ifndef WX_PRECOMP
#include "wx/log.h"
#include "wx/app.h"
- #include "wx/frame.h"
+ #include "wx/toplevel.h"
#include "wx/dcclient.h"
#include "wx/menu.h"
#include "wx/settings.h"
#include "wx/msgdlg.h"
- #include "wx/textctrl.h"
- #include "wx/toolbar.h"
- #include "wx/combobox.h"
- #include "wx/layout.h"
#include "wx/math.h"
#endif
static
void wxgtk_combo_size_request_callback(GtkWidget * WXUNUSED(widget),
GtkRequisition *requisition,
- wxComboBox *win)
+ wxWindow* win)
{
// This callback is actually hooked into the text entry
// of the combo box, not the GtkHBox.
}
//-----------------------------------------------------------------------------
-// "size_allocate"
+// "size_allocate" from m_wxwindow or m_widget
//-----------------------------------------------------------------------------
-static
-void gtk_window_size_callback( GtkWidget *WXUNUSED(widget),
- GtkAllocation * WXUNUSED(alloc),
- wxWindow *win )
+static void
+size_allocate(GtkWidget*, GtkAllocation* alloc, wxWindow* win)
{
- int client_width = 0;
- int client_height = 0;
- win->GetClientSize( &client_width, &client_height );
- if ((client_width == win->m_oldClientWidth) && (client_height == win->m_oldClientHeight))
- return;
-
- if ( !client_width && !client_height )
- {
- // the window is currently unmapped, don't generate size events
- return;
- }
-
- win->m_oldClientWidth = client_width;
- win->m_oldClientHeight = client_height;
-
- if (!win->m_nativeSizeEvent)
+ int w = alloc->width;
+ int h = alloc->height;
+ if (win->m_wxwindow)
{
- wxSizeEvent event( win->GetSize(), win->GetId() );
- event.SetEventObject( win );
- win->GTKProcessEvent( event );
+ const int border = GTK_CONTAINER(win->m_wxwindow)->border_width;
+ w -= 2 * border;
+ h -= 2 * border;
+ if (w < 0) w = 0;
+ if (h < 0) h = 0;
+ }
+ if (win->m_oldClientWidth != w || win->m_oldClientHeight != h)
+ {
+ win->m_oldClientWidth = w;
+ win->m_oldClientHeight = h;
+ // this callback can be connected to m_wxwindow,
+ // so always get size from m_widget->allocation
+ win->m_width = win->m_widget->allocation.width;
+ win->m_height = win->m_widget->allocation.height;
+ if (!win->m_nativeSizeEvent)
+ {
+ wxSizeEvent event(win->GetSize(), win->GetId());
+ event.SetEventObject(win);
+ win->GTKProcessEvent(event);
+ }
}
}
m_oldClientWidth =
m_oldClientHeight = 0;
- m_resizing = false;
-
m_insertCallback = wxInsertChildInWindow;
m_hasFocus = false;
g_signal_connect (connect_widget, "realize",
G_CALLBACK (gtk_window_realized_callback), this);
+ if (!IsTopLevel())
+ {
+ g_signal_connect(m_wxwindow ? m_wxwindow : m_widget, "size_allocate",
+ G_CALLBACK(size_allocate), this);
+ }
+
if (m_wxwindow)
{
- // Catch native resize events
- g_signal_connect (m_wxwindow, "size_allocate",
- G_CALLBACK (gtk_window_size_callback), this);
#if GTK_CHECK_VERSION(2, 8, 0)
if (!gtk_check_version(2,8,0))
{
wxASSERT_MSG( (m_widget != NULL), wxT("invalid window") );
wxASSERT_MSG( (m_parent != NULL), wxT("wxWindowGTK::SetSize requires parent.\n") );
- if (m_resizing) return; /* I don't like recursions */
- m_resizing = true;
-
int currentX, currentY;
GetPosition(¤tX, ¤tY);
if (x == -1 && !(sizeFlags & wxSIZE_ALLOW_MINUS_ONE))
height = sizeBest.y;
}
+ const wxSize oldSize(m_width, m_height);
if (width != -1)
m_width = width;
if (height != -1)
ConstrainSize();
-#if wxUSE_TOOLBAR_NATIVE
- if (wxDynamicCast(GetParent(), wxToolBar))
- {
- // don't take the x,y values, they're wrong because toolbar sets them
- GtkWidget *widget = m_widget;
- gtk_widget_set_size_request (widget, m_width, m_height);
- }
- else
-#endif
- if (m_parent->m_wxwindow == NULL) // i.e. wxNotebook
- {
- // don't set the size for children of wxNotebook, just take the values.
- m_x = x;
- m_y = y;
- m_width = width;
- m_height = height;
- }
- else
+ if (m_parent->m_wxwindow)
{
GtkPizza *pizza = GTK_PIZZA(m_parent->m_wxwindow);
- if ((sizeFlags & wxSIZE_ALLOW_MINUS_ONE) == 0)
- {
- if (x != -1) m_x = x + gtk_pizza_get_xoffset( pizza );
- if (y != -1) m_y = y + gtk_pizza_get_yoffset( pizza );
- }
- else
- {
- m_x = x + gtk_pizza_get_xoffset( pizza );
- m_y = y + gtk_pizza_get_yoffset( pizza );
- }
+ m_x = x + gtk_pizza_get_xoffset(pizza);
+ m_y = y + gtk_pizza_get_yoffset(pizza);
int left_border = 0;
int right_border = 0;
m_height+top_border+bottom_border );
}
- if (m_hasScrolling)
+ if (m_width != oldSize.x || m_height != oldSize.y)
{
- /* Sometimes the client area changes size without the
- whole windows's size changing, but if the whole
- windows's size doesn't change, no wxSizeEvent will
- normally be sent. Here we add an extra test if
- the client test has been changed and this will
- be used then. */
+ // update these variables to keep size_allocate handler
+ // from sending another size event for this change
GetClientSize( &m_oldClientWidth, &m_oldClientHeight );
- }
-
-/*
- wxPrintf( "OnSize sent from " );
- if (GetClassInfo() && GetClassInfo()->GetClassName())
- wxPrintf( GetClassInfo()->GetClassName() );
- wxPrintf( " %d %d %d %d\n", (int)m_x, (int)m_y, (int)m_width, (int)m_height );
-*/
- if (!m_nativeSizeEvent)
- {
- wxSizeEvent event( wxSize(m_width,m_height), GetId() );
- event.SetEventObject( this );
- GetEventHandler()->ProcessEvent( event );
+ gtk_widget_queue_resize(m_widget);
+ if (!m_nativeSizeEvent)
+ {
+ wxSizeEvent event( wxSize(m_width,m_height), GetId() );
+ event.SetEventObject( this );
+ GetEventHandler()->ProcessEvent( event );
+ }
}
-
- m_resizing = false;
}
bool wxWindowGTK::GtkShowFromOnIdle()