monitorEqualizer.cpp

00001 
00002 /* Copyright (c) 2009, Stefan Eilemann <eile@equalizergraphics.com> 
00003  *
00004  * This library is free software; you can redistribute it and/or modify it under
00005  * the terms of the GNU Lesser General Public License version 2.1 as published
00006  * by the Free Software Foundation.
00007  *  
00008  * This library is distributed in the hope that it will be useful, but WITHOUT
00009  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
00010  * FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
00011  * details.
00012  * 
00013  * You should have received a copy of the GNU Lesser General Public License
00014  * along with this library; if not, write to the Free Software Foundation, Inc.,
00015  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
00016  */
00017 
00018 #include "monitorEqualizer.h"
00019 
00020 #include "../compound.h"
00021 #include "../config.h"
00022 #include "../constCompoundVisitor.h"
00023 #include "../log.h"
00024 #include "../frame.h"
00025 #include "../view.h"
00026 #include "../segment.h"
00027 
00028 #include <eq/client/viewport.h>
00029 #include <eq/client/zoom.h>
00030 #include <eq/base/debug.h>
00031 #include <vmmlib/vmmlib.hpp>
00032 
00033 using namespace eq::base;
00034 using namespace std;
00035 
00036 namespace eq
00037 {
00038 namespace server
00039 {
00040 
00041 namespace
00042 {
00043 class OutputFrameFinder : public ConstCompoundVisitor
00044 {
00045 public:
00046     OutputFrameFinder( const std::string& name  )
00047                              : _frame(0)
00048                              , _name( name )  {}
00049 
00050     virtual ~OutputFrameFinder(){}
00051 
00052     virtual VisitorResult visit( const Compound* compound )
00053         {
00054             const FrameVector& outputFrames = compound->getOutputFrames();
00055             for( FrameVector::const_iterator i = outputFrames.begin(); 
00056                  i != outputFrames.end(); ++i )
00057             {
00058                 Frame* frame = *i;
00059 
00060                 if ( frame->getName() == _name )
00061                 {
00062                     _frame = frame;
00063                     return TRAVERSE_TERMINATE;
00064                 }
00065             }
00066             return TRAVERSE_CONTINUE;
00067         }
00068 
00069     Frame* getResult() { return _frame; }
00070 
00071 private:
00072     Frame* _frame;
00073     const std::string& _name;
00074 };
00075 }
00076 
00077 MonitorEqualizer::MonitorEqualizer()
00078 {
00079     EQINFO << "New monitor equalizer @" << (void*)this << endl;
00080 }
00081 
00082 MonitorEqualizer::MonitorEqualizer( const MonitorEqualizer& from )
00083         : Equalizer( from )
00084 {}
00085 
00086 MonitorEqualizer::~MonitorEqualizer()
00087 {
00088     attach( 0 );
00089     EQINFO << "Delete monitor equalizer @" << (void*)this << endl;
00090 }
00091 
00092 void MonitorEqualizer::attach( Compound* compound )
00093 {
00094     _outputFrames.clear();
00095     _viewports.clear();
00096     Equalizer::attach( compound );
00097 }
00098 
00099 void MonitorEqualizer::notifyUpdatePre( Compound* compound, 
00100                                         const uint32_t frameNumber )
00101 {
00102     _updateViewports();
00103     _updateZoomAndOffset();
00104 }
00105 
00106 void MonitorEqualizer::_updateViewports()
00107 {
00108     if( !_outputFrames.empty( ))
00109         return;
00110 
00111     Compound* compound = getCompound();
00112     if( !compound )
00113         return;
00114 
00115     const FrameVector& inputFrames = compound->getInputFrames();
00116     for( FrameVector::const_iterator i = inputFrames.begin(); 
00117          i != inputFrames.end(); ++i )
00118     {
00119         const Frame* frame = *i;
00120         const Compound* root = compound->getRoot();
00121 
00122         // find the output frame
00123         OutputFrameFinder frameFinder( frame->getName() );
00124         root->accept( frameFinder );
00125         Frame* outputFrame = frameFinder.getResult();
00126         
00127         _outputFrames.push_back( outputFrame );
00128         _viewports.push_back( eq::Viewport::FULL );
00129         
00130         if( outputFrame )
00131         {
00132             const Channel* channel = outputFrame->getChannel();
00133             const Segment* segment = channel->getSegment();
00134             const View* view =  channel->getView();
00135         
00136             if( view )
00137             {
00138                 Viewport viewport( segment->getViewport( ));
00139                 viewport.intersect( view->getViewport( ));
00140                 
00141                 _viewports.back() = viewport;
00142             }
00143         }
00144     }
00145 }
00146 
00147 void MonitorEqualizer::_updateZoomAndOffset()
00148 {
00149     const Compound* compound( getCompound( ));
00150     const PixelViewport& pvp( compound->getInheritPixelViewport( ));
00151 
00152     const FrameVector& inputFrames( compound->getInputFrames( ));
00153     const size_t size( inputFrames.size( ));
00154     EQASSERTINFO( size == _outputFrames.size(), 
00155                   size << " != " << _outputFrames.size( ));
00156     EQASSERT( size == _viewports.size( ));
00157 
00158     for( size_t i = 0; i < size; ++i )
00159     {
00160         Frame* frame = inputFrames[ i ];
00161         Frame* outputFrame = _outputFrames[ i ];
00162         if( !outputFrame )
00163             continue;
00164 
00165         const Compound* srcCompound = outputFrame->getCompound();
00166         const Viewport& viewport = _viewports[ i ];
00167 
00168         // compute and apply input frame offset
00169         const int32_t offsetX = static_cast< int32_t >(
00170             static_cast< float >( pvp.w ) * viewport.x );
00171         const int32_t offsetY = static_cast< int32_t >(
00172             static_cast< float >( pvp.h ) * viewport.y );
00173         frame->setOffset( Vector2i( offsetX, offsetY ));
00174         
00175         // compute and apply output frame zoom
00176         const int32_t width   = static_cast< int32_t >(
00177             static_cast< float >( pvp.w ) * viewport.w );
00178         const int32_t height  = static_cast< int32_t >(
00179             static_cast< float >( pvp.h ) * viewport.h ) ; 
00180 
00181         const PixelViewport& srcPVP( srcCompound->getInheritPixelViewport( ));
00182         const float factorW = static_cast< float >( width ) / 
00183                               static_cast< float >( srcPVP.w );
00184         const float factorH = static_cast< float >( height ) / 
00185                               static_cast< float >( srcPVP.h );
00186             
00187         const Zoom newZoom( factorW, factorH );
00188             
00189         outputFrame->setZoom( newZoom );
00190     }
00191 }
00192 
00193 std::ostream& operator << ( std::ostream& os, const MonitorEqualizer* equalizer)
00194 {
00195     if( equalizer )
00196         os << "monitor_equalizer {}" << std::endl;
00197     return os;
00198 }
00199 
00200 }
00201 }
Generated on Mon Aug 10 18:58:40 2009 for Equalizer 0.9 by  doxygen 1.5.8