File indexing completed on 2024-05-19 05:07:22

0001 /*
0002     SPDX-FileCopyrightText: 2004-2006 Ace Jones <acejones@users.sourceforge.net>
0003     SPDX-FileCopyrightText: 2006 Darren Gould <darren_gould@gmx.de>
0004     SPDX-FileCopyrightText: 2007-2010 Alvaro Soliverez <asoliverez@gmail.com>
0005     SPDX-FileCopyrightText: 2010-2019 Thomas Baumgart <tbaumgart@kde.org>
0006     SPDX-FileCopyrightText: 2017-2018 Łukasz Wojniłowicz <lukasz.wojnilowicz@gmail.com>
0007     SPDX-FileCopyrightText: 2018 Michael Kiefer <Michael-Kiefer@web.de>
0008     SPDX-License-Identifier: GPL-2.0-or-later
0009 */
0010 
0011 #ifndef MYMONEYREPORT_H
0012 #define MYMONEYREPORT_H
0013 
0014 // ----------------------------------------------------------------------------
0015 // QT Includes
0016 
0017 // ----------------------------------------------------------------------------
0018 // Project Includes
0019 #include "mymoneyobject.h"
0020 #include "mymoneytransactionfilter.h"
0021 #include "kmm_mymoney_export.h"
0022 #include "mymoneyunittestable.h"
0023 
0024 class QString;
0025 class MyMoneyAccount;
0026 
0027 template <typename T> class QList;
0028 
0029 namespace eMyMoney {
0030 namespace Account {
0031 enum class Type;
0032 }
0033 namespace TransactionFilter {
0034 enum class Date;
0035 }
0036 }
0037 
0038 namespace eMyMoney {
0039 namespace Report {
0040 enum class RowType;
0041 enum class ReportType;
0042 enum class ColumnType;
0043 enum QueryColumn : int;
0044 enum class DetailLevel;
0045 enum class InvestmentSum;
0046 enum class ChartType;
0047 enum class DataLock;
0048 enum class ChartPalette;
0049 }
0050 }
0051 
0052 /**
0053   * This class defines a report within the MyMoneyEngine.  The report class
0054   * contains all the configuration parameters needed to run a report, plus
0055   * XML serialization.
0056   *
0057   * A report is a transactionfilter, so any report can specify which
0058   * transactions it's interested down to the most minute level of detail.
0059   * It extends the transactionfilter by providing identification (name,
0060   * comments, group type, etc) as well as layout information (what kind
0061   * of layout should be used, how the rows & columns should be presented,
0062   * currency converted, etc.)
0063   *
0064   * As noted above, this class only provides a report DEFINITION.  The
0065   * generation and presentation of the report itself are left to higher
0066   * level classes.
0067   *
0068   * @author Ace Jones <acejones@users.sourceforge.net>
0069   */
0070 
0071 class MyMoneyReportPrivate;
0072 class KMM_MYMONEY_EXPORT MyMoneyReport: public MyMoneyObject, public MyMoneyTransactionFilter
0073 {
0074     Q_DECLARE_PRIVATE_D(MyMoneyObject::d_ptr, MyMoneyReport)
0075 
0076     KMM_MYMONEY_UNIT_TESTABLE
0077 
0078 public:
0079     MyMoneyReport();
0080     explicit MyMoneyReport(const QString &id);
0081 
0082     explicit MyMoneyReport(eMyMoney::Report::RowType rt,
0083                            unsigned ct,
0084                            eMyMoney::TransactionFilter::Date dl,
0085                            eMyMoney::Report::DetailLevel ss,
0086                            const QString& name,
0087                            const QString& comment);
0088 
0089     MyMoneyReport(const QString& id,
0090                   const MyMoneyReport& other);
0091 
0092     MyMoneyReport(const MyMoneyReport & other);
0093     MyMoneyReport(MyMoneyReport && other);
0094     MyMoneyReport & operator=(MyMoneyReport other);
0095     friend void swap(MyMoneyReport& first, MyMoneyReport& second);
0096 
0097     ~MyMoneyReport();
0098 
0099     eMyMoney::Report::ReportType reportType() const;
0100     void setReportType(eMyMoney::Report::ReportType rt);
0101 
0102     QString name() const;
0103     void setName(const QString& s);
0104 
0105     bool isShowingRowTotals() const;
0106     void setShowingRowTotals(bool f);
0107 
0108     bool isShowingColumnTotals() const;
0109     void setShowingColumnTotals(bool f);
0110 
0111     eMyMoney::Report::RowType rowType() const;
0112     void setRowType(eMyMoney::Report::RowType rt);
0113     bool isRunningSum() const;
0114 
0115     eMyMoney::Report::ColumnType columnType() const;
0116     void setColumnType(eMyMoney::Report::ColumnType ct);
0117 
0118     bool isConvertCurrency() const;
0119     void setConvertCurrency(bool f);
0120     uint columnPitch() const;
0121 
0122     QString comment() const;
0123     void setComment(const QString& comment);
0124 
0125     eMyMoney::Report::QueryColumn queryColumns() const;
0126     void setQueryColumns(eMyMoney::Report::QueryColumn qc);
0127 
0128     QString group() const;
0129     void setGroup(const QString& group);
0130 
0131     bool isFavorite() const;
0132     void setFavorite(bool f);
0133 
0134     bool isTax() const;
0135     void setTax(bool f);
0136 
0137     bool isInvestmentsOnly() const;
0138     void setInvestmentsOnly(bool f);
0139 
0140     bool isLoansOnly() const;
0141     void setLoansOnly(bool f);
0142 
0143     bool isPropagateBudgetDifference() const;
0144     void setPropagateBudgetDifference(bool f);
0145 
0146     eMyMoney::Report::DetailLevel detailLevel() const;
0147     void setDetailLevel(eMyMoney::Report::DetailLevel detail);
0148 
0149     eMyMoney::Report::InvestmentSum investmentSum() const;
0150     void setInvestmentSum(eMyMoney::Report::InvestmentSum sum);
0151 
0152     bool isHideTransactions() const;
0153     void setHideTransactions(bool f);
0154 
0155     eMyMoney::Report::ChartType chartType() const;
0156     void setChartType(eMyMoney::Report::ChartType type);
0157 
0158     eMyMoney::Report::ChartPalette chartPalette() const;
0159     void setChartPalette(eMyMoney::Report::ChartPalette type);
0160 
0161     bool isChartDataLabels() const;
0162     void setChartDataLabels(bool f);
0163 
0164     bool isChartCHGridLines() const;
0165     void setChartCHGridLines(bool f);
0166 
0167     bool isChartSVGridLines() const;
0168     void setChartSVGridLines(bool f);
0169 
0170     bool isChartByDefault() const;
0171     void setChartByDefault(bool f);
0172 
0173     uint chartLineWidth() const;
0174     void setChartLineWidth(uint f);
0175 
0176     bool isLogYAxis() const;
0177     void setLogYAxis(bool f);
0178 
0179     bool isNegExpenses() const;
0180     void setNegExpenses(bool f);
0181 
0182     QString dataRangeStart() const;
0183     void setDataRangeStart(const QString& f);
0184 
0185     QString dataRangeEnd() const;
0186     void setDataRangeEnd(const QString& f);
0187 
0188     QString dataMajorTick() const;
0189     void setDataMajorTick(const QString& f);
0190 
0191     QString dataMinorTick() const;
0192     void setDataMinorTick(const QString& f);
0193 
0194     uint yLabelsPrecision() const;
0195     void setYLabelsPrecision(int f);
0196 
0197     bool isIncludingSchedules() const;
0198     void setIncludingSchedules(bool f);
0199 
0200     bool isColumnsAreDays() const;
0201     void setColumnsAreDays(bool f);
0202 
0203     bool isIncludingTransfers() const;
0204     void setIncludingTransfers(bool f);
0205 
0206     bool isIncludingUnusedAccounts() const;
0207     void setIncludingUnusedAccounts(bool f);
0208 
0209     bool hasBudget() const;
0210     QString budget() const;
0211 
0212     /**
0213       * Sets the budget used for this report
0214       *
0215       * @param budget The ID of the budget to use, or an empty string
0216       * to indicate a budget is NOT included
0217       * @param fa Whether to display actual data alongside the budget.
0218       * Setting to false means the report displays ONLY the budget itself.
0219       * @warning For now, the budget ID is ignored.  The budget id is
0220       * simply checked for any non-empty string, and if so, hasBudget()
0221       * will return true.
0222       */
0223     void setBudget(const QString& budget, bool fa = true);
0224 
0225     bool isIncludingBudgetActuals() const;
0226     void setIncludingBudgetActuals(bool f);
0227 
0228     bool isIncludingForecast() const;
0229     void setIncludingForecast(bool f);
0230 
0231     bool isIncludingMovingAverage() const;
0232     void setIncludingMovingAverage(bool f);
0233 
0234     int movingAverageDays() const;
0235     void setMovingAverageDays(int days);
0236 
0237     bool isIncludingPrice() const;
0238     void setIncludingPrice(bool f);
0239 
0240     bool isIncludingAveragePrice() const;
0241     void setIncludingAveragePrice(bool f);
0242 
0243     eMyMoney::Report::DataLock dataFilter() const;
0244     bool isDataUserDefined() const;
0245     void setDataFilter(eMyMoney::Report::DataLock u);
0246 
0247     eMyMoney::TransactionFilter::Date dateRange() const;
0248     bool isDateUserDefined() const;
0249 
0250     /**
0251       * Set the underlying date filter and LOCK that filter to the specified
0252       * range.  For example, if @p _u is "CurrentMonth", this report should always
0253       * be updated to the current month no matter when the report is run.
0254       *
0255       * This updating is not entirely automatic, you should update it yourself by
0256       * calling updateDateFilter.
0257       *
0258       * @param _u The date range constant (MyMoneyTransactionFilter::dateRangeE)
0259       *          which this report should be locked to.
0260       */
0261 
0262     void setDateFilter(eMyMoney::TransactionFilter::Date u);
0263 
0264     /**
0265       * Set the underlying date filter using the start and end dates provided.
0266       * Note that this does not LOCK to any range like setDateFilter(unsigned)
0267       * above.  It is just a reimplementation of the MyMoneyTransactionFilter
0268       * version.
0269       *
0270       * @param _db The inclusive begin date of the date range
0271       * @param _de The inclusive end date of the date range
0272       */
0273 
0274     void setDateFilter(const QDate& db, const QDate& de);
0275 
0276     /**
0277       * Set the underlying date filter using the 'date lock' property.
0278       *
0279       * Always call this function before executing the report to be sure that
0280       * the date filters properly match the plain-language 'date lock'.
0281       *
0282       * For example, if the report is date-locked to "Current Month", and the
0283       * last time you loaded or ran the report was in August, but it's now
0284       * September, this function will update the date range to be September,
0285       * as is proper.
0286       */
0287     void updateDateFilter();
0288 
0289     bool isMixedTime() const;
0290     void setMixedTime(bool f);
0291 
0292     int currentDateColumn() const;
0293     void setCurrentDateColumn(int f);
0294 
0295     uint settlementPeriod() const;
0296     void setSettlementPeriod(uint days);
0297 
0298     bool isShowingSTLTCapitalGains() const;
0299     void setShowSTLTCapitalGains(bool f);
0300 
0301     QDate termSeparator() const;
0302     void setTermSeparator(const QDate& date);
0303 
0304     bool isSkippingZero() const;
0305     void setSkipZero(int f);
0306 
0307     /**
0308       * This method allows you to clear the underlying transaction filter
0309       */
0310     void clearTransactionFilter();
0311 
0312     /**
0313       * This method allows you to set the underlying transaction filter
0314       *
0315       * @param _filter The filter which should replace the existing transaction
0316       * filter.
0317       */
0318     void assignFilter(const MyMoneyTransactionFilter& filter);
0319 
0320     /**
0321       * Retrieves a VALID beginning & ending date for this report.
0322       *
0323       * The underlying date filter can return en empty QDate() for either the
0324       * begin or end date or both.  This is typically unacceptable for reports,
0325       * which need the REAL begin and end date.
0326       *
0327       * This function gets the underlying date filter range, and if either is
0328       * an empty QDate(), it determines the missing date from looking at all
0329       * the transactions which match the underlying filter, and returning the
0330       * date of the first or last transaction (as appropriate).
0331       *
0332       * @param _db The inclusive begin date of the date range
0333       * @param _de The inclusive end date of the date range
0334       */
0335     void validDateRange(QDate &db, QDate &de);
0336 
0337     /**
0338       * This method turns on the account group filter and adds the
0339       * @p type to the list of allowed groups.
0340       *
0341       * Note that account group filtering is handled differently
0342       * than all the filters of the underlying class.  This filter
0343       * is meant to be applied to individual splits of matched
0344       * transactions AFTER the underlying filter is used to find
0345       * the matching transactions.
0346       *
0347       * @param type the account group to add to the allowed groups list
0348       */
0349     void addAccountGroup(eMyMoney::Account::Type type);
0350 
0351     /**
0352       * This method returns whether an account group filter has been set,
0353       * and if so, it returns all the account groups set in the filter.
0354       *
0355       * @param list list to append account groups into
0356       * @return return true if an account group filter has been set
0357       */
0358     bool accountGroups(QList<eMyMoney::Account::Type>& list) const;
0359 
0360     /**
0361       * This method returns whether the specified account group
0362       * is allowed by the account groups filter.
0363       *
0364       * @param type group to append account groups into
0365       * @return return true if an account group filter has been set
0366       */
0367     bool includesAccountGroup(eMyMoney::Account::Type type) const;
0368 
0369     /**
0370       * This method is used to test whether a specific account
0371       * passes the accountGroup test and either the Account or
0372       * Category test, depending on which sort of Account it is.
0373       *
0374       * The m_tax and m_investments properties are also considered.
0375       *
0376       * @param acc the account in question
0377       * @return true if account is in filter set, false otherwise
0378       */
0379     bool includes(const MyMoneyAccount& acc) const;
0380 
0381     /**
0382      * Return row type as string.
0383      *
0384      * @param type type to get string for
0385      * @return row type converted to string
0386      */
0387     static QString toString(eMyMoney::Report::RowType type);
0388 
0389     /**
0390      * Return report type as string.
0391      *
0392      * @param type report type to get string for
0393      * @return report type converted to string
0394      */
0395     static QString toString(eMyMoney::Report::ReportType type);
0396 
0397     /**
0398       * This method allows to modify and retrieve the default lineWidth for graphs.
0399       * The default is 2.
0400       */
0401     static void setLineWidth(int width);
0402     static int lineWidth();
0403 
0404     // set the expert mode which shows equity accounts for some reports
0405     static void setExpertMode(bool expertMode);
0406 
0407 private:
0408     void addAccountGroupsByRowType(eMyMoney::Report::RowType rt);
0409 
0410 private:
0411     /**
0412       * This member keeps the current setting for line graphs lineWidth.
0413       * @sa setLineWidth()
0414       */
0415     static int m_lineWidth;
0416 
0417     static bool m_expertMode;
0418 };
0419 
0420 inline void swap(MyMoneyReport& first, MyMoneyReport& second) // krazy:exclude=inline
0421 {
0422     using std::swap;
0423     swap(first.MyMoneyObject::d_ptr, second.MyMoneyObject::d_ptr);
0424     swap(first.MyMoneyTransactionFilter::d_ptr, second.MyMoneyTransactionFilter::d_ptr);
0425 }
0426 
0427 inline MyMoneyReport::MyMoneyReport(MyMoneyReport && other) : MyMoneyReport() // krazy:exclude=inline
0428 {
0429     swap(*this, other);
0430 }
0431 
0432 inline MyMoneyReport & MyMoneyReport::operator=(MyMoneyReport other) // krazy:exclude=inline
0433 {
0434     swap(*this, other);
0435     return *this;
0436 }
0437 
0438 /**
0439   * Make it possible to hold @ref MyMoneyReport objects inside @ref QVariant objects.
0440   */
0441 Q_DECLARE_METATYPE(MyMoneyReport)
0442 
0443 #endif // MYMONEYREPORT_H