Some make corrections for HP and related,

Changed refresh order so that window-less widgets
    don't get overdrawn anymore,
  Prevent GTK from filtering our supposedly unneeded
    expose events,
  Block all expose calls if a resize is requested and
    do a full redraw then, thus removing flicker and
    behaving like wxMSW,
  Moved some doubled expose and draw code from GtkPizza
    to the respective callbacks in window.cpp,
  Set idle priority to a higher value (which should
    indicate a lower priority if I interpret glib.h
    correctly) but the desired side-effect didn't
    really show up.


git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@6533 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Robert Roebling
2000-03-09 13:24:34 +00:00
parent 6da3a3ef1f
commit b6fa52db66
21 changed files with 557 additions and 350 deletions

View File

@@ -751,6 +751,7 @@ SAMPLES_DIST: ALL_GUI_DIST
cp $(SAMPDIR)/drawing/makefile.unx $(DISTDIR)/samples/drawing
cp $(SAMPDIR)/drawing/*.cpp $(DISTDIR)/samples/drawing
cp $(SAMPDIR)/drawing/*.xpm $(DISTDIR)/samples/drawing
cp $(SAMPDIR)/drawing/*.bmp $(DISTDIR)/samples/drawing
mkdir $(DISTDIR)/samples/dynamic
cp $(SAMPDIR)/dynamic/Makefile.in $(DISTDIR)/samples/dynamic
@@ -806,6 +807,7 @@ SAMPLES_DIST: ALL_GUI_DIST
cp $(SAMPDIR)/html/test/*.cpp $(DISTDIR)/samples/html/test
cp $(SAMPDIR)/html/test/*.bmp $(DISTDIR)/samples/html/test
cp $(SAMPDIR)/html/test/*.png $(DISTDIR)/samples/html/test
cp $(SAMPDIR)/html/test/*.gif $(DISTDIR)/samples/html/test
cp $(SAMPDIR)/html/test/*.htm $(DISTDIR)/samples/html/test
cp $(SAMPDIR)/html/test/*.html $(DISTDIR)/samples/html/test
mkdir $(DISTDIR)/samples/html/virtual
@@ -839,10 +841,10 @@ SAMPLES_DIST: ALL_GUI_DIST
cp $(SAMPDIR)/internat/*.xpm $(DISTDIR)/samples/internat
cp $(SAMPDIR)/internat/*.txt $(DISTDIR)/samples/internat
cp $(SAMPDIR)/internat/*.po $(DISTDIR)/samples/internat
cp $(SAMPDIR)/internat/fr/*.po $(DISTDIR)/samples/internat/fr
cp $(SAMPDIR)/internat/fr/*.mo $(DISTDIR)/samples/internat/fr
cp $(SAMPDIR)/internat/de/*.mo $(DISTDIR)/samples/internat/de
cp $(SAMPDIR)/internat/fr/*.po $(DISTDIR)/samples/internat/fr
cp $(SAMPDIR)/internat/de/*.mo $(DISTDIR)/samples/internat/de
cp $(SAMPDIR)/internat/de/*.po $(DISTDIR)/samples/internat/de
mkdir $(DISTDIR)/samples/ipc
cp $(SAMPDIR)/ipc/Makefile.in $(DISTDIR)/samples/ipc

View File

@@ -51,6 +51,7 @@ dnl
#include <gtk/gtk.h>
#include <gtk/gtkfeatures.h>
#include <stdio.h>
#include <stdlib.h>
int
main ()

View File

@@ -33,9 +33,19 @@ typedef enum
GTK_MYSHADOW_OUT
} GtkMyShadowType;
typedef struct _GtkPizzaChild GtkPizzaChild;
typedef struct _GtkPizza GtkPizza;
typedef struct _GtkPizzaClass GtkPizzaClass;
struct _GtkPizzaChild
{
GtkWidget *widget;
gint x;
gint y;
gint width;
gint height;
};
struct _GtkPizza
{
GtkContainer container;

View File

@@ -186,6 +186,8 @@ public:
bool m_isFrame:1; /* faster than IS_KIND_OF */
bool m_acceptsFocus:1; /* not wxStaticBox, not wxStaticBitmap etc. */
bool m_isScrolling;
bool m_clipPaintRegion; /* TRUE after ScrollWindow() */
bool m_queuedFullRedraw; /* TRUE after DoMoveWindow */
// these are true if the style were set before the widget was realized
// (typcally in the constructor) but the actual GTK style must not be set

View File

@@ -33,9 +33,19 @@ typedef enum
GTK_MYSHADOW_OUT
} GtkMyShadowType;
typedef struct _GtkPizzaChild GtkPizzaChild;
typedef struct _GtkPizza GtkPizza;
typedef struct _GtkPizzaClass GtkPizzaClass;
struct _GtkPizzaChild
{
GtkWidget *widget;
gint x;
gint y;
gint width;
gint height;
};
struct _GtkPizza
{
GtkContainer container;

View File

@@ -186,6 +186,8 @@ public:
bool m_isFrame:1; /* faster than IS_KIND_OF */
bool m_acceptsFocus:1; /* not wxStaticBox, not wxStaticBitmap etc. */
bool m_isScrolling;
bool m_clipPaintRegion; /* TRUE after ScrollWindow() */
bool m_queuedFullRedraw; /* TRUE after DoMoveWindow */
// these are true if the style were set before the widget was realized
// (typcally in the constructor) but the actual GTK style must not be set

View File

@@ -128,7 +128,7 @@ enum
Minimal_Test2,
// controls start here (the numbers are, of course, arbitrary)
Minimal_Text = 1000,
Minimal_Text = 1000
};
// ----------------------------------------------------------------------------

View File

@@ -127,7 +127,7 @@ enum
HelpDemo_Help_GNOME,
HelpDemo_Help_Netscape,
// controls start here (the numbers are, of course, arbitrary)
HelpDemo_Text = 1000,
HelpDemo_Text = 1000
};
// ----------------------------------------------------------------------------

View File

@@ -74,7 +74,7 @@
Minimal_Forward,
// controls start here (the numbers are, of course, arbitrary)
Minimal_Text = 1000,
Minimal_Text = 1000
};
// ----------------------------------------------------------------------------

View File

@@ -75,7 +75,7 @@
Minimal_Forward,
// controls start here (the numbers are, of course, arbitrary)
Minimal_Text = 1000,
Minimal_Text = 1000
};
// ----------------------------------------------------------------------------

View File

