00001 #include "gui.h"
00002 
00003 #include "guifactory.h"
00004 #include "widgets/taskdetailswidget.h"
00005 #include "widgets/resourcedetailswidget.h"
00006 #include "widgets/resourcereservationwidget.h"
00007 #include "widgets/projectdetailswidget.h"
00008 #include "widgets/widgetdialog.h"
00009 #include "widgets/invitationselectionwidget.h"
00010 #include "widgets/overviewwidget.h"
00011 
00012 #include <control/controldata.h>
00013 #include <control/controllerinterface.h>
00014 #include <control/models/invitationmodel.h>
00015 
00016 #include <QLabel>
00017 #include <QMessageBox>
00018 #include <QMenuBar>
00019 #include <QFileDialog>
00020 #include <QInputDialog>
00021 #include <QTreeView>
00022 #include <QStatusBar>
00023 #include <QDebug>
00024 
00025 using namespace ui;
00026 
00027 Gui::Gui() : overviewWidget(new OverviewWidget())
00028 {
00029     userLabel = GuiFactory::createLabel(window.statusBar());
00030     timeLabel = GuiFactory::createLabel(window.statusBar());
00031     window.statusBar()->addPermanentWidget(userLabel);
00032     window.statusBar()->addPermanentWidget(timeLabel);
00033 
00034     window.setCentralWidget(overviewWidget);
00035 
00036     
00037     
00038     setUser(user());
00039 }
00040 
00041 void Gui::loadControllers(const QList<control::ControllerInterface*>& c)
00042 {
00043     UiInterface::loadControllers(c);
00044 
00045     window.menuBar()->clear();
00046     QMap<QString, QMenu*> menuMap;
00047 
00048     QList<control::ControllerInterface::DataType> predefinedMenus;
00049     predefinedMenus << control::ControllerInterface::FileData;
00050     predefinedMenus << control::ControllerInterface::UserData;
00051     predefinedMenus << control::ControllerInterface::TaskData;
00052     predefinedMenus << control::ControllerInterface::ProjectData;
00053     predefinedMenus << control::ControllerInterface::ResourceData;
00054     predefinedMenus << control::ControllerInterface::ReservationData;
00055     predefinedMenus << control::ControllerInterface::InvitationData;
00056 
00057     Q_FOREACH (control::ControllerInterface::DataType type, predefinedMenus)
00058     {
00059         QString menuName = control::ControllerInterface::dataTypeToString(type);
00060         QMenu* menu = new QMenu(menuName);
00061         window.menuBar()->addMenu(menu);
00062         menuMap[menuName] = menu;
00063     }
00064 
00065     Q_FOREACH (control::ControllerInterface* controller, c)
00066     {
00067         if (!controller->userCanExecute())
00068             continue;
00069 
00070         QString dataType = controller->dataTypeString();
00071 
00072         if (!menuMap.contains(dataType))
00073         {
00074             QMenu* menu = new QMenu(dataType);
00075             window.menuBar()->addMenu(menu);
00076             menuMap[dataType] = menu;
00077         }
00078 
00079         QAction* action = new QAction(controller->description(), &window);
00080         menuMap[dataType]->addAction(action);
00081         connect(action, SIGNAL(triggered(bool)), controller, SLOT(run()));
00082     }
00083 }
00084 
00085 bool Gui::askQuestion(const QString& before, QAbstractItemModel* model,
00086                       const QString& after)
00087 {
00088     if (model == 0)
00089     {
00090         QMessageBox dialog;
00091 
00092         dialog.setText(before);
00093         dialog.setInformativeText(after);
00094         dialog.setIcon(QMessageBox::Question);
00095         dialog.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
00096 
00097         return dialog.exec() == QMessageBox::Yes;
00098     }
00099     else
00100     {
00101         QWidget* w = new QWidget();
00102         QVBoxLayout* layout = new QVBoxLayout(w);
00103         layout->addWidget(new QLabel(before));
00104 
00105         QAbstractItemView* view = GuiFactory::createView(model);
00106         view->setModel(model);
00107         layout->addWidget(view);
00108 
00109         if (!after.isEmpty())
00110             layout->addWidget(new QLabel(after));
00111 
00112         WidgetDialog dialog(w, &window, QStringList() << "Yes" << "No");
00113         connect(view, SIGNAL(doubleClicked(QModelIndex)), &dialog, SLOT(accept()));
00114 
00115         return dialog.exec() == QDialog::Accepted;
00116     }
00117 }
00118 
00119 control::data::SelectionData Gui::getSelection(const QString& before,
00120                                                QAbstractItemModel* model,
00121                                                SelectionMode mode,
00122                                                const QString& after)
00123 {
00124     QWidget* w = new QWidget();
00125     QVBoxLayout* layout = new QVBoxLayout(w);
00126 
00127     if (!before.isEmpty())
00128         layout->addWidget(new QLabel(before));
00129 
00130     QAbstractItemView* view = GuiFactory::createView(model);
00131     layout->addWidget(view);
00132 
00133     if (mode == SingleSelection)
00134         view->setSelectionMode(QAbstractItemView::SingleSelection);
00135     else
00136         view->setSelectionMode(QAbstractItemView::MultiSelection);
00137 
00138     if (!after.isEmpty())
00139         layout->addWidget(new QLabel(after));
00140 
00141     WidgetDialog dialog(w, &window);
00142     connect(view, SIGNAL(doubleClicked(QModelIndex)), &dialog, SLOT(accept()));
00143     control::data::SelectionData ret;
00144 
00145     if (dialog.exec() == QDialog::Accepted)
00146     {
00147         if (view->selectionModel() != 0)
00148             ret.selection = view->selectionModel()->selectedRows();
00149 
00150         ret.processData = true;
00151     }
00152 
00153     return ret;
00154 }
00155 
00156 control::data::TaskDetails Gui::getTaskDetails(
00157                                 const control::data::TaskRepresentation& rep)
00158 {
00159     TaskDetailsWidget* w = new TaskDetailsWidget(rep.type);
00160     w->setTasks(rep.subTasks);
00161     w->setDetails(rep.details);
00162     w->setUserRequirements(rep.userReqs);
00163     w->setResourceRequirements(rep.resourceReqs);
00164 
00165     WidgetDialog dialog(w, &window);
00166     control::data::TaskDetails ret;
00167 
00168     if (dialog.exec() == QDialog::Accepted)
00169     {
00170         ret = w->currentDetails();
00171         ret.processData = true;
00172     }
00173 
00174     return ret;
00175 }
00176 
00177 
00178 control::data::ReservationDetails Gui::getReservationDetails
00179                                 (control::ResourceReservationModel* reservations)
00180 {
00181     ResourceReservationWidget* w = new ResourceReservationWidget();
00182     w->setResourceReservations(reservations);
00183     WidgetDialog dialog(w, &window);
00184 
00185     control::data::ReservationDetails ret;
00186 
00187     if (dialog.exec() == QDialog::Accepted)
00188     {
00189         ret = w->currentDetails();
00190         ret.processData = true;
00191     }
00192 
00193     return ret;
00194 }
00195 
00196 
00197 control::data::ResourceDetails Gui::getResourceDetails(const QStringList& types)
00198 {
00199     ResourceDetailsWidget* w = new ResourceDetailsWidget(types);
00200     WidgetDialog dialog(w, &window);
00201     control::data::ResourceDetails ret;
00202 
00203     if (dialog.exec() == QDialog::Accepted)
00204     {
00205         ret = w->currentDetails();
00206         ret.processData = true;
00207     }
00208 
00209     return ret;
00210 }
00211 
00212 control::data::ProjectDetails Gui::getProjectDetails()
00213 {
00214     ProjectDetailsWidget* w = new ProjectDetailsWidget();
00215     WidgetDialog dialog(w, &window);
00216 
00217     control::data::ProjectDetails ret;
00218 
00219     if (dialog.exec() == QDialog::Accepted)
00220     {
00221         ret = w->currentDetails();
00222         ret.processData = true;
00223     }
00224 
00225     return ret;
00226 }
00227 
00228 control::data::StringInputData Gui::getChoice(const QStringList& options,
00229                                               const QString& message)
00230 {
00231     bool ok;
00232     QString choice = QInputDialog::getItem(&window, "Make a choice", message, options,
00233                                            0, false, &ok);
00234 
00235     control::data::StringInputData ret;
00236     ret.data = choice;
00237     ret.processData = ok;
00238     return ret;
00239 }
00240 
00241 control::data::StringInputData Gui::showTaskDetails(
00242                              const control::data::TaskRepresentation& rep,
00243                              const QStringList& options, bool editMode)
00244 {
00245     control::data::StringInputData ret;
00246     TaskDetailsWidget* w = new TaskDetailsWidget(rep.type);
00247     w->setTasks(rep.subTasks);
00248     w->setDetails(rep.details);
00249     w->setEditMode(editMode);
00250     w->setUserRequirements(rep.userReqs);
00251     w->setResourceRequirements(rep.resourceReqs);
00252     WidgetDialog dialog(w, &window, options);
00253 
00254     if (dialog.exec() == QDialog::Accepted)
00255     {
00256         ret.processData = true;
00257         ret.data = dialog.chosenOption();
00258     }
00259     else
00260         ret.processData = false;
00261 
00262     return ret;
00263 }
00264 
00265 control::data::SelectionData Gui::getInvitationSelection(
00266                                                 control::InvitationModel* pending,
00267                                                 control::InvitationModel* accepted)
00268 {
00269     InvitationSelectionWidget* w = new InvitationSelectionWidget();
00270     w->setPendingModel(pending);
00271     w->setAcceptedModel(accepted);
00272 
00273     WidgetDialog dialog(w, &window);
00274     connect(w, SIGNAL(doubleClicked()), &dialog, SLOT(accept()));
00275 
00276     control::data::SelectionData data;
00277 
00278     if (dialog.exec() == QDialog::Accepted)
00279     {
00280         data.processData = true;
00281         data.selection = w->selection();
00282     }
00283     else
00284         data.processData = false;
00285 
00286     return data;
00287 }
00288 
00289 void Gui::showModel(QAbstractItemModel* model, const QString& message)
00290 {
00291     QWidget* w = new QWidget();
00292     QVBoxLayout* layout = new QVBoxLayout(w);
00293 
00294     if (!message.isEmpty())
00295         layout->addWidget(new QLabel(message));
00296 
00297     if (model != 0)
00298     {
00299         QAbstractItemView* view = GuiFactory::createView(model);
00300         view->setModel(model);
00301         layout->addWidget(view);
00302     }
00303 
00304     WidgetDialog dialog(w, &window, QStringList("Ok"));
00305 
00306     dialog.exec();
00307 }
00308 
00309 void Gui::setOverview(const control::data::OverviewDetails& details)
00310 {
00311     overviewWidget->setDetails(details);
00312 }
00313 
00314 void Gui::showError(const QString& message)
00315 {
00316     QMessageBox::critical(&window, "Error", message);
00317 }
00318 
00319 void Gui::showWarning(const QString& message)
00320 {
00321     QMessageBox::warning(&window, "Warning", message);
00322 }
00323 
00324 void Gui::showMessage(const QString& message)
00325 {
00326     QMessageBox::information(&window, "Message", message);
00327 }
00328 
00329 control::data::MinMaxDurationData Gui::getMinMaxDuration(const QString& message)
00330 {
00331     QWidget* w = new QWidget();
00332     QVBoxLayout* layout = new QVBoxLayout(w);
00333 
00334     layout->addWidget(new QLabel(message));
00335 
00336     QGroupBox* minGroup = new QGroupBox("Minimum duration", w);
00337     minGroup->setCheckable(true);
00338     QVBoxLayout* minLayout = new QVBoxLayout(minGroup);
00339     DurationWidget* minDuration = new DurationWidget();
00340     minLayout->addWidget(minDuration);
00341     layout->addWidget(minGroup);
00342 
00343     QGroupBox* maxGroup = new QGroupBox("Maximum duration", w);
00344     maxGroup->setCheckable(true);
00345     QVBoxLayout* maxLayout = new QVBoxLayout(maxGroup);
00346     DurationWidget* maxDuration = new DurationWidget();
00347     maxLayout->addWidget(maxDuration);
00348     layout->addWidget(maxGroup);
00349 
00350     WidgetDialog dialog(w, &window);
00351     control::data::MinMaxDurationData ret;
00352 
00353     if (dialog.exec() == QDialog::Accepted)
00354     {
00355         ret.processData = true;
00356         ret.minDurationSet = minGroup->isChecked();
00357         ret.maxDurationSet = maxGroup->isChecked();
00358 
00359         if (ret.minDurationSet)
00360             ret.minDuration = minDuration->currentDuration();
00361 
00362         if (ret.maxDurationSet)
00363             ret.maxDuration = maxDuration->currentDuration();
00364     }
00365     else
00366         ret.processData = false;
00367 
00368     return ret;
00369 }
00370 
00371 control::data::StringInputData Gui::getText(const QString& message)
00372 {
00373     control::data::StringInputData ret;
00374     bool ok;
00375     ret.data = QInputDialog::getText(&window, "Enter text", message,
00376                                      QLineEdit::Normal, "", &ok);
00377     ret.processData = ok;
00378     return ret;
00379 }
00380 
00381 control::data::IntInputData Gui::getInt(const QString& message,
00382                                         int value,
00383                                         int minValue,
00384                                         int maxValue)
00385 {
00386     control::data::IntInputData ret;
00387     bool ok;
00388     ret.data = QInputDialog::getInteger(&window, "Enter number", message, value,
00389                                         minValue, maxValue, 1, &ok);
00390     ret.processData = ok;
00391     return ret;
00392 }
00393 
00394 QString Gui::getOpenFileName(const QString& dir, const QString& filter)
00395 {
00396     return QFileDialog::getOpenFileName(&window, "Open File", dir, filter);
00397 }
00398 
00399 QString Gui::getSaveFileName(const QString& dir, const QString& filter)
00400 {
00401     return QFileDialog::getSaveFileName(&window, "Open File", dir, filter);
00402 }
00403 
00404 control::data::DateTimeInputData Gui::getDateTime(const QString& message)
00405 {
00406     QWidget* w = new QWidget();
00407     QVBoxLayout* layout = new QVBoxLayout(w);
00408 
00409     if (!message.isEmpty())
00410         layout->addWidget(new QLabel(message));
00411 
00412     QDateTimeEdit* edit = GuiFactory::createDateTimeEdit();
00413     layout->addWidget(edit);
00414     GuiFactory::initDateTimeEdit(edit);
00415 
00416     WidgetDialog dlg(w, &window);
00417     control::data::DateTimeInputData ret;
00418 
00419     if (dlg.exec() == QDialog::Accepted)
00420     {
00421         ret.processData = true;
00422         ret.data = edit->dateTime();
00423     }
00424     else
00425         ret.processData = false;
00426 
00427     return ret;
00428 }
00429 
00430 void Gui::start()
00431 {
00432     Q_FOREACH (control::ControllerInterface* c, controllers)
00433     {
00434         if (c->actionType() == control::ControllerInterface::ViewAction &&
00435             c->dataType() == control::ControllerInterface::NoData)
00436         {
00437             c->run();
00438         }
00439     }
00440 
00441     window.showMaximized();
00442 }
00443 
00444 void Gui::setUsername(const QString& name)
00445 {
00446     userLabel->setText(QString("Current user: %1").arg(name));
00447 }
00448 
00449 void Gui::setTime(const QDateTime& time)
00450 {
00451     timeLabel->setText(QString("Current time: %1").arg(time.toString()));
00452 }
00453 
00454