From 147bc4915925b56454d45772c66145f14e33d23b Mon Sep 17 00:00:00 2001 From: Robert Roebling Date: Mon, 11 Oct 1999 15:24:49 +0000 Subject: [PATCH] Tried to make wxGLCanvas work again. WIP. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@3929 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- include/wx/gtk/win_gtk.h | 6 ++ include/wx/gtk/window.h | 9 +-- include/wx/gtk1/win_gtk.h | 6 ++ include/wx/gtk1/window.h | 9 +-- src/gtk/win_gtk.c | 15 ++++- src/gtk/window.cpp | 24 ++++---- src/gtk1/win_gtk.c | 15 ++++- src/gtk1/window.cpp | 24 ++++---- utils/glcanvas/gtk/glcanvas.cpp | 69 ++++++++++++++++++---- utils/glcanvas/gtk/glcanvas.h | 9 +-- utils/glcanvas/samples/penguin/penguin.cpp | 11 ++++ 11 files changed, 139 insertions(+), 58 deletions(-) diff --git a/include/wx/gtk/win_gtk.h b/include/wx/gtk/win_gtk.h index 968d1d1051..f12bc34655 100644 --- a/include/wx/gtk/win_gtk.h +++ b/include/wx/gtk/win_gtk.h @@ -55,6 +55,8 @@ struct _GtkMyFixed gulong configure_serial; gint scroll_x; gint scroll_y; + + gboolean clear_on_draw; }; struct _GtkMyFixedClass @@ -68,9 +70,13 @@ struct _GtkMyFixedClass guint gtk_myfixed_get_type (void); GtkWidget* gtk_myfixed_new (void); + void gtk_myfixed_set_shadow_type (GtkMyFixed *myfixed, GtkMyShadowType type); +void gtk_my_fixed_set_clear (GtkMyFixed *myfixed, + gboolean clear); + void gtk_myfixed_scroll (GtkMyFixed *myfixed, gint dx, gint dy); diff --git a/include/wx/gtk/window.h b/include/wx/gtk/window.h index ae02499808..9f255ab617 100644 --- a/include/wx/gtk/window.h +++ b/include/wx/gtk/window.h @@ -172,14 +172,9 @@ public: float m_oldHorizontalPos; float m_oldVerticalPos; - // we need an extra XGC flag set to get exposed - // events from overlapping children upon moving - // them. this flag will be set in this GC and - // the GC will be used in wxWindow::ScrollWindow(). - GdkGC *m_scrollGC; - // extra (wxGTK-specific) flags bool m_needParent:1; /* ! wxFrame, wxDialog, wxNotebookPage ? */ + bool m_noExpose:1; /* wxGLCanvas has its own redrawing */ bool m_hasScrolling:1; bool m_isScrolling:1; bool m_hasVMT:1; @@ -188,7 +183,7 @@ public: bool m_isStaticBox:1; /* faster than IS_KIND_OF */ bool m_isRadioButton:1; /* faster than IS_KIND_OF */ bool m_isFrame:1; /* faster than IS_KIND_OF */ - bool m_acceptsFocus:1; /* ! wxStaticBox etc. */ + bool m_acceptsFocus:1; /* not wxStaticBox, not wxStaticBitmap etc. */ // 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 diff --git a/include/wx/gtk1/win_gtk.h b/include/wx/gtk1/win_gtk.h index 968d1d1051..f12bc34655 100644 --- a/include/wx/gtk1/win_gtk.h +++ b/include/wx/gtk1/win_gtk.h @@ -55,6 +55,8 @@ struct _GtkMyFixed gulong configure_serial; gint scroll_x; gint scroll_y; + + gboolean clear_on_draw; }; struct _GtkMyFixedClass @@ -68,9 +70,13 @@ struct _GtkMyFixedClass guint gtk_myfixed_get_type (void); GtkWidget* gtk_myfixed_new (void); + void gtk_myfixed_set_shadow_type (GtkMyFixed *myfixed, GtkMyShadowType type); +void gtk_my_fixed_set_clear (GtkMyFixed *myfixed, + gboolean clear); + void gtk_myfixed_scroll (GtkMyFixed *myfixed, gint dx, gint dy); diff --git a/include/wx/gtk1/window.h b/include/wx/gtk1/window.h index ae02499808..9f255ab617 100644 --- a/include/wx/gtk1/window.h +++ b/include/wx/gtk1/window.h @@ -172,14 +172,9 @@ public: float m_oldHorizontalPos; float m_oldVerticalPos; - // we need an extra XGC flag set to get exposed - // events from overlapping children upon moving - // them. this flag will be set in this GC and - // the GC will be used in wxWindow::ScrollWindow(). - GdkGC *m_scrollGC; - // extra (wxGTK-specific) flags bool m_needParent:1; /* ! wxFrame, wxDialog, wxNotebookPage ? */ + bool m_noExpose:1; /* wxGLCanvas has its own redrawing */ bool m_hasScrolling:1; bool m_isScrolling:1; bool m_hasVMT:1; @@ -188,7 +183,7 @@ public: bool m_isStaticBox:1; /* faster than IS_KIND_OF */ bool m_isRadioButton:1; /* faster than IS_KIND_OF */ bool m_isFrame:1; /* faster than IS_KIND_OF */ - bool m_acceptsFocus:1; /* ! wxStaticBox etc. */ + bool m_acceptsFocus:1; /* not wxStaticBox, not wxStaticBitmap etc. */ // 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 diff --git a/src/gtk/win_gtk.c b/src/gtk/win_gtk.c index 10f8d2ca28..18606b962e 100644 --- a/src/gtk/win_gtk.c +++ b/src/gtk/win_gtk.c @@ -187,6 +187,8 @@ gtk_myfixed_init (GtkMyFixed *myfixed) myfixed->scroll_x = 0; myfixed->scroll_y = 0; myfixed->visibility = GDK_VISIBILITY_PARTIAL; + + myfixed->clear_on_draw = TRUE; } GtkWidget* @@ -226,6 +228,16 @@ gtk_myfixed_set_shadow_type (GtkMyFixed *myfixed, } } +void +gtk_my_fixed_set_clear (GtkMyFixed *myfixed, + gboolean clear) +{ + g_return_if_fail (myfixed != NULL); + g_return_if_fail (GTK_IS_MYFIXED (myfixed)); + + myfixed->clear_on_draw = clear; +} + void gtk_myfixed_put (GtkMyFixed *myfixed, GtkWidget *widget, @@ -637,7 +649,8 @@ gtk_myfixed_draw (GtkWidget *widget, myfixed = GTK_MYFIXED (widget); children = myfixed->children; - if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) ) + if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) && + (myfixed->clear_on_draw)) { gdk_window_clear_area( myfixed->bin_window, area->x, area->y, area->width, area->height); diff --git a/src/gtk/window.cpp b/src/gtk/window.cpp index fb798b8e5c..7e235b0c06 100644 --- a/src/gtk/window.cpp +++ b/src/gtk/window.cpp @@ -303,7 +303,7 @@ static void gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *g } //----------------------------------------------------------------------------- -// "draw" of m_wxwindow +// "draw" of m_widget //----------------------------------------------------------------------------- static void gtk_window_own_draw_callback( GtkWidget *widget, GdkRectangle *WXUNUSED(rect), wxWindow *win ) @@ -1766,6 +1766,8 @@ void wxWindow::Init() m_hasVMT = FALSE; m_needParent = TRUE; m_isBeingDeleted = FALSE; + + m_noExpose = FALSE; m_hasScrolling = FALSE; m_isScrolling = FALSE; @@ -1776,7 +1778,6 @@ void wxWindow::Init() m_oldVerticalPos = 0.0; m_resizing = FALSE; - m_scrollGC = (GdkGC*) NULL; m_widgetStyle = (GtkStyle*) NULL; m_insertCallback = (wxInsertChildFunction) NULL; @@ -1977,12 +1978,6 @@ wxWindow::~wxWindow() m_widgetStyle = (GtkStyle*) NULL; } - if (m_scrollGC) - { - gdk_gc_unref( m_scrollGC ); - m_scrollGC = (GdkGC*) NULL; - } - if (m_wxwindow) { gtk_widget_destroy( m_wxwindow ); @@ -2034,12 +2029,15 @@ void wxWindow::PostCreation() if (m_wxwindow) { - /* these get reported to wxWindows -> wxPaintEvent */ - gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event", - GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this ); + if (!m_noExpose) + { + /* these get reported to wxWindows -> wxPaintEvent */ + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event", + GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this ); - gtk_signal_connect( GTK_OBJECT(m_wxwindow), "draw", - GTK_SIGNAL_FUNC(gtk_window_draw_callback), (gpointer)this ); + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "draw", + GTK_SIGNAL_FUNC(gtk_window_draw_callback), (gpointer)this ); + } #if (GTK_MINOR_VERSION > 0) /* these are called when the "sunken" or "raised" borders are drawn */ diff --git a/src/gtk1/win_gtk.c b/src/gtk1/win_gtk.c index 10f8d2ca28..18606b962e 100644 --- a/src/gtk1/win_gtk.c +++ b/src/gtk1/win_gtk.c @@ -187,6 +187,8 @@ gtk_myfixed_init (GtkMyFixed *myfixed) myfixed->scroll_x = 0; myfixed->scroll_y = 0; myfixed->visibility = GDK_VISIBILITY_PARTIAL; + + myfixed->clear_on_draw = TRUE; } GtkWidget* @@ -226,6 +228,16 @@ gtk_myfixed_set_shadow_type (GtkMyFixed *myfixed, } } +void +gtk_my_fixed_set_clear (GtkMyFixed *myfixed, + gboolean clear) +{ + g_return_if_fail (myfixed != NULL); + g_return_if_fail (GTK_IS_MYFIXED (myfixed)); + + myfixed->clear_on_draw = clear; +} + void gtk_myfixed_put (GtkMyFixed *myfixed, GtkWidget *widget, @@ -637,7 +649,8 @@ gtk_myfixed_draw (GtkWidget *widget, myfixed = GTK_MYFIXED (widget); children = myfixed->children; - if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) ) + if ( !(GTK_WIDGET_APP_PAINTABLE (widget)) && + (myfixed->clear_on_draw)) { gdk_window_clear_area( myfixed->bin_window, area->x, area->y, area->width, area->height); diff --git a/src/gtk1/window.cpp b/src/gtk1/window.cpp index fb798b8e5c..7e235b0c06 100644 --- a/src/gtk1/window.cpp +++ b/src/gtk1/window.cpp @@ -303,7 +303,7 @@ static void gtk_window_own_expose_callback( GtkWidget *widget, GdkEventExpose *g } //----------------------------------------------------------------------------- -// "draw" of m_wxwindow +// "draw" of m_widget //----------------------------------------------------------------------------- static void gtk_window_own_draw_callback( GtkWidget *widget, GdkRectangle *WXUNUSED(rect), wxWindow *win ) @@ -1766,6 +1766,8 @@ void wxWindow::Init() m_hasVMT = FALSE; m_needParent = TRUE; m_isBeingDeleted = FALSE; + + m_noExpose = FALSE; m_hasScrolling = FALSE; m_isScrolling = FALSE; @@ -1776,7 +1778,6 @@ void wxWindow::Init() m_oldVerticalPos = 0.0; m_resizing = FALSE; - m_scrollGC = (GdkGC*) NULL; m_widgetStyle = (GtkStyle*) NULL; m_insertCallback = (wxInsertChildFunction) NULL; @@ -1977,12 +1978,6 @@ wxWindow::~wxWindow() m_widgetStyle = (GtkStyle*) NULL; } - if (m_scrollGC) - { - gdk_gc_unref( m_scrollGC ); - m_scrollGC = (GdkGC*) NULL; - } - if (m_wxwindow) { gtk_widget_destroy( m_wxwindow ); @@ -2034,12 +2029,15 @@ void wxWindow::PostCreation() if (m_wxwindow) { - /* these get reported to wxWindows -> wxPaintEvent */ - gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event", - GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this ); + if (!m_noExpose) + { + /* these get reported to wxWindows -> wxPaintEvent */ + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event", + GTK_SIGNAL_FUNC(gtk_window_expose_callback), (gpointer)this ); - gtk_signal_connect( GTK_OBJECT(m_wxwindow), "draw", - GTK_SIGNAL_FUNC(gtk_window_draw_callback), (gpointer)this ); + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "draw", + GTK_SIGNAL_FUNC(gtk_window_draw_callback), (gpointer)this ); + } #if (GTK_MINOR_VERSION > 0) /* these are called when the "sunken" or "raised" borders are drawn */ diff --git a/utils/glcanvas/gtk/glcanvas.cpp b/utils/glcanvas/gtk/glcanvas.cpp index 2095f0fbc2..9ee7d28543 100644 --- a/utils/glcanvas/gtk/glcanvas.cpp +++ b/utils/glcanvas/gtk/glcanvas.cpp @@ -88,7 +88,8 @@ void wxGLContext::SwapBuffers() { if (m_glContext) { - glXSwapBuffers( GDK_DISPLAY(), GDK_WINDOW_XWINDOW( m_widget->window ) ); + GdkWindow *window = GTK_MYFIXED(m_widget)->bin_window; + glXSwapBuffers( GDK_DISPLAY(), GDK_WINDOW_XWINDOW( window ) ); } } @@ -96,7 +97,8 @@ void wxGLContext::SetCurrent() { if (m_glContext) { - glXMakeCurrent( GDK_DISPLAY(), GDK_WINDOW_XWINDOW(m_widget->window), m_glContext ); + GdkWindow *window = GTK_MYFIXED(m_widget)->bin_window; + glXMakeCurrent( GDK_DISPLAY(), GDK_WINDOW_XWINDOW(window), m_glContext ); } } @@ -135,7 +137,7 @@ wxPalette wxGLContext::CreateDefaultPalette() static gint gtk_glwindow_realized_callback( GtkWidget * WXUNUSED(widget), wxGLCanvas *win ) { - win->m_glContext = new wxGLContext( TRUE, win, wxNullPalette, win->m_glContext ); + win->m_glContext = new wxGLContext( TRUE, win, wxNullPalette, win->m_sharedContext ); XFree( g_vi ); g_vi = (XVisualInfo*) NULL; @@ -143,6 +145,34 @@ gtk_glwindow_realized_callback( GtkWidget * WXUNUSED(widget), wxGLCanvas *win ) return FALSE; } +//----------------------------------------------------------------------------- +// "expose_event" of m_wxwindow +//----------------------------------------------------------------------------- + +static void +gtk_glwindow_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExpose *gdk_event, wxGLCanvas *win ) +{ + win->m_exposed = TRUE; + + win->GetUpdateRegion().Union( gdk_event->area.x, + gdk_event->area.y, + gdk_event->area.width, + gdk_event->area.height ); +} + +//----------------------------------------------------------------------------- +// "draw" of m_wxwindow +//----------------------------------------------------------------------------- + +static void +gtk_glwindow_draw_callback( GtkWidget *WXUNUSED(widget), GdkRectangle *rect, wxGLCanvas *win ) +{ + win->m_exposed = TRUE; + + win->GetUpdateRegion().Union( rect->x, rect->y, + rect->width, rect->height ); +} + //--------------------------------------------------------------------------- // wxGlCanvas //--------------------------------------------------------------------------- @@ -181,7 +211,10 @@ bool wxGLCanvas::Create( wxWindow *parent, int *attribList, const wxPalette& palette) { - m_glContext = (wxGLContext*)shared; // const_cast + m_sharedContext = (wxGLContext*)shared; // const_cast + + m_exposed = FALSE; + m_noExpose = TRUE; if (!attribList) { @@ -239,8 +272,17 @@ bool wxGLCanvas::Create( wxWindow *parent, m_glWidget = m_wxwindow; - gtk_signal_connect( GTK_OBJECT(m_glWidget), "realize", + gtk_my_fixed_set_clear( GTK_MYFIXED(m_wxwindow), FALSE ); + + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "realize", GTK_SIGNAL_FUNC(gtk_glwindow_realized_callback), (gpointer) this ); + + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "expose_event", + GTK_SIGNAL_FUNC(gtk_glwindow_expose_callback), (gpointer)this ); + + gtk_signal_connect( GTK_OBJECT(m_wxwindow), "draw", + GTK_SIGNAL_FUNC(gtk_glwindow_draw_callback), (gpointer)this ); + gtk_widget_pop_visual(); gtk_widget_pop_colormap(); @@ -284,12 +326,15 @@ void wxGLCanvas::SetColour( const char *colour ) if (m_glContext) m_glContext->SetColour( colour ); } -GtkWidget *wxGLCanvas::GetConnectWidget() +void wxGLCanvas::OnInternalIdle() { - return m_wxwindow; -} + if (m_glContext && m_exposed) + { + wxPaintEvent event( GetId() ); + event.SetEventObject( this ); + GetEventHandler()->ProcessEvent( event ); -bool wxGLCanvas::IsOwnGtkWindow( GdkWindow *window ) -{ - return (window == m_wxwindow->window); -} + m_exposed = FALSE; + GetUpdateRegion().Clear(); + } +} \ No newline at end of file diff --git a/utils/glcanvas/gtk/glcanvas.h b/utils/glcanvas/gtk/glcanvas.h index fc0d51561e..9b8e910bd5 100644 --- a/utils/glcanvas/gtk/glcanvas.h +++ b/utils/glcanvas/gtk/glcanvas.h @@ -123,16 +123,17 @@ public: void SwapBuffers(); void OnSize(wxSizeEvent& event); + + void OnInternalIdle(); inline wxGLContext* GetContext() const { return m_glContext; } // implementation - virtual GtkWidget *GetConnectWidget(); - bool IsOwnGtkWindow( GdkWindow *window ); - - wxGLContext *m_glContext; + wxGLContext *m_glContext, + *m_sharedContext; GtkWidget *m_glWidget; + bool m_exposed; private: DECLARE_EVENT_TABLE() diff --git a/utils/glcanvas/samples/penguin/penguin.cpp b/utils/glcanvas/samples/penguin/penguin.cpp index 8eaed6a1d9..0d49b80611 100644 --- a/utils/glcanvas/samples/penguin/penguin.cpp +++ b/utils/glcanvas/samples/penguin/penguin.cpp @@ -27,6 +27,7 @@ #include "penguin.h" #include +#include "wx/gtk/win_gtk.h" #define VIEW_ASPECT 1.3 @@ -105,6 +106,14 @@ void TestGLCanvas::OnPaint( wxPaintEvent& event ) if (!GetContext()) return; #endif + printf( "on refresh.\n" ); + int x,y; + GtkMyFixed *fixed = GTK_MYFIXED(m_wxwindow); + gdk_window_get_size( m_wxwindow->window, &x, &y ); + printf( "-> window %d %d.\n", x, y ); + gdk_window_get_size( fixed->bin_window, &x, &y ); + printf( "-> bin_window %d %d.\n", x, y ); + SetCurrent(); /* initialize OpenGL */ @@ -146,6 +155,8 @@ void TestGLCanvas::OnSize(wxSizeEvent& event) int width, height; GetClientSize(& width, & height); + printf( "onsize %d %d.\n", width, height ); + #ifndef __WXMOTIF__ if (GetContext()) #endif -- 2.45.2