Add inner month statistics
This commit is contained in:
parent
cedb13c3ec
commit
84aa1fb42b
|
@ -445,6 +445,17 @@ void KissCount::GetStats(int monthFrom, int yearFrom, int monthTo, int yearTo,
|
|||
_db->GetStats(_user, monthF, yearF, monthT, yearT, accountAmounts, categories);
|
||||
}
|
||||
|
||||
void KissCount::GetMonthStats(int month, int year, int nbDays,
|
||||
std::map<wxString, std::vector<double> >* operations,
|
||||
std::map<wxString, double>* categories)
|
||||
{
|
||||
wxString monthS = wxString::Format(wxT("%d"), month);
|
||||
wxString yearS = wxString::Format(wxT("%d"), year);
|
||||
|
||||
_db->GetMonthStats(_user, monthS, yearS, nbDays, operations, categories);
|
||||
}
|
||||
|
||||
|
||||
std::map<wxString, double>* KissCount::GetNotChecked(int month, int year)
|
||||
{
|
||||
return _db->GetNotChecked(_user, month, year);
|
||||
|
|
|
@ -90,6 +90,10 @@ public:
|
|||
std::map<wxString, std::map<int, std::map<int, double> > >* accountAmounts,
|
||||
std::map<wxString, double>* categories);
|
||||
|
||||
void GetMonthStats(int month, int year, int nbDays,
|
||||
std::map<wxString, std::vector<double> >* operations,
|
||||
std::map<wxString, double>* categories);
|
||||
|
||||
std::map<wxString, double>* GetNotChecked(int month, int year);
|
||||
|
||||
static wxFont ExtractFont(wxString strFont);
|
||||
|
|
|
@ -1406,65 +1406,135 @@ void Database::GetStats(User* user, const wxString& monthFrom, const wxString& y
|
|||
std::vector<Account>::iterator accountIt;
|
||||
std::vector<Category>::iterator categoryIt;
|
||||
|
||||
if (!user->_accounts.empty())
|
||||
{
|
||||
if (accountAmounts)
|
||||
{
|
||||
for (accountIt = user->_accounts.begin(); accountIt != user->_accounts.end(); accountIt++)
|
||||
{
|
||||
req = wxT("SELECT month, year, amount FROM account_amount WHERE account ='") + accountIt->id + wxT("'");
|
||||
req += wxT(" AND (year > '") + yearFrom + wxT("' OR (year == '") + yearFrom + wxT("' AND month >= '") + monthFrom + wxT("'))");
|
||||
req += wxT(" AND (year < '") + yearTo + wxT("' OR (year == '") + yearTo + wxT("' AND month <= '") + monthTo + wxT("'))");
|
||||
|
||||
EXECUTE_SQL_QUERY(req, set, );
|
||||
|
||||
while (set.NextRow())
|
||||
{
|
||||
(*accountAmounts)[accountIt->id][set.GetInt(wxT("year"))][set.GetInt(wxT("month"))] = set.GetInt(wxT("amount"));
|
||||
}
|
||||
set.Finalize();
|
||||
}
|
||||
}
|
||||
|
||||
if (categories)
|
||||
{
|
||||
for (categoryIt = user->_categories.begin(); categoryIt != user->_categories.end(); categoryIt++)
|
||||
{
|
||||
req = wxT("SELECT SUM(amount) as amount FROM operation AS o1 WHERE category='") + categoryIt->id + wxT("'");
|
||||
accountIt = user->_accounts.begin();
|
||||
req += wxT(" AND (account IN('") + accountIt->id;
|
||||
accountIt++;
|
||||
for (;accountIt != user->_accounts.end(); accountIt++)
|
||||
{
|
||||
req += wxT("', '") + accountIt->id ;
|
||||
}
|
||||
req += wxT("')");
|
||||
req += wxT(" OR user='") + user->_id + wxT("')");
|
||||
|
||||
req += wxT(" AND (year > '") + yearFrom + wxT("' OR (year == '") + yearFrom + wxT("' AND month >= '") + monthFrom + wxT("'))");
|
||||
req += wxT(" AND (year < '") + yearTo + wxT("' OR (year == '") + yearTo + wxT("' AND month <= '") + monthTo + wxT("'))");
|
||||
req += wxT(" AND meta='0'");
|
||||
|
||||
req2 = req + wxT(" AND (transfert='' OR transfert IS NULL)");
|
||||
req2 += wxT(" AND amount < 0");
|
||||
|
||||
EXECUTE_SQL_QUERY(req2, set, );
|
||||
|
||||
if (set.NextRow())
|
||||
{
|
||||
(*categories)[categoryIt->id] = -set.GetDouble(wxT("amount"));
|
||||
}
|
||||
set.Finalize();
|
||||
|
||||
// Transfert on blocked accounts must be computed
|
||||
req2 = req + wxT(" AND transfert != ''");
|
||||
req2 = req + wxT(" AND (SELECT blocked FROM account WHERE id=o1.account)");
|
||||
req2 += wxT(" AND amount > 0");
|
||||
|
||||
EXECUTE_SQL_QUERY(req2, set, );
|
||||
|
||||
if (set.NextRow())
|
||||
{
|
||||
(*categories)[categoryIt->id] += set.GetDouble(wxT("amount"));
|
||||
}
|
||||
set.Finalize();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Database::GetMonthStats(User* user, const wxString& month, const wxString& year, int nbDays,
|
||||
std::map<wxString, std::vector<double> >* operations,
|
||||
std::map<wxString, double>* categories)
|
||||
{
|
||||
wxSQLite3ResultSet set;
|
||||
wxString req;
|
||||
std::vector<Account>::iterator accountIt;
|
||||
int previous_amount, previous_day, cur_day;
|
||||
|
||||
if (!user->_accounts.empty())
|
||||
{
|
||||
for (accountIt = user->_accounts.begin(); accountIt != user->_accounts.end(); accountIt++)
|
||||
{
|
||||
req = wxT("SELECT month, year, amount FROM account_amount WHERE account ='") + accountIt->id + wxT("'");
|
||||
req += wxT(" AND (year > '") + yearFrom + wxT("' OR (year == '") + yearFrom + wxT("' AND month >= '") + monthFrom + wxT("'))");
|
||||
req += wxT(" AND (year < '") + yearTo + wxT("' OR (year == '") + yearTo + wxT("' AND month <= '") + monthTo + wxT("'))");
|
||||
req = wxT("SELECT amount FROM account_amount WHERE account ='") + accountIt->id + wxT("'");
|
||||
req += wxT(" AND year = '") + year + wxT("'");
|
||||
req += wxT(" AND month = '") + month + wxT("'");
|
||||
|
||||
EXECUTE_SQL_QUERY(req, set, );
|
||||
|
||||
while (set.NextRow())
|
||||
{
|
||||
(*accountAmounts)[accountIt->id][set.GetInt(wxT("year"))][set.GetInt(wxT("month"))] = set.GetInt(wxT("amount"));
|
||||
(*operations)[accountIt->id].clear();
|
||||
|
||||
previous_amount = set.GetInt(wxT("amount"));
|
||||
}
|
||||
set.Finalize();
|
||||
}
|
||||
|
||||
for (categoryIt = user->_categories.begin(); categoryIt != user->_categories.end(); categoryIt++)
|
||||
{
|
||||
req = wxT("SELECT SUM(amount) as amount FROM operation AS o1 WHERE category='") + categoryIt->id + wxT("'");
|
||||
accountIt = user->_accounts.begin();
|
||||
req += wxT(" AND (account IN('") + accountIt->id;
|
||||
accountIt++;
|
||||
for (;accountIt != user->_accounts.end(); accountIt++)
|
||||
{
|
||||
req += wxT("', '") + accountIt->id ;
|
||||
}
|
||||
req += wxT("')");
|
||||
req += wxT(" OR user='") + user->_id + wxT("')");
|
||||
|
||||
req += wxT(" AND (year > '") + yearFrom + wxT("' OR (year == '") + yearFrom + wxT("' AND month >= '") + monthFrom + wxT("'))");
|
||||
req += wxT(" AND (year < '") + yearTo + wxT("' OR (year == '") + yearTo + wxT("' AND month <= '") + monthTo + wxT("'))");
|
||||
req = wxT("SELECT day, amount FROM operation WHERE");
|
||||
req += wxT(" account = '") + accountIt->id + wxT("'");
|
||||
req += wxT(" AND year = '") + year + wxT("'");
|
||||
req += wxT(" AND month = '") + month + wxT("'");
|
||||
req += wxT(" AND meta='0'");
|
||||
|
||||
req2 = req + wxT(" AND (transfert='' OR transfert IS NULL)");
|
||||
req2 += wxT(" AND amount < 0");
|
||||
req += wxT(" ORDER BY day ASC");
|
||||
|
||||
EXECUTE_SQL_QUERY(req2, set, );
|
||||
EXECUTE_SQL_QUERY(req, set, );
|
||||
|
||||
if (set.NextRow())
|
||||
cur_day = previous_day = -1;
|
||||
while (set.NextRow())
|
||||
{
|
||||
(*categories)[categoryIt->id] = -set.GetDouble(wxT("amount"));
|
||||
cur_day = set.GetInt(wxT("day"));
|
||||
while (cur_day != previous_day)
|
||||
{
|
||||
(*operations)[accountIt->id].push_back(previous_amount);
|
||||
previous_day++;
|
||||
}
|
||||
|
||||
previous_amount += set.GetDouble(wxT("amount"));
|
||||
(*operations)[accountIt->id][cur_day] = previous_amount;
|
||||
}
|
||||
set.Finalize();
|
||||
set.Finalize();
|
||||
|
||||
// Transfert on blocked accounts must be computed
|
||||
req2 = req + wxT(" AND transfert != ''");
|
||||
req2 = req + wxT(" AND (SELECT blocked FROM account WHERE id=o1.account)");
|
||||
req2 += wxT(" AND amount > 0");
|
||||
|
||||
EXECUTE_SQL_QUERY(req2, set, );
|
||||
|
||||
if (set.NextRow())
|
||||
while (cur_day < nbDays)
|
||||
{
|
||||
(*categories)[categoryIt->id] += set.GetDouble(wxT("amount"));
|
||||
(*operations)[accountIt->id].push_back(previous_amount);
|
||||
cur_day++;
|
||||
}
|
||||
set.Finalize();
|
||||
}
|
||||
}
|
||||
|
||||
// Fill categories
|
||||
GetStats(user, month, year, month, year, NULL, categories) ;
|
||||
}
|
||||
|
||||
std::map<wxString, double>* Database::GetNotChecked(User* user, int month, int year)
|
||||
|
|
|
@ -89,6 +89,10 @@ public:
|
|||
const wxString& yearTo, std::map<wxString, std::map<int, std::map<int, double> > >* accountAmounts,
|
||||
std::map<wxString, double>* categories);
|
||||
|
||||
void GetMonthStats(User* user, const wxString& month, const wxString& year, int nbDays,
|
||||
std::map<wxString, std::vector<double> >* operations,
|
||||
std::map<wxString, double>* categories);
|
||||
|
||||
void KillMe(User* user);
|
||||
bool GetOperation(const wxString& id, Operation* op);
|
||||
std::map<wxString, wxString> getSharedAccountOwners(const wxString& account);
|
||||
|
|
|
@ -151,14 +151,17 @@ void StatsPanel::UpdateStats(int monthFrom, int yearFrom, int monthTo, int yearT
|
|||
{
|
||||
std::map<wxString, std::map<int, std::map<int, double> > > accountAmounts;
|
||||
std::map<wxString, double> categories;
|
||||
std::map<wxString, std::vector<double> > operations;
|
||||
std::map<wxString, std::vector<double> >::iterator accountIdIt2;
|
||||
std::map<wxString, double>::iterator categoriesIt;
|
||||
std::map<wxString, std::map<int, std::map<int, double> > >::iterator accountIdIt;
|
||||
std::map<int, std::map<int, double> >::iterator accountYearIt;
|
||||
double total;
|
||||
int size, i, a, b, percents, account;
|
||||
int size, i, a, b, percents, account, nbDays;
|
||||
double *amounts;
|
||||
wxString value;
|
||||
User* user = _kiss->GetUser();
|
||||
wxDateTime date;
|
||||
|
||||
if (_chart)
|
||||
{
|
||||
|
@ -167,58 +170,100 @@ void StatsPanel::UpdateStats(int monthFrom, int yearFrom, int monthTo, int yearT
|
|||
delete _chart;
|
||||
}
|
||||
|
||||
_kiss->GetStats(monthFrom, yearFrom, monthTo, yearTo, &accountAmounts, &categories);
|
||||
|
||||
// first step: create plot
|
||||
_plot = new XYPlot();
|
||||
|
||||
// create dataset
|
||||
XYSimpleDataset *dataset = new XYSimpleDataset();
|
||||
|
||||
// Line on 0 all over the years
|
||||
size = ((yearTo - yearFrom) + 1) * 12;
|
||||
amounts = new double[size*2];
|
||||
for (a=0; a<(size/12); a++)
|
||||
if (monthFrom == monthTo && yearFrom == yearTo)
|
||||
{
|
||||
for(b=0; b<12; b++)
|
||||
{
|
||||
amounts[a*12*2+b*2+0] = a*12+b;
|
||||
amounts[a*12*2+b*2+1] = 0;
|
||||
}
|
||||
}
|
||||
nbDays = date.GetLastMonthDay((wxDateTime::Month)monthFrom, yearFrom).GetDay();
|
||||
|
||||
dataset->AddSerie((double *) amounts, size);
|
||||
delete[] amounts;
|
||||
_kiss->GetMonthStats(monthFrom, yearFrom, nbDays, &operations, &categories);
|
||||
|
||||
for (account = 0, i = 0, accountIdIt = accountAmounts.begin(); accountIdIt != accountAmounts.end();
|
||||
accountIdIt++, i++, account++)
|
||||
{
|
||||
if (!((wxCheckListBox*)_account)->IsChecked(account))
|
||||
// Line on 0 all over the years
|
||||
amounts = new double[nbDays*2];
|
||||
for (a=0; a<nbDays; a++)
|
||||
{
|
||||
i-- ;
|
||||
continue;
|
||||
amounts[a*2+0] = a;
|
||||
amounts[a*2+1] = 0;
|
||||
}
|
||||
|
||||
size = accountAmounts[accountIdIt->first].size();
|
||||
amounts = new double[size*12*2];
|
||||
size = 0;
|
||||
for(a = 0, accountYearIt = accountAmounts[accountIdIt->first].begin();
|
||||
accountYearIt != accountAmounts[accountIdIt->first].end();
|
||||
accountYearIt++, a++)
|
||||
dataset->AddSerie((double *) amounts, nbDays);
|
||||
delete[] amounts;
|
||||
|
||||
for (account = 0, i = 0, accountIdIt2 = operations.begin(); accountIdIt2 != operations.end();
|
||||
accountIdIt2++, i++, account++)
|
||||
{
|
||||
for(b = 0; b<12; b++)
|
||||
if (!((wxCheckListBox*)_account)->IsChecked(account))
|
||||
{
|
||||
if (!accountAmounts[accountIdIt->first][accountYearIt->first].count(b))
|
||||
continue;
|
||||
amounts[size*2+0] = a*12+b;
|
||||
amounts[size*2+1] = accountAmounts[accountIdIt->first][accountYearIt->first][b];
|
||||
size++;
|
||||
i-- ;
|
||||
continue;
|
||||
}
|
||||
|
||||
amounts = new double[nbDays*2];
|
||||
size = 0;
|
||||
for (a=0; a<nbDays; a++)
|
||||
{
|
||||
amounts[a*2+0] = a;
|
||||
amounts[a*2+1] = operations[accountIdIt2->first][a];
|
||||
}
|
||||
dataset->AddSerie((double *) amounts, nbDays);
|
||||
// set serie names to be displayed on legend
|
||||
dataset->SetSerieName(i+1, user->GetAccountName(accountIdIt2->first));
|
||||
delete[] amounts;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
_kiss->GetStats(monthFrom, yearFrom, monthTo, yearTo, &accountAmounts, &categories);
|
||||
|
||||
// Line on 0 all over the years
|
||||
size = ((yearTo - yearFrom) + 1) * 12;
|
||||
amounts = new double[size*2];
|
||||
for (a=0; a<(size/12); a++)
|
||||
{
|
||||
for(b=0; b<12; b++)
|
||||
{
|
||||
amounts[a*12*2+b*2+0] = a*12+b;
|
||||
amounts[a*12*2+b*2+1] = 0;
|
||||
}
|
||||
}
|
||||
dataset->AddSerie((double *) amounts, size);
|
||||
// set serie names to be displayed on legend
|
||||
dataset->SetSerieName(i+1, user->GetAccountName(accountIdIt->first));
|
||||
delete[] amounts;
|
||||
|
||||
dataset->AddSerie((double *) amounts, size);
|
||||
delete[] amounts;
|
||||
|
||||
for (account = 0, i = 0, accountIdIt = accountAmounts.begin(); accountIdIt != accountAmounts.end();
|
||||
accountIdIt++, i++, account++)
|
||||
{
|
||||
if (!((wxCheckListBox*)_account)->IsChecked(account))
|
||||
{
|
||||
i-- ;
|
||||
continue;
|
||||
}
|
||||
|
||||
size = accountAmounts[accountIdIt->first].size();
|
||||
amounts = new double[size*12*2];
|
||||
size = 0;
|
||||
for(a = 0, accountYearIt = accountAmounts[accountIdIt->first].begin();
|
||||
accountYearIt != accountAmounts[accountIdIt->first].end();
|
||||
accountYearIt++, a++)
|
||||
{
|
||||
for(b = 0; b<12; b++)
|
||||
{
|
||||
if (!accountAmounts[accountIdIt->first][accountYearIt->first].count(b))
|
||||
continue;
|
||||
amounts[size*2+0] = a*12+b;
|
||||
amounts[size*2+1] = accountAmounts[accountIdIt->first][accountYearIt->first][b];
|
||||
size++;
|
||||
}
|
||||
}
|
||||
dataset->AddSerie((double *) amounts, size);
|
||||
// set serie names to be displayed on legend
|
||||
dataset->SetSerieName(i+1, user->GetAccountName(accountIdIt->first));
|
||||
delete[] amounts;
|
||||
}
|
||||
}
|
||||
|
||||
// create line renderer and set it to dataset
|
||||
|
@ -296,9 +341,8 @@ void StatsPanel::OnRangeChange(wxCommandEvent& event)
|
|||
_yearTo->GetStringSelection().ToLong(&yearTo);
|
||||
|
||||
if (yearTo > yearFrom ||
|
||||
(yearFrom == yearTo && monthFrom >= monthTo))
|
||||
(yearFrom == yearTo && monthFrom > monthTo))
|
||||
{
|
||||
std::cout << monthFrom << " " << monthTo << " " << _yearFrom->GetStringSelection().mb_str() << " " << yearFrom << " " << yearTo << "\n" ;
|
||||
wxMessageBox(_("Invalide date range"), _("KissCount"), wxICON_ERROR | wxOK);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
#!/bin/bash
|
||||
|
||||
DATE=`date +%d.%m.%Y`
|
||||
DIR="KissCount_build_$DATE"
|
||||
ARCH=`uname -m`
|
||||
DIR="KissCount_build_${DATE}_${ARCH}"
|
||||
FILE="$DIR.tar.bz2"
|
||||
|
||||
rm -f $FILE
|
||||
|
|
Loading…
Reference in New Issue
Block a user