Source file sparkline_widget_sdl.ml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
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
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
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
module W = Miaou_widgets_display.Widgets
module Sparkline_widget = Miaou_widgets_display.Sparkline_widget
type sdl_render_info = {
renderer : Tsdl.Sdl.renderer;
x : int;
y : int;
width : int;
height : int;
char_w : int;
char_h : int;
}
let ansi_to_rgb ansi_code =
match ansi_code with
| "30" -> (0, 0, 0)
| "31" -> (220, 50, 47)
| "32" -> (133, 153, 0)
| "33" -> (181, 137, 0)
| "34" -> (38, 139, 210)
| "35" -> (211, 54, 130)
| "36" -> (42, 161, 152)
| "37" -> (238, 232, 213)
| "90" -> (88, 110, 117)
| "91" -> (220, 50, 47)
| "92" -> (133, 153, 0)
| "93" -> (181, 137, 0)
| "94" -> (38, 139, 210)
| "95" -> (211, 54, 130)
| "96" -> (42, 161, 152)
| "97" -> (253, 246, 227)
| _ -> (133, 153, 0)
let render_sdl info sparkline ~focus:_ ~show_value:_ ?color ?(thresholds = [])
() =
let open Tsdl.Sdl in
let renderer = info.renderer in
if Sparkline_widget.is_empty sparkline then ()
else
let values = Sparkline_widget.get_data sparkline in
let min_val, max_val, _current = Sparkline_widget.get_bounds sparkline in
let range = max_val -. min_val in
let pixel_width = info.width * info.char_w in
let pixel_height = info.height * info.char_h in
let value_to_y v =
if range = 0. then pixel_height / 2
else
let normalized = (v -. min_val) /. range in
pixel_height - int_of_float (normalized *. float_of_int pixel_height)
in
let r, g, b =
match color with Some c -> ansi_to_rgb c | None -> (133, 153, 0)
in
let _ = set_render_draw_blend_mode renderer Blend.mode_blend in
let _ = set_render_draw_color renderer r g b 64 in
let num_values = List.length values in
let x_step = float_of_int pixel_width /. float_of_int (max num_values 1) in
List.iteri
(fun i value ->
let x = info.x + int_of_float (float_of_int i *. x_step) in
let y = info.y + value_to_y value in
let bottom = info.y + pixel_height in
let height = max 1 (bottom - y) in
let rect =
Rect.create ~x ~y ~w:(max 2 (int_of_float x_step)) ~h:height
in
ignore (render_fill_rect renderer (Some rect)))
values ;
let _ = set_render_draw_color renderer r g b 255 in
let points = Array.of_list values in
for i = 0 to Array.length points - 2 do
let x1 = info.x + int_of_float (float_of_int i *. x_step) in
let y1 = info.y + value_to_y points.(i) in
let x2 = info.x + int_of_float (float_of_int (i + 1) *. x_step) in
let y2 = info.y + value_to_y points.(i + 1) in
ignore (render_draw_line renderer x1 y1 x2 y2)
done ;
List.iter
(fun (thresh : Sparkline_widget.threshold) ->
if thresh.value >= min_val && thresh.value <= max_val then
let tr, tg, tb = ansi_to_rgb thresh.color in
let _ = set_render_draw_color renderer tr tg tb 128 in
let y = info.y + value_to_y thresh.value in
ignore (render_draw_line renderer info.x y (info.x + pixel_width) y))
thresholds
let render sparkline ~focus ~show_value ?color ?(thresholds = []) () =
Sparkline_widget.render sparkline ~focus ~show_value ?color ~thresholds ()
let render_with_label sparkline ~label ~focus ?color ?(thresholds = []) () =
Sparkline_widget.render_with_label
sparkline
~label
~focus
?color
~thresholds
()