glimmer-libui-cc-graphs_and_charts 0.1.5 → 0.1.7

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 13c6855a27c49f14aaa6bc865f8d954a4500a86b99943446a9b9c7d8f153bd87
4
- data.tar.gz: 1fb52e2748e28024d4dbd46f9077a4b1e14aae00367487c16b622b514404cf56
3
+ metadata.gz: c2a02d818ffec27e5d64eafa181c90e1362b62ea8f201018fe92705b0d95a664
4
+ data.tar.gz: 6de4a548a1c74d91cc389663d9917311bd66523402ba984ac05a250d8cff5baa
5
5
  SHA512:
6
- metadata.gz: 0ce8817b76f6b9cc5ac0c5fc88223aa4c07625f747d3a79dc95569055862a77e65578543134be4fff45f783a83098d509abf27f7db48fe1bd4fdf1412a4c9fc0
7
- data.tar.gz: 933bdaeb6f80038e708b13dee69f43c7532fe2facc25a37f1598858179b9f8efb08d7a3665b085fee975e90c319df5ce08bc2913430103ae42933d52a738d243
6
+ metadata.gz: 738a36dedf90e91774876d7cc41f545edb00ac03d65cd6bf89eaf30eac5374b4abfa591d007d971476a02dd854ca14a262a7fcda34fdc24ac531b17509ee0dcf
7
+ data.tar.gz: 2039bf32f7d8fb7930c24fda0eba1def6c30db968d452cb219a7ceab604bfed450b87b8d68ae061d75017ea59f6161d46b9fbebd8ab5581727116ebfd32fec82
data/CHANGELOG.md CHANGED
@@ -1,10 +1,21 @@
1
1
  # Change Log
2
2
 
3
+ ## 0.1.7
4
+
5
+ - Scale `y` axis when using `values` option to fill up the vertical graph height if all y-axis values are smaller than `1`
6
+
7
+ ## 0.1.6
8
+
9
+ - Support passing line `values` as a `Hash` map of x-axis values to y-axis values instead of using the combination of `y_values`, `x_value_start`, and `x_interval_in_seconds`
10
+ - Rename `examples/graphs_and_charts/basic_line_graph.rb` to `examples/graphs_and_charts/basic_line_graph_relative.rb`
11
+ - New `examples/graphs_and_charts/basic_line_graph.rb` (replacing older example that got renamed to `basic_line_graph_relative.rb`)
12
+ - Add graph auto-scaling logic to both `examples/graphs_and_charts/basic_line_graph.rb` & `examples/graphs_and_charts/basic_line_graph_relative.rb`
13
+
3
14
  ## 0.1.5
4
15
 
5
16
  - Render circles for every point in addition to the lines connecting all the points
6
17
  - Render a single point if there is only 1 value in `lines` `y_values` instead of rendering nothing until 2 values exist at least
7
- - Support `graph_point_radius`, `graph_selected_point_radius`, and `graph_fill_selected_point` options for custimizing the circle of every rendered point and selected point.
18
+ - Support `graph_point_radius`, `graph_selected_point_radius`, and `graph_fill_selected_point` options for customizing the circle of every rendered point and selected point.
8
19
  - Avoid rendering on top of the grid markers on the left side
9
20
  - Optimize performance of rendering grid markers and showing mouse hover selection stats of a point
10
21
 
data/README.md CHANGED
@@ -1,18 +1,18 @@
1
- # Graphs and Charts 0.1.5 (Alpha)
1
+ # Graphs and Charts 0.1.7 (Alpha)
2
2
  ## [Glimmer DSL for LibUI](https://github.com/AndyObtiva/glimmer-dsl-libui) Custom Controls
