diff options
author | John Wiegley <johnw@newartisans.com> | 2004-07-26 23:33:51 -0400 |
---|---|---|
committer | John Wiegley <johnw@newartisans.com> | 2004-07-26 23:33:51 -0400 |
commit | 161d6f79bd6f4ab45afa1cbae77548c8e508809a (patch) | |
tree | 55391f4997e20de173579d90b43316a968b27c9e /item.cc | |
parent | fde56d0f1214b8fb9de5ba4d42d683ed494c45b0 (diff) | |
download | fork-ledger-161d6f79bd6f4ab45afa1cbae77548c8e508809a.tar.gz fork-ledger-161d6f79bd6f4ab45afa1cbae77548c8e508809a.tar.bz2 fork-ledger-161d6f79bd6f4ab45afa1cbae77548c8e508809a.zip |
initial rev of 2.0
Diffstat (limited to 'item.cc')
-rw-r--r-- | item.cc | 224 |
1 files changed, 224 insertions, 0 deletions
diff --git a/item.cc b/item.cc new file mode 100644 index 00000000..7e45ab07 --- /dev/null +++ b/item.cc @@ -0,0 +1,224 @@ +#include "item.h" + +namespace ledger { + +// jww (2004-07-21): If format.show_empty is set, then include all +// subaccounts, empty balanced or no + +item_t * walk_accounts(const account_t * account, + const constraints_t& constraints, + const bool compute_subtotals) +{ + item_t * item = new item_t; + item->account = account; + item->date = end_date(constraints); + + for (constrained_transactions_list_const_iterator + i(account->transactions.begin(), + account->transactions.end(), constraints); + i != account->transactions.end(); + i++) { + item->value += *(*i); + if (compute_subtotals) + item->total += *(*i); + } + + for (accounts_map::const_iterator i = account->accounts.begin(); + i != account->accounts.end(); + i++) { + item_t * subitem = walk_accounts((*i).second, constraints, + compute_subtotals); + subitem->parent = item; + + if (compute_subtotals) + item->total += subitem->total; + + if (compute_subtotals ? subitem->total : subitem->value) + item->subitems.push_back(subitem); + } + + return item; +} + +static inline void sum_items(const item_t * top, + item_t * item, + const bool compute_subtotals) +{ + if (top->account == item->account) { + item->value += top->value; + if (compute_subtotals) + item->total += top->value; + } + + for (items_deque::const_iterator i = top->subitems.begin(); + i != top->subitems.end(); + i++) + sum_items(*i, item, compute_subtotals); +} + +item_t * walk_items(const item_t * top, + const account_t * account, + const constraints_t& constraints, + const bool compute_subtotals) +{ + item_t * item = new item_t; + item->account = account; + + sum_items(top, item, compute_subtotals); + + for (accounts_map::const_iterator i = account->accounts.begin(); + i != account->accounts.end(); + i++) { + item_t * subitem = walk_items(top, (*i).second, constraints, + compute_subtotals); + subitem->parent = item; + + if (compute_subtotals) + item->total += subitem->total; + + if (compute_subtotals ? subitem->total : subitem->value) + item->subitems.push_back(subitem); + } + + return item; +} + +item_t * walk_entries(entries_list::const_iterator begin, + entries_list::const_iterator end, + const constraints_t& constraints, + const format_t& format) +{ +#if 0 + int last_mon = -1; +#endif + unsigned int count = 0; + item_t * result = NULL; + + for (constrained_entries_list_const_iterator i(begin, end, constraints); + i != end; + i++) { + item_t * item = NULL; + + for (constrained_transactions_list_const_iterator + j((*i)->transactions.begin(), (*i)->transactions.end(), + constraints); + j != (*i)->transactions.end(); + j++) { + assert(*i == (*j)->entry); + + if (! item) { + item = new item_t; + item->index = count++; + item->date = (*i)->date; + item->payee = (*i)->payee; + } + + if (! format.show_inverted) { + item_t * subitem = new item_t; + subitem->parent = item; + subitem->date = item->date; + subitem->account = (*j)->account; + subitem->value = *(*j); + item->subitems.push_back(subitem); + } + + if (format.show_related) + for (transactions_list::iterator k = (*i)->transactions.begin(); + k != (*i)->transactions.end(); + k++) + if (*k != *j && ! ((*k)->flags & TRANSACTION_VIRTUAL)) { + item_t * subitem = new item_t; + subitem->parent = item; + subitem->date = item->date; + subitem->account = (*k)->account; + subitem->value = *(*k); + if (format.show_inverted) + subitem->value.negate(); + item->subitems.push_back(subitem); + } + +#if 0 + // If we are collecting monthly totals, then add them if the + // month of this entry is different from the month of previous + // entries. + + if (format.period == PERIOD_MONTHLY) { + int entry_mon = std::gmtime(&(*i)->date)->tm_mon; + + if (last_mon != -1 && entry_mon != last_mon && + line_balances.size() > 0) { + if (last_date == 0) + last_date = (*i)->date; + + if (reg) { + char buf[32]; + std::strftime(buf, 31, "%B", std::gmtime(&last_date)); + + reg->lines.push_back(register_line_t(last_date, buf)); + reg->lines.back().compute_items(line_balances, total, count); + } else { + count++; + } + + line_balances.clear(); + } + + last_mon = entry_mon; + last_date = (*i)->date; + } +#endif + } + + if (item) { + if (! result) + result = new item_t; + item->parent = result; + result->subitems.push_back(item); + } + } + + return result; + +#if 0 + // Wrap up any left over balance list information. + + if (line_balances.size() > 0) { + assert(format.period == PERIOD_MONTHLY); + assert(last_date != 0); + + if (reg) { + char buf[32]; + std::strftime(buf, 31, "%B", std::gmtime(&last_date)); + + reg->lines.push_back(register_line_t(last_date, buf)); + reg->lines.back().compute_items(line_balances, total, count); + } else { + count++; + } + + //line_balances.clear(); + } + + return count; +#endif +} + +struct cmp_items { + const node_t * sort_order; + + cmp_items(const node_t * _sort_order) : sort_order(_sort_order) {} + + bool operator()(const item_t * left, const item_t * right) const { + assert(left); + assert(right); + assert(sort_order); + return sort_order->compute(left) < sort_order->compute(right); + } +}; + +void item_t::sort(const node_t * sort_order) +{ + std::sort(subitems.begin(), subitems.end(), cmp_items(sort_order)); +} + +} // namespace ledger |