]> git.saurik.com Git - wxWidgets.git/commitdiff
update the samples to use new (non-deprecated) wxGLCanvas API; added more comments...
authorVadim Zeitlin <vadim@wxwidgets.org>
Sun, 10 Feb 2008 13:26:01 +0000 (13:26 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Sun, 10 Feb 2008 13:26:01 +0000 (13:26 +0000)
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@51630 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

samples/opengl/cube/cube.cpp
samples/opengl/cube/cube.h
samples/opengl/isosurf/isosurf.cpp
samples/opengl/isosurf/isosurf.h
samples/opengl/penguin/dxfrenderer.cpp
samples/opengl/penguin/penguin.cpp
samples/opengl/penguin/penguin.h

index 325520181936b914d407cced5306da5ef47bf206..74cd1bf7ebf194a3877541138eaa2ad75130fc01 100644 (file)
@@ -118,40 +118,6 @@ static wxImage DrawDice(int size, unsigned num)
 // implementation
 // ============================================================================
 
-// ----------------------------------------------------------------------------
-// MyApp: the application object
-// ----------------------------------------------------------------------------
-
-IMPLEMENT_APP(MyApp)
-
-bool MyApp::OnInit()
-{
-    if ( !wxApp::OnInit() )
-        return false;
-
-    // Create the main window
-    new MyFrame();
-
-    return true;
-}
-
-int MyApp::OnExit()
-{
-    delete m_glContext;
-
-    return wxApp::OnExit();
-}
-
-TestGLContext& MyApp::GetContext(wxGLCanvas *canvas)
-{
-    if ( !m_glContext )
-        m_glContext = new TestGLContext(canvas);
-    else
-        m_glContext->SetCurrent(*canvas);
-
-    return *m_glContext;
-}
-
 // ----------------------------------------------------------------------------
 // TestGLContext
 // ----------------------------------------------------------------------------
@@ -167,7 +133,7 @@ TestGLContext::TestGLContext(wxGLCanvas *canvas)
     glEnable(GL_LIGHT0);
     glEnable(GL_TEXTURE_2D);
 
-    // add slightly more light, the default lightning is rather dark
+    // add slightly more light, the default lighting is rather dark
     GLfloat ambient[] = { 0.5, 0.5, 0.5, 0.5 };
     glLightfv(GL_LIGHT0, GL_AMBIENT, ambient);
 
@@ -272,19 +238,61 @@ void TestGLContext::DrawRotatedCube(float xangle, float yangle)
     CheckGLError();
 }
 
+
+// ----------------------------------------------------------------------------
+// MyApp: the application object
+// ----------------------------------------------------------------------------
+
+IMPLEMENT_APP(MyApp)
+
+bool MyApp::OnInit()
+{
+    if ( !wxApp::OnInit() )
+        return false;
+
+    new MyFrame();
+
+    return true;
+}
+
+int MyApp::OnExit()
+{
+    delete m_glContext;
+
+    return wxApp::OnExit();
+}
+
+TestGLContext& MyApp::GetContext(wxGLCanvas *canvas)
+{
+    if ( !m_glContext )
+    {
+        // Create the OpenGL context for the first window which needs it:
+        // subsequently created windows will all share the same context.
+        m_glContext = new TestGLContext(canvas);
+    }
+
+    m_glContext->SetCurrent(*canvas);
+
+    return *m_glContext;
+}
+
 // ----------------------------------------------------------------------------
 // TestGLCanvas
 // ----------------------------------------------------------------------------
 
 BEGIN_EVENT_TABLE(TestGLCanvas, wxGLCanvas)
-    EVT_SIZE(TestGLCanvas::OnSize)
     EVT_PAINT(TestGLCanvas::OnPaint)
-
     EVT_KEY_DOWN(TestGLCanvas::OnKeyDown)
 END_EVENT_TABLE()
 
 TestGLCanvas::TestGLCanvas(wxWindow *parent)