3
3
  [![Gem Version](https://badge.fury.io/rb/glimmer-libui-cc-graphs_and_charts.svg)](http://badge.fury.io/rb/glimmer-libui-cc-graphs_and_charts)
4
4
  [![Join the chat at https://gitter.im/AndyObtiva/glimmer](https://badges.gitter.im/AndyObtiva/glimmer.svg)](https://gitter.im/AndyObtiva/glimmer?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
5
5
 
6
6
  Graphs and Charts (Custom Controls) for [Glimmer DSL for LibUI](https://github.com/AndyObtiva/glimmer-dsl-libui)
7
7
 
8
- ![line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph.png)
8
+ ![line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph-relative.png)
9
9
 
10
10
  ## Setup
11
11
 
12
12
  Add this line to Bundler `Gemfile`:
13
13
 
14
14
  ```ruby
15
- gem 'glimmer-libui-cc-graphs_and_charts', '~> 0.1.5'
15
+ gem 'glimmer-libui-cc-graphs_and_charts', '~> 0.1.7'
16
16
  ```
17
17
 
18
18
  Run:
@@ -42,12 +42,59 @@ require 'glimmer/view/line_graph'
42
42
  This makes the `line_graph` [Glimmer DSL for LibUI Custom Control](https://github.com/AndyObtiva/glimmer-dsl-libui#custom-components) available in the Glimmer GUI DSL.
43
43
  You can then nest `line_graph` under `window` or some container like `vertical_box`. By the way, `line_graph` is implemented on top of the [`area` Glimmer DSL for LibUI control](https://github.com/AndyObtiva/glimmer-dsl-libui#area-api).
44
44
 
45
+ Note that you can use in absolute mode or relative mode for determining x-axis values starting from newest point to oldest point along the time x-axis:
46
+ - Absolute Mode: pass `values` which maps x-axis values to y-axis values
47
+ - Relative Mode: pass `y_values`, `x_value_start`, and `x_interval_in_seconds` (x-axis values are calculated automatically in a uniform way from `x_value_start` deducting `x_interval_in_seconds`)
48
+
49
+ **Absolute Mode:**
50
+
51
+ It supports any `Numeric` y-axis values in addition to `Time` x-axis values.
52
+
53
+ ```ruby
54
+ @line_graph = line_graph(
55
+ width: 900,
56
+ height: 300,
57
+ lines: [
58
+ {
59
+ name: 'Stock 1',
60
+ stroke: [163, 40, 39, thickness: 2],
61
+ values: {
62
+ Time.new(2030, 12, 1) => 80,
63
+ Time.new(2030, 12, 2) => 36,
64
+ Time.new(2030, 12, 4) => 10,
65
+ Time.new(2030, 12, 5) => 60,
66
+ Time.new(2030, 12, 6) => 20,
67
+ },
68
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
69
+ },
70
+ {
71
+ name: 'Stock 2',
72
+ stroke: [47, 109, 104, thickness: 2],
73
+ values: {
74
+ Time.new(2030, 12, 1) => 62,
75
+ Time.new(2030, 12, 2) => 0,
76
+ Time.new(2030, 12, 3) => 90,
77
+ Time.new(2030, 12, 5) => 0,
78
+ Time.new(2030, 12, 7) => 17,
79
+ },
80
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
81
+ },
82
+ ],
83
+ )
84
+ ```
85
+
86
+ ![basic line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph.png)
87
+
88
+ **Relative Mode:**
89
+
90
+ Currently, it only supports `Integer` y-axis values in addition to `Time` x-axis values.
91
+
45
92
  ```ruby
46
93
  line_graph(
47
94
  width: 900,
48
95
  height: 300,
49
96
  graph_point_distance: :width_divided_by_point_count,
50
- lines: [
97
+ series: [
51
98
  {
52
99
  name: 'Feature A',
53
100
  stroke: [163, 40, 39, thickness: 2],
@@ -69,11 +116,11 @@ line_graph(
69
116
  )
70
117
  ```
71
118
 
72
- ![basic line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph.png)
119
+ ![basic line graph relative](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph-relative.png)
73
120
 
74
121
  Look into [lib/glimmer/view/line_graph.rb](/lib/glimmer/view/line_graph.rb) to learn about all supported options.
75
122
 
76
- Basic Line Graph Example:
123
+ **Basic Line Graph Example:**
77
124
 
78
125
  [examples/graphs_and_charts/basic_line_graph.rb](/examples/graphs_and_charts/basic_line_graph.rb)
79
126
 
@@ -81,6 +128,61 @@ Basic Line Graph Example:
81
128
  require 'glimmer-dsl-libui'
82
129
  require 'glimmer/view/line_graph'
83
130
 
131
+ class BasicLineGraph
132
+ include Glimmer::LibUI::Application
133
+
134
+ body {
135
+ window('Basic Line Graph', 900, 300) { |main_window|
136
+ @line_graph = line_graph(
137
+ width: 900,
138
+ height: 300,
139
+ lines: [
140
+ {
141
+ name: 'Stock 1',
142
+ stroke: [163, 40, 39, thickness: 2],
143
+ values: {
144
+ Time.new(2030, 12, 1) => 80,
145
+ Time.new(2030, 12, 2) => 36,
146
+ Time.new(2030, 12, 4) => 10,
147
+ Time.new(2030, 12, 5) => 60,
148
+ Time.new(2030, 12, 6) => 20,
149
+ },
150
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
151
+ },
152
+ {
153
+ name: 'Stock 2',
154
+ stroke: [47, 109, 104, thickness: 2],
155
+ values: {
156
+ Time.new(2030, 12, 1) => 62,
157
+ Time.new(2030, 12, 2) => 0,
158
+ Time.new(2030, 12, 3) => 90,
159
+ Time.new(2030, 12, 5) => 0,
160
+ Time.new(2030, 12, 7) => 17,
161
+ },
162
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
163
+ },
164
+ ],
165
+ )
166
+
167
+ on_content_size_changed do
168
+ @line_graph.width = main_window.content_size[0]
169
+ @line_graph.height = main_window.content_size[1]
170
+ end
171
+ }
172
+ }
173
+ end
174
+
175
+ BasicLineGraph.launch
176
+ ```
177
+
178
+ ![basic line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph.png)
179
+
180
+ **Basic Line Graph Relative Example:**
181
+
182
+ ```ruby
183
+ require 'glimmer-dsl-libui'
184
+ require 'glimmer/view/line_graph'
185
+
84
186
  class BasicLineGraph
85
187
  include Glimmer::LibUI::Application
86
188
 
@@ -94,7 +196,7 @@ class BasicLineGraph
94
196
  width: 900,
95
197
  height: 300,
96
198
  graph_point_distance: :width_divided_by_point_count,
97
- lines: [
199
+ series: [
98
200
  {
99
201
  name: 'Feature A',
100
202
  stroke: [163, 40, 39, thickness: 2],
@@ -121,7 +223,7 @@ end
121
223
  BasicLineGraph.launch
122
224
  ```
123
225
 
124
- ![basic line graph](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph.png)
226
+ ![basic line graph relative](/screenshots/glimmer-libui-cc-graphs_and_charts-mac-basic-line-graph-relative.png)
125
227
 
126
228
  Contributing to glimmer-libui-cc-graphs_and_charts
127
229
  ------------------------------------------
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.5
1
+ 0.1.7
@@ -7,36 +7,43 @@ require 'glimmer/view/line_graph'
7
7
  class BasicLineGraph
8
8
  include Glimmer::LibUI::Application
9
9
 
10
- before_body do
11
- @start_time = Time.now
12
- end
13
-
14
10
  body {
15
- window('Basic Line Graph', 900, 330) {
16
- line_graph(
11
+ window('Basic Line Graph', 900, 300) { |main_window|
12
+ @line_graph = line_graph(
17
13
  width: 900,
18
14
  height: 300,
19
- graph_point_distance: :width_divided_by_point_count,
20
15
  lines: [
21
16
  {
22
- name: 'Feature A',
17
+ name: 'Stock 1',
23
18
  stroke: [163, 40, 39, thickness: 2],
24
- x_value_start: @start_time,
25
- x_interval_in_seconds: 8,
19
+ values: {
20
+ Time.new(2030, 12, 1) => 80,
21
+ Time.new(2030, 12, 2) => 36,
22
+ Time.new(2030, 12, 4) => 10,
23
+ Time.new(2030, 12, 5) => 60,
24
+ Time.new(2030, 12, 6) => 20,
25
+ },
26
26
  x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
27
- y_values: [80, 36, 10, 60, 20, 110, 16, 5, 36, 1, 77, 15, 3, 34, 8, 63, 12, 17, 90, 28, 70]
28
27
  },
29
28
  {
30
- name: 'Feature B',
29
+ name: 'Stock 2',
31
30
  stroke: [47, 109, 104, thickness: 2],
32
- x_value_start: @start_time,
33
- x_interval_in_seconds: 8,
31
+ values: {
32
+ Time.new(2030, 12, 1) => 62,
33
+ Time.new(2030, 12, 2) => 0,
34
+ Time.new(2030, 12, 3) => 90,
35
+ Time.new(2030, 12, 5) => 0,
36
+ Time.new(2030, 12, 7) => 17,
37
+ },
34
38
  x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
35
- y_values: [62, 0, 90, 0, 0, 27, 0, 56, 0, 0, 24, 0, 60, 0, 30, 0, 47, 0, 38, 90, 0]
36
39
  },
37
40
  ],
38
- display_attributes_on_hover: true,
39
41
  )
42
+
43
+ on_content_size_changed do
44
+ @line_graph.width = main_window.content_size[0]
45
+ @line_graph.height = main_window.content_size[1]
46
+ end
40
47
  }
41
48
  }
42
49
  end
@@ -0,0 +1,49 @@
1
+ # This line is only needed when running the example from inside the project directory
2
+ $LOAD_PATH.prepend(File.expand_path(File.join(__dir__, '..', '..', 'lib'))) if File.exist?(File.join(__dir__, '..', '..', 'lib'))
3
+
4
+ require 'glimmer-dsl-libui'
5
+ require 'glimmer/view/line_graph'
6
+
7
+ class BasicLineGraph
8
+ include Glimmer::LibUI::Application
9
+
10
+ before_body do
11
+ @start_time = Time.now
12
+ end
13
+
14
+ body {
15
+ window('Basic Line Graph', 900, 330) { |main_window|
16
+ @line_graph = line_graph(
17
+ width: 900,
18
+ height: 300,
19
+ graph_point_distance: :width_divided_by_point_count,
20
+ lines: [
21
+ {
22
+ name: 'Feature A',
23
+ stroke: [163, 40, 39, thickness: 2],
24
+ x_value_start: @start_time,
25
+ x_interval_in_seconds: 8,
26
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
27
+ y_values: [80, 36, 10, 60, 20, 110, 16, 5, 36, 1, 77, 15, 3, 34, 8, 63, 12, 17, 90, 28, 70]
28
+ },
29
+ {
30
+ name: 'Feature B',
31
+ stroke: [47, 109, 104, thickness: 2],
32
+ x_value_start: @start_time,
33
+ x_interval_in_seconds: 8,
34
+ x_value_format: -> (time) {time.strftime("%a %d %b %Y %T GMT")},
35
+ y_values: [62, 0, 90, 0, 0, 27, 0, 56, 0, 0, 24, 0, 60, 0, 30, 0, 47, 0, 38, 90, 0]
36
+ },
37
+ ],
38
+ display_attributes_on_hover: true,
39
+ )
40
+
41
+ on_content_size_changed do
42
+ @line_graph.width = main_window.content_size[0]
43
+ @line_graph.height = main_window.content_size[1] - 30
44
+ end
45
+ }
46
+ }
47
+ end
48
+
49
+ BasicLineGraph.launch
@@ -2,16 +2,16 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Juwelier::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
- # stub: glimmer-libui-cc-graphs_and_charts 0.1.5 ruby lib
5
+ # stub: glimmer-libui-cc-graphs_and_charts 0.1.7 ruby lib
6
6
 
7
7
  Gem::Specification.new do |s|
8
8
  s.name = "glimmer-libui-cc-graphs_and_charts".freeze
9
- s.version = "0.1.5".freeze
9
+ s.version = "0.1.7".freeze
10
10
 
11
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
12
12
  s.require_paths = ["lib".freeze]
13
13
  s.authors = ["Andy Maleh".freeze]
14
- s.date = "2023-12-21"
14
+ s.date = "2023-12-23"
15
15
  s.description = "Graphs and Charts (Custom Controls) for Glimmer DSL for LibUI, like Line Graph.".freeze
16
16
  s.email = "andy.am@gmail.com".freeze
17
17
  s.extra_rdoc_files = [
@@ -25,6 +25,7 @@ Gem::Specification.new do |s|
25
25
  "README.md",
26
26
  "VERSION",
27
27
  "examples/graphs_and_charts/basic_line_graph.rb",
28
+ "examples/graphs_and_charts/basic_line_graph_relative.rb",
28
29
  "glimmer-libui-cc-graphs_and_charts.gemspec",
29
30
  "lib/glimmer-libui-cc-graphs_and_charts.rb",
30
31
  "lib/glimmer/view/line_graph.rb"
@@ -131,6 +131,11 @@ module Glimmer
131
131
  def clear_drawing_cache
132
132
  @graph_point_distance_per_line = nil
133
133
  @y_value_max_for_all_lines = nil
134
+ @x_resolution = nil
135
+ @y_resolution = nil
136
+ @x_value_range_for_all_lines = nil
137
+ @x_value_min_for_all_lines = nil
138
+ @x_value_max_for_all_lines = nil
134
139
  @grid_marker_points = nil
135
140
  @points = nil
136
141
  @grid_marker_number_values = nil
@@ -145,15 +150,23 @@ module Glimmer
145
150
  end
146
151
 
147
152
  def calculate_graph_point_distance_per_line
148
- return unless graph_point_distance == :width_divided_by_point_count
153
+ return unless lines[0]&.[](:y_values) && graph_point_distance == :width_divided_by_point_count
149
154
 
150
155
  @graph_point_distance_per_line ||= lines.inject({}) do |hash, line|
151
156
  value = (width - 2.0*graph_padding_width - graph_grid_marker_padding_width) / (line[:y_values].size - 1).to_f
152
- value = [value, width - 2.0*graph_padding_width - graph_grid_marker_padding_width].min
157
+ value = [value, width_drawable].min
153
158
  hash.merge(line => value)
154
159
  end
155
160
  end
156
161
 
162
+ def width_drawable
163
+ width - 2.0*graph_padding_width - graph_grid_marker_padding_width
164
+ end
165
+
166
+ def height_drawable
167
+ height - 2.0*graph_padding_height
168
+ end
169
+
157
170
  def graph_point_distance_for_line(line)
158
171
  @graph_point_distance_per_line&.[](line) || graph_point_distance
159
172
  end
@@ -176,8 +189,15 @@ module Glimmer
176
189
  @grid_marker_numbers ||= []
177
190
  @graph_stroke_marker_values ||= []
178
191
  @mod_values ||= []
192
+ if lines && lines.all? {|line| line[:values]} && !y_value_max_for_all_lines.nil? && y_value_max_for_all_lines > 1
193
+ return
194
+ end
179
195
  grid_marker_points.each_with_index do |marker_point, index|
180
- @grid_marker_number_values[index] ||= (grid_marker_points.size - index).to_i
196
+ @grid_marker_number_values[index] ||= begin
197
+ value = (grid_marker_points.size - index).to_i
198
+ value = y_value_max_for_all_lines if !y_value_max_for_all_lines.nil? && y_value_max_for_all_lines.to_i != y_value_max_for_all_lines && grid_marker_points.size == 1
199
+ value
200
+ end
181
201
  grid_marker_number_value = @grid_marker_number_values[index]
182
202
  @grid_marker_numbers[index] ||= (grid_marker_number_value >= 1000) ? "#{grid_marker_number_value / 1000}K" : grid_marker_number_value.to_s
183
203
  grid_marker_number = @grid_marker_numbers[index]
@@ -207,7 +227,7 @@ module Glimmer
207
227
  stroke graph_stroke_marker_line
208
228
  }
209
229
  end
210
- if grid_marker_number_value % mod_value == comparison_value
230
+ if grid_marker_number_value % mod_value == comparison_value || grid_marker_number_value != grid_marker_number_value.to_i
211
231
  grid_marker_number_width = estimate_width_of_text(grid_marker_number, grid_marker_number_font)
212
232
  text(marker_point[:x] + 4 + 3, marker_point[:y] - 6, grid_marker_number_width) {
213
233
  string(grid_marker_number) {
@@ -221,10 +241,10 @@ module Glimmer
221
241
 
222
242
  def grid_marker_points
223
243
  if @grid_marker_points.nil?
224
- graph_max = [y_value_max_for_all_lines, 1].max
244
+ graph_y_max = [y_value_max_for_all_lines, y_value_max_for_all_lines.between?(0, 1) ? y_value_max_for_all_lines : 1].max
225
245
  current_graph_height = (height - graph_padding_height * 2)
226
- division_height = current_graph_height / graph_max
227
- @grid_marker_points = graph_max.to_i.times.map do |marker_index|
246
+ division_height = current_graph_height / graph_y_max
247
+ @grid_marker_points = graph_y_max.ceil.times.map do |marker_index|
228
248
  x = graph_padding_width
229
249
  y = graph_padding_height + marker_index * division_height
230
250
  {x: x, y: y}
@@ -244,7 +264,7 @@ module Glimmer
244
264
  def single_line_graph(graph_line)
245
265
  last_point = nil
246
266
  points = calculate_points(graph_line)
247
- points.each do |point|
267
+ points.to_a.each do |point|
248
268
  if last_point
249
269
  line(last_point[:x], last_point[:y], point[:x], point[:y]) {
250
270
  stroke graph_line[:stroke]
@@ -260,14 +280,22 @@ module Glimmer
260
280
  end
261
281
 
262
282
  def calculate_points(graph_line)
283
+ if lines[0]&.[](:y_values)
284
+ calculate_points_relative(graph_line)
285
+ else
286
+ calculate_points_absolute(graph_line)
287
+ end
288
+ end
289
+
290
+ def calculate_points_relative(graph_line)
263
291
  @points ||= {}
264
292
  if @points[graph_line].nil?
265
293
  y_values = graph_line[:y_values] || []
266
294
  y_values = y_values[0, max_visible_point_count(graph_line)]
267
- graph_max = [y_value_max_for_all_lines, 1].max
295
+ graph_y_max = [y_value_max_for_all_lines, 1].max
268
296
  points = y_values.each_with_index.map do |y_value, index|
269
297
  x = width - graph_padding_width - (index * graph_point_distance_for_line(graph_line))
270
- y = ((height - graph_padding_height) - y_value * ((height - graph_padding_height * 2) / graph_max))
298
+ y = ((height - graph_padding_height) - y_value * ((height - graph_padding_height * 2) / graph_y_max))
271
299
  {x: x, y: y, index: index, y_value: y_value}
272
300
  end
273
301
  @points[graph_line] = translate_points(graph_line, points)
@@ -275,9 +303,74 @@ module Glimmer
275
303
  @points[graph_line]
276
304
  end
277
305
 
306
+ def calculate_points_absolute(graph_line)
307
+ @points ||= {}
308
+ if @points[graph_line].nil?
309
+ values = graph_line[:values] || []
310
+ # all points are visible when :values is supplied because we stretch the graph to show them all
311
+ graph_y_max = [y_value_max_for_all_lines, 1].max
312
+ x_value_range_for_all_lines
313
+ points = values.each_with_index.map do |(x_value, y_value), index|
314
+ relative_x_value = x_value - x_value_min_for_all_lines
315
+ scaled_x_value = x_value_range_for_all_lines == 0 ? 0 : relative_x_value.to_f * x_resolution.to_f
316
+ scaled_y_value = y_value_max_for_all_lines == 0 ? 0 : y_value.to_f * y_resolution.to_f
317
+ x = width - graph_padding_width - scaled_x_value
318
+ y = height - graph_padding_height - scaled_y_value
319
+ {x: x, y: y, index: index, x_value: x_value, y_value: y_value}
320
+ end
321
+ # Translation is not supported today
322
+ # TODO consider supporting in the future
323
+ # @points[graph_line] = translate_points(graph_line, points)
324
+ @points[graph_line] = points
325
+ end
326
+ @points[graph_line]
327
+ end
328
+
329
+ # this is the multiplier that we must multiply by the relative x value
330
+ def x_resolution
331
+ @x_resolution ||= width_drawable.to_f / x_value_range_for_all_lines.to_f
332
+ end
333
+
334
+ # this is the multiplier that we must multiply by the relative y value
335
+ def y_resolution
336
+ # TODO in the future, we will use the y range, but today, we assume it starts at 0
337
+ @y_resolution ||= height_drawable.to_f / y_value_max_for_all_lines.to_f
338
+ end
339
+
340
+ def x_value_range_for_all_lines
341
+ @x_value_range_for_all_lines ||= x_value_max_for_all_lines - x_value_min_for_all_lines
342
+ end
343
+
344
+ def x_value_min_for_all_lines
345
+ if @x_value_min_for_all_lines.nil?
346
+ line_visible_x_values = lines.map { |line| line[:values].to_h.keys }
347
+ all_visible_x_values = line_visible_x_values.reduce(:+) || []
348
+ # Right now, we assume Time objects
349
+ # TODO support String representations of Time (w/ some auto-detection of format)
350
+ @x_value_min_for_all_lines = all_visible_x_values.min
351
+ end
352
+ @x_value_min_for_all_lines
353
+ end
354
+
355
+ def x_value_max_for_all_lines
356
+ if @x_value_max_for_all_lines.nil?
357
+ line_visible_x_values = lines.map { |line| line[:values].to_h.keys }
358
+ all_visible_x_values = line_visible_x_values.reduce(:+) || []
359
+ # Right now, we assume Time objects
360
+ # TODO support String representations of Time (w/ some auto-detection of format)
361
+ @x_value_max_for_all_lines = all_visible_x_values.max
362
+ end
363
+ @x_value_max_for_all_lines
364
+ end
365
+
278
366
  def y_value_max_for_all_lines
279
367
  if @y_value_max_for_all_lines.nil?
280
- line_visible_y_values = lines.map { |line| line[:y_values][0, max_visible_point_count(line)] }
368
+ if lines[0]&.[](:y_values)
369
+ line_visible_y_values = lines.map { |line| line[:y_values][0, max_visible_point_count(line)] }
370
+ else
371
+ # When using :values , we always stretch the graph so that all points are visible
372
+ line_visible_y_values = lines.map { |line| line[:values].to_h.values }
373
+ end
281
374
  all_visible_y_values = line_visible_y_values.reduce(:+) || []
282
375
  @y_value_max_for_all_lines = all_visible_y_values.max.to_f
283
376
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: glimmer-libui-cc-graphs_and_charts
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.5
4
+ version: 0.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andy Maleh
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-12-21 00:00:00.000000000 Z
11
+ date: 2023-12-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: glimmer-dsl-libui
@@ -81,6 +81,7 @@ files:
81
81
  - README.md
82
82
  - VERSION
83
83
  - examples/graphs_and_charts/basic_line_graph.rb
84
+ - examples/graphs_and_charts/basic_line_graph_relative.rb
84
85
  - glimmer-libui-cc-graphs_and_charts.gemspec
85
86
  - lib/glimmer-libui-cc-graphs_and_charts.rb
86
87
  - lib/glimmer/view/line_graph.rb