]> Creatis software - bbtk.git/blob - kernel/src/bbtkComplexBlackBoxDescriptor.cxx
d9e8da14fffa779c90cd7d9dafc10c47a755a636
[bbtk.git] / kernel / src / bbtkComplexBlackBoxDescriptor.cxx
1 /*=========================================================================
2                                                                                 
3   Program:   bbtk
4   Module:    $RCSfile: bbtkComplexBlackBoxDescriptor.cxx,v $
5   Language:  C++
6   Date:      $Date: 2008/03/07 10:21:30 $
7   Version:   $Revision: 1.12 $
8                                                                                 
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.
12                                                                                 
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.
16                                                                                 
17 =========================================================================*/
18
19 /**
20  *  \file 
21  *  \brief Class bbtk::ComplexBlackBoxDescriptor : describes a ComplexBlackBox (constituents, connections) and is able to create an instance of it.
22  */
23 #include "bbtkComplexBlackBoxDescriptor.h"
24 #include "bbtkComplexBlackBox.h"
25 //#include "bbtkFactory.h"
26 #include "bbtkMessageManager.h"
27 #include "bbtkUtilities.h"
28
29 namespace bbtk
30 {
31   
32
33   //=======================================================================
34   /// Default ctor
35   ComplexBlackBoxDescriptor::ComplexBlackBoxDescriptor(const std::string& name)
36     : BlackBoxDescriptor(),
37       mFactory(0)
38   {
39     bbtkDebugMessageInc("Kernel",9,"ComplexBlackBoxDescriptor::ComplexBlackBoxDescriptor(\""<<name<<"\")"<<std::endl);
40     SetTypeName(name);
41     AddToCategory("complex box");
42     mPrototype = new ComplexBlackBox(name+std::string("Prototype"),this);
43     bbtkDebugDecTab("Kernel",9);
44   }
45   //=======================================================================
46
47
48
49   //=======================================================================
50   /// Default dtor
51   ComplexBlackBoxDescriptor::~ComplexBlackBoxDescriptor()
52   {
53     bbtkDebugMessageInc("Kernel",9,"ComplexBlackBoxDescriptor::~ComplexBlackBoxDescriptor(\""<<GetTypeName()<<"\")"<<std::endl);
54
55     delete mPrototype;
56
57     bbtkDebugDecTab("Kernel",9);
58   }
59   //=======================================================================
60
61
62   //=======================================================================
63   /// Creates an instance of name <name> of the ComplexBlackBox of which this is the descriptor 
64   BlackBox* ComplexBlackBoxDescriptor::CreateInstance(const std::string& name)
65   {
66     //bbtkError("ComplexBlackBoxDescriptor::CreateInstance not implemented");
67     bbtkDebugMessageInc("Kernel",5,
68                         "ComplexBlackBoxDescriptor::CreateInstance(\""
69                         <<name<<"\") ["
70                         <<GetTypeName()<<"]"<<std::endl);
71     
72     return mPrototype->bbClone(name);
73
74     bbtkDebugDecTab("Kernel",5);
75   }
76   //=======================================================================
77
78
79
80   //=======================================================================
81   /// Adds a black box to the complex box
82   void ComplexBlackBoxDescriptor::Add ( const std::string& type,
83                                         const std::string& name
84                                         )
85   {
86     bbtkDebugMessageInc("Kernel",5,
87                         "ComplexBlackBoxDescriptor::Add(\""
88                         <<type<<"\",\""<<name<<"\") ["
89                         <<GetTypeName()<<"]"<<std::endl);
90     
91     // 
92     if (mFactory == 0) 
93       { 
94         bbtkError("ComplexBlackBoxDescriptor::Add : no factory set");
95       }
96     
97     // Verify that a box with the same name does not exist already
98     if ( mPrototype->bbUnsafeGetBlackBox( name ) ) 
99       {
100         bbtkError("a black box \""<<name<<"\" already exists");
101       }
102     // ok : create new one
103     mPrototype->bbAddBlackBox ( mFactory->NewBlackBox(type,name) );
104
105     bbtkDebugDecTab("Kernel",5);
106   }
107   //=======================================================================
108
109  //=======================================================================
110   /// Adds a black box to the execution list 
111   void ComplexBlackBoxDescriptor::AddToExecutionList ( const std::string& box)
112   {
113     bbtkDebugMessageInc("Kernel",5,
114                         "ComplexBlackBoxDescriptor::AddToExecutionList(\""
115                         <<box<<"\" ["
116                         <<GetTypeName()<<"]"<<std::endl);
117     // Verify that the box exists
118     BlackBox* b = mPrototype->bbUnsafeGetBlackBox( box ); 
119     if ( !b ) 
120       {
121         bbtkError("the black box \""<<box<<"\" does not exist");
122       }
123     // ok 
124     mPrototype->bbAddToExecutionList ( box  );
125
126     bbtkDebugDecTab("Kernel",5);
127     }
128
129
130   //=======================================================================
131   /// Connects two black boxes of the complex box
132   void ComplexBlackBoxDescriptor::Connect ( const std::string& from,
133                                             const std::string& output,
134                                             const std::string& to,
135                                             const std::string& input
136                                             )
137   {
138     bbtkDebugMessageInc("Kernel",5,
139                         "ComplexBlackBoxDescriptor::Connect(\""
140                         <<from<<"\",\""<<output<<"\",\""
141                         <<to<<"\",\""<<input
142                         <<"\") ["
143                         <<GetTypeName()<<"]"<<std::endl);
144   // 
145     if (mFactory == 0) 
146       { 
147         bbtkError("ComplexBlackBoxDescriptor::Connect : no factory set");
148       }
149     
150
151   // Verify that a box with the same name does not exist already
152     BlackBox* bbfrom = mPrototype->bbGetBlackBox( from );
153     if ( !bbfrom ) 
154       {
155         bbtkError("the black box \""<<from<<"\" does not exist");
156       }
157     BlackBox* bbto = mPrototype->bbGetBlackBox( to );
158     if ( !bbto ) 
159       {
160         bbtkError("the black box \""<<to<<"\" does not exist");
161       }
162     
163     Connection* c = mFactory->NewConnection( bbfrom, output, bbto, input );
164
165     mPrototype->bbAddConnection(c);
166
167     bbtkDebugDecTab("Kernel",5);
168   }
169   //=======================================================================
170
171
172   //=======================================================================
173   /// Defines an input of the complex box
174   void ComplexBlackBoxDescriptor::DefineInput ( const std::string& name,
175                                                 const std::string& box,
176                                                 const std::string& input,
177                                                 const std::string& help)
178   {
179     bbtkDebugMessageInc("Kernel",5,
180                         "ComplexBlackBoxDescriptor::DefineInput(\""
181                         <<name<<"\",\""<<box<<"\",\""
182                         <<input<<"\",\""<<help
183                         <<"\") ["
184                         <<GetTypeName()<<"]"<<std::endl);
185
186     BlackBox* bb = mPrototype->bbGetBlackBox( box );
187     if ( !bb ) 
188       {
189         bbtkError("the black box \""<<box<<"\" does not exist");
190       }
191
192     if (!bb->bbHasInput(input) )
193       {
194         bbtkError("the black box \""<<box<<"\" does not have input \""
195                   <<input<<"\"");
196       }
197     
198     AddInputDescriptor ( new ComplexBlackBoxInputDescriptor 
199                          ( typeid(ComplexBlackBoxDescriptor),
200                            name,
201                            help,
202                            box,
203                            input,
204                            bb->bbGetInputType(input)));
205     
206     
207     bbtkDebugDecTab("Kernel",5);
208   }
209   //=======================================================================
210
211   //=======================================================================
212   /// Defines an output of the complex box
213   void ComplexBlackBoxDescriptor::DefineOutput ( const std::string& name,
214                                                  const std::string& box,
215                                                  const std::string& output,
216                                                  const std::string& help)
217   {
218     bbtkDebugMessageInc("Kernel",5,
219                         "ComplexBlackBoxDescriptor::DefineOutput(\""
220                         <<name<<"\",\""<<box<<"\",\""
221                         <<output<<"\",\""<<help
222                         <<"\") ["
223                         <<GetTypeName()<<"]"<<std::endl);
224
225     BlackBox* bb = mPrototype->bbGetBlackBox( box );
226     if ( !bb ) 
227       {
228         bbtkError("the black box \""<<box<<"\" does not exist");
229       }
230
231     if (!bb->bbHasOutput(output) )
232       {
233         bbtkError("the black box \""<<box<<"\" does not have output \""
234                   <<output<<"\"");
235       }
236     
237     AddOutputDescriptor ( new ComplexBlackBoxOutputDescriptor 
238                           ( typeid(ComplexBlackBoxDescriptor),
239                             name,
240                             help,
241                             box,
242                             output,
243                             bb->bbGetOutputType(output)));
244     
245     
246     bbtkDebugDecTab("Kernel",5);
247   }
248   //=======================================================================
249
250   //=======================================================================
251   void ComplexBlackBoxDescriptor::PrintBlackBoxes()
252   {
253     mPrototype->bbPrintBlackBoxes(); 
254   }
255   //=======================================================================
256
257
258   //=======================================================================
259   void ComplexBlackBoxDescriptor::InsertHTMLGraph( std::ofstream& s , 
260                                                    int detail, int level, 
261                                                    const std::string& output_dir, bool relative_link )   
262   {
263     this->mPrototype->bbInsertHTMLGraph( s, 
264                                          detail, level, 
265                                          false, 
266                                          output_dir,
267                                          relative_link );
268   }
269   //=======================================================================
270
271   //=========================================================================
272   void ComplexBlackBoxDescriptor::InsertHtmlHelp ( std::ofstream& s, 
273                                                    int detail, int level,
274                                                    const std::string& output_dir, bool relative_link)
275   {
276     bbtkDebugMessageInc("Kernel",9,
277                         "ComplexBlackBoxDescriptor::InsertHtmlHelp() ["
278                         <<GetTypeName()<<"]"<<std::endl);
279     
280     //-------------
281     // General info 
282     std::string name = GetTypeName();
283     Utilities::html_format(name);
284
285     //   std::ofstream* s = &s1;
286
287     (s) << "<p><hr>\n";
288     (s) << "<a name=\""<<name<<"\"></a>\n";
289     (s) << //"Top:&nbsp;
290       "<a rel=\"top\" accesskey=\"t\" href=\"#Top\">Top</a>\n";
291     // (s) << "Previous:&nbsp;<a rel="previous" accesskey="p" href="#dir">(dir)</a>,
292     // (s) << "Up:&nbsp;<a rel="up" accesskey="u" href="#dir">(dir)</a>
293     (s) << "<h2 class=\"section\">"<<name<<"</h2>\n";
294
295
296     std::string descr = GetDescription();
297     Utilities::html_format(descr);
298     
299     std::string author = GetAuthor();
300     Utilities::html_format(author);
301     
302     std::vector<std::string> categories;
303     // Split the category string 
304     std::string delimiters = ";,";
305     Utilities::SplitString(GetCategory(),
306                            delimiters,categories);
307
308         
309     (s) << "<p><TABLE cellspacing=0  cellpadding=3>\n";
310     (s) << "<TR><TD style='vertical-align: top;'><b> Description </b></TD><TD style='vertical-align: top;'> : </TD><TD style='vertical-align: top;'> " 
311         << descr << "</TD></TR>\n";
312
313     (s) << "<TR><TD style='vertical-align: top;'><b> Author(s) </b></TD><TD style='vertical-align: top;'> : </TD><TD style='vertical-align: top;'>  " 
314         << author << "</TD></TR>\n";
315
316     (s) << "<TR><TD style='vertical-align: top;'><b> Category(s) </b></TD><TD style='vertical-align: top;'> : </TD><TD style='vertical-align: top;'>  ";
317     std::vector<std::string>::iterator ci;
318     for (ci=categories.begin(); ci!=categories.end(); ++ci)
319       {
320         s << "<a href=\"../index-category.html#"<< *ci <<"\">" << *ci 
321           << "</a>&nbsp;\n";
322       }
323     s << "</TD></TR>\n";      
324     std::string inc = GetScriptFileName();
325     if (inc.size()>0) 
326       {
327         s << "<TR><TD style='vertical-align: top;'><b> To use it </b></TD><TD style='vertical-align: top;'> : </TD><TD style='vertical-align: top;'> include ";
328         s << inc << "&nbsp;&nbsp;<a href=\"../../../bbs/"<<inc<<"\">[source]</a>";
329         s << "</TD></TR>\n";
330         
331       }
332     
333     const ComplexBlackBox::BlackBoxMapType& B = mPrototype->bbGetBlackBoxMap();
334         
335     if (B.size()) 
336     {
337            (s) << "<TR><TD style='vertical-align: top;'><b> Uses </b></TD><TD style='vertical-align: top;'> : </TD><TD style='vertical-align: top;'>  ";
338
339            std::set<BlackBoxDescriptor*> pdeps;
340            ComplexBlackBox::BlackBoxMapType::const_iterator b;
341            for ( b = B.begin(); b != B.end(); ++b ) 
342            {
343               BlackBoxDescriptor* d = b->second->bbGetDescriptor();
344               if (pdeps.find(d) != pdeps.end()) 
345             continue;
346               pdeps.insert(d);
347
348               Package* p = d->GetPackage();
349             
350               std::string name = b->second->bbGetTypeName();
351
352               std::string url;
353               if (relative_link) 
354                  url = p->GetDocRelativeURL();
355               else 
356                  url = p->GetDocURL();
357
358               s << "<a href=\"" <<url<<"#"<<name<<"\">" 
359                 << p->GetName()<<"::"<<name<<"</a>\n";
360             }   
361         
362             (s) << "</TD></TR>\n";
363
364      }
365
366      (s) << "</TABLE>\n";
367
368  
369    //-------------
370     // Graph
371     InsertHTMLGraph( s , detail,level, output_dir, relative_link);
372     
373     //-------------
374     // Inputs
375     std::string col("#CCCCFF");
376     
377     //  (s) << "<h3 class=\"subsection\">Inputs</h3>\n";
378     (s) << "<p><TABLE border=1 cellspacing=0 cellpadding=3>\n";
379     (s) << "<TR><TD colspan=3 align=center bgcolor=\""<<col
380       <<"\">Inputs</TD></TR>\n";
381     const BlackBoxDescriptor::InputDescriptorMapType& imap = 
382       GetInputDescriptorMap();
383     
384     InputDescriptorMapType::const_iterator in;
385     
386     for ( in = imap.begin();  in != imap.end(); ++in ) 
387       {
388         std::string name(in->second->GetName());
389         Utilities::html_format(name);
390         
391         std::string type("<");
392         type += in->second->GetTypeName();    
393         type += ">";
394         Utilities::html_format(type);
395         
396         std::string descr(in->second->GetDescription());
397         Utilities::html_format(descr);
398
399         (s) << "<TR><TD style='vertical-align: top;'><B><PRE> "<<name<<" </PRE></B></TD>"
400           << "<TD style='vertical-align: top;'><I><PRE> "<<type<<" </PRE></I></TD>"
401           << "<TD style='vertical-align: top;'>"<<descr<<"</TD></TR>\n";
402         
403       }
404     //  (s) << "</TABLE>\n";
405     
406     
407     //-------------
408     // Outputs
409     //  (s) << "<h3 class=\"subsection\">Outputs</h3>\n";
410     //  (s) << "<TABLE border=1 cellspacing=0>\n";
411     (s) << "<TR><TD colspan=3 align=center bgcolor=\""<<col
412       <<"\">Outputs</TD></TR>\n";
413     
414     const BlackBoxDescriptor::OutputDescriptorMapType& omap = 
415       GetOutputDescriptorMap();
416     
417     BlackBoxDescriptor::OutputDescriptorMapType::const_iterator o;
418     
419     for ( o = omap.begin();  o != omap.end(); ++o ) 
420       {
421         std::string name(o->second->GetName());
422         Utilities::html_format(name);
423         
424         std::string type("<");
425         type += o->second->GetTypeName();    
426         type += ">";
427         Utilities::html_format(type);
428         
429         std::string descr(o->second->GetDescription());
430         Utilities::html_format(descr);
431         
432         (s) << "<TR><TD style='vertical-align: top;'><B><PRE> "<<name<<" </PRE></B></TD>"
433           << "<TD style='vertical-align: top;'><I><PRE> "<<type<<" </PRE></I></TD>"
434           << "<TD style='vertical-align: top;'>"<<descr<<"</TD></TR>\n";
435         
436       }
437     (s) << "</TABLE>\n";
438
439     //------------
440     // End
441
442     bbtkDebugDecTab("Kernel",9);
443    }
444   //=========================================================================
445  
446
447   //=======================================================================
448   void ComplexBlackBoxDescriptor::GetHelp(bool full) const
449   {
450     if (full) bbtkMessage("Help",1,"Complex Black Box <"<<
451                           GetPackage()->GetName()<<"::"
452                           <<GetTypeName()<<">"<<std::endl);
453     bbtkMessage("Help",1," "                << GetDescription() <<std::endl);
454     bbtkMessage("Help",1," By : "           << GetAuthor()      <<std::endl);
455     bbtkMessage("Help",1," Category(s) : "  << GetCategory()     <<std::endl);    
456     if (mInput.size()) 
457       bbtkMessage("Help",1," * Inputs : "<<std::endl);
458     else 
459       bbtkMessage("Help",1," * No inputs"<<std::endl);
460     InputDescriptorMapType::const_iterator i;
461     unsigned int namelmax = 0;
462     unsigned int typelmax = 0;
463     for ( i = mInput.begin();  i != mInput.end(); ++i ) 
464     {
465            if (i->second->GetName().size()>namelmax) 
466              namelmax = i->second->GetName().size();
467            if (i->second->GetTypeName().size()>typelmax) 
468              typelmax = i->second->GetTypeName().size();
469     }
470     OutputDescriptorMapType::const_iterator o;
471     if (full) 
472     {
473            for ( o = mOutput.begin();  o != mOutput.end(); ++o ) 
474            {
475              if (o->second->GetName().size()>namelmax) 
476                namelmax = o->second->GetName().size();
477             if (o->second->GetTypeName().size()>typelmax) 
478                typelmax = o->second->GetTypeName().size();
479            }
480     }
481     //
482
483     for ( i = mInput.begin();  i != mInput.end(); ++i ) 
484     {
485            std::string name(i->second->GetName());
486            name += "'";
487            name.append(1+namelmax-name.size(),' ');
488            std::string type(i->second->GetTypeName());
489            type += ">";
490            type.append(1+typelmax-type.size(),' ');
491            bbtkMessage("Help",1,
492                     "    '"<<name
493                     <<" <"<<type
494                     <<" : "<<i->second->GetDescription()<<std::endl);
495     }
496     if (full) 
497     {
498            if (mOutput.size()) 
499              bbtkMessage("Help",1," * Outputs : "<<std::endl);
500            else 
501              bbtkMessage("Help",1," * No outputs"<<std::endl);
502            for ( o = mOutput.begin();  o != mOutput.end(); ++o ) 
503            {
504              std::string name(o->second->GetName());
505              name += "'";
506              name.append(1+namelmax-name.size(),' ');
507              std::string type(o->second->GetTypeName());
508              type += ">";
509              type.append(1+typelmax-type.size(),' ');
510              bbtkMessage("Help",1,
511                          "    '"<<name
512                          <<" <"<<type
513                          <<" : "<<o->second->GetDescription()<<std::endl);
514            }
515     }
516     if (full) 
517     {
518            const ComplexBlackBox::BlackBoxMapType& B = mPrototype->bbGetBlackBoxMap();
519         
520            if (B.size()) 
521              bbtkMessage("Help",1," * Boxes : "<<std::endl);
522            else 
523              bbtkMessage("Help",1," * No boxes"<<std::endl);
524         
525            ComplexBlackBox::BlackBoxMapType::const_iterator b;
526            for ( b = B.begin(); b != B.end(); ++b ) 
527            {
528              bbtkMessage("Help",1,"    '"<<b->second->bbGetName()<<
529                          "' <"
530                          << b->second->bbGetDescriptor()->GetPackage()->GetName() 
531                          <<"::"
532                          <<b->second->bbGetTypeName()<<">"<<std::endl);
533            }
534     }
535
536   }   
537   //=======================================================================
538
539
540
541 }