gruff 0.9.0-java → 0.12.2-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +21 -4
  3. data/.rubocop_todo.yml +103 -49
  4. data/.travis.yml +3 -6
  5. data/CHANGELOG.md +30 -0
  6. data/README.md +4 -0
  7. data/gruff.gemspec +8 -3
  8. data/lib/gruff.rb +9 -3
  9. data/lib/gruff/accumulator_bar.rb +13 -5
  10. data/lib/gruff/area.rb +22 -5
  11. data/lib/gruff/bar.rb +38 -10
  12. data/lib/gruff/base.rb +325 -236
  13. data/lib/gruff/bezier.rb +18 -4
  14. data/lib/gruff/bullet.rb +22 -14
  15. data/lib/gruff/dot.rb +20 -33
  16. data/lib/gruff/helper/bar_conversion.rb +7 -7
  17. data/lib/gruff/helper/bar_value_label_mixin.rb +3 -0
  18. data/lib/gruff/helper/stacked_mixin.rb +1 -1
  19. data/lib/gruff/histogram.rb +59 -0
  20. data/lib/gruff/line.rb +33 -28
  21. data/lib/gruff/mini/bar.rb +10 -2
  22. data/lib/gruff/mini/legend.rb +9 -4
  23. data/lib/gruff/mini/pie.rb +9 -3
  24. data/lib/gruff/mini/side_bar.rb +18 -4
  25. data/lib/gruff/net.rb +41 -21
  26. data/lib/gruff/patch/rmagick.rb +22 -24
  27. data/lib/gruff/patch/string.rb +9 -4
  28. data/lib/gruff/photo_bar.rb +12 -16
  29. data/lib/gruff/pie.rb +24 -34
  30. data/lib/gruff/renderer/bezier.rb +4 -3
  31. data/lib/gruff/renderer/circle.rb +4 -3
  32. data/lib/gruff/renderer/dash_line.rb +4 -3
  33. data/lib/gruff/renderer/dot.rb +4 -3
  34. data/lib/gruff/renderer/ellipse.rb +4 -3
  35. data/lib/gruff/renderer/line.rb +14 -5
  36. data/lib/gruff/renderer/polygon.rb +5 -4
  37. data/lib/gruff/renderer/polyline.rb +4 -3
  38. data/lib/gruff/renderer/rectangle.rb +3 -2
  39. data/lib/gruff/renderer/renderer.rb +31 -38
  40. data/lib/gruff/renderer/text.rb +29 -7
  41. data/lib/gruff/scatter.rb +26 -24
  42. data/lib/gruff/scene.rb +0 -1
  43. data/lib/gruff/side_bar.rb +51 -20
  44. data/lib/gruff/side_stacked_bar.rb +42 -15
  45. data/lib/gruff/spider.rb +29 -17
  46. data/lib/gruff/stacked_area.rb +19 -8
  47. data/lib/gruff/stacked_bar.rb +34 -13
  48. data/lib/gruff/store/{base_data.rb → basic_data.rb} +9 -7
  49. data/lib/gruff/store/custom_data.rb +8 -6
  50. data/lib/gruff/store/store.rb +7 -6
  51. data/lib/gruff/store/xy_data.rb +10 -7
  52. data/lib/gruff/version.rb +1 -1
  53. metadata +33 -8
  54. data/Rakefile +0 -23
  55. data/docker/Dockerfile +0 -14
  56. data/docker/build.sh +0 -4
  57. data/docker/launch.sh +0 -4
