OpenWalnut 1.3.1
|
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 #include <osg/Camera> 00026 00027 #include "../shaders/WGEPropertyUniform.h" 00028 #include "../shaders/WGEShaderPropertyDefine.h" 00029 #include "WGEPostprocessorGauss.h" 00030 #include "WGEPostprocessorMergeOp.h" 00031 00032 #include "WGEPostprocessorLineAO.h" 00033 00034 WGEPostprocessorLineAO::WGEPostprocessorLineAO(): 00035 WGEPostprocessor( "LineAO", 00036 "LineAO is a special ambient occlusion technique optimized for dense line and tube rendering." ) 00037 { 00038 } 00039 00040 WGEPostprocessorLineAO::WGEPostprocessorLineAO( osg::ref_ptr< WGEOffscreenRenderNode > offscreen, 00041 const WGEPostprocessor::PostprocessorInput& gbuffer ): 00042 WGEPostprocessor( "LineAO", 00043 "LineAO is a special ambient occlusion technique optimized for dense line and tube rendering." ) 00044 { 00045 // the LineAO algorithm has some parameters. Provide these parameters to the user 00046 WPropInt lineaoSamples = m_properties->addProperty( "Samples", "The number of samples to take in screen-space. Higher values produce better " 00047 "quality but can reduce FPS dramatically.", 32 ); 00048 lineaoSamples->setMin( 1 ); 00049 lineaoSamples->setMax( 128 ); 00050 00051 WPropInt lineaoScalers = m_properties->addProperty( "Hemispheres", "The number of hemispheres to sample around each pixel. Higher values " 00052 "produce better quality but can reduce FPS dramatically.", 3 ); 00053 lineaoScalers->setMin( 1 ); 00054 lineaoScalers->setMax( 8 ); 00055 00056 WPropDouble lineaoRadiusSS = m_properties->addProperty( "Radius", "The radius around the pixel to sample for occluders in pixels.", 2.0 ); 00057 lineaoRadiusSS->setMin( 0.01 ); 00058 lineaoRadiusSS->setMax( 10.0 ); 00059 00060 WPropDouble lineaoTotalStrength = m_properties->addProperty( "Total Strength", "The strength of the effect. Higher values emphasize the effect.", 00061 1.0 ); 00062 lineaoTotalStrength->setMin( 0.0 ); 00063 lineaoTotalStrength->setMax( 5.0 ); 00064 00065 WPropDouble lineaoDensityWeight = m_properties->addProperty( "Density Weight", "The strength of the occluder influence in relation to the " 00066 "geometry density. The higher the value, the larger the " 00067 "influence. Low values remove the drop-shadow effect. " 00068 "This defines the influence of one occluder to the overall " 00069 "AO effect.", 1.0 ); 00070 lineaoDensityWeight->setMin( 0.001 ); 00071 lineaoDensityWeight->setMax( 2.0 ); 00072 00073 // NOTE: The paper proposes to use a gaussian pyramid of the depth and normal maps. We skip this step. Skipping this causes the AO to look 00074 // more crispy and more detailed at local scope. 00075 00076 // use the standard postprocessor uber-shader 00077 WGEShader::RefPtr s = new WGEShader( "WGEPostprocessor" ); 00078 s->setDefine( "WGE_POSTPROCESSOR_LINEAO" ); 00079 00080 // also add the m_effectOnly property as shader preprocessor 00081 s->addPreprocessor( m_effectOnlyPreprocessor ); 00082 s->addPreprocessor( WGEShaderPreprocessor::SPtr( 00083 new WGEShaderPropertyDefine< WPropInt >( "WGE_POSTPROCESSOR_LINEAO_SCALERS", lineaoScalers ) ) 00084 ); 00085 s->addPreprocessor( WGEShaderPreprocessor::SPtr( 00086 new WGEShaderPropertyDefine< WPropInt >( "WGE_POSTPROCESSOR_LINEAO_SAMPLES", lineaoSamples ) ) 00087 ); 00088 00089 // create the LineAO rendering pass 00090 osg::ref_ptr< WGEOffscreenTexturePass > lineAOPass = offscreen->addTextureProcessingPass( s, "LineAO" ); 00091 lineAOPass->getOrCreateStateSet()->addUniform( new WGEPropertyUniform< WPropDouble >( "u_lineaoDensityWeight", lineaoDensityWeight ) ); 00092 lineAOPass->getOrCreateStateSet()->addUniform( new WGEPropertyUniform< WPropDouble >( "u_lineaoTotalStrength", lineaoTotalStrength ) ); 00093 lineAOPass->getOrCreateStateSet()->addUniform( new WGEPropertyUniform< WPropDouble >( "u_lineaoRadiusSS", lineaoRadiusSS ) ); 00094 00095 // attach color0 output 00096 m_resultTextures.push_back( lineAOPass->attach( osg::Camera::COLOR_BUFFER0, GL_RGB ) ); 00097 00098 // provide the Gbuffer input 00099 size_t gBufUnitOffset = gbuffer.bind( lineAOPass ); 00100 00101 // this effect needs some additional noise texture: 00102 const size_t size = 64; 00103 osg::ref_ptr< WGETexture2D > randTex = wge::genWhiteNoiseTexture( size, size, 3 ); 00104 lineAOPass->bind( randTex, gBufUnitOffset ); 00105 } 00106 00107 WGEPostprocessorLineAO::~WGEPostprocessorLineAO() 00108 { 00109 // cleanup 00110 } 00111 00112 WGEPostprocessor::SPtr WGEPostprocessorLineAO::create( osg::ref_ptr< WGEOffscreenRenderNode > offscreen, 00113 const WGEPostprocessor::PostprocessorInput& gbuffer ) const 00114 { 00115 return WGEPostprocessor::SPtr( new WGEPostprocessorLineAO( offscreen, gbuffer ) ); 00116 }