Ver código fonte

Added New Database views to include Simulator Sessions

- Enhanced the Default and Easa views with optional display of simulator sessions.
- Encapsulated global statics in the Opl::Globals class and created a Q_GLOBAL_STATIC instance to make it accessible throughout the application.
Felix Turo 3 anos atrás
pai
commit
7d22900d3a

+ 1 - 0
CMakeLists.txt

@@ -24,6 +24,7 @@ set(PROJECT_SOURCES
 
     main.cpp
     src/opl.h
+    src/opl.cpp
 
     # GUI
     mainwindow.h

+ 2 - 2
src/classes/aaircraftentry.cpp

@@ -19,7 +19,7 @@
 #include "src/opl.h"
 
 AAircraftEntry::AAircraftEntry()
-    : AEntry::AEntry(Opl::Db::DEFAULT_AIRCRAFT_POSITION)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_AIRCRAFT, 0))
 {}
 
 AAircraftEntry::AAircraftEntry(RowId_T row_id)
@@ -27,5 +27,5 @@ AAircraftEntry::AAircraftEntry(RowId_T row_id)
 {}
 
 AAircraftEntry::AAircraftEntry(RowData_T table_data)
-    : AEntry::AEntry(Opl::Db::DEFAULT_AIRCRAFT_POSITION, table_data)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_AIRCRAFT, 0), table_data)
 {}

+ 2 - 2
src/classes/aflightentry.cpp

@@ -22,7 +22,7 @@
 #include "src/classes/asettings.h"
 
 AFlightEntry::AFlightEntry()
-    : AEntry::AEntry(Opl::Db::DEFAULT_FLIGHT_POSITION)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_FLIGHTS, 0))
 {}
 
 AFlightEntry::AFlightEntry(RowId_T row_id)
@@ -30,7 +30,7 @@ AFlightEntry::AFlightEntry(RowId_T row_id)
 {}
 
 AFlightEntry::AFlightEntry(RowData_T table_data)
-    : AEntry::AEntry(Opl::Db::DEFAULT_FLIGHT_POSITION, table_data)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_FLIGHTS, 0), table_data)
 {}
 
 const QString AFlightEntry::summary()

+ 2 - 2
src/classes/apilotentry.cpp

@@ -19,7 +19,7 @@
 #include "src/opl.h"
 
 APilotEntry::APilotEntry()
-    : AEntry::AEntry(Opl::Db::DEFAULT_PILOT_POSITION)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_PILOTS, 0))
 {}
 
 APilotEntry::APilotEntry(RowId_T row_id)
@@ -27,7 +27,7 @@ APilotEntry::APilotEntry(RowId_T row_id)
 {}
 
 APilotEntry::APilotEntry(RowData_T table_data)
-    : AEntry::AEntry(Opl::Db::DEFAULT_PILOT_POSITION, table_data)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_PILOTS, 0), table_data)
 {}
 
 const QString APilotEntry::name()

+ 1 - 0
src/classes/astyle.h

@@ -65,6 +65,7 @@ public:
     static const QString& style();
 
     static inline void loadStylesComboBox(QComboBox *combo_box){
+        const QSignalBlocker blocker(combo_box);
         combo_box->addItems(AStyle::styles);
         for (const auto &style_sheet : AStyle::styleSheets) {
             combo_box->addItem(style_sheet.styleSheetName);

+ 2 - 2
src/classes/atailentry.cpp

@@ -19,7 +19,7 @@
 #include "src/opl.h"
 
 ATailEntry::ATailEntry()
-    : AEntry::AEntry(Opl::Db::DEFAULT_TAIL_POSITION)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_TAILS, 0))
 {}
 
 ATailEntry::ATailEntry(RowId_T row_id)
@@ -27,7 +27,7 @@ ATailEntry::ATailEntry(RowId_T row_id)
 {}
 
 ATailEntry::ATailEntry(RowData_T table_data)
-    : AEntry::AEntry(Opl::Db::DEFAULT_TAIL_POSITION, table_data)
+    : AEntry::AEntry(DataPosition(Opl::Db::TABLE_TAILS, 0), table_data)
 {}
 
 const QString ATailEntry::registration()

+ 4 - 4
src/classes/atranslator.cpp

@@ -2,13 +2,13 @@
 
 QTranslator* ATranslator::translator;
 