data/lib/gruff/bezier.rb CHANGED
@@ -1,7 +1,23 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'gruff/base'
4
-
3
+ #
4
+ # Gruff::Bezier is a special line graph that have
5
+ # the bezier curve.
6
+ #
7
+ # Here's how to set up a Gruff::Bezier.
8
+ #
9
+ # dataset = [
10
+ # +0.00, +0.09, +0.19, +0.29, +0.38, +0.47, +0.56, +0.64, +0.71, +0.78,
11
+ # +0.84, +0.89, +0.93, +0.96, +0.98, +0.99, +0.99, +0.99, +0.97, +0.94,
12
+ # +0.90, +0.86, +0.80, +0.74, +0.67, +0.59, +0.51, +0.42, +0.33, +0.23,
13
+ # +0.14, +0.04, -0.06, -0.16, -0.26, -0.36, -0.45, -0.53, -0.62, -0.69,
14
+ # -0.76, -0.82, -0.88, -0.92, -0.96, -0.98, -1.00, -1.00, -1.00, -0.99,
15
+ # -0.96, -0.93, -0.89, -0.84, -0.78, -0.71, -0.64, -0.56, -0.47, -0.38,
16
+ # ]
17
+ # g = Gruff::Bezier.new
18
+ # g.data 'sin', dataset
19
+ # g.write('bezier.png')
20
+ #
5
21
  class Gruff::Bezier < Gruff::Base
6
22
  def draw
7
23
  super
@@ -37,7 +53,5 @@ class Gruff::Bezier < Gruff::Base
37
53
  Gruff::Renderer::Bezier.new(color: data_row.color, width: stroke_width).render(poly_points)
38
54
  end
39
55
  end
40
-
41
- Gruff::Renderer.finish
42
56
  end
43
57
  end
data/lib/gruff/bullet.rb CHANGED
@@ -1,15 +1,22 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'gruff/base'
4
- require 'gruff/themes'
5
-
3
+ #
4
+ # A bullet graph is a variation of a bar graph.
6
5
  # http://en.wikipedia.org/wiki/Bullet_graph
6
+ #
7
+ # Here's how to set up a Gruff::Bullet.
8
+ #
9
+ # g = Gruff::Bullet.new
10
+ # g.title = 'Monthly Revenue'
11
+ # g.data 75, 100, { target: 80, low: 50, high: 90 }
12
+ # g.write('bullet.png')
13
+ #
7
14
  class Gruff::Bullet < Gruff::Base
8
15
  def initialize(target_width = '400x40')
16
+ super
17
+
9
18
  if target_width.is_a?(String)
10
- geometric_width, geometric_height = target_width.split('x')
11
- @columns = geometric_width.to_f
12
- @rows = geometric_height.to_f
19
+ @columns, @rows = target_width.split('x').map(&:to_f)
13
20
  else
14
21
  @columns = target_width.to_f
15
22
  @rows = target_width.to_f / 5.0
@@ -17,12 +24,15 @@ class Gruff::Bullet < Gruff::Base
17
24
  @columns.freeze
18
25
  @rows.freeze
19
26
 
20
- initialize_ivars
21
-
22
- reset_themes
23
27
  self.theme = Gruff::Themes::GREYSCALE
28
+ end
29
+
30
+ def initialize_ivars
31
+ super
32
+
24
33
  @title_font_size = 20
25
34
  end
35
+ private :initialize_ivars
26
36
 
27
37
  def data(value, maximum_value, options = {})
28
38
  @value = value.to_f
@@ -45,7 +55,7 @@ class Gruff::Bullet < Gruff::Base
45
55
  margin = 30.0
46
56
  thickness = @raw_rows / 6.0
47
57
  right_margin = margin
48
- graph_left = (@title && (title_width * 1.3)) || margin
58
+ graph_left = [title_width * 1.3, margin].max
49
59
  graph_width = @raw_columns - graph_left - right_margin
50
60
  graph_height = thickness * 3.0
51
61
 
@@ -73,18 +83,16 @@ class Gruff::Bullet < Gruff::Base
73
83
  # Value
74
84
  rect_renderer = Gruff::Renderer::Rectangle.new(color: @font_color)
75
85
  rect_renderer.render(graph_left, thickness, graph_left + graph_width * (@value / maximum_value), thickness * 2)
76
-
77
- Gruff::Renderer.finish
78
86
  end
