CLAM-Development
1.1
|
00001 /* 00002 * Copyright (c) 2001-2007 MUSIC TECHNOLOGY GROUP (MTG) 00003 * UNIVERSITAT POMPEU FABRA 00004 * 00005 * 00006 * This program is free software; you can redistribute it and/or modify 00007 * it under the terms of the GNU General Public License as published by 00008 * the Free Software Foundation; either version 2 of the License, or 00009 * (at your option) any later version. 00010 * 00011 * This program is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 * GNU General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU General Public License 00017 * along with this program; if not, write to the Free Software 00018 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00019 * 00020 */ 00021 00022 00023 #include "FlattenedNetwork.hxx" 00024 #include "NaiveFlowControl.hxx" 00025 #include "NetworkPlayer.hxx" 00026 #include <algorithm> 00027 #include "ProcessingDefinitionAdapter.hxx" 00028 #include "ConnectionDefinitionAdapter.hxx" 00029 #include "ProcessingFactory.hxx" 00030 #include "XmlStorageErr.hxx" 00031 #ifdef USE_LADSPA //TODO alway include it. move conditional code in LFactory.hxx 00032 # include "ProcessingFactory.hxx" 00033 #endif 00034 00035 namespace CLAM 00036 { 00037 FlattenedNetwork::FlattenedNetwork() : 00038 _name("Unnamed Network"), 00039 _flowControl(new NaiveFlowControl), 00040 _player(0), 00041 _setPasteMode(false) 00042 {} 00043 00044 FlattenedNetwork::~FlattenedNetwork() 00045 { 00046 //std::cerr <<" *\t\t\t~NETWORK"<<std::endl; 00047 Clear(); 00048 if (_flowControl) delete _flowControl; 00049 if (_player) delete _player; 00050 } 00051 00052 void FlattenedNetwork::StoreOn( Storage & storage) const 00053 { 00054 XMLAdapter<std::string> strAdapter( _name, "id"); 00055 storage.Store(strAdapter); 00056 00057 ProcessingsMap::const_iterator it; 00058 for(it=BeginProcessings();it!=EndProcessings();it++) 00059 { 00060 Processing * proc = it->second; 00061 const std::string & name = it->first; 00062 if (!HasSelectionAndContains(name)) 00063 continue; 00064 std::string processingPosition; 00065 std::string processingSize; 00066 // if exists canvas geometries, store them 00067 if (!_processingsGeometries.empty()) 00068 { 00069 Geometry & geometry=_processingsGeometries.find(name)->second; 00070 processingPosition=IntsToString (geometry.x, geometry.y); 00071 processingSize=IntsToString (geometry.width, geometry.height); 00072 } 00073 ProcessingDefinitionAdapter procDefinition(proc, name, processingPosition, processingSize); 00074 XMLComponentAdapter xmlAdapter(procDefinition, "processing", true); 00075 storage.Store(xmlAdapter); 00076 } 00077 00078 // second iteration to store ports. 00079 // XR: maybe it should be all in one iteration but this way 00080 // the xml file is clearer. 00081 00082 for(it=BeginProcessings();it!=EndProcessings();it++) 00083 { 00084 const std::string & name = it->first; 00085 Processing * proc = it->second; 00086 00087 if (!HasSelectionAndContains(name)) 00088 continue; 00089 00090 OutPortRegistry::Iterator itOutPort; 00091 for (itOutPort=proc->GetOutPorts().Begin(); 00092 itOutPort!=proc->GetOutPorts().End(); 00093 itOutPort++) 00094 { 00095 if (!(*itOutPort)->HasConnections()) 00096 continue; 00097 00098 std::string outPortName = name + "." + (*itOutPort)->GetName(); 00099 NamesList namesInPorts = GetInPortsConnectedTo(outPortName); 00100 NamesList::iterator namesIterator; 00101 for(namesIterator=namesInPorts.begin(); 00102 namesIterator!=namesInPorts.end(); 00103 namesIterator++) 00104 { 00105 if (!HasSelectionAndContains(GetProcessingIdentifier(*namesIterator))) 00106 continue; 00107 ConnectionDefinitionAdapter connectionDefinition( outPortName, *namesIterator ); 00108 XMLComponentAdapter xmlAdapter(connectionDefinition, "port_connection", true); 00109 storage.Store(xmlAdapter); 00110 } 00111 } 00112 } 00113 00114 for(it=BeginProcessings();it!=EndProcessings();it++) 00115 { 00116 const std::string & name = it->first; 00117 Processing * proc = it->second; 00118 00119 if (!HasSelectionAndContains(name)) 00120 continue; 00121 00122 OutControlRegistry::Iterator itOutControl; 00123 for (itOutControl=proc->GetOutControls().Begin(); 00124 itOutControl!=proc->GetOutControls().End(); 00125 itOutControl++) 00126 { 00127 std::string outControlName = name+ "." + (*itOutControl)->GetName(); 00128 NamesList namesInControls = GetInControlsConnectedTo(outControlName); 00129 NamesList::iterator namesIterator; 00130 for(namesIterator=namesInControls.begin(); 00131 namesIterator!=namesInControls.end(); 00132 namesIterator++) 00133 { 00134 if (!HasSelectionAndContains(GetProcessingIdentifier(*namesIterator))) 00135 continue; 00136 ConnectionDefinitionAdapter connectionDefinition( outControlName, *namesIterator ); 00137 XMLComponentAdapter xmlAdapter(connectionDefinition, "control_connection", true); 00138 storage.Store(xmlAdapter); 00139 } 00140 } 00141 } 00142 _selectedProcessings.clear(); 00143 _processingsGeometries.clear(); 00144 } 00145 00146 void FlattenedNetwork::LoadFrom( Storage & storage) 00147 { 00148 typedef std::map <std::string, std::string> changeProcNames; 00149 changeProcNames newProcNames; 00150 if (!_setPasteMode) Clear(); 00151 XMLAdapter<std::string> strAdapter( _name, "id"); 00152 storage.Load(strAdapter); 00153 _processingsGeometries.clear(); 00154 00155 while(1) 00156 { 00157 ProcessingDefinitionAdapter procDefinition; 00158 XMLComponentAdapter xmlAdapter(procDefinition, "processing", true); 00159 if(storage.Load(xmlAdapter) == false) break; 00160 std::string name=procDefinition.GetName(); 00161 00162 if (!_setPasteMode) 00163 AddProcessing(name, procDefinition.GetProcessing()); 00164 else 00165 { 00166 CLAM::Processing * processing =procDefinition.GetProcessing(); 00167 std::string key=processing->GetClassName(); 00168 std::string newName= AddProcessing(key); 00169 CLAM::Processing & newProcessing = GetProcessing(newName); 00170 newProcessing.Configure(processing->GetConfig()); 00171 newProcNames.insert(changeProcNames::value_type(name,newName)); 00172 name=newName; 00173 } 00174 // if exists canvas geometries, restore them 00175 if (procDefinition.GetPosition()!="" && procDefinition.GetSize()!="") 00176 { 00177 Geometry processingGeometry; 00178 StringPairToInts(procDefinition.GetPosition(),processingGeometry.x,processingGeometry.y); 00179 StringPairToInts(procDefinition.GetSize(),processingGeometry.width,processingGeometry.height); 00180 _processingsGeometries.insert(ProcessingsGeometriesMap::value_type(name,processingGeometry)); 00181 } 00182 } 00183 00184 while(1) 00185 { 00186 ConnectionDefinitionAdapter connectionDefinition; 00187 XMLComponentAdapter xmlAdapter(connectionDefinition, "port_connection", true); 00188 if (!storage.Load(xmlAdapter)) break; 00189 const std::string & fullOut = connectionDefinition.GetOutName(); 00190 const std::string & fullIn = connectionDefinition.GetInName(); 00191 try 00192 { 00193 if (!_setPasteMode) 00194 ConnectPorts( fullOut, fullIn ); 00195 else 00196 { 00197 const std::string newNameOut = newProcNames.find(GetProcessingIdentifier(fullOut))->second 00198 +"."+GetConnectorIdentifier(fullOut); 00199 const std::string newNameIn = newProcNames.find(GetProcessingIdentifier(fullIn))->second 00200 +"."+GetConnectorIdentifier(fullIn); 00201 ConnectPorts( newNameOut, newNameIn ); 00202 } 00203 00204 } 00205 catch (Err & e) { throw XmlStorageErr(e.what()); } 00206 } 00207 00208 while(1) 00209 { 00210 ConnectionDefinitionAdapter connectionDefinition; 00211 XMLComponentAdapter xmlAdapter(connectionDefinition, "control_connection", true); 00212 if (!storage.Load(xmlAdapter)) break; 00213 const std::string & fullOut = connectionDefinition.GetOutName(); 00214 const std::string & fullIn = connectionDefinition.GetInName(); 00215 try 00216 { 00217 if (!_setPasteMode) 00218 ConnectControls( fullOut, fullIn ); 00219 else 00220 { 00221 const std::string newNameOut = newProcNames.find(GetProcessingIdentifier(fullOut))->second 00222 +"."+GetConnectorIdentifier(fullOut); 00223 const std::string newNameIn = newProcNames.find(GetProcessingIdentifier(fullIn))->second 00224 +"."+GetConnectorIdentifier(fullIn); 00225 ConnectControls( newNameOut, newNameIn ); 00226 } 00227 } 00228 catch (Err & e) { throw XmlStorageErr(e.what()); } 00229 } 00230 _setPasteMode=false; 00231 } 00232 00233 bool FlattenedNetwork::UpdateSelections (const NamesList & processingsNamesList) 00234 { 00235 NamesList::const_iterator namesIterator; 00236 if (!_selectedProcessings.empty() || processingsNamesList.empty()) 00237 { 00238 _selectedProcessings.clear(); 00239 return true; 00240 } 00241 for (namesIterator=processingsNamesList.begin();namesIterator!=processingsNamesList.end();namesIterator++) 00242 _selectedProcessings.insert(*namesIterator); 00243 return false; 00244 } 00245 00246 bool FlattenedNetwork::HasSelectionAndContains(const std::string & name) const 00247 { 00248 NamesSet::const_iterator itFindSelected = _selectedProcessings.find(name); 00249 if (!_selectedProcessings.empty() && itFindSelected==_selectedProcessings.end()) 00250 return false; 00251 return true; 00252 } 00253 00254 bool FlattenedNetwork::SetProcessingsGeometries (const ProcessingsGeometriesMap & processingsGeometries) 00255 { 00256 _processingsGeometries.clear(); 00257 if (processingsGeometries.empty()) 00258 return true; 00259 _processingsGeometries=processingsGeometries; 00260 return false; 00261 } 00262 00263 00264 const FlattenedNetwork::ProcessingsGeometriesMap FlattenedNetwork::GetAndClearGeometries() 00265 { 00266 const ProcessingsGeometriesMap copyProcessingsGeometry(_processingsGeometries); 00267 _processingsGeometries.clear(); 00268 return copyProcessingsGeometry; 00269 } 00270 00271 /* // TODO: use individual geometries loadings/storings??: 00272 const FlattenedNetwork::Geometry FlattenedNetwork::GetAndEraseGeometry(std::string name) 00273 { 00274 const ProcessingsGeometriesMap::iterator itGeometry =_processingsGeometries.find(name); 00275 Geometry geometry=itGeometry->second; 00276 if (itGeometry == _processingsGeometries.end()) 00277 { 00278 geometry.width=0; 00279 geometry.height=0; 00280 return geometry; 00281 } 00282 _processingsGeometries.erase(name); // if exists, erase geometry from map 00283 return geometry; 00284 }*/ 00285 00286 void FlattenedNetwork::StringPairToInts(const std::string & geometryInString, int & a, int & b) 00287 { 00288 a=atoi(geometryInString.substr(0,geometryInString.find(",")).c_str()); 00289 b=atoi(geometryInString.substr(geometryInString.find(",")+1,geometryInString.length()).c_str()); 00290 } 00291 00292 const std::string FlattenedNetwork::IntsToString (const int & a, const int & b) const 00293 { 00294 std::ostringstream stream; 00295 stream<<a<<","<<b; 00296 return stream.str(); 00297 } 00298 00299 // flow and player related methods 00300 void FlattenedNetwork::AddFlowControl(FlowControl* flowControl) 00301 { 00302 if (_flowControl) delete _flowControl; 00303 _flowControl = flowControl; 00304 _flowControl->AttachToNetwork((CLAM::Network*)this); 00305 } 00306 void FlattenedNetwork::SetPlayer(NetworkPlayer* player) 00307 { 00308 if (_player) delete _player; 00309 _player = player; 00310 _player->SetNetworkBackLink(*(CLAM::Network*)this); 00311 _player->Init(); 00312 } 00313 unsigned FlattenedNetwork::BackendBufferSize() 00314 { 00315 if (!_player) return 512; 00316 return _player->BackendBufferSize(); 00317 } 00318 unsigned FlattenedNetwork::BackendSampleRate() 00319 { 00320 if (!_player) return 44100; 00321 return _player->BackendSampleRate(); 00322 } 00323 00324 00325 Processing& FlattenedNetwork::GetProcessing( const std::string & name ) const 00326 { 00327 CLAM_ASSERT( HasProcessing(name), 00328 ("No processing in the network has the name '"+name+"'.").c_str()); 00329 00330 ProcessingsMap::const_iterator it = _processings.find( name ); 00331 return *it->second; 00332 } 00333 00334 void FlattenedNetwork::AddProcessing( const std::string & name, Processing* proc) 00335 { 00336 if (!IsStopped()) Stop(); 00337 00338 if (!_processings.insert( ProcessingsMap::value_type( name, proc ) ).second ) 00339 CLAM_ASSERT(false, "FlattenedNetwork::AddProcessing() Trying to add a processing with a repeated name (key)" ); 00340 proc->SetNetworkBackLink((CLAM::Network*)this); 00341 proc->Configure(proc->GetConfig()); //TODO inefficient. but solves the problem 00342 // of some processings needing the network for configuring its ports. 00343 _flowControl->ProcessingAddedToNetwork(*proc); 00344 } 00345 00346 void FlattenedNetwork::AddProcessing( const std::string & name, const std::string & factoryKey ) 00347 { 00348 Processing * proc=0; 00349 proc = ProcessingFactory::GetInstance().CreateSafe( factoryKey ); 00350 AddProcessing(name, proc); 00351 } 00352 00353 // returns the name that was used so the same one can be used when calling CreateProcessingController (hack) 00354 std::string FlattenedNetwork::AddProcessing( const std::string & factoryKey ) 00355 { 00356 std::string name = GetUnusedName( factoryKey ); 00357 AddProcessing(name, factoryKey ); 00358 return name; 00359 } 00360 00361 std::string FlattenedNetwork::GetUnusedName( const std::string& prefix ) const 00362 { 00363 std::string name; 00364 00365 for ( int i = 0; i<9999999; i++ ) 00366 { 00367 std::stringstream tmp; 00368 tmp << i; 00369 name = i? prefix + "_" + tmp.str() : prefix; 00370 if (!this->HasProcessing( name ) ) return name; 00371 } 00372 CLAM_ASSERT(false, "All valid id's for given prefix are exhausted"); 00373 return ""; 00374 } 00375 00376 void FlattenedNetwork::RemoveProcessing ( const std::string & name) 00377 { 00378 CLAM_ASSERT( _flowControl, 00379 "FlattenedNetwork::RemoveProcessing() - Network should have an attached flow control at this state."); 00380 00381 ProcessingsMap::const_iterator i = _processings.find( name ); 00382 if(i==_processings.end()) 00383 { 00384 std::string msg("FlattenedNetwork::RemoveProcessing() Trying to remove a processing that is not included in the network:"); 00385 msg += name; 00386 CLAM_ASSERT(false, msg.c_str() ); 00387 } 00388 if ( !IsStopped() ) Stop(); 00389 Processing * proc = i->second; 00390 _processings.erase( name ); 00391 00392 _flowControl->ProcessingRemovedFromNetwork(*proc); 00393 delete proc; 00394 } 00395 00396 bool FlattenedNetwork::HasProcessing( const std::string& name ) const 00397 { 00398 ProcessingsMap::const_iterator i = _processings.find( name ); 00399 return i!=_processings.end(); 00400 } 00401 00402 bool FlattenedNetwork::ConfigureProcessing( const std::string & name, const ProcessingConfig & newConfig ) 00403 { 00404 ProcessingsMap::iterator it = _processings.find( name ); 00405 CLAM_ASSERT(it!=_processings.end(),"Wrong processing name to configure in a network"); 00406 Processing * proc = it->second; 00407 if ( !IsStopped() ) Stop(); 00408 bool ok = proc->Configure( newConfig ); 00409 _flowControl->ProcessingConfigured(*proc); 00410 return ok; 00411 } 00412 00413 void FlattenedNetwork::ReconfigureAllProcessings() 00414 { 00415 ProcessingsMap::iterator it; 00416 for( it=_processings.begin(); it!=_processings.end(); it++) 00417 { 00418 Processing* proc = it->second; 00419 proc->Configure( proc->GetConfig() ); 00420 } 00421 } 00422 00423 bool FlattenedNetwork::ConnectPorts( const std::string & producer, const std::string & consumer ) 00424 { 00425 _flowControl->NetworkTopologyChanged(); 00426 00427 OutPortBase & outport = GetOutPortByCompleteName(producer); 00428 InPortBase & inport = GetInPortByCompleteName(consumer); 00429 00430 if ( outport.IsVisuallyConnectedTo(inport) ) 00431 return false; 00432 00433 if ( !outport.IsConnectableTo(inport) ) //they have different type 00434 return false; 00435 00436 if( inport.GetVisuallyConnectedOutPort()) 00437 return false; 00438 00439 if (!IsStopped()) Stop(); 00440 00441 outport.ConnectToIn( inport ); 00442 return true; 00443 } 00444 00445 bool FlattenedNetwork::ConnectControls( const std::string & producer, const std::string & consumer ) 00446 { 00447 OutControl & outcontrol = GetOutControlByCompleteName(producer); 00448 InControl & incontrol = GetInControlByCompleteName(consumer); 00449 00450 if ( outcontrol.IsConnectedTo(incontrol) ) 00451 return false; 00452 00453 if (!IsStopped()) Stop(); 00454 00455 outcontrol.AddLink( incontrol ); 00456 return true; 00457 } 00458 00459 00460 bool FlattenedNetwork::DisconnectPorts( const std::string & producer, const std::string & consumer) 00461 { 00462 _flowControl->NetworkTopologyChanged(); 00463 00464 OutPortBase & outport = GetOutPortByCompleteName(producer); 00465 InPortBase & inport = GetInPortByCompleteName(consumer); 00466 00467 if ( !outport.IsVisuallyConnectedTo(inport)) 00468 return false; 00469 00470 if (!IsStopped()) Stop(); 00471 00472 outport.DisconnectFromIn( inport ); 00473 return true; 00474 } 00475 00476 bool FlattenedNetwork::DisconnectControls( const std::string & producer, const std::string & consumer) 00477 { 00478 OutControl & outcontrol = GetOutControlByCompleteName(producer); 00479 InControl & incontrol = GetInControlByCompleteName(consumer); 00480 00481 if ( !outcontrol.IsConnectedTo( incontrol )) 00482 return false; 00483 00484 if (!IsStopped()) Stop(); 00485 00486 outcontrol.RemoveLink( incontrol ); 00487 return true; 00488 } 00489 00490 std::string FlattenedNetwork::GetConnectorIdentifier( const std::string& str ) const 00491 { 00492 return str.substr( PositionOfLastIdentifier(str)+1 ); 00493 } 00494 00495 std::string FlattenedNetwork::GetProcessingIdentifier( const std::string& str ) const 00496 { 00497 std::size_t length = PositionOfLastIdentifier(str) - PositionOfProcessingIdentifier(str); 00498 return str.substr( PositionOfProcessingIdentifier(str), length); 00499 } 00500 00501 InPortBase & FlattenedNetwork::GetInPortByCompleteName( const std::string & name ) const 00502 { 00503 Processing& proc = GetProcessing( GetProcessingIdentifier(name) ); 00504 return proc.GetInPorts().Get( GetConnectorIdentifier(name) ); 00505 } 00506 00507 OutPortBase & FlattenedNetwork::GetOutPortByCompleteName( const std::string & name ) const 00508 { 00509 Processing& proc = GetProcessing( GetProcessingIdentifier(name) ); 00510 return proc.GetOutPorts().Get( GetConnectorIdentifier(name) ); 00511 } 00512 00513 InControl & FlattenedNetwork::GetInControlByCompleteName( const std::string & name ) const 00514 { 00515 Processing& proc = GetProcessing( GetProcessingIdentifier(name) ); 00516 return proc.GetInControls().Get( GetConnectorIdentifier(name) ); 00517 } 00518 00519 OutControl & FlattenedNetwork::GetOutControlByCompleteName( const std::string & name ) const 00520 { 00521 Processing& proc = GetProcessing( GetProcessingIdentifier(name) ); 00522 return proc.GetOutControls().Get( GetConnectorIdentifier(name) ); 00523 } 00524 00525 bool FlattenedNetwork::IsStopped() const 00526 { 00527 if (! _player) return true; 00528 return _player->IsStopped(); 00529 } 00530 00531 void FlattenedNetwork::Start() 00532 { 00533 ProcessingsMap::iterator it; 00534 for (it=BeginProcessings(); it!=EndProcessings(); it++) 00535 { 00536 if (it->second->IsRunning()) continue; 00537 if (it->second->IsConfigured()) 00538 { 00539 it->second->Start(); 00540 } 00541 else 00542 { 00543 std::cerr << "Warning: could not start processing for not being Configured: '" << it->first<< "' of class " << it->second->GetClassName() << std::endl; 00544 } 00545 } 00546 if (_player) _player->Start(); 00547 } 00548 00549 void FlattenedNetwork::Stop() 00550 { 00551 if (_player) _player->Stop(); 00552 ProcessingsMap::iterator it; 00553 for (it=BeginProcessings(); it!=EndProcessings(); it++) 00554 if (it->second->IsRunning()) 00555 it->second->Stop(); 00556 } 00557 00558 void FlattenedNetwork::Do() 00559 { 00560 _flowControl->Do(); 00561 } 00562 00563 void FlattenedNetwork::Clear() 00564 { 00565 if ( !IsStopped() ) Stop(); 00566 00567 while( !_processings.empty() ) 00568 { 00569 //std::cerr << "REMOVING <"<<_processings.begin()->first<<">"<<std::endl; 00570 RemoveProcessing( _processings.begin()->first ); 00571 } 00572 } 00573 00574 FlattenedNetwork::ProcessingsMap::iterator FlattenedNetwork::BeginProcessings() 00575 { 00576 return _processings.begin(); 00577 } 00578 00579 FlattenedNetwork::ProcessingsMap::iterator FlattenedNetwork::EndProcessings() 00580 { 00581 return _processings.end(); 00582 } 00583 FlattenedNetwork::ProcessingsMap::const_iterator FlattenedNetwork::BeginProcessings() const 00584 { 00585 return _processings.begin(); 00586 } 00587 00588 FlattenedNetwork::ProcessingsMap::const_iterator FlattenedNetwork::EndProcessings() const 00589 { 00590 return _processings.end(); 00591 } 00592 00593 FlattenedNetwork::NamesList FlattenedNetwork::GetInPortsConnectedTo( const std::string & producer ) const 00594 { 00595 OutPortBase & out = GetOutPortByCompleteName( producer ); 00596 NamesList consumers; 00597 00598 if(!out.HasConnections()) 00599 return consumers; 00600 00601 OutPortBase::InPortsList::iterator it; 00602 for(it=out.BeginVisuallyConnectedInPorts(); it!=out.EndVisuallyConnectedInPorts(); it++) 00603 { 00604 std::string completeName(GetNetworkId((*it)->GetProcessing())); 00605 completeName += "."; 00606 completeName += (*it)->GetName(); 00607 consumers.push_back(completeName); 00608 } 00609 return consumers; 00610 } 00611 00612 FlattenedNetwork::NamesList FlattenedNetwork::GetInControlsConnectedTo( const std::string & producer ) const 00613 { 00614 OutControl & out = GetOutControlByCompleteName( producer ); 00615 NamesList consumers; 00616 00617 std::list<InControl*>::iterator it; 00618 for(it=out.BeginInControlsConnected(); 00619 it!=out.EndInControlsConnected(); 00620 it++) 00621 { 00622 std::string completeName(GetNetworkId((*it)->GetProcessing())); 00623 completeName += "."; 00624 completeName += (*it)->GetName(); 00625 consumers.push_back(completeName); 00626 } 00627 return consumers; 00628 } 00629 00630 FlattenedNetwork::InPortsList FlattenedNetwork::GetInPortsConnectedTo( OutPortBase & producer ) const 00631 { 00632 InPortsList consumers; 00633 OutPortBase::InPortsList::iterator it; 00634 for(it=producer.BeginVisuallyConnectedInPorts(); it!=producer.EndVisuallyConnectedInPorts(); it++) 00635 consumers.push_back(*it); 00636 return consumers; 00637 } 00638 00639 const std::string & FlattenedNetwork::GetNetworkId(const Processing * proc) const 00640 { 00641 ProcessingsMap::const_iterator it; 00642 for(it=BeginProcessings(); it!=EndProcessings(); it++) 00643 if(it->second == proc ) 00644 return it->first; 00645 00646 CLAM_ASSERT(false, "Trying to get a network id from a processing not present in it"); 00647 throw 0; // To avoid warning message 00648 } 00649 00650 bool FlattenedNetwork::RenameProcessing( const std::string & oldName, const std::string & newName ) 00651 { 00652 if (oldName==newName) return true; 00653 if( _processings.find( newName ) != _processings.end() ) // newName is being used 00654 return false; 00655 ProcessingsMap::iterator it = _processings.find( oldName ); 00656 Processing * proc = it->second; 00657 _processings.erase( it ); 00658 _processings.insert( ProcessingsMap::value_type( newName, proc ) ); 00659 return true; 00660 } 00661 00662 bool FlattenedNetwork::IsReady() const 00663 { 00664 if (IsEmpty()) return false; 00665 if (HasMisconfiguredProcessings()) return false; 00666 if (HasUnconnectedInPorts()) return false; 00667 return true; 00668 } 00669 00670 bool FlattenedNetwork::IsEmpty() const 00671 { 00672 return _processings.empty(); 00673 } 00674 00675 bool FlattenedNetwork::HasMisconfiguredProcessings() const 00676 { 00677 ProcessingsMap::const_iterator it; 00678 for(it=BeginProcessings(); it!=EndProcessings(); it++) 00679 if(!it->second->IsConfigured()) 00680 return true; 00681 return false; 00682 } 00683 00684 bool FlattenedNetwork::HasUnconnectedInPorts() const 00685 { 00686 for (ProcessingsMap::const_iterator it=BeginProcessings(); it!=EndProcessings(); it++) 00687 { 00688 Processing * proc = it->second; 00689 InPortRegistry::Iterator itInPort; 00690 for (itInPort=proc->GetInPorts().Begin(); 00691 itInPort!=proc->GetInPorts().End(); 00692 itInPort++) 00693 { 00694 if (not (*itInPort)->GetVisuallyConnectedOutPort()) 00695 return true; 00696 } 00697 00698 } 00699 return false; 00700 } 00701 std::string FlattenedNetwork::GetUnconnectedInPorts() const 00702 { 00703 std::string result; 00704 for (ProcessingsMap::const_iterator it=BeginProcessings(); it!=EndProcessings(); it++) 00705 { 00706 Processing * proc = it->second; 00707 InPortRegistry::Iterator itInPort; 00708 for (itInPort=proc->GetInPorts().Begin(); 00709 itInPort!=proc->GetInPorts().End(); 00710 itInPort++) 00711 { 00712 if (not (*itInPort)->GetVisuallyConnectedOutPort()) 00713 result+= it->first+"."+(*itInPort)->GetName()+"\n"; 00714 } 00715 00716 } 00717 return result; 00718 } 00719 00720 bool FlattenedNetwork::HasSyncSource() const 00721 { 00722 ProcessingsMap::const_iterator it; 00723 for(it=BeginProcessings(); it!=EndProcessings(); it++) 00724 if(it->second->IsSyncSource()) 00725 return true; 00726 return false; 00727 } 00728 00729 // TODO: Test GetConfigurationErrors 00730 std::string FlattenedNetwork::GetConfigurationErrors() const 00731 { 00732 std::ostringstream errorMessage; 00733 ProcessingsMap::const_iterator it; 00734 for(it=BeginProcessings(); it!=EndProcessings(); it++) 00735 { 00736 if(it->second->IsConfigured()) continue; 00737 errorMessage << "* Processing '" << it->first << "' is misconfigured:\n"; 00738 errorMessage << it->second->GetConfigErrorMessage() << std::endl; 00739 } 00740 00741 return errorMessage.str(); 00742 } 00743 00744 } 00745