/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2003 Robert Osfield * * This library is open source and may be redistributed and/or modified under * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or * (at your option) any later version. The full license is in LICENSE file * included with this distribution, and on the openscenegraph.org website. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * OpenSceneGraph Public License for more details. */ #ifndef OSGUTIL_SCENEVIEW #define OSGUTIL_SCENEVIEW 1 #include #include #include #include #include #include namespace osgUtil { /** * SceneView is literally a view of a scene, encapsulating the * camera (modelview+projection matrices), global state, lights and the scene itself. Provides * methods for setting up the view and rendering it. */ class OSGUTIL_EXPORT SceneView : public osg::Referenced { public: /** Construct a default scene view.*/ SceneView(osg::DisplaySettings* ds=NULL); /** Set scene view to use default global state, light, camera * and render visitor. */ void setDefaults(); /** Set the data which to view. The data will typically be * an osg::Scene but can be any osg::Node type. */ void setSceneData(osg::Node* node) { _sceneData = node; } /** Get the scene data which to view. The data will typically be * an osg::Scene but can be any osg::Node type. */ osg::Node* getSceneData() { return _sceneData.get(); } /** Get the const scene data which to view. The data will typically be * an osg::Scene but can be any osg::Node type. */ const osg::Node* getSceneData() const { return _sceneData.get(); } /** Set the viewport of the scene view to use specfied osg::Viewport. */ void setViewport(osg::Viewport* viewport) { if (viewport) _viewport = viewport; else { // ensure that _viewport is always valid. _viewport = new osg::Viewport; } } /** Set the viewport of the scene view to specified dimensions. */ void setViewport(int x,int y,int width,int height) { _viewport->setViewport(x,y,width,height); } /** Get the const viewport. */ const osg::Viewport* getViewport() const { return _viewport.get(); } /** Get the viewport. */ osg::Viewport* getViewport() { return _viewport.get(); } /** Get the viewport of the scene view. */ void getViewport(int& x,int& y,int& width,int& height) { _viewport->getViewport(x,y,width,height); } /** Set the DisplaySettings. */ inline void setDisplaySettings(osg::DisplaySettings* vs) { _displaySettings = vs; } /** Get the const DisplaySettings */ inline const osg::DisplaySettings* getDisplaySettings() const { return _displaySettings.get(); } /** Get the DisplaySettings */ inline osg::DisplaySettings* getDisplaySettings() { return _displaySettings.get(); } /** Set the background color used in glClearColor(). Defaults to an off blue color.*/ void setBackgroundColor(const osg::Vec4& color) { _backgroundColor=color; } /** Get the background color.*/ const osg::Vec4& getBackgroundColor() const { return _backgroundColor; } void setGlobalStateSet(osg::StateSet* state) { _globalStateSet = state; } osg::StateSet* getGlobalStateSet() { return _globalStateSet.get(); } const osg::StateSet* getGlobalStateSet() const { return _globalStateSet.get(); } void setLocalStateSet(osg::StateSet* state) { _localStateSet = state; } osg::StateSet* getLocalStateSet() { return _localStateSet.get(); } const osg::StateSet* getLocalStateSet() const { return _localStateSet.get(); } enum LightingMode { HEADLIGHT, // default SKY_LIGHT, NO_SCENEVIEW_LIGHT }; void setLightingMode(LightingMode mode) { _lightingMode=mode; } LightingMode getLightingMode() const { return _lightingMode; } void setLight(osg::Light* light) { _light = light; } osg::Light* getLight() { return _light.get(); } const osg::Light* getLight() const { return _light.get(); } void setState(osg::State* state) { _state = state; } osg::State* getState() { return _state.get(); } const osg::State* getState() const { return _state.get(); } /** set a projection matrix. Note, this will override a camera's projection matrix if it is not NULL.*/ void setProjectionMatrix(const osg::Matrix& matrix) { _projectionMatrix = new osg::RefMatrix(matrix); } void setProjectionMatrix(osg::RefMatrix* matrix) { _projectionMatrix = matrix; } osg::RefMatrix* getProjectionMatrix() { return _projectionMatrix.get(); } const osg::RefMatrix* getProjectionMatrix() const { return _projectionMatrix.get(); } /** set a modelview matrix. Note, this will override a camera's modelview matrix if it is not NULL.*/ void setModelViewMatrix(const osg::Matrix& matrix) { _modelviewMatrix = new osg::RefMatrix(matrix); } void setModelViewMatrix(osg::RefMatrix* matrix) { _modelviewMatrix = matrix; } osg::RefMatrix* getModelViewMatrix() { return _modelviewMatrix.get(); } const osg::RefMatrix* getModelViewMatrix() const { return _modelviewMatrix.get(); } void setInitVisitor(osg::NodeVisitor* av) { _initVisitor = av; } osg::NodeVisitor* getInitVisitor() { return _initVisitor.get(); } const osg::NodeVisitor* getInitVisitor() const { return _initVisitor.get(); } void setUpdateVisitor(osg::NodeVisitor* av) { _updateVisitor = av; } osg::NodeVisitor* getUpdateVisitor() { return _updateVisitor.get(); } const osg::NodeVisitor* getUpdateVisitor() const { return _updateVisitor.get(); } void setCullVisitor(osgUtil::CullVisitor* cv) { _cullVisitor = cv; } osgUtil::CullVisitor* getCullVisitor() { return _cullVisitor.get(); } const osgUtil::CullVisitor* getCullVisitor() const { return _cullVisitor.get(); } void setRenderGraph(osgUtil::RenderGraph* rg) { _rendergraph = rg; } osgUtil::RenderGraph* getRenderGraph() { return _rendergraph.get(); } const osgUtil::RenderGraph* getRenderGraph() const { return _rendergraph.get(); } void setRenderStage(osgUtil::RenderStage* rs) { _renderStage = rs; } osgUtil::RenderStage* getRenderStage() { return _renderStage.get(); } const osgUtil::RenderStage* getRenderStage() const { return _renderStage.get(); } void setCullMask(const osg::Node::NodeMask nm) { _cullMask = nm; } osg::Node::NodeMask getCullMask() const { return _cullMask; } void setCullMaskLeft(const osg::Node::NodeMask nm) { _cullMaskLeft = nm; } osg::Node::NodeMask getCullMaskLeft() const { return _cullMaskLeft; } void setCullMaskRight(const osg::Node::NodeMask nm) { _cullMaskRight = nm; } osg::Node::NodeMask getCullMaskRight() const { return _cullMaskRight; } /** Set the LOD bias for the CullVisitor to use.*/ void setLODScale(float bias) { _LODScale = bias; } /** Get the LOD bias.*/ float getLODScale() const { return _LODScale; } /** Set the Small Feature Culling Pixel Size.*/ void setSmallFeatureCullingPixelSize(float value) { _smallFeatureCullingPixelSize=value; } /** Get the Small Feature Culling Pixel Size.*/ float getSmallFeatureCullingPixelSize() const { return _smallFeatureCullingPixelSize; } /** Set the culling mode for the CullVisitor to use.*/ void setCullingMode(osg::CullStack::CullingMode mode) { _cullingMode = mode; } /** Returns the current CullingMode.*/ osg::CullStack::CullingMode getCullingMode() const { return _cullingMode; } /** Set the ComputeNearFarMode for the CullVisitor to use.*/ void setComputeNearFarMode(CullVisitor::ComputeNearFarMode cnfm) { _computeNearFar=cnfm; } /** Get the ComputeNearFarMode.*/ CullVisitor::ComputeNearFarMode getComputeNearFarMode() const { return _computeNearFar;} /** FusionDistanceMode is used only when working in stereo.*/ enum FusionDistanceMode { /** Use fusion distance from the value set on the SceneView.*/ USE_FUSION_DISTANCE_VALUE, /** Compute the fusion distance by multiplying the screen distance by the fusion distance value.*/ PROPORTIONAL_TO_SCREEN_DISTANCE }; /** Set the FusionDistanceMode and Value. Note, is used only when working in stereo.*/ void setFusionDistance(FusionDistanceMode mode,float value=1.0f) { _fusionDistanceMode = mode; _fusionDistanceValue = value; } /** Get the FusionDistanceMode.*/ FusionDistanceMode getFusionDistanceMode() const { return _fusionDistanceMode; } /** Get the FusionDistanceValue. Note, only used for USE_FUSION_DISTANCE_VALUE & PROPORTIONAL_TO_SCREEN_DISTANCE modes.*/ float getFusionDistanceValue() const { return _fusionDistanceValue; } /** set whether the draw method should call renderer->prioritizeTexture.*/ void setPrioritizeTextures(bool pt) { _prioritizeTextures = pt; } /** get whether the draw method should call renderer->prioritizeTexture.*/ bool getPrioritizeTextures() const { return _prioritizeTextures; } /** Calculate, via glUnProject, the object coordinates of a window point. Note, current implementation requires that SceneView::draw() has been previously called for projectWindowIntoObject to produce valid values. Consistent with OpenGL windows coordinates are calculated relative to the bottom left of the window. Returns true on successful projection. */ bool projectWindowIntoObject(const osg::Vec3& window,osg::Vec3& object) const; /** Calculate, via glUnProject, the object coordinates of a window x,y when projected onto the near and far planes. Note, current implementation requires that SceneView::draw() has been previously called for projectWindowIntoObject to produce valid values. Consistent with OpenGL windows coordinates are calculated relative to the bottom left of the window. Returns true on successful projection. */ bool projectWindowXYIntoObject(int x,int y,osg::Vec3& near_point,osg::Vec3& far_point) const; /** Calculate, via glProject, the object coordinates of a window. Note, current implementation requires that SceneView::draw() has been previously called for projectWindowIntoObject to produce valid values. Consistent with OpenGL windows coordinates are calculated relative to the bottom left of the window, whereas as window API's normally have the top left as the origin, so you may need to pass in (mouseX,window_height-mouseY,...). Returns true on successful projection. */ bool projectObjectIntoWindow(const osg::Vec3& object,osg::Vec3& window) const; /** Set the frame stamp for the current frame.*/ inline void setFrameStamp(osg::FrameStamp* fs) { _frameStamp = fs; } /** Set the frame stamp for the current frame.*/ inline const osg::FrameStamp* getFrameStamp() const { return _frameStamp.get(); } /** Do init traversal of attached scene graph using Init NodeVisitor. * The init traversal is called once for each SceneView, and should * be used to compile display list, texture objects intialize data * not otherwise intializaed during scene graph loading. Note, is * called automatically by update&cull if it hasn't already been called * elsewhere. Also init() should only ever be called within a valid * graphics context.*/ virtual void init(); /** Do app traversal of attached scene graph using App NodeVisitor.*/ virtual void update(); #ifdef USE_DEPREACTED_API virtual void app() { update(); } #endif /** Do cull traversal of attached scene graph using Cull NodeVisitor.*/ virtual void cull(); /** Do draw traversal of draw bins generated by cull traversal.*/ virtual void draw(); protected: virtual ~SceneView(); /** Do cull traversal of attached scene graph using Cull NodeVisitor.*/ virtual void cullStage(osg::RefMatrix* projection,osg::RefMatrix* modelview,osgUtil::CullVisitor* cullVisitor, osgUtil::RenderGraph* rendergraph, osgUtil::RenderStage* renderStage); const osg::Matrix computeMVPW() const; void clearArea(int x,int y,int width,int height,const osg::Vec4& color); osg::ref_ptr _sceneData; osg::ref_ptr _globalStateSet; osg::ref_ptr _localStateSet; osg::ref_ptr _light; osg::ref_ptr _projectionMatrix; osg::ref_ptr _modelviewMatrix; osg::ref_ptr _displaySettings; osg::ref_ptr _state; bool _initCalled; osg::ref_ptr _initVisitor; osg::ref_ptr _updateVisitor; osg::Node::NodeMask _cullMask; osg::ref_ptr _cullVisitor; osg::ref_ptr _rendergraph; osg::ref_ptr _renderStage; osg::Node::NodeMask _cullMaskLeft; osg::ref_ptr _cullVisitorLeft; osg::ref_ptr _rendergraphLeft; osg::ref_ptr _renderStageLeft; osg::Node::NodeMask _cullMaskRight; osg::ref_ptr _cullVisitorRight; osg::ref_ptr _rendergraphRight; osg::ref_ptr _renderStageRight; osg::ref_ptr _frameStamp; osg::Vec4 _backgroundColor; CullVisitor::ComputeNearFarMode _computeNearFar; osg::CullStack::CullingMode _cullingMode; float _LODScale; float _smallFeatureCullingPixelSize; FusionDistanceMode _fusionDistanceMode; float _fusionDistanceValue; osg::ref_ptr _viewport; LightingMode _lightingMode; bool _prioritizeTextures; }; } #endif