79
87
 
80
88
  private
81
89
 
82
90
  def draw_title
83
- return unless @title
91
+ return if hide_title?
84
92
 
85
93
  font_height = calculate_caps_height(scale_fontsize(@title_font_size))
86
94
 
87
95
  text_renderer = Gruff::Renderer::Text.new(@title, font: @font, size: @title_font_size, color: @font_color)
88
- text_renderer.render(1.0, 1.0, font_height / 2, font_height / 2, Magick::NorthWestGravity)
96
+ text_renderer.add_to_render_queue(1.0, 1.0, font_height / 2, font_height / 2, Magick::NorthWestGravity)
89
97
  end
90
98
  end
data/lib/gruff/dot.rb CHANGED
@@ -1,9 +1,18 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'gruff/base'
4
-
5
- # Graph with dots and labels along a vertical access
3
+ #
4
+ # Graph with dots and labels along a vertical access.
6
5
  # see: 'Creating More Effective Graphs' by Robbins
6
+ #
7
+ # Here's how to set up a Gruff::Dot.
8
+ #
9
+ # g = Gruff::Dot.new
10
+ # g.title = 'Dot Graph'
11
+ # g.data :Art, [0, 5, 8, 15]
12
+ # g.data :Philosophy, [10, 3, 2, 8]
13
+ # g.data :Science, [2, 15, 8, 11]
14
+ # g.write('dot.png')
15
+ #
7
16
  class Gruff::Dot < Gruff::Base
8
17
  def draw
9
18
  @has_left_labels = true
@@ -33,8 +42,6 @@ class Gruff::Dot < Gruff::Base
33
42
  draw_label(y_pos, point_index)
34
43
  end
35
44
  end
36
-
37
- Gruff::Renderer.finish
38
45
  end
39
46
 
40
47
  protected
@@ -43,37 +50,17 @@ protected
43
50
  def draw_line_markers
44
51
  return if @hide_line_markers
45
52
 
46
- # Draw horizontal line markers and annotate with numbers
47
- if @y_axis_increment
48
- increment = @y_axis_increment
49
- number_of_lines = (@spread / @y_axis_increment).to_i
50
- else
51
- # Try to use a number of horizontal lines that will come out even.
52
- #
53
- # TODO Do the same for larger numbers...100, 75, 50, 25
54
- if @marker_count.nil?
55
- (3..7).each do |lines|
56
- if @spread % lines == 0.0
57
- @marker_count = lines
58
- break
59
- end
60
- end
61
- @marker_count ||= 5
62
- end
63
- # TODO: Round maximum marker value to a round number like 100, 0.1, 0.5, etc.
64
- increment = (@spread > 0 && @marker_count > 0) ? significant(@spread / @marker_count) : 1
65
- number_of_lines = @marker_count
66
- end
67
-
68
- (0..number_of_lines).each do |index|
69
- marker_label = minimum_value + index * increment
53
+ (0..marker_count).each do |index|
54
+ marker_label = minimum_value + index * @increment
70
55
  x = @graph_left + (marker_label - minimum_value) * @graph_width / @spread
71
- Gruff::Renderer::Line.new(color: @marker_color).render(x, @graph_bottom, x, @graph_bottom + 0.5 * LABEL_MARGIN)
56
+
57
+ line_renderer = Gruff::Renderer::Line.new(color: @marker_color, shadow_color: @marker_shadow_color)
58
+ line_renderer.render(x, @graph_bottom, x, @graph_bottom + 5)
72
59
 
73
60
  unless @hide_line_numbers
74
- label = label(marker_label, increment)
61
+ label = label(marker_label, @increment)
75
62
  text_renderer = Gruff::Renderer::Text.new(label, font: @font, size: @marker_font_size, color: @font_color)
