added very simple html page.
[medard] / src / mainwindow.cpp
1 /*
2  *  Medard for Maemo.
3  *  Copyright (C) 2011 Roman Moravcik
4  *
5  *  This program is free software; you can redistribute it and/or modify
6  *  it under the terms of the GNU General Public License as published by
7  *  the Free Software Foundation; either version 2 of the License, or
8  *  (at your option) any later version.
9  *
10  *  This program is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU General Public License for more details.
14  *
15  *  You should have received a copy of the GNU General Public License
16  *  along with this program; if not, write to the Free Software
17  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  */
19
20 #ifdef MEEGO_EDITION_HARMATTAN
21 #include <MLayout>
22 #include <MAction>
23 #include <MWidgetAction>
24 #include <MComboBox>
25 #endif
26
27 #include <QtGui>
28 #include <QSettings>
29
30 #include "aboutdialog.h"
31 #include "mainwindow.h"
32
33 #ifdef MEEGO_EDITION_HARMATTAN
34 MainWindow::MainWindow(QGraphicsItem *parent) : MApplicationPage(parent)
35 {
36     m_downloader = new MedardDownloader();
37
38     connect(m_downloader, SIGNAL(downloadFinished(const QString &, const QDateTime &)), this,
39             SLOT(downloadedFinished(const QString &, const QDateTime &)));
40     connect(m_downloader, SIGNAL(downloadFailed()), this, SLOT(downloadFailed()));
41
42     m_forecast = new ForecastWidget();
43     m_forecast->setPreferredSize(m_downloader->imageSize());
44
45     m_forecastTypeLabel = new MLabel();
46     m_forecastTypeLabel->setAlignment(Qt::AlignCenter);
47     m_forecastTypeLabel->setPreferredSize(220, 80);
48
49     m_forecastInitialDateLabel = new MLabel();
50     m_forecastInitialDateLabel->setAlignment(Qt::AlignCenter);
51     m_forecastInitialDateLabel->setEnabled(false);
52
53     m_forecastDateLabel = new MLabel();
54     m_forecastDateLabel->setAlignment(Qt::AlignCenter);
55
56     m_downloadRetryButton = new MButton(tr("Download again"));
57     m_downloadRetryButton->setPreferredWidth(220);
58
59     connect(m_downloadRetryButton, SIGNAL(clicked()), this, SLOT(downloadAgainClicked()));
60
61     m_minusDayButton = new MButton(tr("-1 d"));
62     m_minusDayButton->setPreferredWidth(50);
63     m_plusDayButton = new MButton(tr("+1 d"));
64     m_plusDayButton->setPreferredWidth(50);
65     m_minusHourButton = new MButton(tr("-1 h"));
66     m_minusHourButton->setPreferredWidth(50);
67     m_plusHourButton = new MButton(tr("+1 h"));
68     m_plusHourButton->setPreferredWidth(50);
69
70     connect(m_minusDayButton, SIGNAL(clicked()), this, SLOT(minusDayClicked()));
71     connect(m_plusDayButton, SIGNAL(clicked()), this, SLOT(plusDayClicked()));
72     connect(m_minusHourButton, SIGNAL(clicked()), this, SLOT(minusHourClicked()));
73     connect(m_plusHourButton, SIGNAL(clicked()), this, SLOT(plusHourClicked()));
74
75     setupUi();
76     setupMenu();
77
78     loadSettings();
79 }
80 #else
81 MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
82 {
83     m_downloader = new MedardDownloader();
84
85     connect(m_downloader, SIGNAL(downloadFinished(const QString &, const QDateTime &)), this,
86             SLOT(downloadedFinished(const QString &, const QDateTime &)));
87     connect(m_downloader, SIGNAL(downloadFailed()), this, SLOT(downloadFailed()));
88
89     m_forecast = new ForecastWidget();
90     m_forecast->setFixedSize(m_downloader->imageSize());
91
92     m_forecastTypeLabel = new QLabel();
93     m_forecastTypeLabel->setAlignment(Qt::AlignCenter);
94     m_forecastTypeLabel->setFixedSize(220, 80);
95
96     m_forecastInitialDateLabel = new QLabel();
97     m_forecastInitialDateLabel->setAlignment(Qt::AlignCenter);
98     m_forecastInitialDateLabel->setDisabled(true);
99
100     m_forecastDateLabel = new QLabel();
101     m_forecastDateLabel->setAlignment(Qt::AlignCenter);
102
103     m_downloadRetryButton = new QPushButton(tr("Download again"));
104
105     connect(m_downloadRetryButton, SIGNAL(clicked()), this, SLOT(downloadAgainClicked()));
106
107     m_minusDayButton = new QPushButton(tr("-1 d"));
108     m_plusDayButton = new QPushButton(tr("+1 d"));
109     m_minusHourButton = new QPushButton(tr("-1 h"));
110     m_plusHourButton = new QPushButton(tr("+1 h"));
111
112     connect(m_minusDayButton, SIGNAL(clicked()), this, SLOT(minusDayClicked()));
113     connect(m_plusDayButton, SIGNAL(clicked()), this, SLOT(plusDayClicked()));
114     connect(m_minusHourButton, SIGNAL(clicked()), this, SLOT(minusHourClicked()));
115     connect(m_plusHourButton, SIGNAL(clicked()), this, SLOT(plusHourClicked()));
116
117     setupUi();
118     setupMenu();
119
120     loadSettings();
121 }
122 #endif
123
124 MainWindow::~MainWindow()
125 {
126     delete m_downloader;
127 }
128
129 #ifdef MEEGO_EDITION_HARMATTAN
130 void MainWindow::setupUi()
131 {
132     setWindowTitle(tr("Medard"));
133     setPannable(false);
134
135     QGraphicsLinearLayout *mainLayout = new QGraphicsLinearLayout(Qt::Horizontal);
136     centralWidget()->setLayout(mainLayout);
137
138     mainLayout->addItem(m_forecast);
139
140     QGraphicsLinearLayout *layout = new QGraphicsLinearLayout(Qt::Vertical);
141     layout->setContentsMargins(4, 4, 4, 4);
142     layout->setSpacing(8);
143     mainLayout->addItem(layout);
144
145     layout->addItem(m_forecastTypeLabel);
146 /*    layout->addItem(m_forecastInitialDateLabel); */
147     layout->addItem(m_forecastDateLabel);
148     layout->addItem(m_downloadRetryButton);
149
150     QGraphicsLinearLayout *dayNavigationBox = new QGraphicsLinearLayout(Qt::Horizontal);
151     dayNavigationBox->addItem(m_minusDayButton);
152     dayNavigationBox->addItem(m_plusDayButton);
153     layout->addItem(dayNavigationBox);
154
155     QGraphicsLinearLayout *hourNavigationBox = new QGraphicsLinearLayout(Qt::Horizontal);
156     hourNavigationBox->addItem(m_minusHourButton);
157     hourNavigationBox->addItem(m_plusHourButton);
158     layout->addItem(hourNavigationBox);
159
160     hideNavigationButtons(false);
161 }
162 #else
163 void MainWindow::setupUi()
164 {
165 #ifdef Q_WS_MAEMO_5
166     setAttribute(Qt::WA_Maemo5LandscapeOrientation, true);
167 #endif
168     setWindowTitle(tr("Medard"));
169
170     QWidget *widget = new QWidget;
171     setCentralWidget(widget);
172
173     QHBoxLayout *mainLayout = new QHBoxLayout();
174     mainLayout->setMargin(8);
175     mainLayout->setSpacing(4);
176     widget->setLayout(mainLayout);
177
178     mainLayout->addWidget(m_forecast);
179     mainLayout->addSpacing(4);
180
181     QVBoxLayout *layout = new QVBoxLayout();
182     mainLayout->addLayout(layout);
183
184     layout->addWidget(m_forecastTypeLabel);
185     layout->addWidget(m_forecastDateLabel);
186     layout->addSpacing(20);
187     layout->addWidget(m_forecastInitialDateLabel);
188     layout->addSpacing(20);
189     layout->addWidget(m_downloadRetryButton);
190
191     QHBoxLayout *dayNavigationBox = new QHBoxLayout();
192     dayNavigationBox->addWidget(m_minusDayButton);
193     dayNavigationBox->addWidget(m_plusDayButton);
194     layout->addLayout(dayNavigationBox);
195
196     QHBoxLayout *hourNavigationBox = new QHBoxLayout();
197     hourNavigationBox->addWidget(m_minusHourButton);
198     hourNavigationBox->addWidget(m_plusHourButton);
199     layout->addLayout(hourNavigationBox);
200
201     hideNavigationButtons(false);
202 }
203 #endif
204
205 #ifdef MEEGO_EDITION_HARMATTAN
206 void MainWindow::setupMenu()
207 {
208     QStringList forecastDomainList;
209     forecastDomainList << tr("Europe") 
210                        << tr("Czech Republic");
211
212     MWidgetAction *forecastDomainAction = new MWidgetAction(centralWidget());
213     forecastDomainAction->setLocation(MAction::ApplicationMenuLocation);
214
215     m_forecastDomainComboBox = new MComboBox;
216     m_forecastDomainComboBox->setTitle(tr("Domain"));
217     m_forecastDomainComboBox->setStyleName ("CommonComboBox");
218     m_forecastDomainComboBox->setIconVisible(false);
219     m_forecastDomainComboBox->addItems(forecastDomainList);
220     forecastDomainAction->setWidget(m_forecastDomainComboBox);
221     addAction(forecastDomainAction);
222     connect(m_forecastDomainComboBox, SIGNAL(activated(int)), this, SLOT(forecastDomainChanged(int)));
223
224     QStringList forecastTypeList;
225     forecastTypeList << tr("Sea Level Pressure")
226                      << tr("Precipitation")
227                      << tr("Wind Velocity")
228                      << tr("Cloudiness")
229                      << tr("Temperature");
230
231     MWidgetAction *forecastTypeAction = new MWidgetAction(centralWidget());
232     forecastTypeAction->setLocation(MAction::ApplicationMenuLocation);
233
234     m_forecastTypeComboBox = new MComboBox;
235     m_forecastTypeComboBox->setTitle(tr("Forecast"));
236     m_forecastTypeComboBox->setStyleName ("CommonComboBox");
237     m_forecastTypeComboBox->setIconVisible(false);
238     m_forecastTypeComboBox->addItems(forecastTypeList);
239     forecastTypeAction->setWidget(m_forecastTypeComboBox);
240     addAction(forecastTypeAction);
241     connect(m_forecastTypeComboBox, SIGNAL(activated(int)), this, SLOT(forecastTypeChanged(int)));
242
243     MAction *seaLevelPreasureAction = new MAction("icon-m-weather-cloudy", "", this);
244     seaLevelPreasureAction->setLocation(MAction::ToolBarLocation);
245     addAction(seaLevelPreasureAction);
246     connect(seaLevelPreasureAction, SIGNAL(triggered()), this, SLOT(seaLevelPreasureMenuClicked()));
247
248     MAction *precipitationAction = new MAction("icon-m-weather-rain", "", this);
249     precipitationAction->setLocation(MAction::ToolBarLocation);
250     addAction(precipitationAction);
251     connect(precipitationAction, SIGNAL(triggered()), this, SLOT(precipitationMenuClicked()));
252
253     MAction *cloudinessAction = new MAction("icon-m-weather-partly-sunny", "", this);
254     cloudinessAction->setLocation(MAction::ToolBarLocation);
255     addAction(cloudinessAction);
256     connect(cloudinessAction, SIGNAL(triggered()), this, SLOT(cloudinessMenuClicked()));
257
258     MAction *temperatureAction = new MAction("icon-m-weather-hot", "", this);
259     temperatureAction->setLocation(MAction::ToolBarLocation);
260     addAction(temperatureAction);
261     connect(temperatureAction, SIGNAL(triggered()), this, SLOT(temperatureMenuClicked()));
262
263     MAction *aboutAction = new MAction(this);
264     aboutAction->setText(tr("About"));
265     aboutAction->setLocation(MAction::ApplicationMenuLocation);
266     addAction(aboutAction);
267     connect(aboutAction, SIGNAL(triggered()), this, SLOT(aboutMenuClicked()));
268 }
269 #else
270 void MainWindow::setupMenu()
271 {
272     QMenuBar *menu = new QMenuBar();
273     setMenuBar(menu);
274
275     m_domainActionGroup = new QActionGroup(this);
276     m_domainActionGroup->setExclusive(true);
277
278     QAction *domainAction;
279     domainAction = new QAction(tr("Europe"), m_domainActionGroup);
280     domainAction->setCheckable(true);
281     domainAction = new QAction(tr("Czech Republic"), m_domainActionGroup);
282     domainAction ->setCheckable(true);
283     menu->addActions(m_domainActionGroup->actions());
284     connect(m_domainActionGroup, SIGNAL(triggered(QAction *)), this, SLOT(forecastDomainChanged(QAction *)));
285
286     QAction *seaLevelPreasureAction = new QAction(tr("Sea Level Pressure"), this);
287     menu->addAction(seaLevelPreasureAction);
288     connect(seaLevelPreasureAction, SIGNAL(triggered()), this, SLOT(seaLevelPreasureMenuClicked()));
289
290     QAction *precipitationAction = new QAction(tr("Precipitation"), this);
291     menu->addAction(precipitationAction);
292     connect(precipitationAction, SIGNAL(triggered()), this, SLOT(precipitationMenuClicked()));
293
294     QAction *windVelocityAction = new QAction(tr("Wind Velocity"), this);
295     menu->addAction(windVelocityAction);
296     connect(windVelocityAction, SIGNAL(triggered()), this, SLOT(windVelocityMenuClicked()));
297
298     QAction *cloudinessAction = new QAction(tr("Cloudiness"), this);
299     menu->addAction(cloudinessAction);
300     connect(cloudinessAction, SIGNAL(triggered()), this, SLOT(cloudinessMenuClicked()));
301
302     QAction *temperatureAction = new QAction(tr("Temperature"), this);
303     menu->addAction(temperatureAction);
304     connect(temperatureAction, SIGNAL(triggered()), this, SLOT(temperatureMenuClicked()));
305
306     QAction *aboutAction = new QAction(tr("About"), this);
307     menu->addAction(aboutAction);
308     connect(aboutAction, SIGNAL(triggered()), this, SLOT(aboutMenuClicked()));
309 }
310 #endif
311
312 void MainWindow::loadSettings()
313 {
314     QSettings settings;
315
316     int forecastDomain = settings.value("ForecastDomain").toInt();
317     int forecastType = settings.value("ForecastType").toInt();
318
319     m_downloader->setForecastDomain((MedardDownloader::ForecastDomain) forecastDomain);
320 #ifdef MEEGO_EDITION_HARMATTAN
321     m_forecastDomainComboBox->setCurrentIndex(forecastDomain);
322 #else
323     m_domainActionGroup->actions().at(forecastDomain)->setChecked(true);
324 #endif
325
326     switch ((MedardDownloader::ForecastType) forecastType) {
327         case MedardDownloader::SeaLevelPressure:
328             seaLevelPreasureMenuClicked();
329             break;
330
331         case MedardDownloader::Precipitation:
332             precipitationMenuClicked();
333             break;
334
335         case MedardDownloader::WindVelocity:
336             windVelocityMenuClicked();
337             break;
338
339         case MedardDownloader::Cloudiness:
340             cloudinessMenuClicked();
341             break;
342
343         case MedardDownloader::Temperature:
344             temperatureMenuClicked();
345             break;
346     }
347 }
348
349 void MainWindow::showNavigationButtons()
350 {
351     m_downloadRetryButton->hide();
352
353     m_minusDayButton->show();
354     m_plusDayButton->show();
355     m_minusHourButton->show();
356     m_plusHourButton->show();
357 }
358
359 void MainWindow::hideNavigationButtons(bool showRetryButton)
360 {
361     if (showRetryButton)
362         m_downloadRetryButton->show();
363     else
364         m_downloadRetryButton->hide();
365
366     m_minusDayButton->hide();
367     m_plusDayButton->hide();
368     m_minusHourButton->hide();
369     m_plusHourButton->hide();
370 }
371
372 void MainWindow::updateNavigationButtons()
373 {
374     if ((m_downloader->forecastDateOffset() - 24) < m_downloader->minForecastDateOffset()) {
375 #ifdef MEEGO_EDITION_HARMATTAN
376         m_minusDayButton->setEnabled(false);
377         m_plusDayButton->setEnabled(true);
378 #else
379         m_minusDayButton->setDisabled(true);
380         m_plusDayButton->setDisabled(false);
381 #endif
382     } else if ((m_downloader->forecastDateOffset() + 24) > m_downloader->maxForecastDateOffset()) {
383 #ifdef MEEGO_EDITION_HARMATTAN
384         m_minusDayButton->setEnabled(true);
385         m_plusDayButton->setEnabled(false);
386 #else
387         m_minusDayButton->setDisabled(false);
388         m_plusDayButton->setDisabled(true);
389 #endif
390     } else {
391 #ifdef MEEGO_EDITION_HARMATTAN
392         m_minusDayButton->setEnabled(true);
393         m_plusDayButton->setEnabled(true);
394 #else
395         m_minusDayButton->setDisabled(false);
396         m_plusDayButton->setDisabled(false);
397 #endif
398     }
399
400     if ((m_downloader->forecastDateOffset() - 1) < m_downloader->minForecastDateOffset()) {
401 #ifdef MEEGO_EDITION_HARMATTAN
402         m_minusHourButton->setEnabled(false);
403         m_plusHourButton->setEnabled(true);
404 #else
405         m_minusHourButton->setDisabled(true);
406         m_plusHourButton->setDisabled(false);
407 #endif
408     } else if ((m_downloader->forecastDateOffset() + 1) > m_downloader->maxForecastDateOffset()) {
409 #ifdef MEEGO_EDITION_HARMATTAN
410         m_minusHourButton->setEnabled(true);
411         m_plusHourButton->setEnabled(false);
412 #else
413         m_minusHourButton->setDisabled(false);
414         m_plusHourButton->setDisabled(true);
415 #endif
416     } else {
417 #ifdef MEEGO_EDITION_HARMATTAN
418         m_minusHourButton->setEnabled(true);
419         m_plusHourButton->setEnabled(true);
420 #else
421         m_minusHourButton->setDisabled(false);
422         m_plusHourButton->setDisabled(false);
423 #endif
424     }
425 }
426
427 void MainWindow::setForecastType(const QString label, MedardDownloader::ForecastType type)
428 {
429     m_forecastTypeLabel->setText(label);
430     m_forecast->clearImage(false);
431     m_downloader->setForecastType(type);
432     m_downloader->downloadImage();
433
434     QSettings settings;
435     settings.setValue("ForecastType", type);
436 }
437
438 void MainWindow::setForecastDateOffset(int offset)
439 {
440     m_forecast->clearImage(false);
441     m_downloader->setForecastDateOffset(m_downloader->forecastDateOffset() + offset);
442     m_downloader->downloadImage();
443 }
444
445 void MainWindow::seaLevelPreasureMenuClicked()
446 {
447 #ifdef MEEGO_EDITION_HARMATTAN
448     m_forecastTypeComboBox->setCurrentIndex(MedardDownloader::SeaLevelPressure);
449 #endif
450     setForecastType(tr("Sea Level Pressure"), MedardDownloader::SeaLevelPressure);
451 }
452
453 void MainWindow::precipitationMenuClicked()
454 {
455 #ifdef MEEGO_EDITION_HARMATTAN
456     m_forecastTypeComboBox->setCurrentIndex(MedardDownloader::Precipitation);
457 #endif
458     setForecastType(tr("Precipitation"), MedardDownloader::Precipitation);
459 }
460
461 void MainWindow::windVelocityMenuClicked()
462 {
463 #ifdef MEEGO_EDITION_HARMATTAN
464     m_forecastTypeComboBox->setCurrentIndex(MedardDownloader::WindVelocity);
465 #endif
466     setForecastType(tr("Wind Velocity"), MedardDownloader::WindVelocity);
467 }
468
469 void MainWindow::cloudinessMenuClicked()
470 {
471 #ifdef MEEGO_EDITION_HARMATTAN
472     m_forecastTypeComboBox->setCurrentIndex(MedardDownloader::Cloudiness);
473 #endif
474     setForecastType(tr("Cloudiness"), MedardDownloader::Cloudiness);
475 }
476
477 void MainWindow::temperatureMenuClicked()
478 {
479 #ifdef MEEGO_EDITION_HARMATTAN
480     m_forecastTypeComboBox->setCurrentIndex(MedardDownloader::Temperature);
481 #endif
482     setForecastType(tr("Temperature"), MedardDownloader::Temperature);
483 }
484
485 void MainWindow::aboutMenuClicked()
486 {
487     AboutDialog *dialog = new AboutDialog();
488 #ifdef MEEGO_EDITION_HARMATTAN
489     dialog->appear(MSceneWindow::DestroyWhenDismissed);
490 #else
491     dialog->exec();
492 #endif
493 }
494
495 void MainWindow::downloadAgainClicked()
496 {
497     m_forecast->clearImage(false);
498     m_downloader->downloadImage();
499
500     hideNavigationButtons(false);
501 }
502
503 void MainWindow::plusDayClicked()
504 {
505     setForecastDateOffset(+24);
506 }
507
508 void MainWindow::minusDayClicked()
509 {
510     setForecastDateOffset(-24);
511 }
512
513 void MainWindow::plusHourClicked()
514 {
515     setForecastDateOffset(+1);
516 }
517
518 void MainWindow::minusHourClicked()
519 {
520     setForecastDateOffset(-1);
521 }
522
523 #ifdef MEEGO_EDITION_HARMATTAN
524 void MainWindow::forecastDomainChanged(int index)
525 {
526     m_forecast->clearImage(false);
527
528     if (index == 0)
529         m_downloader->setForecastDomain(MedardDownloader::Europe);
530     else
531         m_downloader->setForecastDomain(MedardDownloader::CzechRepublic);
532
533     m_downloader->downloadImage();
534
535     QSettings settings;
536     settings.setValue("ForecastDomain", index);
537 }
538
539 void MainWindow::forecastTypeChanged(int index)
540 {
541     switch ((MedardDownloader::ForecastType) index) {
542         case MedardDownloader::SeaLevelPressure:
543             setForecastType(tr("Sea Level Pressure"), MedardDownloader::SeaLevelPressure);
544             break;
545
546         case MedardDownloader::Precipitation:
547             setForecastType(tr("Precipitation"), MedardDownloader::Precipitation);
548             break;
549
550         case MedardDownloader::WindVelocity:
551             setForecastType(tr("Wind Velocity"), MedardDownloader::WindVelocity);
552             break;
553
554         case MedardDownloader::Cloudiness:
555             setForecastType(tr("Cloudiness"), MedardDownloader::Cloudiness);
556             break;
557
558         case MedardDownloader::Temperature:
559             setForecastType(tr("Temperature"), MedardDownloader::Temperature);
560             break;
561     }
562 }
563
564 #else
565 void MainWindow::forecastDomainChanged(QAction *action)
566 {
567     int forecastDomain = m_domainActionGroup->actions().indexOf(action);
568
569     m_forecast->clearImage(false);
570
571     if (forecastDomain == 0)
572         m_downloader->setForecastDomain(MedardDownloader::Europe);
573     else
574         m_downloader->setForecastDomain(MedardDownloader::CzechRepublic);
575
576     m_downloader->downloadImage();
577
578     QSettings settings;
579     settings.setValue("ForecastDomain", forecastDomain);
580 }
581 #endif
582
583 void MainWindow::downloadedFinished(const QString &filename, const QDateTime &date)
584 {
585     m_forecast->setImage(filename);
586     m_forecastInitialDateLabel->setText(tr("Forecast from:<br>") +
587                                           m_downloader->forecastInitialDate().toString("dd.MM.yyyy, hh:mm"));
588
589     /* upcase the first letter of name of day */
590     QString temp = date.toString("dddd<br>dd.MM.yyyy, hh:mm");
591     m_forecastDateLabel->setText(temp.replace(0, 1, temp.at(0).toUpper()));
592
593     showNavigationButtons();
594     updateNavigationButtons();
595 }
596
597 void MainWindow::downloadFailed()
598 {
599     m_forecast->clearImage(true);
600     m_forecastInitialDateLabel->setText("");
601     m_forecastDateLabel->setText("");
602
603     hideNavigationButtons(true);
604 }