Class: CumulativeFlowDiagram
Constant Summary
Constants inherited
from ChartBase
ChartBase::LABEL_POSITIONS, ChartBase::OKABE_ITO_PALETTE
Instance Attribute Summary
Attributes inherited from ChartBase
#aggregated_project, #all_boards, #atlassian_document_format, #board_id, #canvas_height, #canvas_width, #data_quality, #date_range, #file_system, #fix_versions, #holiday_dates, #issues, #settings, #time_range, #timezone_offset, #x_axis_title, #y_axis_title
Instance Method Summary
collapse
Methods inherited from ChartBase
#aggregated_project?, #before_run, #call_before_run, #canvas, #canvas_responsive?, #chart_format, #collapsible_issues_panel, #color_block, #color_for, #completed_issues_in_range, #current_board, #cycletime, #cycletime_for_issue, #daily_chart_dataset, #date_annotation, #describe_non_working_days, #description_text, #format_integer, #format_status, #header_text, #holidays, #html_directory, #icon_span, #link_to_issue, #next_id, #non_working_day?, #normalize_annotation_datetime, #not_visible_icon, #not_visible_text, #random_color, #render, #render_axis_title, #render_top_text, #resolve_status, #stagger_label_positions, #status_category_color, #to_human_readable, #working_days_annotation, #wrap_and_render
Constructor Details
Long only because of the inline description_text heredoc and one-time setup; splitting wouldn't help.
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 39
def initialize block super()
'Cumulative Flow Diagram'
description_text <<~HTML
<div class="p">
A Cumulative Flow Diagram (CFD) shows how work accumulates across board columns over time.
Each coloured band represents a workflow stage. The top edge of the leftmost band shows
total work entered; the top edge of the rightmost band shows total work completed.
</div>
<div class="p">
A widening band means work is piling up in that stage - a bottleneck. Parallel top edges
(bands staying the same width) indicate smooth flow. Steep rises in the leftmost band
without corresponding rises on the right mean new work is arriving faster than it is
being finished.
</div>
<div class="p">
Dashed lines and hatched regions indicate periods where an item moved backwards through
the workflow (a correction). These highlight rework or process irregularities worth
investigating.
</div>
<div class="p">
The chart also overlays two trend lines and an interactive triangle. The <b>arrival rate</b>
trend line shows how fast work is entering the system; the <b>departure rate</b> trend line
shows how fast it is leaving. Move the mouse over the chart to see a Little's Law triangle
at that point in time, labelled with three derived metrics: <b>Work In Progress (WIP)</b> (items started
but not finished), <b>approximate average cycle time (CT)</b> (roughly how long an average item takes to complete), and
<b>average throughput (TP)</b> (items completed per day). Use the checkbox above the chart to toggle
between the triangle and the normal data tooltips.
</div>
<div class="p">
CT and TP require a future point C where cumulative completions catch up to current arrivals.
When the cursor is near the right edge and that point falls outside the visible date range,
CT and TP cannot be calculated and are hidden; only WIP is shown.
</div>
<div class="p">
See also: This article on <a href="https://blog.mikebowler.ca/2026/03/27/cumulative-flow-diagram/">how to read a CFD</a>.
</div>#{' '}
HTML
@triangle_color = CssVariable['--cfd-triangle-color']
@arrival_rate_line_color = CssVariable['--cfd-arrival-rate-line-color']
@departure_rate_line_color = CssVariable['--cfd-departure-rate-line-color']
instance_eval(&block)
end
|
Instance Method Details
#arrival_rate_line_color(color) ⇒ Object
94
95
96
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 94
def arrival_rate_line_color color
@arrival_rate_line_color = parse_theme_color(color)
end
|
#column_rules(&block) ⇒ Object
86
87
88
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 86
def column_rules &block
@column_rules_block = block
end
|
#departure_rate_line_color(color) ⇒ Object
98
99
100
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 98
def departure_rate_line_color color
@departure_rate_line_color = parse_theme_color(color)
end
|
#run ⇒ Object
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 102
def run
active_columns, active_rules = active_columns_and_rules(current_board.visible_columns)
cfd = CfdDataBuilder.new(
board: current_board,
issues: issues,
date_range: date_range,
columns: active_columns
).run
columns = cfd[:columns]
daily_counts = cfd[:daily_counts]
correction_windows = cfd[:correction_windows]
column_count = columns.size
daily_marginals = marginal_band_heights(daily_counts, column_count)
border_colors = active_rules.map { |rules| rules.color || random_color }
fill_colors = active_rules.zip(border_colors).map { |rules, border| fill_color_for(rules, border) }
data_sets = build_data_sets(
columns: columns, correction_windows: correction_windows, active_rules: active_rules,
daily_marginals: daily_marginals, fill_colors: fill_colors, border_colors: border_colors
)
hatch_windows = correction_windows.map do |w|
{
dataset_index: column_count - 1 - w[:column_index],
start_date: w[:start_date].to_s,
end_date: w[:end_date].to_s,
color: border_colors[w[:column_index]],
fill_color: fill_colors[w[:column_index]]
}
end
wrap_and_render(binding, __FILE__)
end
|
#triangle_color(color) ⇒ Object
90
91
92
|
# File 'lib/jirametrics/cumulative_flow_diagram.rb', line 90
def triangle_color color
@triangle_color = parse_theme_color(color)
end
|