76
- text_renderer.render(0, 0, x, @graph_bottom + (LABEL_MARGIN * 2.0), Magick::CenterGravity)
63
+ text_renderer.add_to_render_queue(0, 0, x, @graph_bottom + (LABEL_MARGIN * 1.5), Magick::CenterGravity)
77
64
  end
78
65
  end
79
66
  end
@@ -84,7 +71,7 @@ protected
84
71
  def draw_label(y_offset, index)
85
72
  draw_unique_label(index) do
86
73
  text_renderer = Gruff::Renderer::Text.new(@labels[index], font: @font, size: @marker_font_size, color: @font_color)
87
- text_renderer.render(1, 1, -@graph_left + LABEL_MARGIN * 2.0, y_offset, Magick::EastGravity)
74
+ text_renderer.add_to_render_queue(@graph_left - LABEL_MARGIN, 1.0, 0.0, y_offset, Magick::EastGravity)
88
75
  end
89
76
  end
90
77
  end
@@ -3,7 +3,7 @@
3
3
  ##
4
4
  # Original Author: David Stokar
5
5
  #
6
- # This class perfoms the y coordinats conversion for the bar class.
6
+ # This class performs the y coordinates conversion for the bar class.
7
7
  #
8
8
  # There are three cases:
9
9
  #
@@ -24,16 +24,16 @@ class Gruff::BarConversion
24
24
  result = []
25
25
 
26
26
  case @mode
27
- when 1 then # Case one
28
- # minimum value >= 0 ( only positive values )
27
+ when 1
28
+ # minimum value >= 0 ( only positive values )
29
29
  result[0] = @graph_top + @graph_height * (1 - data_point) + 1
30
30
  result[1] = @graph_top + @graph_height - 1
31
- when 2 then # Case two
32
- # only negative values
31
+ when 2
32
+ # only negative values
33
33
  result[0] = @graph_top + 1
34
34
  result[1] = @graph_top + @graph_height * (1 - data_point) - 1
35
- when 3 then # Case three
36
- # positive and negative values
35
+ when 3
36
+ # positive and negative values
37
37
  val = data_point - @minimum_value / @spread
38
38
  result[0] = @graph_top + @graph_height * (1 - (val - @zero)) + 1
39
39
  result[1] = @graph_top + @graph_height * (1 - @zero) - 1
@@ -2,6 +2,9 @@
2
2
 
3
3
  # @private
4
4
  module Gruff::Base::BarValueLabelMixin
5
+ using String::GruffCommify
6
+
7
+ # @private
5
8
  class BarValueLabel
6
9
  attr_accessor :coordinates, :values
7
10
 
@@ -5,7 +5,7 @@ module Gruff::Base::StackedMixin
5
5
  # Used by StackedBar and child classes.
6
6
  #
7
7
  # tsal: moved from Base 03 FEB 2007
8
- def get_maximum_by_stack
8
+ def calculate_maximum_by_stack
9
9
  # Get sum of each stack
10
10
  max_hash = {}
11
11
  store.data.each do |data_set|