-            : wxGLCanvas(parent, wxID_ANY, NULL /* attribs */)
+    // With perspective OpenGL graphics, the wxFULL_REPAINT_ON_RESIZE style
+    // flag should always be set, because even making the canvas smaller should
+    // be followed by a paint event that updates the entire canvas with new
+    // viewport settings.
+    : wxGLCanvas(parent, wxID_ANY, NULL /* attribs */,
+                 wxDefaultPosition, wxDefaultSize,
+                 wxFULL_REPAINT_ON_RESIZE)
 {
     m_xangle =
     m_yangle = 30;
@@ -292,27 +300,22 @@ TestGLCanvas::TestGLCanvas(wxWindow *parent)
 
 void TestGLCanvas::OnPaint(wxPaintEvent& WXUNUSED(event))
 {
+    // This is required even though dc is not used otherwise.
     wxPaintDC dc(this);
 
-    wxGetApp().GetContext(this).DrawRotatedCube(m_xangle, m_yangle);
+    // Set the OpenGL viewport according to the client size of this canvas.
+    // This is done here rather than in a wxSizeEvent handler because our
+    // OpenGL rendering context (and thus viewport setting) is used with
+    // multiple canvases: If we updated the viewport in the wxSizeEvent
+    // handler, changing the size of one canvas causes a viewport setting that
+    // is wrong when next another canvas is repainted.
+    const wxSize ClientSize = GetClientSize();
 
-    SwapBuffers();
-}
-
-void TestGLCanvas::OnSize(wxSizeEvent& event)
-{
-    // don't prevent default processing from taking place
-    event.Skip();
-
-    if ( !IsShownOnScreen() )
-        return;
-
-    // set GL viewport (not called by wxGLCanvas::OnSize on all platforms...)
-    int w, h;
-    GetClientSize(&w, &h);
+    glViewport(0, 0, ClientSize.x, ClientSize.y);
 
-    wxGetApp().GetContext(this);
-    glViewport(0, 0, w, h);
+    // Render the graphics and swap the buffers.
+    wxGetApp().GetContext(this).DrawRotatedCube(m_xangle, m_yangle);
+    SwapBuffers();
 }
 
 void TestGLCanvas::OnKeyDown( wxKeyEvent& event )
@@ -355,6 +358,7 @@ void TestGLCanvas::OnKeyDown( wxKeyEvent& event )
     Refresh(false);
 }
 
+
 // ----------------------------------------------------------------------------
 // MyFrame: main application window
 // ----------------------------------------------------------------------------
@@ -400,6 +404,6 @@ void MyFrame::OnClose(wxCommandEvent& WXUNUSED(event))
 
 void MyFrame::OnNewWindow( wxCommandEvent& WXUNUSED(event) )
 {
-    (void) new MyFrame();
+    new MyFrame();
 }
 
index af9e59d61f95daa7b8d242f945e1ecc5be1a61ac..36769b884f84c87e33e3a429d0e3afe17d942295 100644 (file)
@@ -29,12 +29,13 @@ private:
 };
 
 // Define a new application type
-class MyApp: public wxApp
+class MyApp : public wxApp
 {
 public:
     MyApp() { m_glContext = NULL; }
 
-    // get the context we use creating it on demand (and set it as current)
+    // Returns the shared context used by all frames and sets it as current for
+    // the given canvas.
     TestGLContext& GetContext(wxGLCanvas *canvas);
 
     // virtual wxApp methods
@@ -47,7 +48,7 @@ private:
 };
 
 // Define a new frame type
-class MyFrame: public wxFrame
+class MyFrame : public wxFrame
 {
 public:
     MyFrame();
@@ -55,8 +56,6 @@ public:
 private:
     void OnClose(wxCommandEvent& event);
     void OnNewWindow(wxCommandEvent& event);
-    void OnDefRotateLeftKey(wxCommandEvent& event);
-    void OnDefRotateRightKey(wxCommandEvent& event);
 
     DECLARE_EVENT_TABLE()
 };
@@ -68,7 +67,6 @@ public:
 
 private:
     void OnPaint(wxPaintEvent& event);
-    void OnSize(wxSizeEvent& event);
     void OnKeyDown(wxKeyEvent& event);
 
     // angles of rotation around x- and y- axis
