1 /*
2     SPDX-FileCopyrightText: 2019 Volker Krause <vkrause@kde.org>
3 
4     SPDX-License-Identifier: LGPL-2.0-or-later
5 */
6 
7 #ifndef STATISTICSMODEL_H
8 #define STATISTICSMODEL_H
9 
10 #include <QDate>
11 #include <QObject>
12 
13 #include <set>
14 
15 class ReservationManager;
16 class TripGroupManager;
17 
18 /** Statistics data item. */
19 class StatisticsItem
20 {
21     Q_GADGET
22     Q_PROPERTY(QString label MEMBER m_label CONSTANT)
23     Q_PROPERTY(QString value MEMBER m_value CONSTANT)
24     Q_PROPERTY(Trend trend MEMBER m_trend CONSTANT)
25 
26 public:
27     enum Trend {
28         TrendUnknown,
29         TrendUp,
30         TrendDown,
31         TrendUnchanged
32     };
33     Q_ENUM(Trend)
34 
35     StatisticsItem();
36     explicit StatisticsItem(const QString &label, const QString &value, StatisticsItem::Trend trend = TrendUnknown);
37     ~StatisticsItem();
38 
39     QString m_label;
40     QString m_value;
41     Trend m_trend = TrendUnknown;
42 };
43 
Q_DECLARE_METATYPE(StatisticsItem)44 Q_DECLARE_METATYPE(StatisticsItem)
45 
46 /** Provides the data shown in the statistics page. */
47 class StatisticsModel : public QObject
48 {
49     Q_OBJECT
50     Q_PROPERTY(StatisticsItem totalCount READ totalCount NOTIFY changed)
51     Q_PROPERTY(StatisticsItem totalDistance READ totalDistance NOTIFY changed)
52     Q_PROPERTY(StatisticsItem totalNights READ totalNights NOTIFY changed)
53     Q_PROPERTY(StatisticsItem totalCO2 READ totalCO2 NOTIFY changed)
54     Q_PROPERTY(StatisticsItem visitedCountries READ visitedCountries NOTIFY changed)
55 
56     Q_PROPERTY(StatisticsItem flightCount READ flightCount NOTIFY changed)
57     Q_PROPERTY(StatisticsItem flightDistance READ flightDistance NOTIFY changed)
58     Q_PROPERTY(StatisticsItem flightCO2 READ flightCO2 NOTIFY changed)
59 
60     Q_PROPERTY(StatisticsItem trainCount READ trainCount NOTIFY changed)
61     Q_PROPERTY(StatisticsItem trainDistance READ trainDistance NOTIFY changed)
62     Q_PROPERTY(StatisticsItem trainCO2 READ trainCO2 NOTIFY changed)
63 
64     Q_PROPERTY(StatisticsItem busCount READ busCount NOTIFY changed)
65     Q_PROPERTY(StatisticsItem busDistance READ busDistance NOTIFY changed)
66     Q_PROPERTY(StatisticsItem busCO2 READ busCO2 NOTIFY changed)
67 
68     Q_PROPERTY(StatisticsItem carCount READ carCount NOTIFY changed)
69     Q_PROPERTY(StatisticsItem carDistance READ carDistance NOTIFY changed)
70     Q_PROPERTY(StatisticsItem carCO2 READ carCO2 NOTIFY changed)
71 
72     Q_PROPERTY(ReservationManager* reservationManager READ reservationManager WRITE setReservationManager NOTIFY setupChanged)
73     Q_PROPERTY(TripGroupManager* tripGroupManager READ tripGroupManager WRITE setTripGroupManager NOTIFY setupChanged)
74 
75 public:
76     explicit StatisticsModel(QObject *parent = nullptr);
77     ~StatisticsModel() override;
78 
79     ReservationManager* reservationManager() const;
80     void setReservationManager(ReservationManager *resMgr);
81     TripGroupManager* tripGroupManager() const;
82     void setTripGroupManager(TripGroupManager *tripGroupMgr);
83 
84     Q_INVOKABLE void setTimeRange(const QDate &begin, const QDate &end);
85 
86     StatisticsItem totalCount() const;
87     StatisticsItem totalDistance() const;
88     StatisticsItem totalNights() const;
89     StatisticsItem totalCO2() const;
90     StatisticsItem visitedCountries() const;
91 
92     StatisticsItem flightCount() const;
93     StatisticsItem flightDistance() const;
94     StatisticsItem flightCO2() const;
95 
96     StatisticsItem trainCount() const;
97     StatisticsItem trainDistance() const;
98     StatisticsItem trainCO2() const;
99 
100     StatisticsItem busCount() const;
101     StatisticsItem busDistance() const;
102     StatisticsItem busCO2() const;
103 
104     StatisticsItem carCount() const;
105     StatisticsItem carDistance() const;
106     StatisticsItem carCO2() const;
107 
108 Q_SIGNALS:
109     void setupChanged();
110     void changed();
111 
112 private:
113     void recompute();
114 
115     ReservationManager *m_resMgr = nullptr;
116     TripGroupManager *m_tripGroupMgr = nullptr;
117     QDate m_begin;
118     QDate m_end;
119 
120     enum AggregateType { Total, Flight, Train, Bus, Car, AGGREGATE_TYPE_COUNT };
121     enum StatType { TripCount, Distance, CO2, STAT_TYPE_COUNT };
122 
123     AggregateType typeForReservation(const QVariant &res) const;
124     int co2emission(AggregateType type, int distance) const;
125     void computeStats(const QVariant &res, int (&statData)[AGGREGATE_TYPE_COUNT][STAT_TYPE_COUNT]);
126 
127     StatisticsItem::Trend trend(int current, int prev) const;
128     StatisticsItem::Trend trend(AggregateType type, StatType stat) const;
129 
130     std::set<QString> m_countries;
131 
132     int m_statData[AGGREGATE_TYPE_COUNT][STAT_TYPE_COUNT];
133     int m_prevStatData[AGGREGATE_TYPE_COUNT][STAT_TYPE_COUNT];
134     int m_hotelCount = 0;
135     int m_prevHotelCount = 0;
136     int m_tripGroupCount = 0;
137     int m_prevTripGroupCount = 0;
138 };
139 
140 #endif // STATISTICSMODEL_H
141