1 /*=========================================================================
4 Module: $RCSfile: bbtkComplexBlackBox.cxx,v $
6 Date: $Date: 2008/04/21 12:43:05 $
7 Version: $Revision: 1.12 $
9 Copyright (c) CREATIS (Centre de Recherche et d'Applications en Traitement de
10 l'Image). All rights reserved. See Doc/License.txt or
11 http://www.creatis.insa-lyon.fr/Public/bbtk/License.html for details.
13 This software is distributed WITHOUT ANY WARRANTY; without even
14 the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 PURPOSE. See the above copyright notices for more information.
17 =========================================================================*/
22 * \brief class bbtk::ComplexBlackBox : user defined complex black boxes
24 #include "bbtkComplexBlackBox.h"
25 #include "bbtkBlackBoxDescriptor.h"
26 #include "bbtkFactory.h"
27 #include "bbtkConfigurationFile.h"
32 //==========================================================================
33 /// Creates a new complex black box
34 ComplexBlackBox::Pointer ComplexBlackBox::New(const std::string& name,
35 ComplexBlackBoxDescriptor::Pointer desc)
37 bbtkDebugMessage("object",1,"##> ComplexBlackBox::New('"<<name<<"','"<<
38 desc->GetTypeName()<<"')" <<bbtkendl);
39 ComplexBlackBox::Pointer p =
40 MakeBlackBoxPointer(new ComplexBlackBox(name,desc));
41 bbtkDebugMessage("object",2,"<## ComplexBlackBox::New('"<<name<<"','"<<
42 desc->GetTypeName()<<"')" <<bbtkendl);
45 //==========================================================================
47 //=======================================================================
48 /// Usefull constructor
49 ComplexBlackBox::ComplexBlackBox(const std::string &name,
50 ComplexBlackBoxDescriptor::Pointer desc)
53 mLockedDescriptor(desc),
56 bbtkDebugMessage("object",3,
57 "##> ComplexBlackBox::ComplexBlackBox(\""
58 <<name<<"\")"<<std::endl);
59 bbAllocateConnectors();
60 bbtkDebugMessage("object",3,
61 "<## ComplexBlackBox::ComplexBlackBox(\""
62 <<name<<"\")"<<std::endl);
64 //=======================================================================
66 //=======================================================================
67 /// Constructor from an existing box (copy) with a new name
68 ComplexBlackBox::ComplexBlackBox(ComplexBlackBox& from,
69 const std::string &name)
70 : BlackBox(from,name),
71 // The locked descriptor is copied from the unlocked one
72 // to make the box a non-prototype !!
73 mLockedDescriptor(from.mDescriptor),
74 mDescriptor(from.mDescriptor),
75 mExecutionList(from.mExecutionList)
77 bbtkDebugMessage("object",3,
78 "##> ComplexBlackBox::ComplexBlackBox(\""
79 <<from.bbGetName()<<"\",\""
80 <<name<<"\")"<<std::endl);
81 bbtkDebugMessage("object",4," * Cloning Black Boxes"<<std::endl);
82 BlackBoxMapType::const_iterator i;
83 for ( i = from.mBlackBoxMap.begin(); i != from.mBlackBoxMap.end(); ++i )
85 bbtkDebugMessageInc("object",5," * Cloning \""<<i->first<<"\""<<std::endl);
86 BlackBox::Pointer B = i->second->bbClone(i->second->bbGetName());
87 bbUnsafeAddBlackBox(B);
91 bbtkDebugMessage("object",4," * Cloning Connections"<<std::endl);
92 ConnectionListType::const_iterator j;
93 for ( j = from.mConnectionList.begin(); j != from.mConnectionList.end(); ++j )
95 bbtkDebugMessage("object",5," * Cloning \""<<
96 (*j)->GetFullName()<<"\""<<std::endl);
98 BlackBox::Pointer bbfrom = bbGetBlackBox( (*j)->GetOriginalBlackBoxFrom()->bbGetName() );
99 BlackBox::Pointer bbto = bbGetBlackBox( (*j)->GetOriginalBlackBoxTo()->bbGetName() );
101 Connection::Pointer c = mDescriptor.lock()->GetFactory()->
102 NewConnection( bbfrom,
103 (*j)->GetOriginalBlackBoxFromOutput(),
105 (*j)->GetOriginalBlackBoxToInput() );
112 bbAllocateConnectors();
113 bbtkDebugMessage("object",3,
114 "<## ComplexBlackBox::ComplexBlackBox(\""
115 <<from.bbGetName()<<"\",\""
116 <<name<<"\")"<<std::endl);
118 //=======================================================================
120 //=======================================================================
122 ComplexBlackBox::~ComplexBlackBox()
124 bbtkDebugMessage("object",3,
125 "==> ComplexBlackBox::~ComplexBlackBox() ["
126 <<bbGetName()<<"]"<<std::endl);
128 bbtkDebugMessage("object",4,
129 " -> Releasing connections"<<std::endl);
130 mConnectionList.clear();
131 bbtkDebugMessage("object",4,
132 " -> Releasing boxes"<<std::endl);
133 mBlackBoxMap.clear();
137 this->bbDesallocateConnectors();
138 if (mLockedDescriptor)
140 bbtkMessage("object",3," --> Releasing descriptor"<<std::endl);
141 mLockedDescriptor.reset();
142 if (!mDescriptor.expired()) BlackBoxDescriptor::Release(mDescriptor);
145 bbtkDebugMessage("object",3,
146 "<== ComplexBlackBox::~ComplexBlackBox() ["
147 <<bbGetName()<<"]"<<std::endl);
149 //=======================================================================
152 //=========================================================================
153 /// Allocates the i/o connectors of the black box
154 void ComplexBlackBox::bbAllocateConnectors()
156 bbtkDebugMessageInc("Kernel",8,
157 "ComplexBlackBox::bbAllocateConnectors() ["
158 <<bbGetFullName()<<"]"
162 const BlackBoxDescriptor::InputDescriptorMapType& imap
163 = bbGetDescriptor()->GetInputDescriptorMap();
164 BlackBoxDescriptor::InputDescriptorMapType::const_iterator i;
165 for ( i = imap.begin(); i != imap.end(); ++i )
167 bbtkDebugMessage("Kernel",8,"* Allocate \""<<i->first<<"\""<<std::endl);
168 // Redirect the connector to the internal box connector
169 // Cast the BBInputDescriptor into a ComplexBBInputDescriptor
170 ComplexBlackBoxInputDescriptor* d =
171 (ComplexBlackBoxInputDescriptor*)i->second;
172 // Get the internal box connector
173 BlackBoxInputConnector* c =
174 bbUnsafeGetBlackBox ( d->GetTarget() )
175 ->bbGetInputConnectorMap()[ d->GetInput() ];
177 bbGetInputConnectorMap()[i->second->GetName()] = c;
178 //new BlackBoxInputConnector();
182 const BlackBoxDescriptor::OutputDescriptorMapType& omap
183 = bbGetDescriptor()->GetOutputDescriptorMap();
184 BlackBoxDescriptor::OutputDescriptorMapType::const_iterator o;
185 for ( o = omap.begin(); o != omap.end(); ++o )
187 bbtkDebugMessage("Kernel",8,"* Allocate \""<<o->first<<"\""<<std::endl);
188 // Redirect the connector to the internal box connector
189 // Cast the BBOutputDescriptor into a ComplexBBOutputDescriptor
190 ComplexBlackBoxOutputDescriptor* d =
191 (ComplexBlackBoxOutputDescriptor*)o->second;
192 // Get the internal box connector
193 BlackBoxOutputConnector* c =
194 bbUnsafeGetBlackBox ( d->GetTarget() )
195 ->bbGetOutputConnectorMap()[ d->GetOutput() ];
197 bbGetOutputConnectorMap()[o->second->GetName()] = c;
198 //new BlackBoxOutputConnector();
203 bbtkDebugDecTab("Kernel",8);
205 //=========================================================================
208 //=========================================================================
209 /// Desallocates the i/o connectors of the black box
210 void ComplexBlackBox::bbDesallocateConnectors()
212 bbtkDebugMessageInc("Kernel",8,
213 "ComplexBlackBox::DesallocateConnectors()"
216 // The connectors have not been allocated by the complex box
217 // but by the internal boxes. Hence **DO NOT** desallocate !
218 // just clear the maps to avoid that
219 // BlackBox::bbDesallocateConnectors delete the connectors
222 bbGetInputConnectorMap().clear();
223 bbGetOutputConnectorMap().clear();
225 bbtkDebugDecTab("Kernel",8);
228 //=========================================================================
230 //=======================================================================
231 BlackBox::Pointer ComplexBlackBox::bbClone(const std::string& name)
233 bbtkDebugMessageInc("Kernel",9,
234 "ComplexBlackBox::bbClone(\""<<name<<"\") ["
235 <<bbGetFullName()<<"]"<<std::endl);
237 ComplexBlackBox* CBB = new ComplexBlackBox(*this,name);
238 return MakeBlackBoxPointer(CBB);
240 //=======================================================================
242 //=======================================================================
243 /// Main processing method of the box.
244 /// Executes the box so that its outputs are up-to-date on exit
245 void ComplexBlackBox::bbExecute(bool force)
247 bbtkDebugMessageInc("Process",1,
248 "ComplexBlackBox::bbExecute() ["
249 <<bbGetFullName()<<"]"<<std::endl);
252 Wx::BeginBusyCursor();
254 if (mExecutionList.size() != 0)
257 std::vector<std::string>::const_iterator i;
258 for (i=mExecutionList.begin();
259 i!=mExecutionList.end();
262 bbtkDebugMessage("Process",2," -> Executing '"<<*i<<"'"<<std::endl);
263 mBlackBoxMap[*i]->bbExecute(force);
268 std::map<std::string, BlackBox::Pointer>::iterator i;
269 for (i=mBlackBoxMap.begin(); i!=mBlackBoxMap.end(); ++i)
271 i->second->bbExecute(force);
278 bbtkDebugDecTab("Process",1);
281 //==================================================================
283 //==================================================================
284 void ComplexBlackBox::bbSetModifiedStatus(BlackBoxInputConnector* c)
286 bbtkDebugMessage("Process",3,
287 "ComplexBlackBox::bbSetModifiedStatus("
288 <<c<<") ["<<bbGetFullName()<<"]"<<std::endl);
290 c->GetBlackBox()->bbSetModifiedStatus(c);
292 bbtkDebugMessage("Process",3,
293 "EO ComplexBlackBox::bbSetModifiedStatus("
294 <<c<<") ["<<bbGetFullName()<<"]"<<std::endl);
296 //==================================================================
298 //==================================================================
299 void ComplexBlackBox::bbAddToExecutionList( const std::string& name )
301 bbtkDebugMessageInc("Kernel",9,
302 "ComplexBlackBox::bbAddToExecutionList(\""
304 <<bbGetFullName()<<"]"<<std::endl);
306 mExecutionList.push_back( name );
308 bbtkDebugDecTab("Kernel",9);
311 //==================================================================
313 //==================================================================
314 IOStatus ComplexBlackBox::bbBackwardUpdate(Connection::Pointer caller)
316 bbtkDebugMessageInc("Process",1,
317 "ComplexBlackBox::bbBackwardUpdate("
318 <<(caller?caller->GetFullName():"0")<<") ["
319 <<bbGetFullName()<<"]"<<std::endl);
320 // bbtkInternalError("ComplexBlackBox::bbBackwardUpdate should never be called !");
324 bbtkInternalError("ComplexBlackBox::bbBackwardUpdate called with caller=0");
328 IOStatus s = UPTODATE;
329 const BlackBoxDescriptor::OutputDescriptorMapType& omap
330 = bbGetDescriptor()->GetOutputDescriptorMap();
331 BlackBoxDescriptor::OutputDescriptorMapType::const_iterator i
332 = omap.find(caller->GetBlackBoxFromOutput());
335 // Cast the BBOutputDescriptor into a ComplexBBOutputDescriptor
336 ComplexBlackBoxOutputDescriptor* d =
337 (ComplexBlackBoxOutputDescriptor*)i->second;
338 // Get the internal box
339 BlackBox::Pointer b = bbUnsafeGetBlackBox ( d->GetTarget() );
340 // Calls BackwardUpdate on it
341 bbtkDebugMessageInc("Process",2,"Internal box connected to output : "<<d->GetTarget()<<std::endl);
342 // Because internal box can also be a complex box we have to
343 // temporarily change the connection BlackBoxFromOutput to the
346 // std::string oldout = caller->GetBlackBoxFromOutput();
347 // std::cout << "oldout = "<<oldout<<std::endl;
348 // std::cout << "tmpout = "<<d->GetOutput()<<std::endl;
349 // caller->SetBlackBoxFromOutput(d->GetOutput());
351 //Connection newcaller(*caller);
352 //newcaller.SetBlackBoxFromOutput(d->GetOutput());
353 //IOStatus s1 = b->bbBackwardUpdate(&newcaller);
354 IOStatus s1 = b->bbBackwardUpdate(caller);
356 // restore old output
357 // caller->SetBlackBoxFromOutput(oldout);
359 // ??? STATUS OF CBBs ???
360 // ??? Here it is only the final status of the boxes connected to the output
361 if (s1==MODIFIED) s=MODIFIED;
362 bbtkDebugDecTab("Process",2);
366 bbtkError("Connection '"<<caller->GetFullName()<<"' does not point to a valid output of the complex box !");
368 bbtkDebugDecTab("Process",1);
373 //==================================================================
376 //==================================================================
377 Data ComplexBlackBox::bbGetOutput( const std::string &name )
379 bbtkDebugMessageInc("Data",7,
380 "ComplexBlackBox::bbGetOutput(\""<<name<<"\") ["
381 <<bbGetFullName()<<"]"<<std::endl);
383 ComplexBlackBoxOutputDescriptor* d =
384 (ComplexBlackBoxOutputDescriptor*)
385 bbGetDescriptor()->GetOutputDescriptor(name);
387 Data p = bbGetBlackBox(d->GetTarget())->bbGetOutput(d->GetOutput());
390 bbtkDebugDecTab("Data",7);
393 //==================================================================
395 //==================================================================
396 /// Gets the input Data of a given name
397 Data ComplexBlackBox::bbGetInput( const std::string &name )
399 bbtkDebugMessageInc("Data",7,
400 "ComplexBlackBox::bbGetInput(\""<<name<<"\") ["
401 <<bbGetFullName()<<"]"<<std::endl);
403 ComplexBlackBoxInputDescriptor* d =
404 (ComplexBlackBoxInputDescriptor*)
405 bbGetDescriptor()->GetInputDescriptor(name);
407 Data p = bbGetBlackBox(d->GetTarget())->bbGetInput(d->GetInput());
409 bbtkDebugDecTab("Data",7);
412 //==================================================================
414 //==================================================================
415 /// Sets the data of the output called <name>
416 void ComplexBlackBox::bbSetOutput( const std::string &name, Data data)
418 bbtkDebugMessageInc("Data",7,
419 "ComplexBlackBox::bbSetOutput(\""<<name<<"\",data) ["
420 <<bbGetFullName()<<"]"<<std::endl);
422 ComplexBlackBoxOutputDescriptor* d =
423 (ComplexBlackBoxOutputDescriptor*)
424 bbGetDescriptor()->GetOutputDescriptor(name);
426 bbGetBlackBox(d->GetTarget())->bbSetOutput(d->GetOutput(),data);
428 bbtkDebugDecTab("Data",7);
430 //==================================================================
432 //==================================================================
433 /// Sets the data of the input called <name>
434 void ComplexBlackBox::bbSetInput( const std::string &name, Data data,
437 bbtkDebugMessageInc("Data",7,
438 "ComplexBlackBox::bbSetInput(\""<<name<<"\",data) ["
439 <<bbGetFullName()<<"]"<<std::endl);
441 ComplexBlackBoxInputDescriptor* d = (ComplexBlackBoxInputDescriptor*)
442 bbGetDescriptor()->GetInputDescriptor(name);
444 bbGetBlackBox(d->GetTarget())->bbSetInput(d->GetInput(),data,setModified);
446 bbtkDebugDecTab("Data",7);
448 //==================================================================
451 //==================================================================
452 /// Sets the data of the input called <name>
453 void ComplexBlackBox::bbBruteForceSetInputPointer( const std::string &name,
457 bbtkDebugMessageInc("Data",7,
458 "ComplexBlackBox::bbBruteForceSetInputPointer('"
459 <<name<<"',"<<data<<") ["
460 <<bbGetFullName()<<"]"<<std::endl);
462 ComplexBlackBoxInputDescriptor* d = (ComplexBlackBoxInputDescriptor*)
463 bbGetDescriptor()->GetInputDescriptor(name);
465 bbGetBlackBox(d->GetTarget())->bbBruteForceSetInputPointer(d->GetInput(),
469 bbtkDebugDecTab("Data",7);
471 //==================================================================
473 //=========================================================================
474 /// Connects the input <name> to the connection c
475 void ComplexBlackBox::bbConnectInput( const std::string& name, Connection::Pointer c)
477 bbtkDebugMessageInc("Kernel",7,
478 "ComplexBlackBox::bbConnectInput(\""
479 <<name<<"\","<<c<<") ["
480 <<bbGetFullName()<<"]"
483 ComplexBlackBoxInputDescriptor* d = (ComplexBlackBoxInputDescriptor*)
484 bbGetDescriptor()->GetInputDescriptor(name);
486 BlackBox::Pointer t = bbGetBlackBox(d->GetTarget());
488 c->SetBlackBoxToInput(d->GetInput());
489 t->bbConnectInput(d->GetInput(),c);
491 bbtkMessage("Debug",1,"ComplexBlackBox["<<bbGetFullName()<<"]::bbConnectInput : "
492 <<c->GetFullName()<<std::endl);
494 bbtkDebugDecTab("Kernel",7);
496 //=========================================================================
499 //=========================================================================
500 /// Connects the output <name> to the connection c
501 void ComplexBlackBox::bbConnectOutput( const std::string& name, Connection::Pointer c)
503 bbtkDebugMessageInc("Kernel",7,
504 "ComplexBlackBox::bbConnectOutput(\""
505 <<name<<"\","<<c<<") ["
506 <<bbGetFullName()<<"]"<<std::endl);
508 ComplexBlackBoxOutputDescriptor* d = (ComplexBlackBoxOutputDescriptor*)
509 bbGetDescriptor()->GetOutputDescriptor(name);
511 BlackBox::Pointer t = bbGetBlackBox(d->GetTarget());
513 c->SetBlackBoxFrom(t);
514 c->SetBlackBoxFromOutput(d->GetOutput());
515 t->bbConnectOutput(d->GetOutput(),c);
517 bbtkMessage("Debug",5,"ComplexBlackBox["<<bbGetFullName()<<"]::bbConnectOutput : "
518 <<c->GetFullName()<<std::endl);
520 bbtkDebugDecTab("Kernel",7);
522 //=========================================================================
525 //==================================================================
526 /// Adds the black box to the complex box
527 void ComplexBlackBox::bbAddBlackBox( BlackBox::Pointer b)
529 bbtkDebugMessageInc("Kernel",7,
530 "ComplexBlackBox::AddBlackBox(\""<<b->bbGetName()
532 <<bbGetFullName()<<"]"<<std::endl);
534 if ( bbUnsafeGetBlackBox(b->bbGetName()) )
536 bbtkError("a black box called \""<<b->bbGetName()
537 <<"\" already exists");
539 b->bbSetParent(GetThisPointer<ComplexBlackBox>());
540 mBlackBoxMap[b->bbGetName()] = b;
542 bbtkDebugDecTab("Kernel",7);
544 //==================================================================
546 //==================================================================
547 /// Adds the black box to the complex box (unsafe)
548 void ComplexBlackBox::bbUnsafeAddBlackBox( BlackBox::Pointer b)
550 bbtkDebugMessageInc("Kernel",7,
551 "ComplexBlackBox::UnsafeAddBlackBox(\""<<b->bbGetName()
553 <<bbGetFullName()<<"]"<<std::endl);
555 b->bbSetParent(GetThisPointer<ComplexBlackBox>());
556 mBlackBoxMap[b->bbGetName()] = b;
558 bbtkDebugDecTab("Kernel",7);
560 //==================================================================
562 //==================================================================
563 /// Removes the black box from the complex box
564 void ComplexBlackBox::bbRemoveBlackBox( const std::string& name,
565 bool remove_connections )
567 bbtkDebugMessageInc("Kernel",7,
568 "ComplexBlackBox::RemoveBlackBox(\""<<name<<"\") ["
569 <<bbGetFullName()<<"]"<<std::endl);
571 BlackBoxMapType::iterator i = mBlackBoxMap.find(name);
572 if ( i == mBlackBoxMap.end() )
574 bbtkError("the black box \""<<name<<"\" does not exist");
576 BlackBox::WeakPointer p = i->second;
578 if (remove_connections)
580 ConnectionListType::const_iterator j;
581 for ( j = mConnectionList.begin();
582 j != mConnectionList.end(); ++j )
587 if (p.use_count()!=1)
589 bbtkError("the black box \""<<name<<"\" is still connected");
592 mBlackBoxMap.erase(i);
595 // Unload orphan dl packages
596 Package::UnLoadReleasedDynamicallyLoadedPackages();
598 bbtkDebugDecTab("Kernel",7);
600 //==================================================================
602 //==================================================================
603 /// Adds the connection to the complex box
604 void ComplexBlackBox::bbAddConnection( Connection::Pointer c)
606 bbtkDebugMessageInc("Kernel",7,
607 "ComplexBlackBox::AddConnection(\""<<"..."<<"\") ["
608 <<bbGetFullName()<<"]"<<std::endl);
610 mConnectionList.push_back(c);
612 bbtkDebugDecTab("Kernel",7);
614 //==================================================================
615 // void RemoveConnection( );
617 //==================================================================
618 /// Returns the black box with name <name>
619 BlackBox::Pointer ComplexBlackBox::bbGetBlackBox( const std::string& name )
621 bbtkDebugMessageInc("Kernel",9,
622 "ComplexBlackBox::GetBlackBox(\""<<name<<"\") ["
623 <<bbGetFullName()<<"]"<<std::endl);
625 BlackBoxMapType::iterator i = mBlackBoxMap.find(name);
626 if ( i == mBlackBoxMap.end() )
628 bbtkError("the black box \""<<name<<"\" does not exist");
631 bbtkDebugDecTab("Kernel",9);
634 //==================================================================
636 //==================================================================
637 /// Returns the black box with name <name> : does not throw an exception
638 /// if it does not exist but return a null pointer
639 BlackBox::Pointer ComplexBlackBox::bbUnsafeGetBlackBox( const std::string& name )
641 bbtkDebugMessageInc("Kernel",9,
642 "ComplexBlackBox::UnsafeGetBlackBox(\""<<name<<"\") ["
643 <<bbGetFullName()<<"]"
646 BlackBoxMapType::iterator i = mBlackBoxMap.find(name);
647 if ( i == mBlackBoxMap.end() )
649 bbtkDebugDecTab("Kernel",9);
650 return BlackBox::Pointer();
653 bbtkDebugDecTab("Kernel",9);
657 //==================================================================
659 //==================================================================
660 void ComplexBlackBox::bbPrintBlackBoxes()
662 bbtkDebugMessageInc("Kernel",9,
663 "ComplexBlackBox::PrintBlackBoxes() ["
664 <<bbGetFullName()<<"]"
667 BlackBoxMapType::iterator i;
668 for ( i = mBlackBoxMap.begin(); i != mBlackBoxMap.end(); ++i )
670 bbtkMessage("Help",1,i->second->bbGetFullName()<<std::endl);
673 bbtkDebugDecTab("Kernel",9);
675 //==================================================================
679 //=========================================================================
681 void ComplexBlackBox::bbWriteDotInputOutputName(FILE *ff,bool inputoutput,int detail, int level)
685 fprintf(ff,"%s_IN_%p",bbGetTypeName().c_str(),this);
687 fprintf(ff,"%s_OUT_%p",bbGetTypeName().c_str(),this);
690 //=========================================================================
693 //=========================================================================
694 BlackBox::Pointer ComplexBlackBox::bbFindBlackBox(const std::string &blackboxname)
696 BlackBox::Pointer blackbox;
697 std::string subname="";
698 std::string restname="";
699 std::string delimiters(">");
700 // Skip delimiters at beginning.
701 std::string::size_type lastPos = blackboxname.find_first_not_of(delimiters, 0);
702 // Find first "non-delimiter".
703 std::string::size_type pos = blackboxname.find_first_of(delimiters, lastPos);
705 // Found a token, add it to the vector.
706 subname = blackboxname.substr(lastPos, pos - lastPos);
707 restname = blackboxname.substr(lastPos+pos - lastPos+1, 999);
709 if (restname==subname)
714 BlackBoxMapType::iterator i = mBlackBoxMap.find(subname);
715 if ( i != mBlackBoxMap.end() )
717 blackbox = i->second;
720 blackbox = blackbox->bbFindBlackBox(restname);
725 //=========================================================================
727 //=========================================================================
728 void ComplexBlackBox::bbInsertHTMLGraph( std::ofstream& s,
732 const std::string& output_dir,
736 std::string directory(output_dir);
738 if (output_dir.length() == 0)
740 // Don't pollute the file store with "temp_dir" directories ...
741 std::string default_temp_dir = ConfigurationFile::GetInstance().Get_default_temp_dir();
742 directory = default_temp_dir + "/" + "temp_dir";
745 std::string simplefilename (this->bbGetTypeName()+"_"+this->bbGetName());
746 std::string simplefilename_png (simplefilename+".png");
747 std::string filename (directory+"/"+simplefilename);
748 std::string filename_png (filename+".png");
749 std::string filename_cmap (filename+".cmap");
750 std::string filename_dot (filename+".dot");
752 std::string filename_png2 ("\"" + filename_png + "\"");
753 std::string filename_cmap2 ("\"" + filename_cmap + "\"");
754 std::string filename_dot2 ("\"" + filename_dot + "\"");
757 std::string command1 ("dot -T png -o "
758 + filename_png2 + " " + filename_dot2);
759 std::string command1a("dot -T cmap -o "
760 + filename_cmap2 + " " + filename_dot2);
762 // 1. Generating .dot file
764 ff = fopen(filename_dot.c_str(),"w");
765 fprintf(ff,"digraph bbtk_graph{\n");
766 fprintf(ff,"rankdir=LR%s\n",";");
767 fprintf(ff,"node [shape=record]%s\n",";");
769 this->bbWriteDotFileBlackBox(ff,
770 GetThisPointer<ComplexBlackBox>(),
778 // 2. Executing .dot file -> png
779 system( command1.c_str() );
780 // 3. Executing .dot file -> cmap
781 system( command1a.c_str() );
783 // 4. HTML code insertion
785 (s) << "<center><img src=\"" << simplefilename_png
786 << "\" border=\"0\" usemap=\"#map_"<< simplefilename
787 <<"\" alt=\"\"></center>\n";
790 (s) << "<map name=\"map_"<< simplefilename <<"\">\n";
793 ff2=fopen(filename_cmap.c_str(),"r");
806 //=========================================================================
809 //=========================================================================
810 /// Write Graphviz-dot description in file
811 void ComplexBlackBox::bbWriteDotFileBlackBox(FILE *ff,
812 BlackBox::Pointer parentblackbox,
813 int detail, int level,
818 std::string valueStr("");
819 Package::Pointer package = this->bbGetDescriptor()->GetPackage();
824 tmp1 = this->bbGetDescriptor()->GetPackage()->GetDocRelativeURL();
826 tmp1 = this->bbGetDescriptor()->GetPackage()->GetDocURL();
833 std::string tmp2=bbGetTypeName();
834 std::string url(tmp1 + "#" + tmp2 );
835 fprintf( ff , "subgraph cluster_%s_%p {\n",bbGetName().c_str(),this);
837 if (!( (bbGetTypeName()=="workspace") && (bbGetName()=="workspacePrototype")) )
839 fprintf( ff , " URL = \"%s\" %s",url.c_str(),";");
842 std::string boxname="["+bbGetTypeName()+"]";
843 if (GetThisPointer<ComplexBlackBox>()!=parentblackbox)
851 boxname = bbGetName();
852 boxname = boxname + " [" +this->bbGetDescriptor()->GetPackage()->GetName()+"::"+ bbGetTypeName() + "]";
856 fprintf( ff , " label = \"%s\"%s\n", boxname.c_str() ,";");
860 // fprintf( ff , " style=filled%s\n",";");
861 // fprintf( ff , " color=grey%s\n",";");
862 fprintf( ff , " node [style=filled]%s\n",";");
863 fprintf( ff , " fillcolor=grey%s\n",";");
864 fprintf( ff , " edge [color=blue]%s\n",";");
868 std::string labelStr1;
869 std::string labelStr2;
870 labelStr1 = boxname + "\\n(output)" ;
871 labelStr2 = " | {{ ";
874 OutputConnectorMapType::iterator i;
876 const BlackBoxDescriptor::OutputDescriptorMapType& omap = this->bbGetDescriptor()->GetOutputDescriptorMap();
877 BlackBoxDescriptor::OutputDescriptorMapType::const_iterator o;
878 for ( o = omap.begin(); o != omap.end(); ++o )
882 labelStr2=labelStr2+" | ";
885 if (instanceOrtype==true)
887 valueStr = this->bbGetOutputAsString(o->second->GetName()/*
890 labelStr2=labelStr2+"<"+o->second->GetName().c_str()+"> " + valueStr + o->second->GetName().c_str();
893 labelStr2 = labelStr2+ " } }";
899 labelStr1 = labelStr1 + labelStr2;
904 bbWriteDotInputOutputName(ff,false,detail,level);
905 fprintf( ff , " [shape=record, style=filled,fillcolor=grey,color=red,label=\"%s\"]%s\n",labelStr1.c_str(),";" );
910 labelStr1 = boxname + "\\n(input)" ;
911 labelStr2 = " | {{ ";
913 InputConnectorMapType::iterator ii;
915 const BlackBoxDescriptor::InputDescriptorMapType& imap = this->bbGetDescriptor()->GetInputDescriptorMap();
916 BlackBoxDescriptor::InputDescriptorMapType::const_iterator iii;
917 for ( iii = imap.begin(); iii != imap.end(); ++iii )
921 labelStr2=labelStr2+" | ";
924 if (instanceOrtype==true)
926 valueStr = this->bbGetInputAsString(iii->second->GetName()/*,factory*/) + " = ";
928 labelStr2=labelStr2+"<"+iii->second->GetName().c_str()+"> " + valueStr + iii->second->GetName().c_str();
932 labelStr2 = labelStr2+ " } }";
935 labelStr1 = labelStr1 + labelStr2;
939 bbWriteDotInputOutputName(ff,true,detail,level);
940 fprintf( ff , " [shape=record, style=filled,fillcolor=grey,color=red,label=\"%s\"]%s\n",labelStr1.c_str(),";" );
945 BlackBoxMapType::iterator j;
946 for ( j = mBlackBoxMap.begin(); j != mBlackBoxMap.end(); ++j )
950 j->second->bbWriteDotFileBlackBox(ff,
959 fprintf( ff , "}\n\n");
961 fprintf( ff , " edge[color=blue]%s\n",";");
965 // Relation Input with the inside BlackBox of the this ComplexBlackbox
966 ComplexBlackBoxDescriptor::InputDescriptorMapType::iterator xx;
967 ComplexBlackBoxDescriptor::InputDescriptorMapType idmt=bbGetDescriptor()->GetInputDescriptorMap();
968 for ( xx = idmt.begin(); xx != idmt.end(); ++xx )
970 ComplexBlackBoxInputDescriptor *cbbid = (ComplexBlackBoxInputDescriptor*)xx->second;
973 bbWriteDotInputOutputName(ff,true,detail,level);
976 fprintf(ff,":%s",cbbid->GetName().c_str() );
979 BlackBox::Pointer bb = bbGetBlackBox( cbbid->GetTarget() );
980 bb->bbWriteDotInputOutputName(ff,true,detail,level);
983 fprintf(ff,":%s \n", cbbid->GetInput().c_str() );
993 // Relation Output ComplexBlackBox
994 ComplexBlackBoxDescriptor::OutputDescriptorMapType::iterator yy;
995 ComplexBlackBoxDescriptor::OutputDescriptorMapType odmt=bbGetDescriptor()->GetOutputDescriptorMap();
996 for ( yy = odmt.begin(); yy != odmt.end(); ++yy )
998 ComplexBlackBoxOutputDescriptor *cbbod = (ComplexBlackBoxOutputDescriptor*)yy->second;
1000 BlackBox::Pointer bb = bbGetBlackBox( cbbod->GetTarget() );
1001 bb->bbWriteDotInputOutputName(ff,false,detail,level);
1004 fprintf(ff,":%s", cbbod->GetOutput().c_str() );
1007 bbWriteDotInputOutputName(ff,false,detail,level);
1010 fprintf(ff,":%s",cbbod->GetName().c_str() );
1019 // Relation from the out side of this ComplexBlackBox with its Inputs
1020 if (GetThisPointer<ComplexBlackBox>()!=parentblackbox) {
1021 for ( ii = bbGetInputConnectorMap().begin();
1022 ii != bbGetInputConnectorMap().end(); ++ii )
1026 Connection::Pointer con = ii->second->GetConnection();
1028 BlackBox::Pointer a=con->GetBlackBoxFrom();
1029 BlackBox::Pointer b=con->GetBlackBoxTo();
1031 a->bbWriteDotInputOutputName(ff,false,detail,level);
1034 fprintf(ff,":%s",con->GetBlackBoxFromOutput().c_str());
1037 b->bbWriteDotInputOutputName(ff,true,detail,level);
1040 fprintf(ff,":%s",con->GetBlackBoxToInput().c_str());
1042 fprintf(ff,"%s\n",";");
1046 } // if parentblackbox
1048 //=========================================================================
1055 //=======================================================================
1056 /// Generates the list of the packages of which its depends
1057 /// (cause an internal box belongs to it)
1058 void ComplexBlackBox::GetPackagesDependencies(std::vector<Package*>& deps)
1061 BlackBoxMapType::iterator i;
1062 for ( i = mBlackBoxMap.begin(); i != mBlackBoxMap.end(); ++i )
1064 deps.push_back(i->second->bbGetDescriptor()->GetPackage());
1068 //=======================================================================
1071 //=======================================================================
1072 void ComplexBlackBox::Check(bool recursive)
1074 bbtkMessage("Debug",1,"**** Checking Complex Black Box "<<(void*)this
1075 <<" ["<<bbGetFullName()<<"]"<<std::endl);
1077 BlackBoxMapType::const_iterator i;
1078 for ( i = mBlackBoxMap.begin(); i != mBlackBoxMap.end(); ++i )
1080 i->second->Check(recursive);
1082 ConnectionListType::const_iterator j;
1083 for ( j = mConnectionList.begin();
1084 j != mConnectionList.end(); ++j )
1088 bbtkMessage("Debug",1,"**** Checking Complex Black Box "<<(void*)this
1089 <<" ["<<bbGetFullName()<<"] ... OK"<<std::endl);
1092 //=======================================================================
1094 //=========================================================================
1095 /// Returns the name with the name of the parent prepended if any
1096 std::string ComplexBlackBox::bbGetNameWithParent() const
1098 if (!IsAPrototype()) return BlackBox::bbGetNameWithParent();
1099 if (bbGetDescriptor())
1101 return bbGetDescriptor()->GetFullTypeName() + ":" + bbGetName();
1105 return std::string(":") + bbGetName();
1108 //=========================================================================
1110 //==========================================================================
1111 std::string ComplexBlackBox::GetObjectName() const
1113 return std::string("ComplexBlackBox '")+bbGetNameWithParent()
1116 //==========================================================================
1118 //==========================================================================
1119 std::string ComplexBlackBox::GetObjectInfo() const
1121 std::stringstream i;
1122 i << " - "<<mBlackBoxMap.size() << " boxes / "
1123 <<mConnectionList.size() << " connections" << std::endl;
1126 //==========================================================================
1128 //==========================================================================
1129 size_t ComplexBlackBox::GetObjectSize() const
1131 size_t s = Superclass::GetObjectSize();
1132 s += ComplexBlackBox::GetObjectInternalSize();
1135 //==========================================================================
1136 //==========================================================================
1137 size_t ComplexBlackBox::GetObjectInternalSize() const
1139 size_t s = sizeof(ComplexBlackBox);
1142 //==========================================================================
1143 //==========================================================================
1144 size_t ComplexBlackBox::GetObjectRecursiveSize() const
1146 size_t s = Superclass::GetObjectRecursiveSize();
1147 s += ComplexBlackBox::GetObjectInternalSize();
1148 BlackBoxMapType::const_iterator i;
1149 for ( i = mBlackBoxMap.begin(); i != mBlackBoxMap.end(); ++i )
1151 s += i->second->GetObjectRecursiveSize();
1153 ConnectionListType::const_iterator j;
1154 for ( j = mConnectionList.begin();
1155 j != mConnectionList.end(); ++j )
1157 s += (*j)->GetObjectRecursiveSize();
1161 //==========================================================================