@@ -79,4 +77,3 @@ private:
 };
 
 #endif // _WX_CUBE_H_
-
index 00ab92808d50bf800c3581e2b95af945a62553d8..f89ba3f71f0a7b2356f07ac130016b75db8d5f54 100644 (file)
@@ -47,8 +47,9 @@
 #undef GL_EXT_vertex_array
 #endif
 
-#include "isosurf.h"
+#include <fstream>
 
+#include "isosurf.h"
 #include "../../sample.xpm"
 
 // The following part is taken largely unchanged from the original C Version
@@ -72,31 +73,24 @@ static GLfloat xrot;
 static GLfloat yrot;
 
 
-static void read_surface( const wxChar *filename )
+static void read_surface(const char *filename)
 {
-    FILE *f = wxFopen(filename,_T("r"));
-    if (!f)
+    std::ifstream inFile(filename);
+    numverts = 0;
+
+    if ( !inFile )
     {
-        wxString msg = _T("Couldn't read ");
-        msg += filename;
-        wxMessageBox(msg);
+        wxLogError("Couldn't read \"%s\"", filename);
         return;
     }
 
-    numverts = 0;
-    while (!feof(f) && numverts<MAXVERTS)
+    while ((inFile >> verts[numverts][0] >> verts[numverts][1] >> verts[numverts][2]
+                   >> norms[numverts][0] >> norms[numverts][1] >> norms[numverts][2]) && numverts<MAXVERTS)
     {
-        fscanf( f, "%f %f %f  %f %f %f",
-            &verts[numverts][0], &verts[numverts][1], &verts[numverts][2],
-            &norms[numverts][0], &norms[numverts][1], &norms[numverts][2] );
         numverts++;
     }
 
-    numverts--;
-
     wxPrintf(_T("%d vertices, %d triangles\n"), numverts, numverts-2);
-
-    fclose(f);
 }
 
 
@@ -134,7 +128,7 @@ static void draw1()
 
     glPopMatrix();
 
-    glFlush();
+    glFlush(); // Not really necessary: buffer swapping below implies glFlush()
 }
 
 
@@ -238,8 +232,6 @@ static GLenum Args(int argc, wxChar **argv)
     return GL_TRUE;
 }
 
-// The following part was written for wxWidgets 1.66
-MyFrame *frame = NULL;
 
 IMPLEMENT_APP(MyApp)
 
@@ -252,16 +244,37 @@ bool MyApp::OnInit()
     Args(argc, argv);
 
     // Create the main frame window
-    frame = new MyFrame(NULL, wxT("wxWidgets OpenGL Isosurf Sample"),
+    new MyFrame(NULL, wxT("wxWidgets OpenGL Isosurf Sample"),
         wxDefaultPosition, wxDefaultSize);
 
+    read_surface("isosurf.dat");
+
+    Init();
+
+    return true;
+}
+
+BEGIN_EVENT_TABLE(MyFrame, wxFrame)
+    EVT_MENU(wxID_EXIT, MyFrame::OnExit)
+END_EVENT_TABLE()
+
+// My frame constructor
+MyFrame::MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
+    const wxSize& size, long style)
+    : wxFrame(frame, wxID_ANY, title, pos, size, style),
+      m_canvas(NULL)
+{
+    SetIcon(wxICON(sample));
+
+
     // Make a menubar
     wxMenu *fileMenu = new wxMenu;
 
     fileMenu->Append(wxID_EXIT, _T("E&xit"));
     wxMenuBar *menuBar = new wxMenuBar;
     menuBar->Append(fileMenu, _T("&File"));
-    frame->SetMenuBar(menuBar);
+    SetMenuBar(menuBar);
+
 
   // Make a TestGLCanvas
 
@@ -288,31 +301,11 @@ bool MyApp::OnInit()
         doubleBuffer = GL_FALSE;
     }
 
