// MFC_OSG.cpp : implementation of the cOSG class // #include "stdafx.h" #include "MFC_OSG.h" cOSG::cOSG(HWND hWnd) : m_hWnd(hWnd) { } cOSG::~cOSG() { mViewer->setDone(true); Sleep(1000); mViewer->stopThreading(); delete mViewer; } void cOSG::InitOSG(std::string modelname) { // Store the name of the model to load m_ModelName = modelname; // Init different parts of OSG InitManipulators(); InitSceneGraph(); InitCameraConfig(); } void cOSG::InitManipulators(void) { // Create a trackball manipulator trackball = new osgGA::TrackballManipulator(); // Create a Manipulator Switcher keyswitchManipulator = new osgGA::KeySwitchMatrixManipulator; // Add our trackball manipulator to the switcher keyswitchManipulator->addMatrixManipulator( '1', "Trackball", trackball.get()); // Init the switcher to the first manipulator (in this case the only manipulator) keyswitchManipulator->selectMatrixManipulator(0); // Zero based index Value } void cOSG::InitSceneGraph(void) { // Init the main Root Node/Group mRoot = new osg::Group; // Load the Model from the model name mModel = osgDB::readNodeFile(m_ModelName); // Optimize the model osgUtil::Optimizer optimizer; optimizer.optimize(mModel.get()); optimizer.reset(); // Add the model to the scene mRoot->addChild(mModel.get()); } void cOSG::InitCameraConfig(void) { // Local Variable to hold window size data RECT rect; // Create the viewer for this window mViewer = new osgViewer::Viewer(); // Add a Stats Handler to the viewer mViewer->addEventHandler(new osgViewer::StatsHandler); // Get the current window size ::GetWindowRect(m_hWnd, &rect); // Init the GraphicsContext Traits osg::ref_ptr traits = new osg::GraphicsContext::Traits; // Init the Windata Variable that holds the handle for the Window to display OSG in. osg::ref_ptr windata = new osgViewer::GraphicsWindowWin32::WindowData(m_hWnd); // Setup the traits parameters traits->x = 0; traits->y = 0; traits->width = rect.right - rect.left; traits->height = rect.bottom - rect.top; traits->windowDecoration = false; traits->doubleBuffer = true; traits->sharedContext = 0; traits->setInheritedWindowPixelFormat = true; traits->inheritedWindowData = windata; // Create the Graphics Context osg::GraphicsContext* gc = osg::GraphicsContext::createGraphicsContext(traits.get()); // Init a new Camera (Master for this View) osg::ref_ptr camera = new osg::Camera; // Assign Graphics Context to the Camera camera->setGraphicsContext(gc); // Set the viewport for the Camera camera->setViewport(new osg::Viewport(traits->x, traits->y, traits->width, traits->height)); // Add the Camera to the Viewer mViewer->addSlave(camera.get()); // Add the Camera Manipulator to the Viewer mViewer->setCameraManipulator(keyswitchManipulator.get()); // Set the Scene Data mViewer->setSceneData(mRoot.get()); // Realize the Viewer mViewer->realize(); // Correct aspect ratio double fovy,aspectRatio,z1,z2; mViewer->getCamera()->getProjectionMatrixAsPerspective(fovy,aspectRatio,z1,z2); aspectRatio=double(traits->width)/double(traits->height); mViewer->getCamera()->setProjectionMatrixAsPerspective(fovy,aspectRatio,z1,z2); } void cOSG::PreFrameUpdate() { // Due any preframe updates in this routine } void cOSG::PostFrameUpdate() { // Due any postframe updates in this routine } void cOSG::Render(void* ptr) { cOSG* osg = (cOSG*)ptr; osgViewer::Viewer* viewer = osg->getViewer(); // You have two options for the main viewer loop // viewer->run() or // while(!viewer->done()) { viewer->frame(); } //viewer->run(); while(!viewer->done()) { osg->PreFrameUpdate(); viewer->frame(); osg->PostFrameUpdate(); //Sleep(10); // Use this command if you need to allow other processes to have cpu time } // For some reason this has to be here to avoid issue: // if you have multiple OSG windows up // and you exit one then all stop rendering AfxMessageBox("Exit Rendering Thread"); _endthread(); }