lib/client/canvas.cpp

00001 
00002 /* Copyright (c) 2009-2010, 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 "canvas.h"
00019 
00020 #include "canvasVisitor.h"
00021 #include "config.h"
00022 #include "global.h"
00023 #include "layout.h"
00024 #include "nodeFactory.h"
00025 #include "segment.h"
00026 
00027 #include <eq/net/dataIStream.h>
00028 #include <eq/net/dataOStream.h>
00029 
00030 namespace eq
00031 {
00032 
00033 Canvas::Canvas()
00034         : _config( 0 )
00035         , _activeLayout( 0 )
00036 {
00037 }
00038 
00039 Canvas::~Canvas()
00040 {
00041     EQASSERT( !_config );
00042 }
00043 
00044 void Canvas::serialize( net::DataOStream& os, const uint64_t dirtyBits )
00045 {
00046     Frustum::serialize( os, dirtyBits );
00047 
00048     if( dirtyBits & DIRTY_LAYOUT )
00049         os << _activeLayout;
00050 
00051     EQASSERT( !(dirtyBits & DIRTY_CHILDREN ));
00052 }
00053 
00054 void Canvas::deserialize( net::DataIStream& is, const uint64_t dirtyBits )
00055 {
00056     Frustum::deserialize( is, dirtyBits );
00057 
00058     if( dirtyBits & DIRTY_LAYOUT )
00059         is >> _activeLayout;
00060 
00061     if( dirtyBits & DIRTY_CHILDREN )
00062     {
00063         EQASSERT( _segments.empty( ));
00064         EQASSERT( _config );
00065 
00066         NodeFactory* nodeFactory = Global::getNodeFactory();
00067         uint32_t id;
00068         for( is >> id; id != EQ_ID_INVALID; is >> id )
00069         {
00070             Segment* segment = nodeFactory->createSegment();
00071             segment->_canvas = this;
00072             _segments.push_back( segment );
00073 
00074             _config->mapObject( segment, id );
00075             // RO, don't: segment->becomeMaster();
00076         }
00077         for( is >> id; id != EQ_ID_INVALID; is >> id )
00078         {
00079             EQASSERT( _config );
00080             if( id == EQ_ID_NONE )
00081                 _layouts.push_back( 0 );
00082             else
00083             {
00084                 Layout* layout = _config->findLayout( id );
00085                 _layouts.push_back( layout );
00086                 EQASSERT( layout );
00087             }
00088         }
00089     }
00090 }
00091 
00092 void Canvas::_deregister()
00093 {
00094     EQASSERT( _config );
00095     EQASSERT( isMaster( ));
00096     NodeFactory* nodeFactory = Global::getNodeFactory();
00097 
00098     for( SegmentVector::const_iterator i = _segments.begin(); 
00099          i != _segments.end(); ++i )
00100     {
00101         Segment* segment = *i;
00102         EQASSERT( segment->getID() != EQ_ID_INVALID );
00103         EQASSERT( !segment->isMaster( ));
00104 
00105         _config->unmapObject( segment );
00106         segment->_canvas = 0;
00107         nodeFactory->releaseSegment( segment );
00108     }
00109     
00110     _segments.clear();
00111     _config->deregisterObject( this );
00112 }
00113 
00114 const Layout* Canvas::getActiveLayout() const
00115 {
00116     EQASSERT( _activeLayout < _layouts.size( ));
00117     return _layouts[ _activeLayout ];
00118 }
00119 
00120 void Canvas::useLayout( const uint32_t index )
00121 {
00122     if( _activeLayout == index )
00123         return;
00124 
00125     _activeLayout = index;
00126     setDirty( DIRTY_LAYOUT );
00127 }
00128 
00129 namespace
00130 {
00131 template< class C >
00132 VisitorResult _accept( C* canvas, CanvasVisitor& visitor )
00133 {
00134     VisitorResult result = visitor.visitPre( canvas );
00135     if( result != TRAVERSE_CONTINUE )
00136         return result;
00137 
00138     const SegmentVector& segments = canvas->getSegments();
00139     for( SegmentVector::const_iterator i = segments.begin(); 
00140          i != segments.end(); ++i )
00141     {
00142         switch( (*i)->accept( visitor ))
00143         {
00144             case TRAVERSE_TERMINATE:
00145                 return TRAVERSE_TERMINATE;
00146 
00147             case TRAVERSE_PRUNE:
00148                 result = TRAVERSE_PRUNE;
00149                 break;
00150                 
00151             case TRAVERSE_CONTINUE:
00152             default:
00153                 break;
00154         }
00155     }
00156 
00157     switch( visitor.visitPost( canvas ))
00158     {
00159         case TRAVERSE_TERMINATE:
00160             return TRAVERSE_TERMINATE;
00161 
00162         case TRAVERSE_PRUNE:
00163             return TRAVERSE_PRUNE;
00164                 
00165         case TRAVERSE_CONTINUE:
00166         default:
00167             break;
00168     }
00169 
00170     return result;
00171 }
00172 }
00173 
00174 VisitorResult Canvas::accept( CanvasVisitor& visitor )
00175 {
00176     return _accept( this, visitor );
00177 }
00178 
00179 VisitorResult Canvas::accept( CanvasVisitor& visitor ) const
00180 {
00181     return _accept( this, visitor );
00182 }
00183 
00184 }
Generated on Sat Feb 6 12:59:42 2010 for Equalizer 0.9.1 by  doxygen 1.6.1