root/OpenSceneGraph/trunk/examples/osgviewerWX/osgviewerWX.cpp @ 13396

Revision 13130, 8.5 kB (checked in by robert, 12 hours ago)

From Jason Beverage, "It looks like the Callback header got accidentally removed from the CMakeLists.txt in the submission yesterday for the geometry instancing example."

  • Property svn:eol-style set to native
Line 
1// For compilers that support precompilation, includes "wx.h".
2#include "wx/wxprec.h"
3
4#ifdef __BORLANDC__
5#pragma hdrstop
6#endif
7
8#ifndef WX_PRECOMP
9#include "wx/wx.h"
10#endif
11
12// For wxCURSOR_BLANK below, but isn't used a.t.m.
13//#ifdef WIN32
14//#include "wx/msw/wx.rc"
15//#endif
16
17#include "osgviewerWX.h"
18
19
20#include <osgViewer/ViewerEventHandlers>
21#include <osgGA/TrackballManipulator>
22#include <osgDB/ReadFile>
23#include <wx/image.h>
24#include <wx/menu.h>
25
26#include <iostream>
27
28// `Main program' equivalent, creating windows and returning main app frame
29bool wxOsgApp::OnInit()
30{
31    if (argc<2)
32    {
33        std::cout << wxString(argv[0]).mb_str() <<": requires filename argument." << std::endl;
34        return false;
35    }
36
37    int width = 800;
38    int height = 600;
39
40    // Create the main frame window
41
42    MainFrame *frame = new MainFrame(NULL, wxT("wxWidgets OSG Sample"),
43        wxDefaultPosition, wxSize(width, height));
44
45    // create osg canvas
46    //    - initialize
47
48    int attributes[7];
49    attributes[0] = int(WX_GL_DOUBLEBUFFER);
50    attributes[1] = WX_GL_RGBA;
51    attributes[2] = WX_GL_DEPTH_SIZE;
52    attributes[3] = 8;
53    attributes[4] = WX_GL_STENCIL_SIZE;
54    attributes[5] = 8;
55    attributes[6] = 0;
56
57    OSGCanvas *canvas = new OSGCanvas(frame, wxID_ANY, wxDefaultPosition,
58        wxSize(width, height), wxSUNKEN_BORDER, wxT("osgviewerWX"), attributes);
59
60    GraphicsWindowWX* gw = new GraphicsWindowWX(canvas);
61
62    canvas->SetGraphicsWindow(gw);
63
64    osgViewer::Viewer *viewer = new osgViewer::Viewer;
65    viewer->getCamera()->setGraphicsContext(gw);
66    viewer->getCamera()->setViewport(0,0,width,height);
67    viewer->addEventHandler(new osgViewer::StatsHandler);
68    viewer->setThreadingModel(osgViewer::Viewer::SingleThreaded);
69
70    // load the scene.
71    wxString fname(argv[1]);
72    osg::ref_ptr<osg::Node> loadedModel = osgDB::readNodeFile(std::string(fname.mb_str()));
73    if (!loadedModel)
74    {
75        std::cout << argv[0] <<": No data loaded." << std::endl;
76        return false;
77    }
78
79    viewer->setSceneData(loadedModel.get());
80    viewer->setCameraManipulator(new osgGA::TrackballManipulator);
81    frame->SetViewer(viewer);
82
83    /* Show the frame */
84    frame->Show(true);
85
86    return true;
87}
88
89IMPLEMENT_APP(wxOsgApp)
90
91BEGIN_EVENT_TABLE(MainFrame, wxFrame)
92    EVT_IDLE(MainFrame::OnIdle)
93END_EVENT_TABLE()
94
95/* My frame constructor */
96MainFrame::MainFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
97    const wxSize& size, long style)
98    : wxFrame(frame, wxID_ANY, title, pos, size, style)
99{
100}
101
102void MainFrame::SetViewer(osgViewer::Viewer *viewer)
103{
104    _viewer = viewer;
105}
106
107void MainFrame::OnIdle(wxIdleEvent &event)
108{
109    if (!_viewer->isRealized())
110        return;
111
112    _viewer->frame();
113
114    event.RequestMore();
115}
116
117BEGIN_EVENT_TABLE(OSGCanvas, wxGLCanvas)
118    EVT_SIZE                (OSGCanvas::OnSize)
119    EVT_PAINT               (OSGCanvas::OnPaint)
120    EVT_ERASE_BACKGROUND    (OSGCanvas::OnEraseBackground)
121
122    EVT_CHAR                (OSGCanvas::OnChar)
123    EVT_KEY_UP              (OSGCanvas::OnKeyUp)
124
125    EVT_ENTER_WINDOW        (OSGCanvas::OnMouseEnter)
126    EVT_LEFT_DOWN           (OSGCanvas::OnMouseDown)
127    EVT_MIDDLE_DOWN         (OSGCanvas::OnMouseDown)
128    EVT_RIGHT_DOWN          (OSGCanvas::OnMouseDown)
129    EVT_LEFT_UP             (OSGCanvas::OnMouseUp)
130    EVT_MIDDLE_UP           (OSGCanvas::OnMouseUp)
131    EVT_RIGHT_UP            (OSGCanvas::OnMouseUp)
132    EVT_MOTION              (OSGCanvas::OnMouseMotion)
133    EVT_MOUSEWHEEL          (OSGCanvas::OnMouseWheel)
134END_EVENT_TABLE()
135
136OSGCanvas::OSGCanvas(wxWindow *parent, wxWindowID id,
137    const wxPoint& pos, const wxSize& size, long style, const wxString& name, int *attributes)
138    : wxGLCanvas(parent, id, pos, size, style|wxFULL_REPAINT_ON_RESIZE, name, attributes)
139{
140    // default cursor to standard
141    _oldCursor = *wxSTANDARD_CURSOR;
142}
143
144OSGCanvas::~OSGCanvas()
145{
146}
147
148void OSGCanvas::OnPaint( wxPaintEvent& WXUNUSED(event) )
149{
150    /* must always be here */
151    wxPaintDC dc(this);
152}
153
154void OSGCanvas::OnSize(wxSizeEvent& event)
155{
156    // this is also necessary to update the context on some platforms
157    wxGLCanvas::OnSize(event);
158
159    // set GL viewport (not called by wxGLCanvas::OnSize on all platforms...)
160    int width, height;
161    GetClientSize(&width, &height);
162
163    if (_graphics_window.valid())
164    {
165        // update the window dimensions, in case the window has been resized.
166        _graphics_window->getEventQueue()->windowResize(0, 0, width, height);
167        _graphics_window->resized(0,0,width,height);
168    }
169}
170
171void OSGCanvas::OnEraseBackground(wxEraseEvent& WXUNUSED(event))
172{
173    /* Do nothing, to avoid flashing on MSW */
174}
175
176void OSGCanvas::OnChar(wxKeyEvent &event)
177{
178#if wxUSE_UNICODE
179    int key = event.GetUnicodeKey();
180#else
181    int key = event.GetKeyCode();
182#endif
183
184    if (_graphics_window.valid())
185        _graphics_window->getEventQueue()->keyPress(key);
186
187    // If this key event is not processed here, we should call
188    // event.Skip() to allow processing to continue.
189}
190
191void OSGCanvas::OnKeyUp(wxKeyEvent &event)
192{
193#if wxUSE_UNICODE
194    int key = event.GetUnicodeKey();
195#else
196    int key = event.GetKeyCode();
197#endif
198
199    if (_graphics_window.valid())
200        _graphics_window->getEventQueue()->keyRelease(key);
201
202    // If this key event is not processed here, we should call
203    // event.Skip() to allow processing to continue.
204}
205
206void OSGCanvas::OnMouseEnter(wxMouseEvent &event)
207{
208    // Set focus to ourselves, so keyboard events get directed to us
209    SetFocus();
210}
211
212void OSGCanvas::OnMouseDown(wxMouseEvent &event)
213{
214    if (_graphics_window.valid())
215    {
216        _graphics_window->getEventQueue()->mouseButtonPress(event.GetX(), event.GetY(),
217            event.GetButton());
218    }
219}
220
221void OSGCanvas::OnMouseUp(wxMouseEvent &event)
222{
223    if (_graphics_window.valid())
224    {
225        _graphics_window->getEventQueue()->mouseButtonRelease(event.GetX(), event.GetY(),
226            event.GetButton());
227    }
228}
229
230void OSGCanvas::OnMouseMotion(wxMouseEvent &event)
231{
232    if (_graphics_window.valid())
233        _graphics_window->getEventQueue()->mouseMotion(event.GetX(), event.GetY());
234}
235
236void OSGCanvas::OnMouseWheel(wxMouseEvent &event)
237{
238    int delta = event.GetWheelRotation() / event.GetWheelDelta() * event.GetLinesPerAction();
239
240    if (_graphics_window.valid()) {
241        _graphics_window->getEventQueue()->mouseScroll(
242            delta>0 ?
243            osgGA::GUIEventAdapter::SCROLL_UP :
244            osgGA::GUIEventAdapter::SCROLL_DOWN);
245    }
246}
247
248void OSGCanvas::UseCursor(bool value)
249{
250    if (value)
251    {
252        // show the old cursor
253        SetCursor(_oldCursor);
254    }
255    else
256    {
257        // remember the old cursor
258        _oldCursor = GetCursor();
259
260        // hide the cursor
261        //    - can't find a way to do this neatly, so create a 1x1, transparent image
262        wxImage image(1,1);
263        image.SetMask(true);
264        image.SetMaskColour(0, 0, 0);
265        wxCursor cursor(image);
266        SetCursor(cursor);
267
268        // On wxGTK, only works as of version 2.7.0
269        // (http://trac.wxwidgets.org/ticket/2946)
270        // SetCursor( wxStockCursor( wxCURSOR_BLANK ) );
271    }
272}
273
274GraphicsWindowWX::GraphicsWindowWX(OSGCanvas *canvas)
275{
276    _canvas = canvas;
277
278    _traits = new GraphicsContext::Traits;
279
280    wxPoint pos = _canvas->GetPosition();
281    wxSize  size = _canvas->GetSize();
282
283    _traits->x = pos.x;
284    _traits->y = pos.y;
285    _traits->width = size.x;
286    _traits->height = size.y;
287
288    init();
289}
290
291GraphicsWindowWX::~GraphicsWindowWX()
292{
293}
294
295void GraphicsWindowWX::init()
296{
297    if (valid())
298    {
299        setState( new osg::State );
300        getState()->setGraphicsContext(this);
301
302        if (_traits.valid() && _traits->sharedContext.valid())
303        {
304            getState()->setContextID( _traits->sharedContext->getState()->getContextID() );
305            incrementContextIDUsageCount( getState()->getContextID() );
306        }
307        else
308        {
309            getState()->setContextID( osg::GraphicsContext::createNewContextID() );
310        }
311    }
312}
313
314void GraphicsWindowWX::grabFocus()
315{
316    // focus the canvas
317    _canvas->SetFocus();
318}
319
320void GraphicsWindowWX::grabFocusIfPointerInWindow()
321{
322    // focus this window, if the pointer is in the window
323    wxPoint pos = wxGetMousePosition();
324    if (wxFindWindowAtPoint(pos) == _canvas)
325        _canvas->SetFocus();
326}
327
328void GraphicsWindowWX::useCursor(bool cursorOn)
329{
330    _canvas->UseCursor(cursorOn);
331}
332
333bool GraphicsWindowWX::makeCurrentImplementation()
334{
335    _canvas->SetCurrent();
336    return true;
337}
338
339void GraphicsWindowWX::swapBuffersImplementation()
340{
341    _canvas->SwapBuffers();
342}
Note: See TracBrowser for help on using the browser.