-    frame->m_canvas = new TestGLCanvas(frame, wxID_ANY, wxDefaultPosition,
-        wxDefaultSize, 0, _T("TestGLCanvas"), gl_attrib );
-
-  // Show the frame
-    frame->Show(true);
-
-    frame->m_canvas->SetCurrent();
-    read_surface( _T("isosurf.dat") );
-
-    Init();
-
-    return true;
-}
-
-BEGIN_EVENT_TABLE(MyFrame, wxFrame)
-    EVT_MENU(wxID_EXIT, MyFrame::OnExit)
-END_EVENT_TABLE()
+    // Show the frame
+    Show(true);
 
-// My frame constructor
-MyFrame::MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
-    const wxSize& size, long style)
-    : wxFrame(frame, wxID_ANY, title, pos, size, style)
-{
-    m_canvas = NULL;
-    SetIcon(wxICON(sample));
+    m_canvas = new TestGLCanvas(this, wxID_ANY, wxDefaultPosition,
+        GetClientSize(), 0, _T("TestGLCanvas"), gl_attrib );
 }
 
 MyFrame::~MyFrame()
@@ -336,16 +329,23 @@ BEGIN_EVENT_TABLE(TestGLCanvas, wxGLCanvas)
     EVT_PAINT(TestGLCanvas::OnPaint)
     EVT_CHAR(TestGLCanvas::OnChar)
     EVT_MOUSE_EVENTS(TestGLCanvas::OnMouseEvent)
-    EVT_ERASE_BACKGROUND(TestGLCanvas::OnEraseBackground)
 END_EVENT_TABLE()
 
-TestGLCanvas::TestGLCanvas(wxWindow *parent, wxWindowID id,
-    const wxPoint& pos, const wxSize& size, long style,
-    const wxString& name, int* gl_attrib)
-    : wxGLCanvas(parent, id, pos, size, style|wxFULL_REPAINT_ON_RESIZE, name, gl_attrib)
+TestGLCanvas::TestGLCanvas(wxWindow *parent,
+                           wxWindowID id,
+                           const wxPoint& pos,
+                           const wxSize& size,
+                           long style,
+                           const wxString& name,
+                           int* gl_attrib)
+    : wxGLCanvas(parent, id, gl_attrib, pos, size,
+                 style | wxFULL_REPAINT_ON_RESIZE, name)
 {
-    parent->Show(true);
-    SetCurrent();
+    // Explicitly create a new rendering context instance for this canvas.
+    m_glRC = new wxGLContext(this);
+
+    // Make the new context current (activate it for use) with this canvas.
+    SetCurrent(*m_glRC);
 
     /* Make sure server supports the vertex array extension */
     char* extensions = (char *) glGetString( GL_EXTENSIONS );
@@ -355,6 +355,10 @@ TestGLCanvas::TestGLCanvas(wxWindow *parent, wxWindowID id,
     }
 }
 
+TestGLCanvas::~TestGLCanvas()
+{
+    delete m_glRC;
+}
 
 void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
 {
@@ -362,11 +366,9 @@ void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
     // OnPaint handlers must always create a wxPaintDC.
     wxPaintDC dc(this);
 
-#ifndef __WXMOTIF__
-    if (!GetContext()) return;
-#endif
-
-    SetCurrent();
+    // This is normally only necessary if there is more than one wxGLCanvas
+    // or more than one wxGLContext in the application.
+    SetCurrent(*m_glRC);
 
     draw1();
     SwapBuffers();
@@ -374,19 +376,15 @@ void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
 
 void TestGLCanvas::OnSize(wxSizeEvent& event)
 {
-    // this is also necessary to update the context on some platforms
-    wxGLCanvas::OnSize(event);
-
-    // set GL viewport (not called by wxGLCanvas::OnSize on all platforms...)
-    int w, h;
-    GetClientSize(&w, &h);
-#ifndef __WXMOTIF__
-    if (GetContext())
-#endif
-    {
-        SetCurrent();
-        glViewport(0, 0, (GLint) w, (GLint) h);
-    }
+    // This is normally only necessary if there is more than one wxGLCanvas
+    // or more than one wxGLContext in the application.
+    SetCurrent(*m_glRC);
+
+    // It's up to the application code to update the OpenGL viewport settings.
+    // This is OK here only because there is only one canvas that uses the
+    // context. See the cube sample for that case that multiple canvases are
+    // made current with one context.
+    glViewport(0, 0, event.GetSize().x, event.GetSize().y);
 }
 
 void TestGLCanvas::OnChar(wxKeyEvent& event)
@@ -450,7 +448,10 @@ void TestGLCanvas::OnMouseEvent(wxMouseEvent& event)
     static int dragging = 0;
     static float last_x, last_y;
 
-    //printf("%f %f %d\n", event.GetX(), event.GetY(), (int)event.LeftIsDown());
+    // Allow default processing to happen, or else the canvas cannot gain focus
+    // (for key events).
+    event.Skip();
+
     if(event.LeftIsDown())
     {
         if(!dragging)
@@ -467,12 +468,8 @@ void TestGLCanvas::OnMouseEvent(wxMouseEvent& event)
         last_y = event.GetY();
     }
     else
+    {
         dragging = 0;
-
-}
-
-void TestGLCanvas::OnEraseBackground( wxEraseEvent& WXUNUSED(event) )
-{
-    // Do nothing, to avoid flashing.
+    }
 }
 