@@ -928,9 +928,11 @@ wxFileDialog::wxFileDialog(wxWindow *parent,
Centre( wxBOTH );
/*
if (m_fileName.IsEmpty())
m_list->SetFocus();
else
*/
m_text->SetFocus();
wxEndBusyCursor();

View File

@@ -95,8 +95,8 @@ bool wxYield()
if (has_idle)
{
/* re-add idle handler */
wxTheApp->m_idleTag = gtk_idle_add( wxapp_idle_callback, (gpointer) NULL );
/* re-add idle handler (very low priority) */
wxTheApp->m_idleTag = gtk_idle_add_priority( 500, wxapp_idle_callback, (gpointer) NULL );
}
// disable log flushing from here because a call to wxYield() shouldn't
@@ -177,9 +177,9 @@ void wxapp_install_idle_handler()
indicating that the idle is over. It may also
get called from other thread for sending events
to the main thread (and processing these in
idle time). */
idle time). Very low priority. */
wxTheApp->m_idleTag = gtk_idle_add( wxapp_idle_callback, (gpointer) NULL );
wxTheApp->m_idleTag = gtk_idle_add_priority( 500, wxapp_idle_callback, (gpointer) NULL );
g_isIdle = FALSE;
}

View File

@@ -2019,7 +2019,10 @@ wxPaintDC::wxPaintDC()
wxPaintDC::wxPaintDC( wxWindow *win )
: wxWindowDC( win )
{
#if USE_PAINT_REGION
#if USE_PAINT_REGION
if (!win->m_clipPaintRegion)
return;
m_paintClippingRegion = win->GetUpdateRegion();
m_currentClippingRegion.Union( m_paintClippingRegion );

View File

@@ -834,6 +834,7 @@ void wxFrame::GtkOnSize( int WXUNUSED(x), int WXUNUSED(y),
gtk_pizza_set_size( GTK_PIZZA(m_wxwindow),
m_frameStatusBar->m_widget,
xx, yy, ww, hh );
gtk_widget_draw( m_frameStatusBar->m_widget, (GdkRectangle*) NULL );
}
#endif

View File

@@ -30,7 +30,6 @@ extern "C" {
(y >= G_MINSHORT) && (y <= G_MAXSHORT))
typedef struct _GtkPizzaAdjData GtkPizzaAdjData;
typedef struct _GtkPizzaChild GtkPizzaChild;
struct _GtkPizzaAdjData
{
@@ -38,22 +37,13 @@ struct _GtkPizzaAdjData
gint dy;
};
struct _GtkPizzaChild
{
GtkWidget *widget;
gint x;
gint y;
gint width;
gint height;
};
static void gtk_pizza_class_init (GtkPizzaClass *klass);
static void gtk_pizza_init (GtkPizza *pizza);
static void gtk_pizza_class_init (GtkPizzaClass *klass);
static void gtk_pizza_init (GtkPizza *pizza);
static void gtk_pizza_realize (GtkWidget *widget);
static void gtk_pizza_unrealize (GtkWidget *widget);
static void gtk_pizza_realize (GtkWidget *widget);
static void gtk_pizza_unrealize (GtkWidget *widget);
static void gtk_pizza_map (GtkWidget *widget);
static void gtk_pizza_map (GtkWidget *widget);
static void gtk_pizza_size_request (GtkWidget *widget,
GtkRequisition *requisition);
@@ -67,42 +57,42 @@ static void gtk_pizza_add (GtkContainer *container,
GtkWidget *widget);
static void gtk_pizza_remove (GtkContainer *container,
GtkWidget *widget);
static void gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data);
static void gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data);
static void gtk_pizza_position_child (GtkPizza *pizza,
GtkPizzaChild *child);
GtkPizzaChild *child);
static void gtk_pizza_allocate_child (GtkPizza *pizza,
GtkPizzaChild *child);
GtkPizzaChild *child);
static void gtk_pizza_position_children (GtkPizza *pizza);
static void gtk_pizza_adjust_allocations_recurse (GtkWidget *widget,
gpointer cb_data);
static void gtk_pizza_adjust_allocations (GtkPizza *pizza,
gint dx,
gint dy);
gpointer cb_data);
static void gtk_pizza_adjust_allocations (GtkPizza *pizza,
gint dx,
gint dy);
static void gtk_pizza_expose_area (GtkPizza *pizza,
gint x,
gint y,
gint width,
gint height);
static void gtk_pizza_expose_area (GtkPizza *pizza,
gint x,
gint y,
gint width,
gint height);
static void gtk_pizza_adjustment_changed (GtkAdjustment *adjustment,
GtkPizza *pizza);
GtkPizza *pizza);
static GdkFilterReturn gtk_pizza_filter (GdkXEvent *gdk_xevent,
GdkEvent *event,
gpointer data);
GdkEvent *event,
gpointer data);
static GdkFilterReturn gtk_pizza_main_filter (GdkXEvent *gdk_xevent,
GdkEvent *event,
gpointer data);
GdkEvent *event,
gpointer data);
static GtkType gtk_pizza_child_type (GtkContainer *container);
static void gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
static void gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
GtkAdjustment *hadj,
GtkAdjustment *vadj);
@@ -200,7 +190,7 @@ gtk_pizza_init (GtkPizza *pizza)
pizza->visibility = GDK_VISIBILITY_PARTIAL;
pizza->clear_on_draw = TRUE;
pizza->use_filter = FALSE;
pizza->use_filter = TRUE;
}
GtkWidget*
@@ -222,7 +212,7 @@ gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
}
void
gtk_pizza_set_shadow_type (GtkPizza *pizza,
gtk_pizza_set_shadow_type (GtkPizza *pizza,
GtkMyShadowType type)
{
g_return_if_fail (pizza != NULL);
@@ -241,8 +231,8 @@ gtk_pizza_set_shadow_type (GtkPizza *pizza,
}
void
gtk_pizza_set_clear (GtkPizza *pizza,
gboolean clear)
gtk_pizza_set_clear (GtkPizza *pizza,
gboolean clear)
{
g_return_if_fail (pizza != NULL);
g_return_if_fail (GTK_IS_PIZZA (pizza));
@@ -251,8 +241,8 @@ gtk_pizza_set_clear (GtkPizza *pizza,
}
void
gtk_pizza_set_filter (GtkPizza *pizza,
gboolean use)
gtk_pizza_set_filter (GtkPizza *pizza,
gboolean use)
{
g_return_if_fail (pizza != NULL);
g_return_if_fail (GTK_IS_PIZZA (pizza));
@@ -261,12 +251,12 @@ gtk_pizza_set_filter (GtkPizza *pizza,
}
void
gtk_pizza_put (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
gtk_pizza_put (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
{
GtkPizzaChild *child_info;
@@ -311,10 +301,10 @@ gtk_pizza_put (GtkPizza *pizza,
}
void
gtk_pizza_move (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y)
gtk_pizza_move (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y)
{
GtkPizzaChild *child;
GList *children;
@@ -345,10 +335,10 @@ gtk_pizza_move (GtkPizza *pizza,
}
void
gtk_pizza_resize (GtkPizza *pizza,
GtkWidget *widget,
gint width,
gint height)
gtk_pizza_resize (GtkPizza *pizza,
GtkWidget *widget,
gint width,
gint height)
{
GtkPizzaChild *child;
GList *children;
@@ -381,12 +371,12 @@ gtk_pizza_resize (GtkPizza *pizza,
}
void
gtk_pizza_set_size (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
gtk_pizza_set_size (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
{
GtkPizzaChild *child;
GList *children;
@@ -539,7 +529,7 @@ gtk_pizza_realize (GtkWidget *widget)
widget->style = gtk_style_attach (widget->style, widget->window);
gtk_style_set_background (widget->style, widget->window, GTK_STATE_NORMAL);
gtk_style_set_background (widget->style, pizza->bin_window, GTK_STATE_NORMAL);
gtk_style_set_background (widget->style, pizza->bin_window, GTK_STATE_NORMAL );
/* add filters for intercepting visibility and expose events */
gdk_window_add_filter (widget->window, gtk_pizza_main_filter, pizza);
@@ -579,7 +569,7 @@ gtk_pizza_unrealize (GtkWidget *widget)
static void
gtk_pizza_size_request (GtkWidget *widget,
GtkRequisition *requisition)
GtkRequisition *requisition)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -612,7 +602,7 @@ gtk_pizza_size_request (GtkWidget *widget,
static void
gtk_pizza_size_allocate (GtkWidget *widget,
GtkAllocation *allocation)
GtkAllocation *allocation)
{
GtkPizza *pizza;
gint border;
@@ -660,70 +650,17 @@ gtk_pizza_size_allocate (GtkWidget *widget,
static void
gtk_pizza_draw (GtkWidget *widget,
GdkRectangle *area)
GdkRectangle *area)
{
GtkPizza *pizza;
GtkPizzaChild *child;
GdkRectangle child_area;
GList *children;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PIZZA (widget));
pizza = GTK_PIZZA (widget);
children = pizza->children;
if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) &&
(pizza->clear_on_draw))
{
gdk_window_clear_area( pizza->bin_window,
area->x, area->y, area->width, area->height);
}
while (children)
{
child = children->data;
children = children->next;
if (gtk_widget_intersect (child->widget, area, &child_area))
gtk_widget_draw (child->widget, &child_area);
}
/* We handle all draws events in window.cpp now. */
return;
}
static gint
gtk_pizza_expose (GtkWidget *widget,
GdkEventExpose *event)
GdkEventExpose *event)
{
GtkPizza *pizza;
GtkPizzaChild *child;
GdkEventExpose child_event;
GList *children;
g_return_val_if_fail (widget != NULL, FALSE);
g_return_val_if_fail (GTK_IS_PIZZA (widget), FALSE);
g_return_val_if_fail (event != NULL, FALSE);
pizza = GTK_PIZZA (widget);
if (event->window != pizza->bin_window)
return FALSE;
children = pizza->children;
while (children)
{
child = children->data;
children = children->next;
child_event = *event;
if (GTK_WIDGET_NO_WINDOW (child->widget) &&
GTK_WIDGET_DRAWABLE (child->widget) &&
gtk_widget_intersect (child->widget, &event->area, &child_event.area))
{
gtk_widget_event (child->widget, (GdkEvent*) &child_event);
}
}
/* We handle all expose events in window.cpp now. */
return FALSE;
}
@@ -740,7 +677,7 @@ gtk_pizza_add (GtkContainer *container,
static void
gtk_pizza_remove (GtkContainer *container,
GtkWidget *widget)
GtkWidget *widget)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -782,9 +719,9 @@ gtk_pizza_remove (GtkContainer *container,
static void
gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data)
gboolean include_internals,
GtkCallback callback,
gpointer callback_data)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -812,7 +749,7 @@ gtk_pizza_forall (GtkContainer *container,
static void
gtk_pizza_position_child (GtkPizza *pizza,
GtkPizzaChild *child)
GtkPizzaChild *child)
{
gint x;
gint y;
@@ -844,7 +781,7 @@ gtk_pizza_position_child (GtkPizza *pizza,
static void
gtk_pizza_allocate_child (GtkPizza *pizza,
GtkPizzaChild *child)
GtkPizzaChild *child)
{
GtkAllocation allocation;
GtkRequisition requisition;
@@ -1166,6 +1103,9 @@ gtk_pizza_filter (GdkXEvent *gdk_xevent,
pizza = GTK_PIZZA (data);
if (!pizza->use_filter)
return GDK_FILTER_CONTINUE;
switch (xevent->type)
{
case Expose:
@@ -1210,6 +1150,9 @@ gtk_pizza_main_filter (GdkXEvent *gdk_xevent,
xevent = (XEvent *)gdk_xevent;
pizza = GTK_PIZZA (data);
if (!pizza->use_filter)
return GDK_FILTER_CONTINUE;
if (xevent->type == VisibilityNotify)
{

View File

@@ -381,10 +381,13 @@ static void draw_frame( GtkWidget *widget, wxWindow *win )
// "expose_event" of m_widget
//-----------------------------------------------------------------------------
static void gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
gint gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
{
if (gdk_event->count > 0) return;
if (gdk_event->count > 0) return FALSE;
draw_frame( widget, win );
return TRUE;
}
//-----------------------------------------------------------------------------
@@ -610,12 +613,18 @@ static long map_to_wx_keysym( KeySym keysym )
// "expose_event" of m_wxwindow
//-----------------------------------------------------------------------------
static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExpose *gdk_event, wxWindow *win )
static int gtk_window_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
{
DEBUG_MAIN_THREAD
if (g_isIdle)
wxapp_install_idle_handler();
if (win->m_queuedFullRedraw)
return TRUE;
/*
if (win->GetName() == wxT("grid window"))
if (win->GetName() == wxT("htmlWindow"))
{
wxPrintf( wxT("OnExpose from ") );
if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
@@ -634,10 +643,7 @@ static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExp
if (gdk_event->count > 0)
return;
if (!win->m_hasVMT)
return;
return TRUE;
wxEraseEvent eevent( win->GetId() );
eevent.SetEventObject( win );
@@ -648,25 +654,85 @@ static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExp
win->GetEventHandler()->ProcessEvent( event );
win->GetUpdateRegion().Clear();
/* The following code will result in all window-less widgets
being redrawn if the wxWindows class is given a chance to
paint *anything* because it will then be allowed to paint
over the window-less widgets */
GtkPizza *pizza = GTK_PIZZA (widget);
GList *children = pizza->children;
while (children)
{
GtkPizzaChild *child = (GtkPizzaChild*) children->data;
children = children->next;
GdkEventExpose child_event = *gdk_event;
if (GTK_WIDGET_NO_WINDOW (child->widget) &&
GTK_WIDGET_DRAWABLE (child->widget))
{
child_event.area.x = child->widget->allocation.x;
child_event.area.y = child->widget->allocation.y;
child_event.area.width = child->widget->allocation.width;
child_event.area.height = child->widget->allocation.height;
gtk_widget_event (child->widget, (GdkEvent*) &child_event);
}
}
return TRUE;
}
//-----------------------------------------------------------------------------
// "event" of m_wxwindow
//-----------------------------------------------------------------------------
/* GTK thinks it is clever and filters out a certain amount of "unneeded"
expose events. We need them, of course, so we override the main event
procedure in GtkWidget by giving our own handler for all system events,
looking for the expose events and then we can always send them. */
gint gtk_window_event_event_callback( GtkWidget *widget, GdkEventExpose *event, wxWindow *win )
{
if (event->type == GDK_EXPOSE)
{
gint ret = gtk_window_expose_callback( widget, event, win );
return ret;
}
return FALSE;
}
//-----------------------------------------------------------------------------
// "draw" of m_wxwindow
//-----------------------------------------------------------------------------
static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
GdkRectangle *rect, wxWindow *win )
/* This callback is a complete replacement of the gtk_pizza_draw() function,
which disabled. */
static void gtk_window_draw_callback( GtkWidget *widget, GdkRectangle *rect, wxWindow *win )
{
DEBUG_MAIN_THREAD
if (g_isIdle)
wxapp_install_idle_handler();
if ((rect->x == 0) && (rect->y == 0) && (rect->width <= 1) && (rect->height <= 1))
if (win->m_queuedFullRedraw)
return;
GtkPizza *pizza = GTK_PIZZA (widget);
if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) &&
(pizza->clear_on_draw))
{
gdk_window_clear_area( pizza->bin_window,
rect->x, rect->y, rect->width, rect->height);
}
/*
if (win->GetName() == wxT("grid window"))
if (win->GetName() == wxT("htmlWindow"))
{
wxPrintf( wxT("OnDraw from ") );
if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
@@ -677,13 +743,10 @@ static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
(int)rect->height );
}
*/
win->GetUpdateRegion().Union( rect->x, rect->y,
rect->width, rect->height );
if (!win->m_hasVMT)
return;
wxEraseEvent eevent( win->GetId() );
eevent.SetEventObject( win );
win->GetEventHandler()->ProcessEvent(eevent);
@@ -693,6 +756,17 @@ static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
win->GetEventHandler()->ProcessEvent( event );
win->GetUpdateRegion().Clear();
GList *children = pizza->children;
while (children)
{
GtkPizzaChild *child = (GtkPizzaChild*) children->data;
children = children->next;
GdkRectangle child_area;
if (gtk_widget_intersect (child->widget, rect, &child_area))
gtk_widget_draw (child->widget, (GdkRectangle*) NULL );
}
}
//-----------------------------------------------------------------------------
@@ -1974,6 +2048,9 @@ void wxWindow::Init()
m_isFrame = FALSE;
m_acceptsFocus = FALSE;
m_clipPaintRegion = FALSE;
m_queuedFullRedraw = FALSE;
m_cursor = *wxSTANDARD_CURSOR;
#ifdef HAVE_XIM
@@ -2008,21 +2085,12 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
}
m_insertCallback = wxInsertChildInWindow;
m_widget = gtk_scrolled_window_new( (GtkAdjustment *) NULL, (GtkAdjustment *) NULL );
GTK_WIDGET_UNSET_FLAGS( m_widget, GTK_CAN_FOCUS );
#ifdef __WXDEBUG__
debug_focus_in( m_widget, wxT("wxWindow::m_widget"), name );
#endif
GtkScrolledWindow *scrolledWindow = GTK_SCROLLED_WINDOW(m_widget);
#ifdef __WXDEBUG__
debug_focus_in( scrolledWindow->hscrollbar, wxT("wxWindow::hsrcollbar"), name );
debug_focus_in( scrolledWindow->vscrollbar, wxT("wxWindow::vsrcollbar"), name );
#endif
GtkScrolledWindowClass *scroll_class = GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(m_widget)->klass );
scroll_class->scrollbar_spacing = 0;
@@ -2033,10 +2101,6 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
m_wxwindow = gtk_pizza_new();
#ifdef __WXDEBUG__
debug_focus_in( m_wxwindow, wxT("wxWindow::m_wxwindow"), name );
#endif
gtk_container_add( GTK_CONTAINER(m_widget), m_wxwindow );
#if (GTK_MINOR_VERSION > 0)
@@ -2221,6 +2285,9 @@ void wxWindow::PostCreation()
if (!m_noExpose)
{
/* these get reported to wxWindows -> wxPaintEvent */
gtk_signal_connect( GTK_OBJECT(m_wxwindow), "event",
GTK_SIGNAL_FUNC(gtk_window_event_event_callback), (gpointer)this );
gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event",
GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this );
@@ -2320,6 +2387,24 @@ bool wxWindow::Destroy()
void wxWindow::DoMoveWindow(int x, int y, int width, int height)
{
if (m_wxwindow && GTK_PIZZA(m_wxwindow)->bin_window)
{
/* Normally, GTK will send expose events only for the regions
which actually got exposed. Sadly, wxMSW invalidates
the whole window so we have to do that, too. We could
simply add a complete refresh, but we would then get
the normal GTK expose events in surplus, so we shut
off the expose events and schedule a full redraw to
be done in OnInternalIdle, where we restore the handling
of expose events. */
m_queuedFullRedraw = TRUE;
GdkEventMask mask = gdk_window_get_events( GTK_PIZZA(m_wxwindow)->bin_window );
mask = (GdkEventMask)(mask & ~GDK_EXPOSURE_MASK);
gdk_window_set_events( GTK_PIZZA(m_wxwindow)->bin_window, mask );
}
gtk_pizza_set_size( GTK_PIZZA(m_parent->m_wxwindow), m_widget, x, y, width, height );
}
@@ -2330,7 +2415,7 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
if (m_resizing) return; /* I don't like recursions */
m_resizing = TRUE;
if (m_parent->m_wxwindow == NULL) /* i.e. wxNotebook */
{
/* don't set the size for children of wxNotebook, just take the values. */
@@ -2391,6 +2476,12 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
if (m_hasScrolling)
{
/* 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. */
GetClientSize( &m_oldClientWidth, &m_oldClientHeight );
}
@@ -2461,6 +2552,27 @@ void wxWindow::OnInternalIdle()
}
UpdateWindowUI();
if (m_queuedFullRedraw)
{
/* See also wxWindow::DoMoveWindow for explanation of this code. What
we test here is if the requested size of the window is the same as
the actual size of window, in which case all expose events that resulted
from resizing the window have been sent (and discarded) and we can
now do our full redraw and switch on expose event handling again. */
if ((m_width == m_widget->allocation.width) && (m_height == m_widget->allocation.height))
{
m_queuedFullRedraw = FALSE;
m_updateRegion.Clear();
m_updateRegion.Union( 0,0,m_width,m_height );
gtk_widget_draw( m_wxwindow, (GdkRectangle*) NULL );
GdkEventMask mask = gdk_window_get_events( GTK_PIZZA(m_wxwindow)->bin_window );
mask = (GdkEventMask)(mask | GDK_EXPOSURE_MASK);
gdk_window_set_events( GTK_PIZZA(m_wxwindow)->bin_window, mask );
}
}
}
void wxWindow::DoGetSize( int *width, int *height ) const
@@ -2898,37 +3010,65 @@ void wxWindow::Refresh( bool eraseBackground, const wxRect *rect )
{
if (m_wxwindow)
{
/*
GtkPizza *pizza = GTK_PIZZA(m_wxwindow);
gboolean old_clear = pizza->clear_on_draw;
gtk_pizza_set_clear( pizza, FALSE );
gtk_widget_draw( m_wxwindow, (GdkRectangle*) NULL );
gtk_pizza_set_clear( pizza, old_clear );
*/
GdkEventExpose gdk_event;
gdk_event.count = 0;
gdk_event.area.x = 0;
gdk_event.area.y = 0;
gdk_event.area.width = m_wxwindow->allocation.width;
gdk_event.area.height = m_wxwindow->allocation.height;
gtk_window_expose_callback( m_wxwindow, &gdk_event, this );
}
else
{
gtk_widget_draw( m_widget, (GdkRectangle*) NULL );
}
}
else
{
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
if (m_wxwindow)
{
/*
GtkPizza *pizza = GTK_PIZZA(m_wxwindow);
gboolean old_clear = pizza->clear_on_draw;
gtk_pizza_set_clear( pizza, FALSE );
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
gtk_widget_draw( m_wxwindow, &gdk_rect );
gtk_window_draw_callback( m_wxwindow, &gdk_rect, this );
gtk_pizza_set_clear( pizza, old_clear );
*/
GdkEventExpose gdk_event;
gdk_event.count = 0;
gdk_event.area.x = rect->x;
gdk_event.area.y = rect->y;
gdk_event.area.width = rect->width;
gdk_event.area.height = rect->height;
gtk_window_expose_callback( m_wxwindow, &gdk_event, this );
}
else
{
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
gtk_widget_draw( m_widget, &gdk_rect );
}
}
}
@@ -3452,7 +3592,9 @@ void wxWindow::ScrollWindow( int dx, int dy, const wxRect* WXUNUSED(rect) )
if ((dx == 0) && (dy == 0)) return;
m_clipPaintRegion = TRUE;
gtk_pizza_scroll( GTK_PIZZA(m_wxwindow), -dx, -dy );
m_clipPaintRegion = FALSE;
/*
if (m_children.GetCount() > 0)

View File

@@ -95,8 +95,8 @@ bool wxYield()
if (has_idle)
{
/* re-add idle handler */
wxTheApp->m_idleTag = gtk_idle_add( wxapp_idle_callback, (gpointer) NULL );
/* re-add idle handler (very low priority) */
wxTheApp->m_idleTag = gtk_idle_add_priority( 500, wxapp_idle_callback, (gpointer) NULL );
}
// disable log flushing from here because a call to wxYield() shouldn't
@@ -177,9 +177,9 @@ void wxapp_install_idle_handler()
indicating that the idle is over. It may also
get called from other thread for sending events
to the main thread (and processing these in
idle time). */
idle time). Very low priority. */
wxTheApp->m_idleTag = gtk_idle_add( wxapp_idle_callback, (gpointer) NULL );
wxTheApp->m_idleTag = gtk_idle_add_priority( 500, wxapp_idle_callback, (gpointer) NULL );
g_isIdle = FALSE;
}

View File

@@ -2019,7 +2019,10 @@ wxPaintDC::wxPaintDC()
wxPaintDC::wxPaintDC( wxWindow *win )
: wxWindowDC( win )
{
#if USE_PAINT_REGION
#if USE_PAINT_REGION
if (!win->m_clipPaintRegion)
return;
m_paintClippingRegion = win->GetUpdateRegion();
m_currentClippingRegion.Union( m_paintClippingRegion );

View File

@@ -834,6 +834,7 @@ void wxFrame::GtkOnSize( int WXUNUSED(x), int WXUNUSED(y),
gtk_pizza_set_size( GTK_PIZZA(m_wxwindow),
m_frameStatusBar->m_widget,
xx, yy, ww, hh );
gtk_widget_draw( m_frameStatusBar->m_widget, (GdkRectangle*) NULL );
}
#endif

View File

@@ -30,7 +30,6 @@ extern "C" {
(y >= G_MINSHORT) && (y <= G_MAXSHORT))
typedef struct _GtkPizzaAdjData GtkPizzaAdjData;
typedef struct _GtkPizzaChild GtkPizzaChild;
struct _GtkPizzaAdjData
{
@@ -38,22 +37,13 @@ struct _GtkPizzaAdjData
gint dy;
};
struct _GtkPizzaChild
{
GtkWidget *widget;
gint x;
gint y;
gint width;
gint height;
};
static void gtk_pizza_class_init (GtkPizzaClass *klass);
static void gtk_pizza_init (GtkPizza *pizza);
static void gtk_pizza_class_init (GtkPizzaClass *klass);
static void gtk_pizza_init (GtkPizza *pizza);
static void gtk_pizza_realize (GtkWidget *widget);
static void gtk_pizza_unrealize (GtkWidget *widget);
static void gtk_pizza_realize (GtkWidget *widget);
static void gtk_pizza_unrealize (GtkWidget *widget);
static void gtk_pizza_map (GtkWidget *widget);
static void gtk_pizza_map (GtkWidget *widget);
static void gtk_pizza_size_request (GtkWidget *widget,
GtkRequisition *requisition);
@@ -67,42 +57,42 @@ static void gtk_pizza_add (GtkContainer *container,
GtkWidget *widget);
static void gtk_pizza_remove (GtkContainer *container,
GtkWidget *widget);
static void gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data);
static void gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data);
static void gtk_pizza_position_child (GtkPizza *pizza,
GtkPizzaChild *child);
GtkPizzaChild *child);
static void gtk_pizza_allocate_child (GtkPizza *pizza,
GtkPizzaChild *child);
GtkPizzaChild *child);
static void gtk_pizza_position_children (GtkPizza *pizza);
static void gtk_pizza_adjust_allocations_recurse (GtkWidget *widget,
gpointer cb_data);
static void gtk_pizza_adjust_allocations (GtkPizza *pizza,
gint dx,
gint dy);
gpointer cb_data);
static void gtk_pizza_adjust_allocations (GtkPizza *pizza,
gint dx,
gint dy);
static void gtk_pizza_expose_area (GtkPizza *pizza,
gint x,
gint y,
gint width,
gint height);
static void gtk_pizza_expose_area (GtkPizza *pizza,
gint x,
gint y,
gint width,
gint height);
static void gtk_pizza_adjustment_changed (GtkAdjustment *adjustment,
GtkPizza *pizza);
GtkPizza *pizza);
static GdkFilterReturn gtk_pizza_filter (GdkXEvent *gdk_xevent,
GdkEvent *event,
gpointer data);
GdkEvent *event,
gpointer data);
static GdkFilterReturn gtk_pizza_main_filter (GdkXEvent *gdk_xevent,
GdkEvent *event,
gpointer data);
GdkEvent *event,
gpointer data);
static GtkType gtk_pizza_child_type (GtkContainer *container);
static void gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
static void gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
GtkAdjustment *hadj,
GtkAdjustment *vadj);
@@ -200,7 +190,7 @@ gtk_pizza_init (GtkPizza *pizza)
pizza->visibility = GDK_VISIBILITY_PARTIAL;
pizza->clear_on_draw = TRUE;
pizza->use_filter = FALSE;
pizza->use_filter = TRUE;
}
GtkWidget*
@@ -222,7 +212,7 @@ gtk_pizza_scroll_set_adjustments (GtkPizza *pizza,
}
void
gtk_pizza_set_shadow_type (GtkPizza *pizza,
gtk_pizza_set_shadow_type (GtkPizza *pizza,
GtkMyShadowType type)
{
g_return_if_fail (pizza != NULL);
@@ -241,8 +231,8 @@ gtk_pizza_set_shadow_type (GtkPizza *pizza,
}
void
gtk_pizza_set_clear (GtkPizza *pizza,
gboolean clear)
gtk_pizza_set_clear (GtkPizza *pizza,
gboolean clear)
{
g_return_if_fail (pizza != NULL);
g_return_if_fail (GTK_IS_PIZZA (pizza));
@@ -251,8 +241,8 @@ gtk_pizza_set_clear (GtkPizza *pizza,
}
void
gtk_pizza_set_filter (GtkPizza *pizza,
gboolean use)
gtk_pizza_set_filter (GtkPizza *pizza,
gboolean use)
{
g_return_if_fail (pizza != NULL);
g_return_if_fail (GTK_IS_PIZZA (pizza));
@@ -261,12 +251,12 @@ gtk_pizza_set_filter (GtkPizza *pizza,
}
void
gtk_pizza_put (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
gtk_pizza_put (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
{
GtkPizzaChild *child_info;
@@ -311,10 +301,10 @@ gtk_pizza_put (GtkPizza *pizza,
}
void
gtk_pizza_move (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y)
gtk_pizza_move (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y)
{
GtkPizzaChild *child;
GList *children;
@@ -345,10 +335,10 @@ gtk_pizza_move (GtkPizza *pizza,
}
void
gtk_pizza_resize (GtkPizza *pizza,
GtkWidget *widget,
gint width,
gint height)
gtk_pizza_resize (GtkPizza *pizza,
GtkWidget *widget,
gint width,
gint height)
{
GtkPizzaChild *child;
GList *children;
@@ -381,12 +371,12 @@ gtk_pizza_resize (GtkPizza *pizza,
}
void
gtk_pizza_set_size (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
gtk_pizza_set_size (GtkPizza *pizza,
GtkWidget *widget,
gint x,
gint y,
gint width,
gint height)
{
GtkPizzaChild *child;
GList *children;
@@ -539,7 +529,7 @@ gtk_pizza_realize (GtkWidget *widget)
widget->style = gtk_style_attach (widget->style, widget->window);
gtk_style_set_background (widget->style, widget->window, GTK_STATE_NORMAL);
gtk_style_set_background (widget->style, pizza->bin_window, GTK_STATE_NORMAL);
gtk_style_set_background (widget->style, pizza->bin_window, GTK_STATE_NORMAL );
/* add filters for intercepting visibility and expose events */
gdk_window_add_filter (widget->window, gtk_pizza_main_filter, pizza);
@@ -579,7 +569,7 @@ gtk_pizza_unrealize (GtkWidget *widget)
static void
gtk_pizza_size_request (GtkWidget *widget,
GtkRequisition *requisition)
GtkRequisition *requisition)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -612,7 +602,7 @@ gtk_pizza_size_request (GtkWidget *widget,
static void
gtk_pizza_size_allocate (GtkWidget *widget,
GtkAllocation *allocation)
GtkAllocation *allocation)
{
GtkPizza *pizza;
gint border;
@@ -660,70 +650,17 @@ gtk_pizza_size_allocate (GtkWidget *widget,
static void
gtk_pizza_draw (GtkWidget *widget,
GdkRectangle *area)
GdkRectangle *area)
{
GtkPizza *pizza;
GtkPizzaChild *child;
GdkRectangle child_area;
GList *children;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PIZZA (widget));
pizza = GTK_PIZZA (widget);
children = pizza->children;
if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) &&
(pizza->clear_on_draw))
{
gdk_window_clear_area( pizza->bin_window,
area->x, area->y, area->width, area->height);
}
while (children)
{
child = children->data;
children = children->next;
if (gtk_widget_intersect (child->widget, area, &child_area))
gtk_widget_draw (child->widget, &child_area);
}
/* We handle all draws events in window.cpp now. */
return;
}
static gint
gtk_pizza_expose (GtkWidget *widget,
GdkEventExpose *event)
GdkEventExpose *event)
{
GtkPizza *pizza;
GtkPizzaChild *child;
GdkEventExpose child_event;
GList *children;
g_return_val_if_fail (widget != NULL, FALSE);
g_return_val_if_fail (GTK_IS_PIZZA (widget), FALSE);
g_return_val_if_fail (event != NULL, FALSE);
pizza = GTK_PIZZA (widget);
if (event->window != pizza->bin_window)
return FALSE;
children = pizza->children;
while (children)
{
child = children->data;
children = children->next;
child_event = *event;
if (GTK_WIDGET_NO_WINDOW (child->widget) &&
GTK_WIDGET_DRAWABLE (child->widget) &&
gtk_widget_intersect (child->widget, &event->area, &child_event.area))
{
gtk_widget_event (child->widget, (GdkEvent*) &child_event);
}
}
/* We handle all expose events in window.cpp now. */
return FALSE;
}
@@ -740,7 +677,7 @@ gtk_pizza_add (GtkContainer *container,
static void
gtk_pizza_remove (GtkContainer *container,
GtkWidget *widget)
GtkWidget *widget)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -782,9 +719,9 @@ gtk_pizza_remove (GtkContainer *container,
static void
gtk_pizza_forall (GtkContainer *container,
gboolean include_internals,
GtkCallback callback,
gpointer callback_data)
gboolean include_internals,
GtkCallback callback,
gpointer callback_data)
{
GtkPizza *pizza;
GtkPizzaChild *child;
@@ -812,7 +749,7 @@ gtk_pizza_forall (GtkContainer *container,
static void
gtk_pizza_position_child (GtkPizza *pizza,
GtkPizzaChild *child)
GtkPizzaChild *child)
{
gint x;
gint y;
@@ -844,7 +781,7 @@ gtk_pizza_position_child (GtkPizza *pizza,
static void
gtk_pizza_allocate_child (GtkPizza *pizza,
GtkPizzaChild *child)
GtkPizzaChild *child)
{
GtkAllocation allocation;
GtkRequisition requisition;
@@ -1166,6 +1103,9 @@ gtk_pizza_filter (GdkXEvent *gdk_xevent,
pizza = GTK_PIZZA (data);
if (!pizza->use_filter)
return GDK_FILTER_CONTINUE;
switch (xevent->type)
{
case Expose:
@@ -1210,6 +1150,9 @@ gtk_pizza_main_filter (GdkXEvent *gdk_xevent,
xevent = (XEvent *)gdk_xevent;
pizza = GTK_PIZZA (data);
if (!pizza->use_filter)
return GDK_FILTER_CONTINUE;
if (xevent->type == VisibilityNotify)
{

View File

@@ -381,10 +381,13 @@ static void draw_frame( GtkWidget *widget, wxWindow *win )
// "expose_event" of m_widget
//-----------------------------------------------------------------------------
static void gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
gint gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
{
if (gdk_event->count > 0) return;
if (gdk_event->count > 0) return FALSE;
draw_frame( widget, win );
return TRUE;
}
//-----------------------------------------------------------------------------
@@ -610,12 +613,18 @@ static long map_to_wx_keysym( KeySym keysym )
// "expose_event" of m_wxwindow
//-----------------------------------------------------------------------------
static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExpose *gdk_event, wxWindow *win )
static int gtk_window_expose_callback( GtkWidget *widget, GdkEventExpose *gdk_event, wxWindow *win )
{
DEBUG_MAIN_THREAD
if (g_isIdle)
wxapp_install_idle_handler();
if (win->m_queuedFullRedraw)
return TRUE;
/*
if (win->GetName() == wxT("grid window"))
if (win->GetName() == wxT("htmlWindow"))
{
wxPrintf( wxT("OnExpose from ") );
if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
@@ -634,10 +643,7 @@ static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExp
if (gdk_event->count > 0)
return;
if (!win->m_hasVMT)
return;
return TRUE;
wxEraseEvent eevent( win->GetId() );
eevent.SetEventObject( win );
@@ -648,25 +654,85 @@ static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExp
win->GetEventHandler()->ProcessEvent( event );
win->GetUpdateRegion().Clear();
/* The following code will result in all window-less widgets
being redrawn if the wxWindows class is given a chance to
paint *anything* because it will then be allowed to paint
over the window-less widgets */
GtkPizza *pizza = GTK_PIZZA (widget);
GList *children = pizza->children;
while (children)
{
GtkPizzaChild *child = (GtkPizzaChild*) children->data;
children = children->next;
GdkEventExpose child_event = *gdk_event;
if (GTK_WIDGET_NO_WINDOW (child->widget) &&
GTK_WIDGET_DRAWABLE (child->widget))
{
child_event.area.x = child->widget->allocation.x;
child_event.area.y = child->widget->allocation.y;
child_event.area.width = child->widget->allocation.width;
child_event.area.height = child->widget->allocation.height;
gtk_widget_event (child->widget, (GdkEvent*) &child_event);
}
}
return TRUE;
}
//-----------------------------------------------------------------------------
// "event" of m_wxwindow
//-----------------------------------------------------------------------------
/* GTK thinks it is clever and filters out a certain amount of "unneeded"
expose events. We need them, of course, so we override the main event
procedure in GtkWidget by giving our own handler for all system events,
looking for the expose events and then we can always send them. */
gint gtk_window_event_event_callback( GtkWidget *widget, GdkEventExpose *event, wxWindow *win )
{
if (event->type == GDK_EXPOSE)
{
gint ret = gtk_window_expose_callback( widget, event, win );
return ret;
}
return FALSE;
}
//-----------------------------------------------------------------------------
// "draw" of m_wxwindow
//-----------------------------------------------------------------------------
static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
GdkRectangle *rect, wxWindow *win )
/* This callback is a complete replacement of the gtk_pizza_draw() function,
which disabled. */
static void gtk_window_draw_callback( GtkWidget *widget, GdkRectangle *rect, wxWindow *win )
{
DEBUG_MAIN_THREAD
if (g_isIdle)
wxapp_install_idle_handler();
if ((rect->x == 0) && (rect->y == 0) && (rect->width <= 1) && (rect->height <= 1))
if (win->m_queuedFullRedraw)
return;
GtkPizza *pizza = GTK_PIZZA (widget);
if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) &&
(pizza->clear_on_draw))
{
gdk_window_clear_area( pizza->bin_window,
rect->x, rect->y, rect->width, rect->height);
}
/*
if (win->GetName() == wxT("grid window"))
if (win->GetName() == wxT("htmlWindow"))
{
wxPrintf( wxT("OnDraw from ") );
if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
@@ -677,13 +743,10 @@ static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
(int)rect->height );
}
*/
win->GetUpdateRegion().Union( rect->x, rect->y,
rect->width, rect->height );
if (!win->m_hasVMT)
return;
wxEraseEvent eevent( win->GetId() );
eevent.SetEventObject( win );
win->GetEventHandler()->ProcessEvent(eevent);
@@ -693,6 +756,17 @@ static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget),
win->GetEventHandler()->ProcessEvent( event );
win->GetUpdateRegion().Clear();
GList *children = pizza->children;
while (children)
{
GtkPizzaChild *child = (GtkPizzaChild*) children->data;
children = children->next;
GdkRectangle child_area;
if (gtk_widget_intersect (child->widget, rect, &child_area))
gtk_widget_draw (child->widget, (GdkRectangle*) NULL );
}
}
//-----------------------------------------------------------------------------
@@ -1974,6 +2048,9 @@ void wxWindow::Init()
m_isFrame = FALSE;
m_acceptsFocus = FALSE;
m_clipPaintRegion = FALSE;
m_queuedFullRedraw = FALSE;
m_cursor = *wxSTANDARD_CURSOR;
#ifdef HAVE_XIM
@@ -2008,21 +2085,12 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
}
m_insertCallback = wxInsertChildInWindow;
m_widget = gtk_scrolled_window_new( (GtkAdjustment *) NULL, (GtkAdjustment *) NULL );
GTK_WIDGET_UNSET_FLAGS( m_widget, GTK_CAN_FOCUS );
#ifdef __WXDEBUG__
debug_focus_in( m_widget, wxT("wxWindow::m_widget"), name );
#endif
GtkScrolledWindow *scrolledWindow = GTK_SCROLLED_WINDOW(m_widget);
#ifdef __WXDEBUG__
debug_focus_in( scrolledWindow->hscrollbar, wxT("wxWindow::hsrcollbar"), name );
debug_focus_in( scrolledWindow->vscrollbar, wxT("wxWindow::vsrcollbar"), name );
#endif
GtkScrolledWindowClass *scroll_class = GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(m_widget)->klass );
scroll_class->scrollbar_spacing = 0;
@@ -2033,10 +2101,6 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
m_wxwindow = gtk_pizza_new();
#ifdef __WXDEBUG__
debug_focus_in( m_wxwindow, wxT("wxWindow::m_wxwindow"), name );
#endif
gtk_container_add( GTK_CONTAINER(m_widget), m_wxwindow );
#if (GTK_MINOR_VERSION > 0)
@@ -2221,6 +2285,9 @@ void wxWindow::PostCreation()
if (!m_noExpose)
{
/* these get reported to wxWindows -> wxPaintEvent */
gtk_signal_connect( GTK_OBJECT(m_wxwindow), "event",
GTK_SIGNAL_FUNC(gtk_window_event_event_callback), (gpointer)this );
gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event",
GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this );
@@ -2320,6 +2387,24 @@ bool wxWindow::Destroy()
void wxWindow::DoMoveWindow(int x, int y, int width, int height)
{
if (m_wxwindow && GTK_PIZZA(m_wxwindow)->bin_window)
{
/* Normally, GTK will send expose events only for the regions
which actually got exposed. Sadly, wxMSW invalidates
the whole window so we have to do that, too. We could
simply add a complete refresh, but we would then get
the normal GTK expose events in surplus, so we shut
off the expose events and schedule a full redraw to
be done in OnInternalIdle, where we restore the handling
of expose events. */
m_queuedFullRedraw = TRUE;
GdkEventMask mask = gdk_window_get_events( GTK_PIZZA(m_wxwindow)->bin_window );
mask = (GdkEventMask)(mask & ~GDK_EXPOSURE_MASK);
gdk_window_set_events( GTK_PIZZA(m_wxwindow)->bin_window, mask );
}
gtk_pizza_set_size( GTK_PIZZA(m_parent->m_wxwindow), m_widget, x, y, width, height );
}
@@ -2330,7 +2415,7 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
if (m_resizing) return; /* I don't like recursions */
m_resizing = TRUE;
if (m_parent->m_wxwindow == NULL) /* i.e. wxNotebook */
{
/* don't set the size for children of wxNotebook, just take the values. */
@@ -2391,6 +2476,12 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
if (m_hasScrolling)
{
/* 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. */
GetClientSize( &m_oldClientWidth, &m_oldClientHeight );
}
@@ -2461,6 +2552,27 @@ void wxWindow::OnInternalIdle()
}
UpdateWindowUI();
if (m_queuedFullRedraw)
{
/* See also wxWindow::DoMoveWindow for explanation of this code. What
we test here is if the requested size of the window is the same as
the actual size of window, in which case all expose events that resulted
from resizing the window have been sent (and discarded) and we can
now do our full redraw and switch on expose event handling again. */
if ((m_width == m_widget->allocation.width) && (m_height == m_widget->allocation.height))
{
m_queuedFullRedraw = FALSE;
m_updateRegion.Clear();
m_updateRegion.Union( 0,0,m_width,m_height );
gtk_widget_draw( m_wxwindow, (GdkRectangle*) NULL );
GdkEventMask mask = gdk_window_get_events( GTK_PIZZA(m_wxwindow)->bin_window );
mask = (GdkEventMask)(mask | GDK_EXPOSURE_MASK);
gdk_window_set_events( GTK_PIZZA(m_wxwindow)->bin_window, mask );
}
}
}
void wxWindow::DoGetSize( int *width, int *height ) const
@@ -2898,37 +3010,65 @@ void wxWindow::Refresh( bool eraseBackground, const wxRect *rect )
{
if (m_wxwindow)
{
/*
GtkPizza *pizza = GTK_PIZZA(m_wxwindow);
gboolean old_clear = pizza->clear_on_draw;
gtk_pizza_set_clear( pizza, FALSE );
gtk_widget_draw( m_wxwindow, (GdkRectangle*) NULL );
gtk_pizza_set_clear( pizza, old_clear );
*/
GdkEventExpose gdk_event;
gdk_event.count = 0;
gdk_event.area.x = 0;
gdk_event.area.y = 0;
gdk_event.area.width = m_wxwindow->allocation.width;
gdk_event.area.height = m_wxwindow->allocation.height;
gtk_window_expose_callback( m_wxwindow, &gdk_event, this );
}
else
{
gtk_widget_draw( m_widget, (GdkRectangle*) NULL );
}
}
else
{
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
if (m_wxwindow)
{
/*
GtkPizza *pizza = GTK_PIZZA(m_wxwindow);
gboolean old_clear = pizza->clear_on_draw;
gtk_pizza_set_clear( pizza, FALSE );
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
gtk_widget_draw( m_wxwindow, &gdk_rect );
gtk_window_draw_callback( m_wxwindow, &gdk_rect, this );
gtk_pizza_set_clear( pizza, old_clear );
*/
GdkEventExpose gdk_event;
gdk_event.count = 0;
gdk_event.area.x = rect->x;
gdk_event.area.y = rect->y;
gdk_event.area.width = rect->width;
gdk_event.area.height = rect->height;
gtk_window_expose_callback( m_wxwindow, &gdk_event, this );
}
else
{
GdkRectangle gdk_rect;
gdk_rect.x = rect->x;
gdk_rect.y = rect->y;
gdk_rect.width = rect->width;
gdk_rect.height = rect->height;
gtk_widget_draw( m_widget, &gdk_rect );
}
}
}
@@ -3452,7 +3592,9 @@ void wxWindow::ScrollWindow( int dx, int dy, const wxRect* WXUNUSED(rect) )
if ((dx == 0) && (dy == 0)) return;
m_clipPaintRegion = TRUE;
gtk_pizza_scroll( GTK_PIZZA(m_wxwindow), -dx, -dy );
m_clipPaintRegion = FALSE;
/*
if (m_children.GetCount() > 0)