OpenWalnut  1.4.0
WGEUtils.h
00001 //---------------------------------------------------------------------------
00002 //
00003 // Project: OpenWalnut ( http://www.openwalnut.org )
00004 //
00005 // Copyright 2009 OpenWalnut Community, BSV@Uni-Leipzig and CNCF@MPI-CBS
00006 // For more information see http://www.openwalnut.org/copying
00007 //
00008 // This file is part of OpenWalnut.
00009 //
00010 // OpenWalnut is free software: you can redistribute it and/or modify
00011 // it under the terms of the GNU Lesser General Public License as published by
00012 // the Free Software Foundation, either version 3 of the License, or
00013 // (at your option) any later version.
00014 //
00015 // OpenWalnut is distributed in the hope that it will be useful,
00016 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00017 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00018 // GNU Lesser General Public License for more details.
00019 //
00020 // You should have received a copy of the GNU Lesser General Public License
00021 // along with OpenWalnut. If not, see <http://www.gnu.org/licenses/>.
00022 //
00023 //---------------------------------------------------------------------------
00024 
00025 #ifndef WGEUTILS_H
00026 #define WGEUTILS_H
00027 
00028 #include <string>
00029 #include <vector>
00030 
00031 #include <osg/Array>
00032 #include <osg/Vec3>
00033 #include <osg/Vec4>
00034 #include <osg/Camera>
00035 #include <osg/Uniform>
00036 
00037 #include "../common/WColor.h"
00038 #include "../common/WBoundingBox.h"
00039 #include "../common/WAssert.h"
00040 #include "../common/WPropertyVariable.h"
00041 
00042 #include "shaders/WGEPropertyUniform.h"
00043 #include "WGECamera.h"
00044 
00045 namespace wge
00046 {
00047     /**
00048      * Enable transparency for the given node. This enabled blending and sets the node to the transparency bin.
00049      *
00050      * \param node the node
00051      */
00052     void enableTransparency( osg::ref_ptr< osg::Node > node );
00053 
00054     /**
00055      * Transforms a direction given via two points into a RGB color.
00056      *
00057      * \param pos1 First point
00058      * \param pos2 Second point
00059      *
00060      * \return converts a vector to a color
00061      */
00062     WColor getRGBAColorFromDirection( const WPosition &pos1, const WPosition &pos2 );
00063 
00064     /**
00065      * Converts a whole vector of WPositions into an osg::Vec3Array.
00066      *
00067      * \param posArray The given positions vector
00068      *
00069      * \return Refernce to the same vector but as osg::Vec3Array.
00070      */
00071     osg::ref_ptr< osg::Vec3Array > osgVec3Array( const std::vector< WPosition >& posArray );
00072 
00073     /**
00074      * Converts screen coordinates into Camera coordinates.
00075      *
00076      * \param screen the screen coordinates
00077      * \param camera The matrices of this camera will used for unprojecting.
00078      *
00079      * \return un-projects a screen coordinate back to world space
00080      */
00081     osg::Vec3 unprojectFromScreen( const osg::Vec3 screen, osg::ref_ptr< WGECamera > camera  );
00082 
00083     /**
00084      * Converts screen coordinates into Camera coordinates.
00085      * \note this method can be useful to work with vectors (w component 0)
00086      *
00087      * \param screen the screen coordinates
00088      * \param camera The matrices of this camera will used for unprojecting.
00089      *
00090      * \return un-projects a screen coordinate back to world space
00091      */
00092     osg::Vec4 unprojectFromScreen( const osg::Vec4 screen, osg::ref_ptr< WGECamera > camera  );
00093 
00094     /**
00095      * creates the same color as the atlas colormap shader from the index
00096      *
00097      * \param index unsigned char that indexes the color
00098      * \return the color
00099      */
00100     WColor createColorFromIndex( int index );
00101 
00102     /**
00103      * creates a rgb WColor from a HSV value
00104      * \param h hue
00105      * \param s saturation
00106      * \param v value
00107      * \return the color
00108      */
00109     WColor createColorFromHSV( int h, float s = 1.0, float v = 1.0 );
00110 
00111     /**
00112      * creates the nth color of a partition of the hsv color circle
00113      *
00114      * \param n number of the color
00115      * \return the color
00116      */
00117     WColor getNthHSVColor( int n );
00118 
00119     /**
00120      * Creates a osg::Uniform with given type and name and applies it to the given node.
00121      *
00122      * \tparam T This is the data used for the uniform. It may be a PropertyType, an integral or an osg::Uniform.
00123      *
00124      * \param node Node where the uniform should be bound to.
00125      * \param prop The type of the uniform.
00126      * \param name The name of the uniform.
00127      */
00128     template< typename T >
00129     void bindAsUniform( osg::Node* node, T prop, std::string name );
00130 
00131     /**
00132      * Generate a proxy cube, which ensures OSG does proper near-far plane calculation and culling. This is especially useful if you create some
00133      * geometry and modify it on the GPU by shaders. In these cases, OSG will not properly cull and near-far clip. This cull proxy is basically a
00134      * cube, which gets shrinked to zero size on the GPU. This ensures you cannot see it, but it makes OSG see you proper bounding volume.
00135      *
00136      * \param bbox the bounding box to cover
00137      *
00138      * \return the proxy. Add it to your scene root.
00139      */
00140     osg::ref_ptr< osg::Node > generateCullProxy( const WBoundingBox& bbox );
00141 
00142     /**
00143      * Generate a proxy cube, which ensures OSG does proper near-far plane calculation and culling. This is especially useful if you create some
00144      * geometry and modify it on the GPU by shaders. In these cases, OSG will not properly cull and near-far clip. This cull proxy is basically a
00145      * cube, which gets shrinked to zero size on the GPU. This ensures you cannot see it, but it makes OSG see you proper bounding volume.
00146      *
00147      * \note dynamic cull proxys use the getBound method of the specified node before culling. So if you implement objects that change their size
00148      * dynamically, add a  osg::Node::ComputeBoundingSphereCallback to them
00149      *
00150      * \note This method uses update callbacks. Remember to add your own callbacks via addUpdateCallback, instead of setUpdateCallback.
00151      *
00152      * \param node the node
00153      *
00154      * \return the proxy. Add it to your scene root.
00155      */
00156     osg::ref_ptr< osg::Node > generateDynamicCullProxy( osg::ref_ptr< osg::Node > node );
00157 }
00158 
00159 inline WColor wge::getRGBAColorFromDirection( const WPosition &pos1, const WPosition &pos2 )
00160 {
00161     WPosition direction( normalize( pos2 - pos1 ) );
00162     return WColor( std::abs( direction[0] ), std::abs( direction[1] ), std::abs( direction[2] ), 1.0f );
00163 }
00164 
00165 namespace wge
00166 {
00167     template< typename T >
00168     inline void bindAsUniform( osg::Node* node, T prop, std::string name )
00169     {
00170         osg::ref_ptr< osg::Uniform > uniform = new osg::Uniform( name.c_str(), prop );
00171         osg::StateSet *states = node->getOrCreateStateSet();
00172         states->addUniform( uniform );
00173     }
00174 
00175     /**
00176      * Template specialization for double values.
00177      *
00178      * \param node Node where the uniform should be bound to.
00179      * \param prop The type of the uniform.
00180      * \param name The name of the uniform.
00181      */
00182     template<>
00183     inline void bindAsUniform< double >( osg::Node* node, double prop, std::string name )
00184     {
00185         osg::ref_ptr< osg::Uniform > uniform( new osg::Uniform( name.c_str(), static_cast< float >( prop ) ) );
00186         osg::StateSet *states = node->getOrCreateStateSet();
00187         states->addUniform( uniform );
00188     }
00189 
00190     /**
00191      * Template specialization for size_t values.
00192      *
00193      * \param node Node where the uniform should be bound to.
00194      * \param prop The type of the uniform.
00195      * \param name The name of the uniform.
00196      */
00197     template<>
00198     inline void bindAsUniform< size_t >( osg::Node* node, size_t prop, std::string name )
00199     {
00200         osg::ref_ptr< osg::Uniform > uniform( new osg::Uniform( name.c_str(), static_cast< int >( prop ) ) );
00201         osg::StateSet *states = node->getOrCreateStateSet();
00202         states->addUniform( uniform );
00203     }
00204 
00205     /**
00206      * Template specialization for WPropDouble values.
00207      *
00208      * \param node Node where the uniform should be bound to.
00209      * \param prop The type of the uniform.
00210      * \param name The name of the uniform.
00211      */
00212     template<>
00213     inline void bindAsUniform< WPropDouble >( osg::Node* node, WPropDouble prop, std::string name )
00214     {
00215         osg::ref_ptr< osg::Uniform > uniform( new WGEPropertyUniform< WPropDouble >( name, prop ) );
00216         osg::StateSet *states = node->getOrCreateStateSet();
00217         states->addUniform( uniform );
00218     }
00219 
00220     /**
00221      * Template specialization for WPropColor values.
00222      *
00223      * \param node Node where the uniform should be bound to.
00224      * \param prop The type of the uniform.
00225      * \param name The name of the uniform.
00226      */
00227     template<>
00228     inline void bindAsUniform< WPropColor >( osg::Node* node, WPropColor prop, std::string name )
00229     {
00230         osg::ref_ptr< osg::Uniform > uniform( new WGEPropertyUniform< WPropColor >( name, prop ) );
00231         osg::StateSet *states = node->getOrCreateStateSet();
00232         states->addUniform( uniform );
00233     }
00234 
00235     /**
00236      * Template specialization for osg::Uniform values.
00237      *
00238      * \param node Node where the uniform should be bound to.
00239      * \param uniform The type of the uniform.
00240      */
00241     template<>
00242     inline void bindAsUniform< osg::ref_ptr< osg::Uniform > >( osg::Node* node, osg::ref_ptr< osg::Uniform > uniform, std::string /* name */ )
00243     {
00244         osg::StateSet *states = node->getOrCreateStateSet();
00245         states->addUniform( uniform );
00246     }
00247 }
00248 #endif  // WGEUTILS_H
00249