index cc85da042d1c2ff0a19c6f40e44c8e8f75a7c7a6..15f6dc2164677b1c012e58965ab28a556be4f682 100644 (file)
 #define _WX_ISOSURF_H_
 
 // Define a new application type
-class MyApp: public wxApp
+class MyApp : public wxApp
 {
 public:
-    bool OnInit();
+    virtual bool OnInit();
 };
 
-#if wxUSE_GLCANVAS
 
-class TestGLCanvas: public wxGLCanvas
+class TestGLCanvas : public wxGLCanvas
 {
 public:
-    TestGLCanvas(wxWindow *parent, wxWindowID id = wxID_ANY,
-        const wxPoint& pos = wxDefaultPosition,
-        const wxSize& size = wxDefaultSize, long style = 0,
-        const wxString& name = _T("TestGLCanvas"), int *gl_attrib = NULL);
+    TestGLCanvas(wxWindow *parent,
+                 wxWindowID id = wxID_ANY,
+                 const wxPoint& pos = wxDefaultPosition,
+                 const wxSize& size = wxDefaultSize,
+                 long style = 0,
+                 const wxString& name = _T("TestGLCanvas"),
+                 int *gl_attrib = NULL);
 
-   ~TestGLCanvas(){};
+    virtual ~TestGLCanvas();
 
     void OnPaint(wxPaintEvent& event);
     void OnSize(wxSizeEvent& event);
-    void OnEraseBackground(wxEraseEvent& event);
     void OnChar(wxKeyEvent& event);
     void OnMouseEvent(wxMouseEvent& event);
 
+
+private:
+    wxGLContext* m_glRC;
+
+    DECLARE_NO_COPY_CLASS(TestGLCanvas)
     DECLARE_EVENT_TABLE()
 };
 
-#endif // #if wxUSE_GLCANVAS
-
 
-class MyFrame: public wxFrame
+class MyFrame : public wxFrame
 {
 public:
-    MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
-        const wxSize& size, long style = wxDEFAULT_FRAME_STYLE);
+    MyFrame(wxFrame *frame,
+            const wxString& title,
+            const wxPoint& pos,
+            const wxSize& size,
+            long style = wxDEFAULT_FRAME_STYLE);
 
     virtual ~MyFrame();
 
-#if wxUSE_GLCANVAS
     TestGLCanvas *m_canvas;
-#endif
 
 private :
-
     void OnExit(wxCommandEvent& event);
 
-DECLARE_EVENT_TABLE()
+    DECLARE_EVENT_TABLE()
 };
 
-#endif // #ifndef _WX_ISOSURF_H_
+#endif // _WX_ISOSURF_H_
 
index 3448b558ce34e3efbb4b2c4d76524ace0a9219d6..e03a3624361519418a0287960bdd8bd76606577e 100644 (file)
@@ -33,6 +33,8 @@
     #include <GL/glu.h>
 #endif
 
+#include <sstream>
+
 #include "dxfrenderer.h"
 
 #include "wx/listimpl.cpp"