@@ -0,0 +1,59 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'histogram'
4
+
5
+ #
6
+ # Here's how to set up a Gruff::Histogram.
7
+ #
8
+ # g = Gruff::Histogram.new
9
+ # g.title = 'Histogram Graph'
10
+ # g.minimum_bin = 10
11
+ # g.bin_width = 20
12
+ # g.data :A, [10, 10, 20, 30, 40, 40, 40, 40, 40, 40, 50, 10, 10, 10]
13
+ # g.data :B, [100, 100, 100, 100, 90, 90, 80, 30, 30, 30, 30, 30]
14
+ # g.write('histogram.png')
15
+ #
16
+ class Gruff::Histogram < Gruff::Bar
17
+ # Specifies interpolation between the min and max of the set. Default is +10+.
18
+ attr_writer :bin_width
19
+
20
+ # Specifies minimum value for bin.
21
+ attr_writer :minimum_bin
22
+
23
+ # Specifies maximum value for bin.
24
+ attr_writer :maximum_bin
25
+
26
+ def initialize(*)
27
+ super
28
+ @data = []
29
+ end
30
+
31
+ def initialize_ivars
32
+ super
33
+ @bin_width = 10
34
+ @minimum_bin = nil
35
+ @maximum_bin = nil
36
+ end
37
+ private :initialize_ivars
38
+
39
+ def data(name, data_points = [], color = nil)
40
+ @data << [name, data_points, color]
41
+ end
42
+
43
+ def draw
44
+ @data.each do |(name, data_points, color)|
45
+ bins, freqs = HistogramArray.new(data_points).histogram(bin_width: @bin_width, min: @minimum_bin, max: @maximum_bin)
46
+ bins.each_with_index do |bin, index|
47
+ @labels[index] = bin
48
+ end
49
+ store.add(name, freqs, color)
50
+ end
51
+
52
+ super
53
+ end
54
+
55
+ # @private
56
+ class HistogramArray < Array
57
+ include ::Histogram
58
+ end
59
+ end
data/lib/gruff/line.rb CHANGED
@@ -1,41 +1,41 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'gruff/base'
4
-
5
- # Here's how to make a Line graph:
3
+ #
4
+ # Here's how to make a Gruff::Line.
6
5
  #
7
6
  # g = Gruff::Line.new
8
7
  # g.title = "A Line Graph"
9
8
  # g.data 'Fries', [20, 23, 19, 8]
10
9
  # g.data 'Hamburgers', [50, 19, 99, 29]
11
- # g.write("test/output/line.png")
10
+ # g.write("line.png")
12
11
  #
13
12
  # There are also other options described below, such as {#baseline_value}, {#baseline_color},
14
- # {#hide_dots}, and {#hide_lines}.
13
+ # {#hide_dots=}, and {#hide_lines=}.
14
+ #
15
15
  class Gruff::Line < Gruff::Base
16
16
  # Allow for reference lines ( which are like baseline ... just allowing for more & on both axes ).
17
17
  attr_accessor :reference_lines
18
- attr_accessor :reference_line_default_color
19
- attr_accessor :reference_line_default_width
18
+ attr_writer :reference_line_default_color
19
+ attr_writer :reference_line_default_width
20
20
 
21
21
  # Allow for vertical marker lines.
22
- attr_accessor :show_vertical_markers
22
+ attr_writer :show_vertical_markers
23
23
 
24
24
  # Dimensions of lines and dots; calculated based on dataset size if left unspecified.
25
- attr_accessor :line_width
26
- attr_accessor :dot_radius
25
+ attr_writer :line_width
26
+ attr_writer :dot_radius
27
27
 
28
28
  # default is +'circle'+, other options include square.
29
- attr_accessor :dot_style
29
+ attr_writer :dot_style
30
30
 
31
- # Hide parts of the graph to fit more datapoints, or for a different appearance.
32
- attr_accessor :hide_dots, :hide_lines
31
+ # Hide parts of the graph to fit more data points, or for a different appearance.
32
+ attr_writer :hide_dots, :hide_lines
33
33
 
34
34
  # accessors for support of xy data.
35
- attr_accessor :minimum_x_value
35
+ attr_writer :minimum_x_value
36
36
 
37
37
  # accessors for support of xy data.
38
- attr_accessor :maximum_x_value
38
+ attr_writer :maximum_x_value
39
39
 
40
40
  # Get the value if somebody has defined it.
41
41
  def baseline_value
@@ -67,7 +67,7 @@ class Gruff::Line < Gruff::Base
67
67
  # g = Gruff::Line.new(400, false) # 400px wide, no lines (for backwards compatibility)
68
68
  # g = Gruff::Line.new(false) # Defaults to 800px wide, no lines (for backwards compatibility)
69
69
  #
70
- # The preferred way is to call {#hide_dots} or {#hide_lines} instead.
70
+ # The preferred way is to call {#hide_dots=} or {#hide_lines=} instead.
71
71
  def initialize(*args)