-void ATranslator::installTranslator(Opl::Translations language)
+void ATranslator::installTranslator(Opl::Translation language)
 {
     translator = new QTranslator();
-    if (translator->load(Opl::L10N_FILES[language]))
-        LOG << "Translations loaded. Selected language: " << Opl::L10N_FILES[language].right(2);
+    if (translator->load(Opl::GLOBALS->getLanguageFilePath(language)))
+        LOG << "Translations loaded. Selected language: " << Opl::GLOBALS->getLanguageFilePath(language);
     else
-        LOG << "Loading translations has failed. Selected language: " << Opl::L10N_FILES[language].right(2);
+        LOG << "Loading translations has failed. Selected language: " << Opl::GLOBALS->getLanguageFilePath(language);
 
 
     if (qApp->installTranslator(translator))

+ 1 - 1
src/classes/atranslator.h

@@ -21,7 +21,7 @@ public:
     /*!
      * \brief Installs a QTranslator with the selected language. Defaults to English. Call this function before constructing the Main Window.
      */
-    static void installTranslator(Opl::Translations language = Opl::Translations::English);
+    static void installTranslator(Opl::Translation language = Opl::Translation::English);
 
 private:
     static QTranslator *translator;

+ 1 - 1
src/database/adatabase.h

@@ -133,9 +133,9 @@ public:
  * to hot database data.
  */
 class ADatabase : public QObject {
-    Q_OBJECT
 
 private:
+    Q_OBJECT
     static ADatabase* self;
     TableNames_T tableNames;
     TableColumns_T tableColumns;

+ 91 - 2
src/database/adbsetup.cpp

@@ -175,7 +175,39 @@ const static auto CREATE_VIEW_DEFAULT = QStringLiteral("CREATE VIEW viewDefault
         " INNER JOIN tails on flights.acft = tails.tail_id "
         " ORDER BY date DESC ");
 
-const static auto CREATE_VIEW_EASA = QStringLiteral("CREATE VIEW viewEASA AS "
+const static auto CREATE_VIEW_DEFAULT_SIM = QStringLiteral( "CREATE VIEW viewDefaultSim AS SELECT flight_id AS 'rowid',  "
+        " doft as 'Date',  "
+        " dept AS 'Dept',  "
+        " printf('%02d',(tofb/60))||':'||printf('%02d',(tofb%60)) AS 'Time',  "
+        " dest AS 'Dest', printf('%02d',(tonb/60))||':'||printf('%02d',(tonb%60)) AS 'Time ',  "
+        " printf('%02d',(tblk/60))||':'||printf('%02d',(tblk%60)) AS 'Total',  "
+        " CASE  WHEN pilot_id = 1 THEN alias  ELSE lastname||', '||substr(firstname, 1, 1)||'.'  END  AS 'Name PIC',  "
+        " CASE  WHEN variant IS NOT NULL THEN make||' '||model||'-'||variant  ELSE make||' '||model  END  AS 'Type',  "
+        " registration AS 'Registration',   "
+        " null AS 'Sim Type',"
+        " null AS 'Time of Session',"
+        " remarks AS 'Remarks'"
+        " FROM flights  "
+        " INNER JOIN pilots on flights.pic = pilots.pilot_id  INNER JOIN tails on flights.acft = tails.tail_id  "
+        " UNION"
+        " SELECT session_id,"
+        " date,"
+        " null,"
+        " null,"
+        " null,"
+        " null,"
+        " 'SIM',"
+        " null,"
+        " aircraftType,"
+        " registration,"
+        " deviceType,"
+        " printf('%02d',(totalTime/60))||':'||printf('%02d',(totalTime%60)),"
+        " remarks"
+        " FROM simulators"
+        " ORDER BY date DESC"
+            );
+
+const static auto CREATE_VIEW_EASA = QStringLiteral("CREATE VIEW viewEasa AS "
         " SELECT "
         " flight_id, doft as 'Date', "
         " dept AS 'Dept', "
@@ -208,7 +240,62 @@ const static auto CREATE_VIEW_EASA = QStringLiteral("CREATE VIEW viewEASA AS "
         " FROM flights "
         " INNER JOIN pilots on flights.pic = pilots.pilot_id "
         " INNER JOIN tails on flights.acft = tails.tail_id "
-        " ORDER BY date DESC");
+        " ORDER BY date DESC"
+                                                    );
+
+const static auto CREATE_VIEW_EASA_SIM = QStringLiteral(" CREATE VIEW viewEasaSim AS "
+            " SELECT  flight_id, doft as 'Date',   "
+            " dept AS 'Dept',  printf('%02d',(tofb/60))||':'||printf('%02d',(tofb%60)) AS 'Time',   "
+            " dest AS 'Dest', printf('%02d',(tonb/60))||':'||printf('%02d',(tonb%60)) AS 'Time ',   "
+            " CASE  WHEN variant IS NOT NULL THEN make||' '||model||'-'||variant  ELSE make||' '||model  END  AS 'Type',   "
+            " registration AS 'Registration',   "
+            " (SELECT printf('%02d',(tSPSE/60))||':'||printf('%02d',(tSPSE%60)) WHERE tSPSE IS NOT NULL) AS 'SP SE',   "
+            " (SELECT printf('%02d',(tSPME/60))||':'||printf('%02d',(tSPME%60)) WHERE tSPME IS NOT NULL) AS 'SP ME',   "
+            " (SELECT printf('%02d',(tMP/60))||':'||printf('%02d',(tMP%60)) WHERE tMP IS NOT NULL) AS 'MP',   "
+            " printf('%02d',(tblk/60))||':'||printf('%02d',(tblk%60)) AS 'Total',   "
+            " CASE  WHEN pilot_id = 1 THEN alias  ELSE lastname||', '||substr(firstname, 1, 1)||'.'  END  AS 'Name PIC',   "
+            " ldgDay AS 'L/D',   "
+            " ldgNight AS 'L/N',   "
+            " (SELECT printf('%02d',(tNight/60))||':'||printf('%02d',(tNight%60)) WHERE tNight IS NOT NULL)  AS 'Night',   "
+            " (SELECT printf('%02d',(tIFR/60))||':'||printf('%02d',(tIFR%60)) WHERE tIFR IS NOT NULL)  AS 'IFR',   "
+            " (SELECT printf('%02d',(tPIC/60))||':'||printf('%02d',(tPIC%60)) WHERE tPIC IS NOT NULL)  AS 'PIC',   "
+            " (SELECT printf('%02d',(tSIC/60))||':'||printf('%02d',(tSIC%60)) WHERE tSIC IS NOT NULL)  AS 'SIC',   "
+            " (SELECT printf('%02d',(tDual/60))||':'||printf('%02d',(tDual%60)) WHERE tDual IS NOT NULL)  AS 'Dual',   "
+            " (SELECT printf('%02d',(tFI/60))||':'||printf('%02d',(tFI%60)) WHERE tFI IS NOT NULL)  AS 'FI', "
+            " null AS 'Sim Type', "
+            " null AS 'Time of Session', "
+            " remarks AS 'Remarks'   "
+            " FROM flights   "
+            " INNER JOIN pilots on flights.pic = pilots.pilot_id   "
+            " INNER JOIN tails on flights.acft = tails.tail_id   "
+            " UNION "
+            " SELECT session_id, "
+            " date, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " aircraftType, "
+            " registration, "
+            " null, "
+            " null, "
+            " null, "
+            " 'SIM', "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " null, "
+            " deviceType, "
+            " printf('%02d',(totalTime/60))||':'||printf('%02d',(totalTime%60)), "
+            " remarks "
+            " FROM simulators "
+            " ORDER BY date DESC "
+            );
 
 const static auto CREATE_VIEW_TAILS = QStringLiteral("CREATE VIEW viewTails AS "
         " SELECT "
@@ -270,7 +357,9 @@ const static QStringList DATABASE_TABLES = {
 };
 const static QStringList DATABASE_VIEWS = {
     CREATE_VIEW_DEFAULT,
+    CREATE_VIEW_DEFAULT_SIM,
     CREATE_VIEW_EASA,
+    CREATE_VIEW_EASA_SIM,
     CREATE_VIEW_TAILS,
     CREATE_VIEW_PILOTS,
     CREATE_VIEW_TOTALS,

+ 4 - 2
src/gui/dialogues/firstrundialog.cpp

@@ -44,8 +44,10 @@ FirstRunDialog::FirstRunDialog(QWidget *parent) :
     ui->logoLabel->setPixmap(QPixmap(Opl::Assets::LOGO));
 
     // Approach Combo Box and Function Combo Box
-    Opl::loadApproachTypes(ui->approachComboBox);
-    Opl::loadPilotFunctios(ui->functionComboBox);
+    Opl::GLOBALS->loadApproachTypes(ui->approachComboBox);
+    Opl::GLOBALS->loadPilotFunctios(ui->functionComboBox);
+    Opl::GLOBALS->fillViewNamesComboBox(ui->logbookViewComboBox);
+
 
     // Style combo box
     const QSignalBlocker style_blocker(ui->styleComboBox);

+ 1 - 12
src/gui/dialogues/firstrundialog.ui

@@ -24,7 +24,7 @@
    <item row="2" column="0" colspan="2">
     <widget class="QStackedWidget" name="stackedWidget">
      <property name="currentIndex">
-      <number>4</number>
+      <number>3</number>
      </property>
      <widget class="QWidget" name="personalDataPage">
       <layout class="QGridLayout" name="gridLayout_9">
@@ -147,7 +147,6 @@
         <widget class="QLabel" name="importLabel">
          <property name="font">
           <font>
-           <weight>75</weight>
            <bold>true</bold>
           </font>
          </property>
@@ -740,16 +739,6 @@
            <property name="toolTip">
             <string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Determines how your logbook is displayed in the logbook tab. This has no influence on what details are logged, just on what is displayed by default.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
            </property>
-           <item>
-            <property name="text">
-             <string>Default</string>
-            </property>
-           </item>
-           <item>
-            <property name="text">
-             <string>EASA Part-FCL</string>
-            </property>
-           </item>
           </widget>
          </item>
         </layout>

+ 3 - 3
src/gui/dialogues/newflightdialog.cpp

@@ -89,8 +89,8 @@ void NewFlightDialog::init()
     for (const auto& line_edit : *mandatoryLineEdits)
         line_edit->installEventFilter(this);
     // Approach Combo Box and Function Combo Box
-    Opl::loadApproachTypes(ui->approachComboBox);
-    Opl::loadPilotFunctios(ui->functionComboBox);
+    Opl::GLOBALS->loadApproachTypes(ui->approachComboBox);
+    Opl::GLOBALS->loadPilotFunctios(ui->functionComboBox);
 
     setupRawInputValidation();
     setupSignalsAndSlots();
@@ -462,7 +462,7 @@ RowData_T NewFlightDialog::prepareFlightEntryData()
         new_data.insert(Opl::Db::FLIGHTS_LDGNIGHT, 0);
         new_data.insert(Opl::Db::FLIGHTS_LDGDAY, ui->landingSpinBox->value());
     }
-    if (ui->approachComboBox->currentText() == Opl::APPROACH_TYPES[3]) // ILS CAT III
+    if (ui->approachComboBox->currentText() == Opl::GLOBALS->getApproachTypes()[3]) // ILS CAT III
         new_data.insert(Opl::Db::FLIGHTS_AUTOLAND, ui->landingSpinBox->value());
 
     // Additional Data

+ 1 - 1
src/gui/dialogues/newsimdialog.cpp

@@ -11,7 +11,7 @@ NewSimDialog::NewSimDialog(QWidget *parent) :
 {
     ui->setupUi(this);
     ui->dateLineEdit->setText(ADate::currentDate());
-    Opl::loadSimulatorTypes(ui->typeComboBox);
+    Opl::GLOBALS->loadSimulatorTypes(ui->typeComboBox);
 
     const QStringList aircraft_list = aDB->getCompletionList(ADatabaseTarget::aircraft);
     auto completer = new QCompleter(aircraft_list, ui->acftLineEdit);

+ 11 - 17
src/gui/widgets/logbookwidget.cpp

@@ -41,6 +41,8 @@ LogbookWidget::LogbookWidget(ACompletionData& completion_data, QWidget *parent)
 {
     ui->setupUi(this);
 
+    Opl::GLOBALS->fillViewNamesComboBox(ui->viewsComboBox);
+
     //customContextMenu for tablewidget
     menu  = new QMenu(this);
     menu->addAction(ui->actionEdit_Flight);
@@ -71,33 +73,19 @@ LogbookWidget::~LogbookWidget()
  */
 void LogbookWidget::setupModelAndView(int view_id)
 {
-    switch (view_id) {
-    case 0:
-        LOG << "Loading Default View...";
-        displayModel->setTable(QStringLiteral("viewDefault"));
-        displayModel->select();
-        break;
-    case 1:
-        LOG << "Loading EASA View...";
-        displayModel->setTable(QStringLiteral("viewEASA"));
-        displayModel->select();
-        break;
-    default:
-        LOG << "Loading Default View...";
-        displayModel->setTable(QStringLiteral("viewDefault"));
-        displayModel->select();
-    }
+    displayModel->setTable(Opl::GLOBALS->getViewIdentifier(Opl::DbViewName(view_id)));
+    displayModel->select();
 
     view->setModel(displayModel);
     view->setSelectionBehavior(QAbstractItemView::SelectRows);
     view->setSelectionMode(QAbstractItemView::ExtendedSelection);
     view->setEditTriggers(QAbstractItemView::NoEditTriggers);
     view->setContextMenuPolicy(Qt::CustomContextMenu);
+    view->resizeColumnsToContents();
     view->horizontalHeader()->setStretchLastSection(QHeaderView::Stretch);
     view->verticalHeader()->hide();
     view->setAlternatingRowColors(true);
     view->hideColumn(0);
-    view->resizeColumnsToContents();
     view->show();
 }
 
@@ -304,3 +292,9 @@ void LogbookWidget::repopulateModel()
     setupModelAndView(ASettings::read(ASettings::Main::LogbookView).toInt());
     connectSignalsAndSlots();
 }
+
+void LogbookWidget::on_viewsComboBox_currentIndexChanged(int index)
+{
+    setupModelAndView(index);
+}
+

+ 3 - 4
src/gui/widgets/logbookwidget.h

@@ -27,6 +27,7 @@
 #include <QTableView>
 #include "src/gui/widgets/settingswidget.h"
 #include "src/classes/acompletiondata.h"
+#include "src/opl.h"
 
 namespace Ui {
 class LogbookWidget;
@@ -52,10 +53,6 @@ public:
     ~LogbookWidget();
 
 private slots:
-    //void on_newFlightButton_clicked();
-    //void on_editFlightButton_clicked();
-    //void on_deleteFlightPushButton_clicked();
-    //void on_showAllButton_clicked();
     void flightsTableView_selectionChanged();
     void on_tableView_customContextMenuRequested(const QPoint &pos);
     void on_actionDelete_Flight_triggered();
@@ -64,6 +61,8 @@ private slots:
     void on_flightSearchLlineEdit_textChanged(const QString &arg1);
     void on_flightSearchComboBox_currentIndexChanged(int);
 
+    void on_viewsComboBox_currentIndexChanged(int index);
+
 public slots:
     void refresh();
     void onLogbookWidget_viewSelectionChanged(SettingsWidget::SettingSignal signal);

+ 6 - 5
src/gui/widgets/logbookwidget.ui

@@ -14,12 +14,10 @@
    <string>Form</string>
   </property>
   <layout class="QGridLayout" name="gridLayout">
-   <item row="0" column="0">
+   <item row="1" column="0">
     <widget class="QTableView" name="tableView">
      <property name="font">
-      <font>
-       <family>Cantarell</family>
-      </font>
+      <font/>
      </property>
      <property name="styleSheet">
       <string notr="true"/>
@@ -32,7 +30,7 @@
      </property>
     </widget>
    </item>
-   <item row="1" column="0">
+   <item row="2" column="0">
     <widget class="QStackedWidget" name="stackedWidget">
      <widget class="QWidget" name="defaultPage">
       <layout class="QGridLayout" name="gridLayout_2">
@@ -121,6 +119,9 @@
      </widget>
     </widget>
    </item>
+   <item row="0" column="0">
+    <widget class="QComboBox" name="viewsComboBox"/>
+   </item>
   </layout>
   <widget class="QLabel" name="spacerLabel">
    <property name="geometry">

+ 5 - 11
src/gui/widgets/settingswidget.cpp

@@ -53,18 +53,12 @@ void SettingsWidget::changeEvent(QEvent *event)
 
 void SettingsWidget::setupComboBoxes(){
     {
-        // Style combo box
-        const QSignalBlocker style_blocker(ui->styleComboBox);
+        // Set up Combo Boxes
         AStyle::loadStylesComboBox(ui->styleComboBox);
-        // Approach Combo Box and Function Combo Box
-        const QSignalBlocker approach_blocker(ui->approachComboBox);
-        Opl::loadApproachTypes(ui->approachComboBox);
-        const QSignalBlocker function_blocker(ui->functionComboBox);
-        Opl::loadPilotFunctios(ui->functionComboBox);
-
-        // Language Combo Box
-        for (const auto &lang : Opl::L10N_NAMES)
-            ui->languageComboBox->addItem(lang);
+        Opl::GLOBALS->loadApproachTypes(ui->approachComboBox);
+        Opl::GLOBALS->loadPilotFunctios(ui->functionComboBox);
+        Opl::GLOBALS->fillViewNamesComboBox(ui->logbookViewComboBox);
+        Opl::GLOBALS->fillLanguageComboBox(ui->languageComboBox);
     }
 }
 

+ 1 - 11
src/gui/widgets/settingswidget.ui

@@ -17,7 +17,7 @@
    <item row="0" column="0">
     <widget class="QTabWidget" name="tabWidget">
      <property name="currentIndex">
-      <number>4</number>
+      <number>3</number>
      </property>
      <widget class="QWidget" name="personalTab">
       <attribute name="title">
@@ -926,16 +926,6 @@
          <property name="toolTip">
           <string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Determines how your logbook is displayed in the logbook tab. This has no influence on what details are logged, just on what is displayed by default.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
          </property>
-         <item>
-          <property name="text">
-           <string>Default</string>
-          </property>
-         </item>
-         <item>
-          <property name="text">
-           <string>EASA Part-FCL</string>
-          </property>
-         </item>
         </widget>
        </item>
        <item row="5" column="0">

+ 40 - 0
src/opl.cpp

@@ -0,0 +1,40 @@
+#include "opl.h"
+
+namespace Opl {
+
+void OplGlobals::fillLanguageComboBox(QComboBox *combo_box) const
+{
+    QSignalBlocker blocker(combo_box);
+    for (const auto &language : L10N_DisplayNames)
+        combo_box->addItem(language);
+}
+
+void OplGlobals::fillViewNamesComboBox(QComboBox *combo_box) const
+{
+    const QSignalBlocker blocker(combo_box);
+    for (int i = 0; i < DATABASE_VIEW_DISPLAY_NAMES.size(); i++)
+        combo_box->addItem(DATABASE_VIEW_DISPLAY_NAMES.value(DbViewName(i)));
+}
+
+void OplGlobals::loadPilotFunctios(QComboBox *combo_box) const
+{
+    const QSignalBlocker blocker(combo_box);
+    for (int i = PilotFunction::PIC; i < PILOT_FUNCTIONS.size(); i++)
+        combo_box->addItem(PILOT_FUNCTIONS.value(PilotFunction(i)));
+}
+
+void OplGlobals::loadSimulatorTypes(QComboBox *combo_box) const
+{
+    const QSignalBlocker blocker(combo_box);
+    for (int i = 0; i < SIMULATOR_TYPES.size(); i++)
+        combo_box->addItem(SIMULATOR_TYPES.value(SimulatorTypes(i)));
+}
+
+void OplGlobals::loadApproachTypes(QComboBox *combo_box) const
+{
+    const QSignalBlocker blocker(combo_box);
+    for (const auto &approach : APPROACH_TYPES)
+        combo_box->addItem(approach);
+}
+
+} // namespace Opl

+ 92 - 68
src/opl.h

@@ -84,86 +84,110 @@ public:
     };
 }; // class ANotificationHandler
 
-enum class Translations {English, German, Spanish};
-
-const static QMap<Opl::Translations, QString> L10N_FILES {
-    {Opl::Translations::English, QStringLiteral("l10n/openpilotlog_en")},
-    {Opl::Translations::German,  QStringLiteral("l10n/openpilotlog_de")},
-    {Opl::Translations::Spanish, QStringLiteral("l10n/openpilotlog_es")},
-};
-static const QMap<Translations, QString> L10N_NAMES {
-    {Opl::Translations::English, QStringLiteral("English")},
-    {Opl::Translations::German,  QStringLiteral("Deutsch")},
-    {Opl::Translations::Spanish, QStringLiteral("Español")},
-};
-
 /*!
  * \brief PilotFunction
  * Pilot in Command, Pilot in Command under Supervision, Second in Command (Co-Pilot), Dual, Flight Instructor
  */
 enum PilotFunction {PIC = 0, PICUS = 1, SIC = 2, DUAL = 3, FI = 4};
 
-static const QMap<PilotFunction, QLatin1String> PILOT_FUNCTIONS = {
-    {PilotFunction::PIC, QLatin1String("PIC")},
-    {PilotFunction::PICUS, QLatin1String("PICUS")},
-    {PilotFunction::SIC, QLatin1String("SIC")},
-    {PilotFunction::DUAL, QLatin1String("DUAL")},
-    {PilotFunction::FI, QLatin1String("FI")},
-};
+/*!
+ * \brief Enumerates the available translations
+ */
+enum Translation {English, German, Spanish};
 
-inline void loadPilotFunctios(QComboBox *combo_box)
-{
-    for (int i = PilotFunction::PIC; i < PILOT_FUNCTIONS.size(); i++)
-        combo_box->addItem(PILOT_FUNCTIONS.value(PilotFunction(i)));
-};
+/*!
+ * \brief Enumerates the available SQL views in the database
+ */
+enum DbViewName {Default, DefaultWithSim, Easa, EasaWithSim};
 
 /*!
- * \brief Flight and Navigation Procedures Trainer 1/2, Flight Simulation Training Device
+ * \brief Enumerates the Simulator Types: Flight and Navigation Procedures Trainer 1/2, Flight Simulation Training Device
  */
 enum SimulatorTypes {FNPTI = 0, FNPTII = 1, FSTD = 2};
 
-static const QMap<SimulatorTypes, QString> SIMULATOR_TYPES = {
-    {FNPTI,  QStringLiteral("FNPT I")},
-    {FNPTII, QStringLiteral("FNPT II")},
-    {FSTD,   QStringLiteral("FSTD")},
-};
+/*!
+ * \brief The OplGlobals class encapsulates non-POD globals to avoid making them static. It is available
+ * as a global static object via the Opl::GLOBAL makro and may be used as if it were a pointer, guaranteed to be initialized exactly once.
+ * For more information, see (Q_GLOBAL_STATIC)[https://doc.qt.io/qt-5/qglobalstatic.html#details]
+ */
+class OplGlobals : public QObject {
+public:
+    OplGlobals() = default;
 
-inline void loadSimulatorTypes(QComboBox *combo_box)
-{
-    for (int i = 0; i < SIMULATOR_TYPES.size(); i++)
-        combo_box->addItem(SIMULATOR_TYPES.value(SimulatorTypes(i)));
-}
+    void fillLanguageComboBox(QComboBox *combo_box) const;
+    void fillViewNamesComboBox(QComboBox *combo_box) const;
+    void loadPilotFunctios(QComboBox *combo_box) const;
+    void loadSimulatorTypes(QComboBox *combo_box) const;
+    void loadApproachTypes(QComboBox *combo_box) const;
 
-static const QStringList APPROACH_TYPES = {
-        QStringLiteral("VISUAL"),
-        QStringLiteral("ILS CAT I"),
-        QStringLiteral("ILS CAT II"),
-        QStringLiteral("ILS CAT III"),
-        QStringLiteral("GLS"),
-        QStringLiteral("MLS"),
-        QStringLiteral("LOC"),
-        QStringLiteral("LOC/DME"),
-        QStringLiteral("RNAV"),
-        QStringLiteral("RNAV (LNAV)"),
-        QStringLiteral("RNAV (LNAV/VNAV)"),
-        QStringLiteral("RNAV (LPV)"),
-        QStringLiteral("RNAV (RNP)"),
-        QStringLiteral("RNAV (RNP-AR)"),
-        QStringLiteral("VOR"),
-        QStringLiteral("VOR/DME"),
-        QStringLiteral("NDB"),
-        QStringLiteral("NDB/DME"),
-        QStringLiteral("TACAN"),
-        QStringLiteral("SRA"),
-        QStringLiteral("PAR"),
-        QStringLiteral("OTHER")
-};
+    inline const QStringList &getApproachTypes() const {return APPROACH_TYPES;}
+    inline const QString getLanguageFilePath(Translation language) const {return L10N_FilePaths.value(language);}
+    inline const QString getViewIdentifier(DbViewName view_name) const {return DATABASE_VIEWS.value(view_name);}
+
+private:
+    Q_OBJECT
 
-inline void loadApproachTypes(QComboBox *combo_box)
-{
-    for (const auto & approach : APPROACH_TYPES)
-        combo_box->addItem(approach);
+    const QMap<Opl::Translation, QString> L10N_FilePaths {
+        {Translation::English, QStringLiteral("l10n/openpilotlog_en")},
+        {Translation::German,  QStringLiteral("l10n/openpilotlog_de")},
+        {Translation::Spanish, QStringLiteral("l10n/openpilotlog_es")},
+    };
+    const QMap<Translation, QString> L10N_DisplayNames {
+        {Translation::English, tr("English")},
+        {Translation::German,  tr("Deutsch")},
+        {Translation::Spanish, tr("Español")},
+    };
+    const QMap<DbViewName, QString> DATABASE_VIEWS = {
+        {Default,        QStringLiteral("viewDefault")},
+        {DefaultWithSim, QStringLiteral("viewDefaultSim")},
+        {Easa,           QStringLiteral("viewEasa")},
+        {EasaWithSim,    QStringLiteral("viewEasaSim")},
+    };
+    const QMap<DbViewName, QString> DATABASE_VIEW_DISPLAY_NAMES = {
+        {Default,        tr("Default")},
+        {DefaultWithSim, tr("Default with Simulator")},
+        {Easa,           tr("EASA-FCL")},
+        {EasaWithSim,    tr("EASA-FCL with Simulator")},
+    };
+    const QMap<PilotFunction, QLatin1String> PILOT_FUNCTIONS = {
+        {PilotFunction::PIC,   QLatin1String("PIC")},
+        {PilotFunction::PICUS, QLatin1String("PICUS")},
+        {PilotFunction::SIC,   QLatin1String("SIC")},
+        {PilotFunction::DUAL,  QLatin1String("DUAL")},
+        {PilotFunction::FI,    QLatin1String("FI")},
+    };
+    const QMap<SimulatorTypes, QString> SIMULATOR_TYPES = {
+        {FNPTI,  QStringLiteral("FNPT I")},
+        {FNPTII, QStringLiteral("FNPT II")},
+        {FSTD,   QStringLiteral("FSTD")},
+    };
+    const QStringList APPROACH_TYPES = {
+            QStringLiteral("VISUAL"),
+            QStringLiteral("ILS CAT I"),
+            QStringLiteral("ILS CAT II"),
+            QStringLiteral("ILS CAT III"),
+            QStringLiteral("GLS"),
+            QStringLiteral("MLS"),
+            QStringLiteral("LOC"),
+            QStringLiteral("LOC/DME"),
+            QStringLiteral("RNAV"),
+            QStringLiteral("RNAV (LNAV)"),
+            QStringLiteral("RNAV (LNAV/VNAV)"),
+            QStringLiteral("RNAV (LPV)"),
+            QStringLiteral("RNAV (RNP)"),
+            QStringLiteral("RNAV (RNP-AR)"),
+            QStringLiteral("VOR"),
+            QStringLiteral("VOR/DME"),
+            QStringLiteral("NDB"),
+            QStringLiteral("NDB/DME"),
+            QStringLiteral("TACAN"),
+            QStringLiteral("SRA"),
+            QStringLiteral("PAR"),
+            QStringLiteral("OTHER")
+    };
 };
+//Make available as a global static
+Q_GLOBAL_STATIC(OplGlobals, GLOBALS)
 
 namespace Date {
 
@@ -288,10 +312,10 @@ static const auto SIMULATORS_REMARKS     = QStringLiteral("remarks");
 static const auto ROWID                  = QStringLiteral("rowid");
 static const auto NULL_TIME_hhmm         = QStringLiteral("00:00");
 
-static const auto DEFAULT_FLIGHT_POSITION   = DataPosition(TABLE_FLIGHTS, 0);
-static const auto DEFAULT_PILOT_POSITION    = DataPosition(TABLE_PILOTS, 0);
-static const auto DEFAULT_TAIL_POSITION     = DataPosition(TABLE_TAILS, 0);
-static const auto DEFAULT_AIRCRAFT_POSITION = DataPosition(TABLE_AIRCRAFT, 0);
+//static const auto DEFAULT_FLIGHT_POSITION   = DataPosition(TABLE_FLIGHTS, 0);
+//static const auto DEFAULT_PILOT_POSITION    = DataPosition(TABLE_PILOTS, 0);
+//static const auto DEFAULT_TAIL_POSITION     = DataPosition(TABLE_TAILS, 0);
+//static const auto DEFAULT_AIRCRAFT_POSITION = DataPosition(TABLE_AIRCRAFT, 0);
 
 } // namespace opl::db