@@ -435,6 +437,22 @@ bool DXFRenderer::ParseTables(wxInputStream& stream)
     return false;
 }
 
+// This method is used instead of numStr.ToDouble(d) because the latter
+// (wxString::ToDouble()) takes the systems proper locale into account,
+// whereas the implementation below works with the default locale.
+// (Converting numbers that are formatted in the default locale can fail
+//  with system locales that use e.g. the comma as the decimal separator.)
+static double ToDouble(const wxString& numStr)
+{
+    double             d;
+    std::string        numStr_(numStr.c_str());
+    std::istringstream iss(numStr_);
+
+    iss >> d;
+
+    return d;
+}
+
 // parse entities section: save 3DFACE and LINE entities
 bool DXFRenderer::ParseEntities(wxInputStream& stream)
 {
@@ -490,8 +508,8 @@ bool DXFRenderer::ParseEntities(wxInputStream& stream)
             state = 2;
         else if (state > 0)
         {
-            double d;
-            line2.ToDouble(&d);
+            const double d=ToDouble(line2);
+
             if (line1 == wxT("10"))
                 v[0].x = d;
             else if (line1 == wxT("20"))
index 9ad96d9e8f45ea41ba644b207488720b9644556e..e18cb95adc1c5cdea3c349c7e131c43e7e94bdee 100644 (file)
@@ -94,8 +94,10 @@ MyFrame::MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
     menuBar->Append(helpMenu, wxT("&Help"));
     SetMenuBar(menuBar);
 
+    Show(true);
+
     m_canvas = new TestGLCanvas(this, wxID_ANY, wxDefaultPosition,
-        wxSize(300, 300), wxSUNKEN_BORDER);
+        GetClientSize(), wxSUNKEN_BORDER);
 }
 
 // File|Open... command
@@ -139,10 +141,21 @@ BEGIN_EVENT_TABLE(TestGLCanvas, wxGLCanvas)
     EVT_MOUSE_EVENTS(TestGLCanvas::OnMouse)
 END_EVENT_TABLE()
 
