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