loader.cpp
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #include "loader.h"
00019
00020 #include "canvas.h"
00021 #include "compound.h"
00022 #include "config.h"
00023 #include "layout.h"
00024 #include "observer.h"
00025 #include "segment.h"
00026 #include "serverVisitor.h"
00027 #include "view.h"
00028
00029 using namespace std;
00030
00031 namespace eq
00032 {
00033 namespace server
00034 {
00035
00036 namespace
00037 {
00038 class UnusedOutputChannelFinder : public ConfigVisitor
00039 {
00040 public:
00041 UnusedOutputChannelFinder() : _candidate( 0 ) {}
00042
00043 virtual VisitorResult visit( Channel* channel )
00044 {
00045 if( _candidate )
00046 return TRAVERSE_CONTINUE;
00047
00048 const View* view = channel->getView();
00049 if( !view )
00050 return TRAVERSE_CONTINUE;
00051
00052
00053 _candidate = channel;
00054 Config* config = channel->getConfig();
00055 config->accept( *this );
00056
00057 if( _candidate )
00058 _channels.push_back( _candidate );
00059 _candidate = 0;
00060
00061 return TRAVERSE_CONTINUE;
00062 };
00063
00064 virtual VisitorResult visit( Compound* compound )
00065 {
00066 if( !_candidate )
00067 return TRAVERSE_PRUNE;
00068
00069 const Channel* channel = compound->getChannel();
00070 if( !channel )
00071 return TRAVERSE_CONTINUE;
00072
00073 if( _candidate == channel )
00074 {
00075 _candidate = 0;
00076 return TRAVERSE_TERMINATE;
00077 }
00078 return TRAVERSE_PRUNE;
00079 }
00080
00081 const ChannelVector& getResult() const { return _channels; }
00082
00083 private:
00084 Channel* _candidate;
00085 ChannelVector _channels;
00086 };
00087
00088 }
00089
00090 void Loader::addOutputCompounds( ServerPtr server )
00091 {
00092 const ConfigVector& configs = server->getConfigs();
00093 for( ConfigVector::const_iterator i = configs.begin();
00094 i != configs.end(); ++i )
00095 {
00096 UnusedOutputChannelFinder finder;
00097 Config* config = *i;
00098 config->accept( finder );
00099
00100 const ChannelVector& channels = finder.getResult();
00101 if( channels.empty( ))
00102 continue;
00103
00104 Compound* group = new Compound;
00105 config->addCompound( group );
00106
00107 for( ChannelVector::const_iterator j = channels.begin();
00108 j != channels.end(); ++j )
00109 {
00110 Compound* compound = new Compound;
00111 group->addChild( compound );
00112
00113 Channel* channel = *j;
00114 compound->setChannel( channel );
00115 }
00116 }
00117 }
00118
00119 namespace
00120 {
00121 static void _addDestinationViews( Compound* compound )
00122 {
00123 Channel* channel = compound->getChannel();
00124
00125 if( channel )
00126 {
00127 if( channel->getView( ))
00128 return;
00129
00130 Layout* layout = new Layout;
00131 View* view = new View;
00132 *static_cast< eq::Frustum* >( view ) = compound->getFrustum();
00133 layout->addView( view );
00134
00135 Canvas* canvas = new Canvas;
00136 canvas->addLayout( layout );
00137
00138 Segment* segment = new Segment;
00139 segment->setChannel( channel );
00140 canvas->addSegment( segment );
00141
00142 Config* config = compound->getConfig();
00143 config->addLayout( layout );
00144 config->addCanvas( canvas );
00145
00146 Channel* newChannel = config->findChannel( segment, view );
00147 EQASSERT( newChannel );
00148
00149 compound->setChannel( newChannel );
00150 compound->setViewport( Viewport::FULL );
00151
00152 return;
00153 }
00154
00155
00156 CompoundVector segments;
00157 const CompoundVector& children = compound->getChildren();
00158 for( CompoundVector::const_iterator i = children.begin();
00159 i != children.end(); ++i )
00160 {
00161 Compound* child = *i;
00162 Channel* childChannel = child->getChannel();
00163 if( childChannel )
00164 {
00165 if( !childChannel->getView( ))
00166 segments.push_back( child );
00167 }
00168 else
00169 _addDestinationViews( child );
00170 }
00171
00172 if( segments.empty( ))
00173 return;
00174
00175 Layout* layout = new Layout;
00176 View* view = new View;
00177 layout->addView( view );
00178
00179 Canvas* canvas = new Canvas;
00180 canvas->addLayout( layout );
00181 *static_cast< eq::Frustum* >( canvas ) = compound->getFrustum();
00182
00183 for( CompoundVector::const_iterator i = segments.begin();
00184 i != segments.end(); ++i )
00185 {
00186 Compound* child = *i;
00187 Segment* segment = new Segment;
00188
00189 segment->setChannel( child->getChannel( ));
00190 segment->setViewport( child->getViewport( ));
00191 *static_cast< eq::Frustum* >( segment ) = child->getFrustum();
00192
00193 canvas->addSegment( segment );
00194 }
00195
00196 Config* config = compound->getConfig();
00197 config->addLayout( layout );
00198 config->addCanvas( canvas );
00199
00200 for( size_t i = 0; i < segments.size(); ++i )
00201 {
00202 Segment* segment = canvas->getSegments()[ i ];
00203 Channel* newChannel = config->findChannel( segment, view );
00204 EQASSERT( newChannel );
00205
00206 segments[i]->setChannel( newChannel );
00207 segments[i]->setViewport( Viewport::FULL );
00208 }
00209 }
00210
00211 class AddDestinationViewVisitor : public ServerVisitor
00212 {
00213 virtual VisitorResult visitPre( Config* config )
00214 {
00215 if( config->getCanvases().empty( ))
00216 return TRAVERSE_CONTINUE;
00217
00218 return TRAVERSE_PRUNE;
00219 }
00220
00221 virtual VisitorResult visit( Compound* compound )
00222 {
00223 _addDestinationViews( compound );
00224 return TRAVERSE_PRUNE;
00225 }
00226 };
00227
00228 }
00229
00230 void Loader::addDestinationViews( ServerPtr server )
00231 {
00232 AddDestinationViewVisitor visitor;
00233 server->accept( visitor );
00234 }
00235
00236 namespace
00237 {
00238 class AddObserverVisitor : public ServerVisitor
00239 {
00240 virtual VisitorResult visitPre( Config* config )
00241 {
00242 const ObserverVector& observers = config->getObservers();
00243 if( !observers.empty( ))
00244 return TRAVERSE_PRUNE;
00245
00246 config->addObserver( new Observer );
00247 return TRAVERSE_CONTINUE;
00248 }
00249
00250 virtual VisitorResult visit( View* view )
00251 {
00252 const ObserverVector& observers = view->getConfig()->getObservers();
00253 EQASSERT( observers.size() == 1 );
00254
00255 view->setObserver( observers.front( ));
00256 return TRAVERSE_CONTINUE;
00257 }
00258 };
00259
00260 }
00261
00262 void Loader::addDefaultObserver( ServerPtr server )
00263 {
00264 AddObserverVisitor visitor;
00265 server->accept( visitor );
00266 }
00267
00268 }
00269 }