-TestGLCanvas::TestGLCanvas(wxWindow *parent, wxWindowID id,
-    const wxPoint& pos, const wxSize& size, long style, const wxString& name)
-    : wxGLCanvas(parent, id, pos, size, style|wxFULL_REPAINT_ON_RESIZE, name)
+TestGLCanvas::TestGLCanvas(wxWindow *parent,
+                           wxWindowID id,
+                           const wxPoint& pos,
+                           const wxSize& size,
+                           long style,
+                           const wxString& name)
+    : wxGLCanvas(parent, id, NULL, pos, size,
+                 style | wxFULL_REPAINT_ON_RESIZE, name)
 {
+    // Explicitly create a new rendering context instance for this canvas.
+    m_glRC = new wxGLContext(this);
+
+    // Make the new context current (activate it for use) with this canvas.
+    SetCurrent(*m_glRC);
+
     m_gldata.initialized = false;
 
     // initialize view matrix
@@ -154,6 +167,7 @@ TestGLCanvas::TestGLCanvas(wxWindow *parent, wxWindowID id,
 
 TestGLCanvas::~TestGLCanvas()
 {
+    delete m_glRC;
 }
 
 void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
@@ -161,11 +175,7 @@ void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
     // must always be here
     wxPaintDC dc(this);
 
-#ifndef __WXMOTIF__
-    if (!GetContext()) return;
-#endif
-
-    SetCurrent();
+    SetCurrent(*m_glRC);
 
     // Initialize OpenGL
     if (!m_gldata.initialized)
@@ -195,11 +205,11 @@ void TestGLCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
     SwapBuffers();
 }
 
-void TestGLCanvas::OnSize(wxSizeEvent& event)
+void TestGLCanvas::OnSize(wxSizeEvent& WXUNUSED(event))
 {
-    // this is also necessary to update the context on some platforms
-    wxGLCanvas::OnSize(event);
-    // Reset the OpenGL view aspect
+    // Reset the OpenGL view aspect.
+    // This is OK only because there is only one canvas that uses the context.
+    // See the cube sample for that case that multiple canvases are made current with one context.
     ResetProjectionMode();
 }
 
@@ -293,18 +303,21 @@ void TestGLCanvas::InitGL()
 
 void TestGLCanvas::ResetProjectionMode()
 {
+    // This is normally only necessary if there is more than one wxGLCanvas
+    // or more than one wxGLContext in the application.
+    SetCurrent(*m_glRC);
+
     int w, h;
     GetClientSize(&w, &h);
-#ifndef __WXMOTIF__
-    if ( GetContext() )
-#endif
-    {
-        SetCurrent();
-        glViewport(0, 0, (GLint) w, (GLint) h);
-        glMatrixMode(GL_PROJECTION);
-        glLoadIdentity();
-        gluPerspective(45.0f, (GLfloat)w/h, 1.0, 100.0);
-        glMatrixMode(GL_MODELVIEW);
-        glLoadIdentity();
-    }
+
+    // It's up to the application code to update the OpenGL viewport settings.
+    // In order to avoid extensive context switching, consider doing this in
+    // OnPaint() rather than here, though.
+    glViewport(0, 0, (GLint) w, (GLint) h);
+
+    glMatrixMode(GL_PROJECTION);
+    glLoadIdentity();
+    gluPerspective(45.0f, (GLfloat)w/h, 1.0, 100.0);
+    glMatrixMode(GL_MODELVIEW);
+    glLoadIdentity();
 }
index 63efc497f44d62567d2203fa6588366566f1f638..b5aae0eea17088e043e9b076e1b774e6868d34fc 100644 (file)
@@ -31,6 +31,7 @@ extern "C"
 
 #include "dxfrenderer.h"
 
+
 // OpenGL view data
 struct GLData
 {
@@ -40,40 +41,40 @@ struct GLData
     float zoom;                 // field of view in degrees
 };
 
+
 // Define a new application type
-class MyApp: public wxApp
+class MyApp : public wxApp
 {
 public:
-    bool OnInit();
+    virtual bool OnInit();
 };
 
+
 // Define a new frame type
 class TestGLCanvas;
 
-class MyFrame: public wxFrame
+
+class MyFrame : public wxFrame
 {
 public:
     MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
-        const wxSize& size, long style = wxDEFAULT_FRAME_STYLE);
+            const wxSize& size, long style = wxDEFAULT_FRAME_STYLE);
 
     void OnMenuFileOpen(wxCommandEvent& event);
     void OnMenuFileExit(wxCommandEvent& event);
     void OnMenuHelpAbout(wxCommandEvent& event);
 
-#if wxUSE_GLCANVAS
-    void SetCanvas( TestGLCanvas *canvas ) { m_canvas = canvas; }
+    void SetCanvas(TestGLCanvas *canvas) { m_canvas = canvas; }
     TestGLCanvas *GetCanvas() { return m_canvas; }
 
 private:
     TestGLCanvas *m_canvas;
-#endif
 
     DECLARE_EVENT_TABLE()
 };
 
-#if wxUSE_GLCANVAS
 
-class TestGLCanvas: public wxGLCanvas
+class TestGLCanvas : public wxGLCanvas
 {
 public:
     TestGLCanvas(wxWindow *parent, wxWindowID id = wxID_ANY,
@@ -81,7 +82,7 @@ public:
         const wxSize& size = wxDefaultSize, long style = 0,
         const wxString& name = wxT("TestGLCanvas"));
 
-    ~TestGLCanvas();
+    virtual ~TestGLCanvas();
 
     void LoadDXF(const wxString& filename);
 
@@ -95,13 +96,12 @@ private:
     void InitGL();
     void ResetProjectionMode();
 
-    GLData m_gldata;
-    DXFRenderer m_renderer;
+    wxGLContext* m_glRC;
+    GLData       m_gldata;
+    DXFRenderer  m_renderer;
 
+    DECLARE_NO_COPY_CLASS(TestGLCanvas)
     DECLARE_EVENT_TABLE()
 };
 
-#endif // #if wxUSE_GLCANVAS
-
 #endif // #ifndef _WX_PENGUIN_H_
-