diff options
Diffstat (limited to '')
-rw-r--r-- | src/hist_source.hh | 84 |
1 files changed, 64 insertions, 20 deletions
diff --git a/src/hist_source.hh b/src/hist_source.hh index a6399ad..81245af 100644 --- a/src/hist_source.hh +++ b/src/hist_source.hh @@ -92,7 +92,14 @@ public: return *this; } - bool attrs_in_use(const text_attrs& attrs) const { + stacked_bar_chart& with_show_state(show_state ss) + { + this->sbc_show_state = ss; + return *this; + } + + bool attrs_in_use(const text_attrs& attrs) const + { for (const auto& ident : this->sbc_idents) { if (ident.ci_attrs == attrs) { return true; @@ -168,6 +175,7 @@ public: void chart_attrs_for_value(const listview_curses& lc, int& left, + unsigned long width, const T& ident, double value, string_attrs_t& value_out) const @@ -177,10 +185,9 @@ public: require(ident_iter != this->sbc_ident_lookup.end()); size_t ident_index = ident_iter->second; - unsigned long width, avail_width; + unsigned long avail_width; bucket_stats_t overall_stats; struct line_range lr; - vis_line_t height; lr.lr_unit = line_range::unit::codepoint; @@ -193,30 +200,41 @@ public: return; } - lc.get_dimensions(height, width); - for (size_t lpc = 0; lpc < this->sbc_idents.size(); lpc++) { if (this->sbc_show_state.template is<show_all>() || lpc == (size_t) ident_to_show) { - overall_stats.merge(this->sbc_idents[lpc].ci_stats, - this->sbc_do_stacking); + overall_stats.merge(this->sbc_idents[lpc].ci_stats); } } + if (this->sbc_max_row_value > overall_stats.bs_max_value) { + overall_stats.bs_max_value = this->sbc_max_row_value; + } + if (this->sbc_row_sum > overall_stats.bs_max_value) { + overall_stats.bs_max_value = this->sbc_row_sum; + } if (this->sbc_show_state.template is<show_all>()) { - avail_width = width - this->sbc_idents.size(); + if (this->sbc_idents.size() == 1) { + avail_width = width; + } else if (width < this->sbc_max_row_items) { + avail_width = 0; + } else { + avail_width = width; + } } else { avail_width = width - 1; } - avail_width -= this->sbc_left + this->sbc_right; + if (avail_width > (this->sbc_left + this->sbc_right)) { + avail_width -= this->sbc_left + this->sbc_right; + } lr.lr_start = left; const auto& ci = this->sbc_idents[ident_index]; int amount; - if (value == 0.0) { + if (value == 0.0 || avail_width < 0) { amount = 0; } else if ((overall_stats.bs_max_value - 0.01) <= value && value <= (overall_stats.bs_max_value + 0.01)) @@ -228,6 +246,7 @@ public: amount = (int) rint(percent * avail_width); amount = std::max(1, amount); } + require_ge(amount, 0); lr.lr_end = left = lr.lr_start + amount; if (!ci.ci_attrs.empty() && !lr.empty()) { @@ -241,13 +260,35 @@ public: { this->sbc_idents.clear(); this->sbc_ident_lookup.clear(); - this->sbc_show_state = show_all(); + this->sbc_show_state = show_none(); + this->sbc_row_sum = 0; + this->sbc_row_items = 0; + this->sbc_max_row_value = 0; + this->sbc_max_row_items = 0; } void add_value(const T& ident, double amount = 1.0) { struct chart_ident& ci = this->find_ident(ident); ci.ci_stats.update(amount); + this->sbc_row_sum += amount; + if (ci.ci_last_seen_row != this->sbc_row_counter) { + ci.ci_last_seen_row = this->sbc_row_counter; + this->sbc_row_items += 1; + } + } + + void next_row() + { + if (this->sbc_row_sum > this->sbc_max_row_value) { + this->sbc_max_row_value = this->sbc_row_sum; + } + if (this->sbc_row_items > this->sbc_max_row_items) { + this->sbc_max_row_items = this->sbc_row_items; + } + this->sbc_row_sum = 0; + this->sbc_row_items = 0; + this->sbc_row_counter += 1; } struct bucket_stats_t { @@ -256,15 +297,10 @@ public: { } - void merge(const bucket_stats_t& rhs, bool do_stacking) + void merge(const bucket_stats_t& rhs) { this->bs_min_value = std::min(this->bs_min_value, rhs.bs_min_value); - if (do_stacking) { - this->bs_max_value += rhs.bs_max_value; - } else { - this->bs_max_value - = std::max(this->bs_max_value, rhs.bs_max_value); - } + this->bs_max_value = std::max(this->bs_max_value, rhs.bs_max_value); } double width() const @@ -296,6 +332,7 @@ protected: T ci_ident; text_attrs ci_attrs; bucket_stats_t ci_stats; + ssize_t ci_last_seen_row{-1}; }; struct chart_ident& find_ident(const T& ident) @@ -313,7 +350,13 @@ protected: unsigned long sbc_left{0}, sbc_right{0}; std::vector<struct chart_ident> sbc_idents; std::unordered_map<T, unsigned int> sbc_ident_lookup; - show_state sbc_show_state{show_all()}; + show_state sbc_show_state{show_none()}; + + ssize_t sbc_row_counter{0}; + double sbc_row_sum{0}; + size_t sbc_row_items{0}; + double sbc_max_row_value{0}; + size_t sbc_max_row_items{0}; }; class hist_source2 @@ -368,7 +411,7 @@ public: return 0; } - nonstd::optional<struct timeval> time_for_row(vis_line_t row) override; + nonstd::optional<row_info> time_for_row(vis_line_t row) override; nonstd::optional<vis_line_t> row_for_time( struct timeval tv_bucket) override; @@ -403,6 +446,7 @@ private: time_t hs_last_row; std::map<int64_t, struct bucket_block> hs_blocks; stacked_bar_chart<hist_type_t> hs_chart; + bool hs_needs_flush{false}; }; #endif |