Imported Upstream version 1.8.8
[platform/upstream/doxygen.git] / addon / doxywizard / wizard.cpp
1 #include "wizard.h"
2 #include "input.h"
3 #include "doxywizard.h"
4
5 #include <math.h>
6 #include <QtGui>
7
8 // options configurable via the wizard
9 #define STR_PROJECT_NAME          QString::fromAscii("PROJECT_NAME")
10 #define STR_PROJECT_LOGO          QString::fromAscii("PROJECT_LOGO")
11 #define STR_PROJECT_BRIEF         QString::fromAscii("PROJECT_BRIEF")
12 #define STR_INPUT                 QString::fromAscii("INPUT")
13 #define STR_OUTPUT_DIRECTORY      QString::fromAscii("OUTPUT_DIRECTORY")
14 #define STR_PROJECT_NUMBER        QString::fromAscii("PROJECT_NUMBER")
15 #define STR_RECURSIVE             QString::fromAscii("RECURSIVE")
16 #define STR_OPTIMIZE_OUTPUT_FOR_C QString::fromAscii("OPTIMIZE_OUTPUT_FOR_C")
17 #define STR_OPTIMIZE_OUTPUT_JAVA  QString::fromAscii("OPTIMIZE_OUTPUT_JAVA")
18 #define STR_OPTIMIZE_FOR_FORTRAN  QString::fromAscii("OPTIMIZE_FOR_FORTRAN")
19 #define STR_OPTIMIZE_OUTPUT_VHDL  QString::fromAscii("OPTIMIZE_OUTPUT_VHDL")
20 #define STR_CPP_CLI_SUPPORT       QString::fromAscii("CPP_CLI_SUPPORT")
21 #define STR_HIDE_SCOPE_NAMES      QString::fromAscii("HIDE_SCOPE_NAMES")
22 #define STR_EXTRACT_ALL           QString::fromAscii("EXTRACT_ALL")
23 #define STR_SOURCE_BROWSER        QString::fromAscii("SOURCE_BROWSER")
24 #define STR_GENERATE_HTML         QString::fromAscii("GENERATE_HTML")
25 #define STR_GENERATE_LATEX        QString::fromAscii("GENERATE_LATEX")
26 #define STR_GENERATE_MAN          QString::fromAscii("GENERATE_MAN")
27 #define STR_GENERATE_RTF          QString::fromAscii("GENERATE_RTF")
28 #define STR_GENERATE_XML          QString::fromAscii("GENERATE_XML")
29 #define STR_GENERATE_HTMLHELP     QString::fromAscii("GENERATE_HTMLHELP")
30 #define STR_GENERATE_TREEVIEW     QString::fromAscii("GENERATE_TREEVIEW")
31 #define STR_USE_PDFLATEX          QString::fromAscii("USE_PDFLATEX")
32 #define STR_PDF_HYPERLINKS        QString::fromAscii("PDF_HYPERLINKS")
33 #define STR_SEARCHENGINE          QString::fromAscii("SEARCHENGINE")
34 #define STR_HAVE_DOT              QString::fromAscii("HAVE_DOT")
35 #define STR_CLASS_DIAGRAMS        QString::fromAscii("CLASS_DIAGRAMS")
36 #define STR_CLASS_GRAPH           QString::fromAscii("CLASS_GRAPH")
37 #define STR_COLLABORATION_GRAPH   QString::fromAscii("COLLABORATION_GRAPH")
38 #define STR_GRAPHICAL_HIERARCHY   QString::fromAscii("GRAPHICAL_HIERARCHY")
39 #define STR_INCLUDE_GRAPH         QString::fromAscii("INCLUDE_GRAPH")
40 #define STR_INCLUDED_BY_GRAPH     QString::fromAscii("INCLUDED_BY_GRAPH")
41 #define STR_CALL_GRAPH            QString::fromAscii("CALL_GRAPH")
42 #define STR_CALLER_GRAPH          QString::fromAscii("CALLER_GRAPH")
43 #define STR_HTML_COLORSTYLE_HUE   QString::fromAscii("HTML_COLORSTYLE_HUE")
44 #define STR_HTML_COLORSTYLE_SAT   QString::fromAscii("HTML_COLORSTYLE_SAT")
45 #define STR_HTML_COLORSTYLE_GAMMA QString::fromAscii("HTML_COLORSTYLE_GAMMA")
46
47 static bool g_optimizeMapping[6][6] = 
48 {
49   // A: OPTIMIZE_OUTPUT_FOR_C
50   // B: OPTIMIZE_OUTPUT_JAVA
51   // C: OPTIMIZE_FOR_FORTRAN
52   // D: OPTIMIZE_OUTPUT_VHDL
53   // E: CPP_CLI_SUPPORT
54   // F: HIDE_SCOPE_NAMES
55   // A     B     C     D     E      F
56   { false,false,false,false,false,false }, // 0: C++
57   { false,false,false,false,true, false }, // 1: C++/CLI
58   { false,true, false,false,false,false }, // 2: C#/Java
59   { true, false,false,false,false,true  }, // 3: C/PHP 
60   { false,false,true, false,false,false }, // 4: Fortran
61   { false,false,false,true, false,false }, // 5: VHDL
62 };
63
64 static QString g_optimizeOptionNames[6] =
65 {
66   STR_OPTIMIZE_OUTPUT_FOR_C,
67   STR_OPTIMIZE_OUTPUT_JAVA,
68   STR_OPTIMIZE_FOR_FORTRAN,
69   STR_OPTIMIZE_OUTPUT_VHDL,
70   STR_CPP_CLI_SUPPORT,
71   STR_HIDE_SCOPE_NAMES
72 };
73
74 //==========================================================================
75
76 static bool stringVariantToBool(const QVariant &v)
77 {
78   QString s = v.toString().toLower();
79   return s==QString::fromAscii("yes") || s==QString::fromAscii("true") || s==QString::fromAscii("1");
80
81
82 static bool getBoolOption(
83     const QHash<QString,Input*>&model,const QString &name)
84 {
85   Input *option = model[name];
86   Q_ASSERT(option!=0);
87   return stringVariantToBool(option->value());
88
89
90 static int getIntOption(
91     const QHash<QString,Input*>&model,const QString &name)
92 {
93   Input *option = model[name];
94   Q_ASSERT(option!=0);
95   return option->value().toInt();
96
97
98 static QString getStringOption(
99     const QHash<QString,Input*>&model,const QString &name)
100 {
101   Input *option = model[name];
102   Q_ASSERT(option!=0);
103   return option->value().toString();
104 }
105
106 static void updateBoolOption(
107     const QHash<QString,Input*>&model,const QString &name,bool bNew)
108 {
109   Input *option = model[name];
110   Q_ASSERT(option!=0);
111   bool bOld = stringVariantToBool(option->value());
112   if (bOld!=bNew)
113   {
114     option->value()=QString::fromAscii(bNew ? "true" : "false");
115     option->update();
116   }
117 }
118
119 static void updateIntOption(
120     const QHash<QString,Input*>&model,const QString &name,int iNew)
121 {
122   Input *option = model[name];
123   Q_ASSERT(option!=0);
124   int iOld = option->value().toInt();
125   if (iOld!=iNew)
126   {
127     option->value()=QString::fromAscii("%1").arg(iNew);
128     option->update();
129   }
130 }
131
132
133 static void updateStringOption(
134     const QHash<QString,Input*>&model,const QString &name,const QString &s)
135 {
136   Input *option = model[name];
137   Q_ASSERT(option!=0);
138   if (option->value().toString()!=s)
139   {
140     option->value() = s;
141     option->update();
142   }
143 }
144
145 //==========================================================================
146
147 TuneColorDialog::TuneColorDialog(int hue,int sat,int gamma,QWidget *parent) : QDialog(parent)
148 {
149    setWindowTitle(tr("Tune the color of the HTML output"));
150    QGridLayout *layout = new QGridLayout(this);
151    m_image = new QImage(QString::fromAscii(":/images/tunecolor.png"));
152    m_imageLab = new QLabel;
153    updateImage(hue,sat,gamma);
154    layout->addWidget(new QLabel(tr("Example output: use the sliders on the right to adjust the color")),0,0);
155    layout->addWidget(m_imageLab,1,0);
156    QHBoxLayout *buttonsLayout = new QHBoxLayout;
157
158    QPushButton *okButton = new QPushButton(tr("Ok"));
159    connect(okButton,SIGNAL(clicked()),SLOT(accept()));
160    okButton->setDefault(true);
161    QPushButton *cancelButton = new QPushButton(tr("Cancel"));
162    connect(cancelButton,SIGNAL(clicked()),SLOT(reject()));
163
164    ColorPicker *huePicker = new ColorPicker(ColorPicker::Hue);
165    huePicker->setCol(hue,sat,gamma);
166    huePicker->setFixedWidth(20);
167    layout->addWidget(huePicker,1,1);
168    ColorPicker *satPicker = new ColorPicker(ColorPicker::Saturation);
169    satPicker->setCol(hue,sat,gamma);
170    satPicker->setFixedWidth(20);
171    layout->addWidget(satPicker,1,2);
172    ColorPicker *gamPicker = new ColorPicker(ColorPicker::Gamma);
173    gamPicker->setCol(hue,sat,gamma);
174    gamPicker->setFixedWidth(20);
175    layout->addWidget(gamPicker,1,3);
176
177    connect(huePicker,SIGNAL(newHsv(int,int,int)),satPicker,SLOT(setCol(int,int,int)));
178    connect(satPicker,SIGNAL(newHsv(int,int,int)),huePicker,SLOT(setCol(int,int,int)));
179    connect(huePicker,SIGNAL(newHsv(int,int,int)),gamPicker,SLOT(setCol(int,int,int)));
180    connect(satPicker,SIGNAL(newHsv(int,int,int)),gamPicker,SLOT(setCol(int,int,int)));
181    connect(gamPicker,SIGNAL(newHsv(int,int,int)),satPicker,SLOT(setCol(int,int,int)));
182    connect(gamPicker,SIGNAL(newHsv(int,int,int)),huePicker,SLOT(setCol(int,int,int)));
183    connect(huePicker,SIGNAL(newHsv(int,int,int)),this,SLOT(updateImage(int,int,int)));
184    connect(satPicker,SIGNAL(newHsv(int,int,int)),this,SLOT(updateImage(int,int,int)));
185    connect(gamPicker,SIGNAL(newHsv(int,int,int)),this,SLOT(updateImage(int,int,int)));
186
187    buttonsLayout->addStretch();
188    buttonsLayout->addWidget(okButton);
189    buttonsLayout->addWidget(cancelButton);
190    layout->addLayout(buttonsLayout,5,0,1,4);
191 }
192
193 void hsl2rgb(double h,double s,double l,
194              double *pRed,double *pGreen,double *pBlue)
195 {
196   double v;
197   double r,g,b;
198
199   r = l;   // default to gray
200   g = l;
201   b = l;
202   v = (l <= 0.5) ? (l * (1.0 + s)) : (l + s - l * s);
203   if (v > 0)
204   {
205     double m;
206     double sv;
207     int sextant;
208     double fract, vsf, mid1, mid2;
209
210     m       = l + l - v;
211     sv      = (v - m ) / v;
212     h      *= 6.0;
213     sextant = (int)h;
214     fract   = h - sextant;
215     vsf     = v * sv * fract;
216     mid1    = m + vsf;
217     mid2    = v - vsf;
218     switch (sextant)
219     {
220       case 0:
221         r = v;
222         g = mid1;
223         b = m;
224         break;
225       case 1:
226         r = mid2;
227         g = v;
228         b = m;
229         break;
230       case 2:
231         r = m;
232         g = v;
233         b = mid1;
234         break;
235       case 3:
236         r = m;
237         g = mid2;
238         b = v;
239         break;
240       case 4:
241         r = mid1;
242         g = m;
243         b = v;
244         break;
245       case 5:
246         r = v;
247         g = m;
248         b = mid2;
249         break;
250     }
251   }
252   *pRed   = r;
253   *pGreen = g;
254   *pBlue  = b;
255 }
256
257
258
259 void TuneColorDialog::updateImage(int hue,int sat,int gam)
260 {
261   QImage coloredImg(m_image->width(),m_image->height(),QImage::Format_RGB32);
262   uint *srcPixel = (uint *)m_image->scanLine(0);
263   uint *dstPixel = (uint *)coloredImg.scanLine(0);
264   uint nrPixels = coloredImg.width()*coloredImg.height();
265   for (uint i=0;i<nrPixels;i++,srcPixel++,dstPixel++)
266   {
267     QColor c = QColor::fromRgb(*srcPixel);
268     double r,g,b;
269     hsl2rgb(hue/359.0, sat/255.0, pow(c.green()/255.0,gam/100.0),&r,&g,&b);
270     *dstPixel = qRgb((int)(r*255.0),(int)(g*255.0),(int)(b*255.0));
271   }
272   m_imageLab->setPixmap(QPixmap::fromImage(coloredImg));
273   m_hue = hue;
274   m_sat = sat;
275   m_gam = gam;
276 }
277
278 int TuneColorDialog::getHue() const
279 {
280   return m_hue;
281 }
282
283 int TuneColorDialog::getSaturation() const
284 {
285   return m_sat;
286 }
287
288 int TuneColorDialog::getGamma() const
289 {
290   return m_gam;
291 }
292
293 //==========================================================================
294
295 ColorPicker::ColorPicker(Mode m)
296 {
297   m_hue = 220;
298   m_gam = 100;
299   m_sat = 100;
300   m_mode = m;
301   m_pix = 0;
302 }
303
304 ColorPicker::~ColorPicker()
305 {
306   delete m_pix;
307 }
308
309 void ColorPicker::paintEvent(QPaintEvent*)
310 {
311   int w = width() - 5;
312
313   QRect r(0, foff, w, height() - 2*foff);
314   int wi = r.width() - 2;
315   int hi = r.height() - 2;
316   if (!m_pix || m_pix->height() != hi || m_pix->width() != wi) 
317   {
318     delete m_pix;
319     QImage img(wi, hi, QImage::Format_RGB32);
320     int y;
321     uint *pixel = (uint *) img.scanLine(0);
322     for (y = 0; y < hi; y++) 
323     {
324       const uint *end = pixel + wi;
325       int yh = y2hue(y+coff);
326       int ys = y2sat(y+coff);
327       int yg = y2gam(y+coff);
328       while (pixel < end) 
329       {
330         QColor c;
331         c.setHsv(yh, ys, (int)(255*pow(0.7,yg/100.0)));
332         *pixel = c.rgb();
333         ++pixel;
334       }
335     }
336     m_pix = new QPixmap(QPixmap::fromImage(img));
337   }
338   QPainter p(this);
339   p.drawPixmap(1, coff, *m_pix);
340   const QPalette &g = palette();
341   qDrawShadePanel(&p, r, g, true);
342   p.setPen(g.foreground().color());
343   p.setBrush(g.foreground());
344   QPolygon a;
345   int y = m_mode==Hue ?        hue2y(m_hue) : 
346           m_mode==Saturation ? sat2y(m_sat) :
347                                gam2y(m_gam);
348   a.setPoints(3, w, y, w+5, y+5, w+5, y-5);
349   p.eraseRect(w, 0, 5, height());
350   p.drawPolygon(a);
351 }
352
353 void ColorPicker::mouseMoveEvent(QMouseEvent *m)
354 {
355   if      (m_mode==Hue)        setHue(y2hue(m->y())); 
356   else if (m_mode==Saturation) setSat(y2sat(m->y()));
357   else                         setGam(y2gam(m->y()));
358 }
359
360 void ColorPicker::mousePressEvent(QMouseEvent *m)
361 {
362   if      (m_mode==Hue)        setHue(y2hue(m->y())); 
363   else if (m_mode==Saturation) setSat(y2sat(m->y()));
364   else                         setGam(y2gam(m->y()));
365 }
366
367 void ColorPicker::setHue(int h)
368 {
369   if (h==m_hue) return;
370   m_hue = qMax(0,qMin(h,359));
371   delete m_pix; m_pix=0;
372   repaint();
373   emit newHsv(m_hue,m_sat,m_gam);
374 }
375
376 void ColorPicker::setSat(int s)
377 {
378   if (s==m_sat) return;
379   m_sat = qMax(0,qMin(s,255));
380   delete m_pix; m_pix=0;
381   repaint();
382   emit newHsv(m_hue,m_sat,m_gam);
383 }
384
385 void ColorPicker::setGam(int g)
386 {
387   if (g==m_gam) return;
388   m_gam = qMax(40,qMin(g,240));
389   delete m_pix; m_pix=0;
390   repaint();
391   emit newHsv(m_hue,m_sat,m_gam);
392 }
393
394 void ColorPicker::setCol(int h, int s, int g)
395 {
396   if (m_hue!=h || m_sat!=s || m_gam!=g)
397   {
398     m_hue = h;
399     m_sat = s;
400     m_gam = g;
401     delete m_pix; m_pix=0;
402     repaint();
403   }
404 }
405
406 int ColorPicker::y2hue(int y)
407 {
408   int d = height() - 2*coff - 1;
409   return m_mode==Hue ? (y - coff)*359/d : m_hue;
410 }
411
412 int ColorPicker::hue2y(int v)
413 {
414   int d = height() - 2*coff - 1;
415   return coff + v*d/359;
416 }
417
418 int ColorPicker::y2sat(int y)
419 {
420   int d = height() - 2*coff - 1;
421   return m_mode==Saturation ? 255 - (y - coff)*255/d : m_sat;
422 }
423
424 int ColorPicker::sat2y(int v)
425 {
426   int d = height() - 2*coff - 1;
427   return coff + (255-v)*d/255;
428 }
429
430 int ColorPicker::y2gam(int y)
431 {
432   int d = height() - 2*coff - 1;
433   return m_mode==Gamma ? 240 - (y - coff)*200/d : m_gam;
434 }
435
436 int ColorPicker::gam2y(int g)
437 {
438   int d = height() - 2*coff - 1;
439   return coff + (240-g)*d/200;
440 }
441
442 //==========================================================================
443
444 Step1::Step1(Wizard *wizard,const QHash<QString,Input*> &modelData) : m_wizard(wizard), m_modelData(modelData)
445 {
446   QVBoxLayout *layout = new QVBoxLayout(this);
447   layout->setMargin(4);
448   layout->setSpacing(8);
449   QLabel *l = new QLabel(this);
450   l->setText(tr("Provide some information "
451               "about the project you are documenting"));
452   layout->addWidget(l);
453   QWidget *w      = new QWidget( this );
454   QGridLayout *grid = new QGridLayout(w);
455   grid->setSpacing(10);
456
457   // project name
458   QLabel *projName = new QLabel(this);
459   projName->setText(tr("Project name:"));
460   projName->setAlignment(Qt::AlignRight|Qt::AlignVCenter);
461   // project brief
462   QLabel *projBrief = new QLabel(this);
463   projBrief->setText(tr("Project synopsis:"));
464   projBrief->setAlignment(Qt::AlignRight|Qt::AlignVCenter);
465   // project version
466   QLabel *projVersion = new QLabel(this);
467   projVersion->setText(tr("Project version or id:"));
468   projVersion->setAlignment(Qt::AlignRight|Qt::AlignVCenter);
469   // project icon
470   QLabel *projLogo = new QLabel(this);
471   projLogo->setMinimumSize(1,55);
472   projLogo->setText(tr("Project logo:"));
473   projLogo->setAlignment(Qt::AlignRight|Qt::AlignVCenter);
474
475   grid->addWidget(projName,0,0);
476   grid->addWidget(projBrief,1,0);
477   grid->addWidget(projVersion,2,0);
478   grid->addWidget(projLogo,3,0);
479
480   m_projName   = new QLineEdit;
481   m_projBrief  = new QLineEdit;
482   m_projNumber = new QLineEdit;
483   QPushButton *projIconSel = new QPushButton(this);
484   projIconSel->setText(tr("Select..."));
485   m_projIconLab = new QLabel;
486
487   grid->addWidget(m_projName,0,1,1,2);
488   grid->addWidget(m_projBrief,1,1,1,2);
489   grid->addWidget(m_projNumber,2,1,1,2);
490   grid->addWidget(projIconSel,3,1);
491   grid->addWidget(m_projIconLab,3,2);
492
493   grid->setColumnStretch(2,1);
494
495   w->setLayout(grid);
496
497   layout->addWidget(w);
498
499   //---------------------------------------------------
500   QFrame *f = new QFrame( this );
501   f->setFrameStyle( QFrame::HLine | QFrame::Sunken );
502   layout->addWidget(f);
503   
504   l = new QLabel(this);
505   l->setText(tr("Specify the directory to scan for source code"));
506   layout->addWidget(l);
507   QWidget *row = new QWidget;
508   QHBoxLayout *rowLayout = new QHBoxLayout(row);
509   rowLayout->setSpacing(10);
510   l = new QLabel(this);
511   l->setText(tr("Source code directory:"));
512   rowLayout->addWidget(l);
513   m_sourceDir = new QLineEdit;
514   m_srcSelectDir = new QPushButton(this);
515   m_srcSelectDir->setText(tr("Select..."));
516   rowLayout->addWidget(m_sourceDir);
517   rowLayout->addWidget(m_srcSelectDir);
518   layout->addWidget(row);
519
520   m_recursive = new QCheckBox(this);
521   m_recursive->setText(tr("Scan recursively"));
522   m_recursive->setChecked(TRUE);
523   layout->addWidget(m_recursive);
524
525   //---------------------------------------------------
526   f = new QFrame( this );
527   f->setFrameStyle( QFrame::HLine | QFrame::Sunken );
528   layout->addWidget(f);
529
530   l = new QLabel(this);
531   l->setText(tr("Specify the directory where doxygen should "
532               "put the generated documentation"));
533   layout->addWidget(l);
534   row = new QWidget;
535   rowLayout = new QHBoxLayout(row);
536   rowLayout->setSpacing(10);
537   l = new QLabel(this);
538   l->setText(tr("Destination directory:"));
539   rowLayout->addWidget(l);
540   m_destDir = new QLineEdit;
541   m_dstSelectDir = new QPushButton(this);
542   m_dstSelectDir->setText(tr("Select..."));
543   rowLayout->addWidget(m_destDir);
544   rowLayout->addWidget(m_dstSelectDir);
545   layout->addWidget(row);
546   layout->addStretch(1);
547   setLayout(layout);
548
549   connect(projIconSel,SIGNAL(clicked()),
550           this,SLOT(selectProjectIcon()));
551   connect(m_srcSelectDir,SIGNAL(clicked()),
552           this,SLOT(selectSourceDir()));
553   connect(m_dstSelectDir,SIGNAL(clicked()),
554           this,SLOT(selectDestinationDir()));
555   connect(m_projName,SIGNAL(textChanged(const QString &)),SLOT(setProjectName(const QString &)));
556   connect(m_projBrief,SIGNAL(textChanged(const QString &)),SLOT(setProjectBrief(const QString &)));
557   connect(m_projNumber,SIGNAL(textChanged(const QString &)),SLOT(setProjectNumber(const QString &)));
558   connect(m_sourceDir,SIGNAL(textChanged(const QString &)),SLOT(setSourceDir(const QString &)));
559   connect(m_recursive,SIGNAL(stateChanged(int)),SLOT(setRecursiveScan(int)));
560   connect(m_destDir,SIGNAL(textChanged(const QString &)),SLOT(setDestinationDir(const QString &)));
561 }
562
563 void Step1::selectProjectIcon()
564 {
565   QString path = QFileInfo(MainWindow::instance().configFileName()).path();
566   QString iconName = QFileDialog::getOpenFileName(this,
567                                     tr("Select project icon/image"),path);
568   if (iconName.isEmpty())
569   {
570     m_projIconLab->setText(tr("No Project logo selected."));
571   }
572   else
573   {
574     QFile Fout(iconName);
575     if(!Fout.exists()) 
576     {
577       m_projIconLab->setText(tr("Sorry, cannot find file(")+iconName+QString::fromAscii(");"));
578     }
579     else
580     {
581       QPixmap pm(iconName);
582       if (!pm.isNull())
583       {
584         m_projIconLab->setPixmap(pm.scaledToHeight(55,Qt::SmoothTransformation));
585       }
586       else
587       {
588         m_projIconLab->setText(tr("Sorry, no preview available (")+iconName+QString::fromAscii(");"));
589       }
590     }
591   }
592   updateStringOption(m_modelData,STR_PROJECT_LOGO,iconName);
593 }
594
595 void Step1::selectSourceDir()
596 {
597   QString path = QFileInfo(MainWindow::instance().configFileName()).path();
598   QString dirName = QFileDialog::getExistingDirectory(this,
599         tr("Select source directory"),path);
600   QDir dir(path);
601   if (!MainWindow::instance().configFileName().isEmpty() && dir.exists())
602   {
603     dirName = dir.relativeFilePath(dirName);
604   }
605   if (dirName.isEmpty())
606   {
607     dirName=QString::fromAscii(".");
608   }
609   m_sourceDir->setText(dirName);
610 }
611
612 void Step1::selectDestinationDir()
613 {
614   QString path = QFileInfo(MainWindow::instance().configFileName()).path();
615   QString dirName = QFileDialog::getExistingDirectory(this,
616         tr("Select destination directory"),path);
617   QDir dir(path);
618   if (!MainWindow::instance().configFileName().isEmpty() && dir.exists())
619   {
620     dirName = dir.relativeFilePath(dirName);
621   }
622   if (dirName.isEmpty())
623   {
624     dirName=QString::fromAscii(".");
625   }
626   m_destDir->setText(dirName);
627 }
628
629 void Step1::setProjectName(const QString &name)
630 {
631   updateStringOption(m_modelData,STR_PROJECT_NAME,name);
632 }
633
634 void Step1::setProjectBrief(const QString &desc)
635 {
636   updateStringOption(m_modelData,STR_PROJECT_BRIEF,desc);
637 }
638
639 void Step1::setProjectNumber(const QString &num)
640 {
641   updateStringOption(m_modelData,STR_PROJECT_NUMBER,num);
642 }
643
644 void Step1::setSourceDir(const QString &dir)
645 {
646   Input *option = m_modelData[STR_INPUT];
647   if (option->value().toStringList().count()>0)
648   {
649     QStringList sl = option->value().toStringList();
650     if (sl[0]!=dir)
651     {
652       sl[0] = dir;
653       option->value() = sl;
654       option->update();
655     }
656   }
657   else
658   {
659     option->value() = QStringList() << dir;
660     option->update();
661   }
662 }
663
664 void Step1::setDestinationDir(const QString &dir)
665 {
666   updateStringOption(m_modelData,STR_OUTPUT_DIRECTORY,dir);
667 }
668
669 void Step1::setRecursiveScan(int s)
670 {
671   updateBoolOption(m_modelData,STR_RECURSIVE,s==Qt::Checked);
672 }
673
674 void Step1::init()
675 {
676   Input *option;
677   m_projName->setText(getStringOption(m_modelData,STR_PROJECT_NAME));
678   m_projBrief->setText(getStringOption(m_modelData,STR_PROJECT_BRIEF));
679   m_projNumber->setText(getStringOption(m_modelData,STR_PROJECT_NUMBER));
680   QString iconName = getStringOption(m_modelData,STR_PROJECT_LOGO);
681   if (!iconName.isEmpty())
682   {
683     QFile Fout(iconName);
684     if(!Fout.exists()) 
685     {
686       m_projIconLab->setText(tr("Sorry, cannot find file(")+iconName+QString::fromAscii(");"));
687     }
688     else
689     {
690       QPixmap pm(iconName);
691       if (!pm.isNull())
692       {
693         m_projIconLab->setPixmap(pm.scaledToHeight(55,Qt::SmoothTransformation));
694       }
695       else
696       {
697         m_projIconLab->setText(tr("Sorry, no preview available (")+iconName+QString::fromAscii(");"));
698       }
699     }
700   }
701   else
702   {
703     m_projIconLab->setText(tr("No Project logo selected."));
704   }
705   option = m_modelData[STR_INPUT];
706   if (option->value().toStringList().count()>0)
707   {
708     m_sourceDir->setText(option->value().toStringList().first());
709   }
710   m_recursive->setChecked(
711       getBoolOption(m_modelData,STR_RECURSIVE) ? Qt::Checked : Qt::Unchecked);
712   m_destDir->setText(getStringOption(m_modelData,STR_OUTPUT_DIRECTORY));
713 }
714
715
716 //==========================================================================
717
718 Step2::Step2(Wizard *wizard,const QHash<QString,Input*> &modelData) 
719   : m_wizard(wizard), m_modelData(modelData)
720 {
721   QRadioButton *r;
722   QVBoxLayout *layout = new QVBoxLayout(this);
723
724   //---------------------------------------------------
725   m_extractModeGroup = new QButtonGroup(this);
726   m_extractMode = new QGroupBox(this);
727   m_extractMode->setTitle(tr("Select the desired extraction mode:"));
728   QGridLayout *gbox = new QGridLayout( m_extractMode );
729   r = new QRadioButton(tr("Documented entities only"));
730   r->setChecked(true);
731   m_extractModeGroup->addButton(r, 0);
732   gbox->addWidget(r,1,0);
733   // 1 -> EXTRACT_ALL = NO
734   r = new QRadioButton(tr("All Entities"));
735   m_extractModeGroup->addButton(r, 1);
736   gbox->addWidget(r,2,0);
737   // 2 -> EXTRACT_ALL = YES
738   m_crossRef = new QCheckBox(m_extractMode);
739   m_crossRef->setText(tr("Include cross-referenced source code in the output"));
740   // m_crossRef -> SOURCE_BROWSER = YES/NO
741   gbox->addWidget(m_crossRef,3,0);
742   layout->addWidget(m_extractMode);
743   
744   //---------------------------------------------------
745   QFrame *f = new QFrame( this );
746   f->setFrameStyle( QFrame::HLine | QFrame::Sunken );
747   layout->addWidget(f);
748
749   m_optimizeLangGroup = new QButtonGroup(this);
750   m_optimizeLang = new QGroupBox(this);
751   m_optimizeLang->setTitle(tr("Select programming language to optimize the results for"));
752   gbox = new QGridLayout( m_optimizeLang ); 
753   
754   r = new QRadioButton(m_optimizeLang);
755   r->setText(tr("Optimize for C++ output"));
756   r->setChecked(true);
757   m_optimizeLangGroup->addButton(r, 0);
758   // 0 -> OPTIMIZE_OUTPUT_FOR_C = NO
759   //      OPTIMIZE_OUTPUT_JAVA  = NO
760   //      OPTIMIZE_FOR_FORTRAN  = NO
761   //      OPTIMIZE_OUTPUT_VHDL  = NO
762   //      CPP_CLI_SUPPORT       = NO
763   //      HIDE_SCOPE_NAMES      = NO
764   gbox->addWidget(r,0,0);
765   r = new QRadioButton(tr("Optimize for C++/CLI output"));
766   gbox->addWidget(r,1,0);
767   m_optimizeLangGroup->addButton(r, 1);
768   // 1 -> OPTIMIZE_OUTPUT_FOR_C = NO
769   //      OPTIMIZE_OUTPUT_JAVA  = NO
770   //      OPTIMIZE_FOR_FORTRAN  = NO
771   //      OPTIMIZE_OUTPUT_VHDL  = NO
772   //      CPP_CLI_SUPPORT       = YES
773   //      HIDE_SCOPE_NAMES      = NO
774   r = new QRadioButton(tr("Optimize for Java or C# output"));
775   m_optimizeLangGroup->addButton(r, 2);
776   // 2 -> OPTIMIZE_OUTPUT_FOR_C = NO
777   //      OPTIMIZE_OUTPUT_JAVA  = YES
778   //      OPTIMIZE_FOR_FORTRAN  = NO
779   //      OPTIMIZE_OUTPUT_VHDL  = NO
780   //      CPP_CLI_SUPPORT       = NO
781   //      HIDE_SCOPE_NAMES      = NO
782   gbox->addWidget(r,2,0);
783   r = new QRadioButton(tr("Optimize for C or PHP output"));
784   m_optimizeLangGroup->addButton(r, 3);
785   // 3 -> OPTIMIZE_OUTPUT_FOR_C = YES
786   //      OPTIMIZE_OUTPUT_JAVA  = NO
787   //      OPTIMIZE_FOR_FORTRAN  = NO
788   //      OPTIMIZE_OUTPUT_VHDL  = NO
789   //      CPP_CLI_SUPPORT       = NO
790   //      HIDE_SCOPE_NAMES      = YES
791   gbox->addWidget(r,3,0);
792   r = new QRadioButton(tr("Optimize for Fortran output"));
793   m_optimizeLangGroup->addButton(r, 4);
794   // 4 -> OPTIMIZE_OUTPUT_FOR_C = NO
795   //      OPTIMIZE_OUTPUT_JAVA  = NO
796   //      OPTIMIZE_FOR_FORTRAN  = YES
797   //      OPTIMIZE_OUTPUT_VHDL  = NO
798   //      CPP_CLI_SUPPORT       = NO
799   //      HIDE_SCOPE_NAMES      = NO
800   gbox->addWidget(r,4,0);
801   r = new QRadioButton(tr("Optimize for VHDL output"));
802   m_optimizeLangGroup->addButton(r, 5);
803   // 5 -> OPTIMIZE_OUTPUT_FOR_C = NO
804   //      OPTIMIZE_OUTPUT_JAVA  = NO
805   //      OPTIMIZE_FOR_FORTRAN  = NO
806   //      OPTIMIZE_OUTPUT_VHDL  = YES
807   //      CPP_CLI_SUPPORT       = NO
808   //      HIDE_SCOPE_NAMES      = NO
809   gbox->addWidget(r,5,0);
810
811   layout->addWidget(m_optimizeLang);
812   layout->addStretch(1);
813
814   connect(m_crossRef,SIGNAL(stateChanged(int)),
815           SLOT(changeCrossRefState(int)));
816   connect(m_optimizeLangGroup,SIGNAL(buttonClicked(int)),
817           SLOT(optimizeFor(int)));
818   connect(m_extractModeGroup,SIGNAL(buttonClicked(int)),
819           SLOT(extractMode(int)));
820 }
821
822
823 void Step2::optimizeFor(int choice)
824 {
825   for (int i=0;i<6;i++)
826   {
827     updateBoolOption(m_modelData,
828                      g_optimizeOptionNames[i],
829                      g_optimizeMapping[choice][i]);
830   }
831 }
832
833 void Step2::extractMode(int choice)
834 {
835   updateBoolOption(m_modelData,STR_EXTRACT_ALL,choice==1);
836 }
837
838 void Step2::changeCrossRefState(int choice)
839 {
840   updateBoolOption(m_modelData,STR_SOURCE_BROWSER,choice==Qt::Checked);
841 }
842
843 void Step2::init()
844 {
845   m_extractModeGroup->button(
846       getBoolOption(m_modelData,STR_EXTRACT_ALL) ? 1 : 0)->setChecked(true);
847   m_crossRef->setChecked(getBoolOption(m_modelData,STR_SOURCE_BROWSER));
848
849   int x=0;
850   if (getBoolOption(m_modelData,STR_CPP_CLI_SUPPORT))            x=1;
851   else if (getBoolOption(m_modelData,STR_OPTIMIZE_OUTPUT_JAVA))  x=2;
852   else if (getBoolOption(m_modelData,STR_OPTIMIZE_OUTPUT_FOR_C)) x=3;
853   else if (getBoolOption(m_modelData,STR_OPTIMIZE_FOR_FORTRAN))  x=4;
854   else if (getBoolOption(m_modelData,STR_OPTIMIZE_OUTPUT_VHDL))  x=5;
855   m_optimizeLangGroup->button(x)->setChecked(true);
856 }
857
858 //==========================================================================
859
860 Step3::Step3(Wizard *wizard,const QHash<QString,Input*> &modelData) 
861   : m_wizard(wizard), m_modelData(modelData)
862 {
863   QVBoxLayout *vbox = 0;
864   QRadioButton *r   = 0;
865
866   QGridLayout *gbox = new QGridLayout( this );
867   gbox->addWidget(new QLabel(tr("Select the output format(s) to generate")),0,0);
868   {
869     m_htmlOptions = new QGroupBox(tr("HTML"));
870     m_htmlOptions->setCheckable(true);
871     // GENERATE_HTML
872     m_htmlOptionsGroup = new QButtonGroup(m_htmlOptions);
873     QRadioButton *r = new QRadioButton(tr("plain HTML"));
874     r->setChecked(true);
875     m_htmlOptionsGroup->addButton(r, 0);
876     vbox = new QVBoxLayout;
877     vbox->addWidget(r);
878     r = new QRadioButton(tr("with navigation panel"));
879     m_htmlOptionsGroup->addButton(r, 1);
880     // GENERATE_TREEVIEW
881     vbox->addWidget(r);
882     r = new QRadioButton(tr("prepare for compressed HTML (.chm)"));
883     m_htmlOptionsGroup->addButton(r, 2);
884     // GENERATE_HTMLHELP
885     vbox->addWidget(r);
886     m_searchEnabled=new QCheckBox(tr("With search function"));
887     vbox->addWidget(m_searchEnabled);
888     // SEARCH_ENGINE
889     QHBoxLayout *hbox = new QHBoxLayout;
890     m_tuneColor=new QPushButton(tr("Change color..."));
891     hbox->addWidget(m_tuneColor);
892     hbox->addStretch(1);
893     vbox->addLayout(hbox);
894     m_htmlOptions->setLayout(vbox);
895     m_htmlOptions->setChecked(true);
896   }
897   gbox->addWidget(m_htmlOptions,1,0);
898
899   {
900     m_texOptions = new QGroupBox(tr("LaTeX"));
901     m_texOptions->setCheckable(true);
902     // GENERATE_LATEX
903     m_texOptionsGroup = new QButtonGroup(m_texOptions);
904     vbox = new QVBoxLayout;
905     r = new QRadioButton(tr("as intermediate format for hyperlinked PDF"));
906     m_texOptionsGroup->addButton(r, 0);
907     // PDF_HYPERLINKS = YES
908     r->setChecked(true);
909     vbox->addWidget(r);
910     r = new QRadioButton(tr("as intermediate format for PDF"));
911     m_texOptionsGroup->addButton(r, 1);
912     // PDF_HYPERLINKS = NO, USE_PDFLATEX = YES
913     vbox->addWidget(r);
914     r = new QRadioButton(tr("as intermediate format for PostScript"));
915     m_texOptionsGroup->addButton(r, 2);
916     // USE_PDFLATEX = NO
917     vbox->addWidget(r);
918     vbox->addStretch(1);
919     m_texOptions->setLayout(vbox);
920     m_texOptions->setChecked(true);
921   }
922   gbox->addWidget(m_texOptions,2,0);
923
924   m_manEnabled=new QCheckBox(tr("Man pages"));
925   // GENERATE_MAN
926   m_rtfEnabled=new QCheckBox(tr("Rich Text Format (RTF)"));
927   // GENERATE_RTF
928   m_xmlEnabled=new QCheckBox(tr("XML"));
929   // GENERATE_XML
930   gbox->addWidget(m_manEnabled,3,0);
931   gbox->addWidget(m_rtfEnabled,4,0);
932   gbox->addWidget(m_xmlEnabled,5,0);
933
934   gbox->setRowStretch(6,1);
935   connect(m_htmlOptions,SIGNAL(toggled(bool)),SLOT(setHtmlEnabled(bool)));
936   connect(m_texOptions,SIGNAL(toggled(bool)),SLOT(setLatexEnabled(bool)));
937   connect(m_manEnabled,SIGNAL(stateChanged(int)),SLOT(setManEnabled(int)));
938   connect(m_rtfEnabled,SIGNAL(stateChanged(int)),SLOT(setRtfEnabled(int)));
939   connect(m_xmlEnabled,SIGNAL(stateChanged(int)),SLOT(setXmlEnabled(int)));
940   connect(m_searchEnabled,SIGNAL(stateChanged(int)),SLOT(setSearchEnabled(int)));
941   connect(m_htmlOptionsGroup,SIGNAL(buttonClicked(int)),
942           SLOT(setHtmlOptions(int)));
943   connect(m_texOptionsGroup,SIGNAL(buttonClicked(int)),
944           SLOT(setLatexOptions(int)));
945   connect(m_tuneColor,SIGNAL(clicked()),SLOT(tuneColorDialog()));
946 }
947
948 void Step3::tuneColorDialog()
949 {
950   int hue = getIntOption(m_modelData,STR_HTML_COLORSTYLE_HUE);
951   int sat = getIntOption(m_modelData,STR_HTML_COLORSTYLE_SAT);
952   int gam = getIntOption(m_modelData,STR_HTML_COLORSTYLE_GAMMA);
953   TuneColorDialog tuneColor(hue,sat,gam,this);
954   if (tuneColor.exec()==QDialog::Accepted)
955   {
956     updateIntOption(m_modelData,STR_HTML_COLORSTYLE_HUE,tuneColor.getHue());
957     updateIntOption(m_modelData,STR_HTML_COLORSTYLE_SAT,tuneColor.getSaturation());
958     updateIntOption(m_modelData,STR_HTML_COLORSTYLE_GAMMA,tuneColor.getGamma());
959   }
960 }
961
962 void Step3::setHtmlEnabled(bool b)
963 {
964   updateBoolOption(m_modelData,STR_GENERATE_HTML,b);
965 }
966
967 void Step3::setLatexEnabled(bool b)
968 {
969   updateBoolOption(m_modelData,STR_GENERATE_LATEX,b);
970 }
971
972 void Step3::setManEnabled(int state)
973 {
974   updateBoolOption(m_modelData,STR_GENERATE_MAN,state==Qt::Checked);
975 }
976
977 void Step3::setRtfEnabled(int state)
978 {
979   updateBoolOption(m_modelData,STR_GENERATE_RTF,state==Qt::Checked);
980 }
981
982 void Step3::setXmlEnabled(int state)
983 {
984   updateBoolOption(m_modelData,STR_GENERATE_XML,state==Qt::Checked);
985 }
986
987 void Step3::setSearchEnabled(int state)
988 {
989   updateBoolOption(m_modelData,STR_SEARCHENGINE,state==Qt::Checked);
990 }
991
992 void Step3::setHtmlOptions(int id)
993 {
994   if (id==0) // plain HTML
995   {
996     updateBoolOption(m_modelData,STR_GENERATE_HTMLHELP,false);
997     updateBoolOption(m_modelData,STR_GENERATE_TREEVIEW,false);
998   }
999   else if (id==1) // with navigation tree
1000   {
1001     updateBoolOption(m_modelData,STR_GENERATE_HTMLHELP,false);
1002     updateBoolOption(m_modelData,STR_GENERATE_TREEVIEW,true);
1003   }
1004   else if (id==2) // with compiled help
1005   {
1006     updateBoolOption(m_modelData,STR_GENERATE_HTMLHELP,true);
1007     updateBoolOption(m_modelData,STR_GENERATE_TREEVIEW,false);
1008   }
1009 }
1010
1011 void Step3::setLatexOptions(int id)
1012 {
1013   if (id==0) // hyperlinked PDF
1014   {
1015     updateBoolOption(m_modelData,STR_USE_PDFLATEX,true);
1016     updateBoolOption(m_modelData,STR_PDF_HYPERLINKS,true);
1017   }
1018   else if (id==1) // PDF
1019   {
1020     updateBoolOption(m_modelData,STR_USE_PDFLATEX,true);
1021     updateBoolOption(m_modelData,STR_PDF_HYPERLINKS,false);
1022   }
1023   else if (id==2) // PostScript
1024   {
1025     updateBoolOption(m_modelData,STR_USE_PDFLATEX,false);
1026     updateBoolOption(m_modelData,STR_PDF_HYPERLINKS,false);
1027   }
1028 }
1029
1030 void Step3::init()
1031 {
1032   m_htmlOptions->setChecked(getBoolOption(m_modelData,STR_GENERATE_HTML));
1033   m_texOptions->setChecked(getBoolOption(m_modelData,STR_GENERATE_LATEX));
1034   m_manEnabled->setChecked(getBoolOption(m_modelData,STR_GENERATE_MAN));
1035   m_rtfEnabled->setChecked(getBoolOption(m_modelData,STR_GENERATE_RTF));
1036   m_xmlEnabled->setChecked(getBoolOption(m_modelData,STR_GENERATE_XML));
1037   m_searchEnabled->setChecked(getBoolOption(m_modelData,STR_SEARCHENGINE));
1038   if (getBoolOption(m_modelData,STR_GENERATE_HTMLHELP))
1039   {
1040     m_htmlOptionsGroup->button(2)->setChecked(true); // compiled help
1041   }
1042   else if (getBoolOption(m_modelData,STR_GENERATE_TREEVIEW))
1043   {
1044     m_htmlOptionsGroup->button(1)->setChecked(true); // navigation tree
1045   }
1046   else
1047   {
1048     m_htmlOptionsGroup->button(0)->setChecked(true); // plain HTML
1049   }
1050   if (!getBoolOption(m_modelData,STR_USE_PDFLATEX))
1051   {
1052     m_texOptionsGroup->button(2)->setChecked(true); // PostScript
1053   }
1054   else if (!getBoolOption(m_modelData,STR_PDF_HYPERLINKS))
1055   {
1056     m_texOptionsGroup->button(1)->setChecked(true); // Plain PDF
1057   }
1058   else
1059   {
1060     m_texOptionsGroup->button(0)->setChecked(true); // PDF with hyperlinks
1061   }
1062 }
1063
1064 //==========================================================================
1065
1066 Step4::Step4(Wizard *wizard,const QHash<QString,Input*> &modelData) 
1067   : m_wizard(wizard), m_modelData(modelData)
1068 {
1069   m_diagramModeGroup = new QButtonGroup(this);
1070   QGridLayout *gbox = new QGridLayout( this );
1071   gbox->addWidget(new QLabel(tr("Diagrams to generate")),0,0);
1072
1073   QRadioButton *rb = new QRadioButton(tr("No diagrams"));
1074   m_diagramModeGroup->addButton(rb, 0);
1075   gbox->addWidget(rb,1,0);
1076   // CLASS_DIAGRAMS = NO, HAVE_DOT = NO
1077   rb->setChecked(true);
1078   rb = new QRadioButton(tr("Use built-in class diagram generator"));
1079   m_diagramModeGroup->addButton(rb, 1);
1080   // CLASS_DIAGRAMS = YES, HAVE_DOT = NO
1081   gbox->addWidget(rb,2,0);
1082   rb = new QRadioButton(tr("Use dot tool from the GraphViz package"));
1083   m_diagramModeGroup->addButton(rb, 2);
1084   gbox->addWidget(rb,3,0);
1085   // CLASS_DIAGRAMS = NO, HAVE_DOT = YES
1086
1087   m_dotGroup = new QGroupBox(tr("Dot graphs to generate"));
1088     QVBoxLayout *vbox = new QVBoxLayout;
1089     m_dotClass=new QCheckBox(tr("Class diagrams"));
1090     // CLASS_GRAPH
1091     m_dotCollaboration=new QCheckBox(tr("Collaboration diagrams"));
1092     // COLLABORATION_GRAPH
1093     m_dotInheritance=new QCheckBox(tr("Overall Class hierarchy"));
1094     // GRAPHICAL_HIERARCHY
1095     m_dotInclude=new QCheckBox(tr("Include dependency graphs"));
1096     // INCLUDE_GRAPH
1097     m_dotIncludedBy=new QCheckBox(tr("Included by dependency graphs"));
1098     // INCLUDED_BY_GRAPH
1099     m_dotCall=new QCheckBox(tr("Call graphs"));
1100     // CALL_GRAPH
1101     m_dotCaller=new QCheckBox(tr("Called by graphs"));
1102     // CALLER_GRAPH
1103     vbox->addWidget(m_dotClass);
1104     vbox->addWidget(m_dotCollaboration);
1105     vbox->addWidget(m_dotInheritance);
1106     vbox->addWidget(m_dotInclude);
1107     vbox->addWidget(m_dotIncludedBy);
1108     vbox->addWidget(m_dotCall);
1109     vbox->addWidget(m_dotCaller);
1110     vbox->addStretch(1);
1111     m_dotGroup->setLayout(vbox);
1112     m_dotClass->setChecked(true);
1113     m_dotGroup->setEnabled(false);
1114   gbox->addWidget(m_dotGroup,4,0);
1115
1116   m_dotInclude->setChecked(true);
1117   m_dotCollaboration->setChecked(true);
1118   gbox->setRowStretch(5,1);
1119
1120   connect(m_diagramModeGroup,SIGNAL(buttonClicked(int)),
1121           this,SLOT(diagramModeChanged(int)));
1122   connect(m_dotClass,SIGNAL(stateChanged(int)),
1123           this,SLOT(setClassGraphEnabled(int)));
1124   connect(m_dotCollaboration,SIGNAL(stateChanged(int)),
1125           this,SLOT(setCollaborationGraphEnabled(int)));
1126   connect(m_dotInheritance,SIGNAL(stateChanged(int)),
1127           this,SLOT(setGraphicalHierarchyEnabled(int)));
1128   connect(m_dotInclude,SIGNAL(stateChanged(int)),
1129           this,SLOT(setIncludeGraphEnabled(int)));
1130   connect(m_dotIncludedBy,SIGNAL(stateChanged(int)),
1131           this,SLOT(setIncludedByGraphEnabled(int)));
1132   connect(m_dotCall,SIGNAL(stateChanged(int)),
1133           this,SLOT(setCallGraphEnabled(int)));
1134   connect(m_dotCaller,SIGNAL(stateChanged(int)),
1135           this,SLOT(setCallerGraphEnabled(int)));
1136 }
1137
1138 void Step4::diagramModeChanged(int id)
1139 {
1140   if (id==0) // no diagrams
1141   {
1142     updateBoolOption(m_modelData,STR_HAVE_DOT,false);
1143     updateBoolOption(m_modelData,STR_CLASS_DIAGRAMS,false);
1144   }
1145   else if (id==1) // builtin diagrams
1146   {
1147     updateBoolOption(m_modelData,STR_HAVE_DOT,false);
1148     updateBoolOption(m_modelData,STR_CLASS_DIAGRAMS,true);
1149   }
1150   else if (id==2) // dot diagrams
1151   {
1152     updateBoolOption(m_modelData,STR_HAVE_DOT,true);
1153     updateBoolOption(m_modelData,STR_CLASS_DIAGRAMS,false);
1154   }
1155   m_dotGroup->setEnabled(id==2);
1156 }
1157
1158 void Step4::setClassGraphEnabled(int state)
1159 {
1160   updateBoolOption(m_modelData,STR_CLASS_GRAPH,state==Qt::Checked);
1161 }
1162
1163 void Step4::setCollaborationGraphEnabled(int state)
1164 {
1165   updateBoolOption(m_modelData,STR_COLLABORATION_GRAPH,state==Qt::Checked);
1166 }
1167
1168 void Step4::setGraphicalHierarchyEnabled(int state)
1169 {
1170   updateBoolOption(m_modelData,STR_GRAPHICAL_HIERARCHY,state==Qt::Checked);
1171 }
1172
1173 void Step4::setIncludeGraphEnabled(int state)
1174 {
1175   updateBoolOption(m_modelData,STR_INCLUDE_GRAPH,state==Qt::Checked);
1176 }
1177
1178 void Step4::setIncludedByGraphEnabled(int state)
1179 {
1180   updateBoolOption(m_modelData,STR_INCLUDED_BY_GRAPH,state==Qt::Checked);
1181 }
1182
1183 void Step4::setCallGraphEnabled(int state)
1184 {
1185   updateBoolOption(m_modelData,STR_CALL_GRAPH,state==Qt::Checked);
1186 }
1187
1188 void Step4::setCallerGraphEnabled(int state)
1189 {
1190   updateBoolOption(m_modelData,STR_CALLER_GRAPH,state==Qt::Checked);
1191 }
1192
1193 void Step4::init()
1194 {
1195   if (getBoolOption(m_modelData,STR_HAVE_DOT))
1196   {
1197     m_diagramModeGroup->button(2)->setChecked(true); // Dot
1198   }
1199   else if (getBoolOption(m_modelData,STR_CLASS_DIAGRAMS))
1200   {
1201     m_diagramModeGroup->button(1)->setChecked(true); // Builtin diagrams
1202   }
1203   else
1204   {
1205     m_diagramModeGroup->button(0)->setChecked(true); // no diagrams
1206   }
1207   m_dotClass->setChecked(getBoolOption(m_modelData,STR_CLASS_GRAPH));
1208   m_dotCollaboration->setChecked(getBoolOption(m_modelData,STR_COLLABORATION_GRAPH));
1209   m_dotInheritance->setChecked(getBoolOption(m_modelData,STR_GRAPHICAL_HIERARCHY));
1210   m_dotInclude->setChecked(getBoolOption(m_modelData,STR_INCLUDE_GRAPH));
1211   m_dotIncludedBy->setChecked(getBoolOption(m_modelData,STR_INCLUDED_BY_GRAPH));
1212   m_dotCall->setChecked(getBoolOption(m_modelData,STR_CALL_GRAPH));
1213   m_dotCaller->setChecked(getBoolOption(m_modelData,STR_CALLER_GRAPH));
1214 }
1215
1216 //==========================================================================
1217
1218 Wizard::Wizard(const QHash<QString,Input*> &modelData, QWidget *parent) : 
1219   QSplitter(parent), m_modelData(modelData)
1220 {
1221   m_treeWidget = new QTreeWidget;
1222   m_treeWidget->setColumnCount(1);
1223   m_treeWidget->setHeaderLabels(QStringList() << QString::fromAscii("Topics"));
1224   QList<QTreeWidgetItem*> items;
1225   items.append(new QTreeWidgetItem((QTreeWidget*)0,QStringList(tr("Project"))));
1226   items.append(new QTreeWidgetItem((QTreeWidget*)0,QStringList(tr("Mode"))));
1227   items.append(new QTreeWidgetItem((QTreeWidget*)0,QStringList(tr("Output"))));
1228   items.append(new QTreeWidgetItem((QTreeWidget*)0,QStringList(tr("Diagrams"))));
1229   m_treeWidget->insertTopLevelItems(0,items);
1230
1231   m_topicStack = new QStackedWidget;
1232   m_step1 = new Step1(this,modelData);
1233   m_step2 = new Step2(this,modelData);
1234   m_step3 = new Step3(this,modelData);
1235   m_step4 = new Step4(this,modelData);
1236   m_topicStack->addWidget(m_step1);
1237   m_topicStack->addWidget(m_step2);
1238   m_topicStack->addWidget(m_step3);
1239   m_topicStack->addWidget(m_step4);
1240
1241   QWidget *rightSide = new QWidget;
1242   QGridLayout *grid = new QGridLayout(rightSide);
1243   m_prev = new QPushButton(tr("Previous"));
1244   m_prev->setEnabled(false);
1245   m_next = new QPushButton(tr("Next"));
1246   grid->addWidget(m_topicStack,0,0,1,2);
1247   grid->addWidget(m_prev,1,0,Qt::AlignLeft);
1248   grid->addWidget(m_next,1,1,Qt::AlignRight);
1249   grid->setColumnStretch(0,1);
1250   grid->setRowStretch(0,1);
1251   addWidget(m_treeWidget);
1252   addWidget(rightSide);
1253
1254   connect(m_treeWidget,
1255           SIGNAL(currentItemChanged(QTreeWidgetItem *,QTreeWidgetItem *)),
1256           SLOT(activateTopic(QTreeWidgetItem *,QTreeWidgetItem *)));
1257   connect(m_next,SIGNAL(clicked()),SLOT(nextTopic()));
1258   connect(m_prev,SIGNAL(clicked()),SLOT(prevTopic()));
1259
1260   refresh();
1261 }
1262
1263 Wizard::~Wizard()
1264 {
1265 }
1266
1267 void Wizard::activateTopic(QTreeWidgetItem *item,QTreeWidgetItem *)
1268 {
1269   if (item)
1270   {
1271     
1272     QString label = item->text(0);
1273     if (label==tr("Project"))
1274     {
1275       m_topicStack->setCurrentWidget(m_step1);
1276       m_prev->setEnabled(false);
1277       m_next->setEnabled(true);
1278     }
1279     else if (label==tr("Mode"))
1280     {
1281       m_topicStack->setCurrentWidget(m_step2);
1282       m_prev->setEnabled(true);
1283       m_next->setEnabled(true);
1284     }
1285     else if (label==tr("Output"))
1286     {
1287       m_topicStack->setCurrentWidget(m_step3);
1288       m_prev->setEnabled(true);
1289       m_next->setEnabled(true);
1290     }
1291     else if (label==tr("Diagrams"))
1292     {
1293       m_topicStack->setCurrentWidget(m_step4);
1294       m_prev->setEnabled(true);
1295       m_next->setEnabled(true);
1296     }
1297   }
1298 }
1299
1300 void Wizard::nextTopic()
1301 {
1302   if (m_topicStack->currentIndex()+1==m_topicStack->count()) // last topic
1303   {
1304     done();
1305   }
1306   else
1307   {
1308     m_topicStack->setCurrentIndex(m_topicStack->currentIndex()+1);
1309     m_next->setEnabled(m_topicStack->count()!=m_topicStack->currentIndex()+1);
1310     m_prev->setEnabled(m_topicStack->currentIndex()!=0);
1311     m_treeWidget->setCurrentItem(m_treeWidget->invisibleRootItem()->child(m_topicStack->currentIndex()));
1312   }
1313 }
1314
1315 void Wizard::prevTopic()
1316 {
1317   m_topicStack->setCurrentIndex(m_topicStack->currentIndex()-1);
1318   m_next->setEnabled(m_topicStack->count()!=m_topicStack->currentIndex()+1);
1319   m_prev->setEnabled(m_topicStack->currentIndex()!=0);
1320   m_treeWidget->setCurrentItem(m_treeWidget->invisibleRootItem()->child(m_topicStack->currentIndex()));
1321 }
1322
1323 void Wizard::refresh()
1324 {
1325   m_treeWidget->setCurrentItem(m_treeWidget->invisibleRootItem()->child(0));
1326   m_step1->init();
1327   m_step2->init();
1328   m_step3->init();
1329   m_step4->init();
1330 }