72
72
  raise ArgumentError, 'Wrong number of arguments' if args.length > 2
73
73
 
@@ -76,7 +76,15 @@ class Gruff::Line < Gruff::Base
76
76
  else
77
77
  super args.shift
78
78
  end
79
+ end
79
80
 
81
+ def initialize_store
82
+ @store = Gruff::Store.new(Gruff::Store::XYData)
83
+ end
84
+ private :initialize_store
85
+
86
+ def initialize_ivars
87
+ super
80
88
  @reference_lines = {}
81
89
  @reference_line_default_color = 'red'
82
90
  @reference_line_default_width = 5
@@ -85,12 +93,13 @@ class Gruff::Line < Gruff::Base
85
93
  @maximum_x_value = nil
86
94
  @minimum_x_value = nil
87
95
 
96
+ @line_width = nil
97
+ @dot_radius = nil
88
98
  @dot_style = 'circle'
89
99
 
90
100
  @show_vertical_markers = false
91
-
92
- @store = Gruff::Store.new(Gruff::Store::XYData)
93
101
  end
102
+ private :initialize_ivars
94
103
 
95
104
  # This method allows one to plot a dataset with both X and Y data.
96
105
  #
@@ -123,7 +132,7 @@ class Gruff::Line < Gruff::Base
123
132
  # g.data("Capples", [1, 1, 2, 2, 3, 3])
124
133
  #
125
134
  # # labels will be drawn at the x locations of the keys passed in.
126
- # In this example the lables are drawn at x positions 2, 4, and 6:
135
+ # In this example the labels are drawn at x positions 2, 4, and 6:
127
136
  # g.labels = {0 => '2003', 2 => '2004', 4 => '2005', 6 => '2006'}
128
137
  # # The 0 => '2003' label will be ignored since it is outside the chart range.
129
138
  def dataxy(name, x_data_points = [], y_data_points = [], color = nil)
@@ -144,11 +153,9 @@ class Gruff::Line < Gruff::Base
144
153
  end
145
154
 
146
155
  def draw_reference_line(reference_line, left, right, top, bottom)
147
- config = {
148
- color: reference_line[:color] || @reference_line_default_color,
149
- width: reference_line[:width] || @reference_line_default_width
150
- }
151
- Gruff::Renderer::DashLine.new(config).render(left, top, right, bottom)
156
+ color = reference_line[:color] || @reference_line_default_color
157
+ width = reference_line[:width] || @reference_line_default_width
158
+ Gruff::Renderer::DashLine.new(color: color, width: width).render(left, top, right, bottom)
152
159
  end
153
160
 
154
161
  def draw_horizontal_reference_line(reference_line)
@@ -210,8 +217,8 @@ class Gruff::Line < Gruff::Base
210
217
  new_y = @graph_top + (@graph_height - y_data * @graph_height)
211
218
 
212
219
  # Reset each time to avoid thin-line errors
213
- stroke_width = line_width || clip_value_if_greater_than(@columns / (store.norm_data.first.y_points.size * 4), 5.0)
214
- circle_radius = dot_radius || clip_value_if_greater_than(@columns / (store.norm_data.first.y_points.size * 2.5), 5.0)
220
+ stroke_width = @line_width || clip_value_if_greater_than(@columns / (store.norm_data.first.y_points.size * 4), 5.0)
221
+ circle_radius = @dot_radius || clip_value_if_greater_than(@columns / (store.norm_data.first.y_points.size * 2.5), 5.0)
215
222
 
216
223
  if !@hide_lines && prev_x && prev_y
217
224
  Gruff::Renderer::Line.new(color: data_row.color, width: stroke_width)
@@ -226,8 +233,6 @@ class Gruff::Line < Gruff::Base
226
233
  prev_y = new_y
227
234
  end
228
235
  end
229
-
230
- Gruff::Renderer.finish
231
236
  end
232
237
 
233
238
  private