Commit | Line | Data |
---|---|---|
438d0d5f SK |
1 | #! /bin/bash |
2 | ||
365549a9 SK |
3 | produce_mpd_state() { |
4 | echo 'status' \ | |
5 | | nc 127.0.0.1 6600 \ | |
6 | | awk ' | |
7 | { | |
8 | status[$1] = $2 | |
9 | } | |
10 | ||
11 | /^time: +[0-9]+:[0-9]+$/ { | |
12 | split($2, time, ":") | |
13 | seconds_current = time[1] | |
14 | seconds_total = time[2] | |
15 | ||
16 | hours = int(seconds_current / 60 / 60); | |
17 | secs_beyond_hours = seconds_current - (hours * 60 * 60); | |
18 | mins = int(secs_beyond_hours / 60); | |
19 | secs = secs_beyond_hours - (mins * 60); | |
20 | if (hours > 0) { | |
21 | current_time = sprintf("%d:%.2d:%.2d", hours, mins, secs) | |
22 | } else { | |
23 | current_time = sprintf("%.2d:%.2d", mins, secs) | |
24 | } | |
25 | ||
26 | if (seconds_total > 0) { | |
27 | time_percentage = (seconds_current / seconds_total) * 100 | |
28 | current_percentage = sprintf("%d%%", time_percentage) | |
29 | } else { | |
30 | current_percentage = "~" | |
31 | } | |
32 | } | |
33 | ||
34 | END { | |
35 | state = status["state:"] | |
36 | ||
37 | if (state == "play") { | |
38 | symbol = "▶" | |
39 | } else if (state == "pause") { | |
40 | symbol = "❚❚" | |
41 | } else if (state == "stop") { | |
42 | symbol = "⬛" | |
43 | } else { | |
44 | symbol = "--" | |
45 | } | |
46 | ||
47 | printf(\ | |
48 | "%s %s %s", | |
49 | status["state:"], current_time, current_percentage\ | |
50 | ) | |
51 | } | |
52 | ' | |
53 | } | |
54 | ||
55 | produce_mpd_song() { | |
56 | echo 'currentsong' \ | |
57 | | nc 127.0.0.1 6600 \ | |
58 | | awk ' | |
59 | /^OK/ { | |
60 | next | |
61 | } | |
62 | ||
63 | { | |
64 | key = $1 | |
65 | sub("^" key " +", "") | |
66 | val = $0 | |
67 | data[key] = val | |
68 | } | |
69 | ||
70 | END { | |
71 | name = data["Name:"] | |
72 | title = data["Title:"] | |
73 | file = data["file:"] | |
74 | ||
75 | if (name) { | |
76 | out = name | |
77 | } else if (title) { | |
78 | out = title | |
79 | } else if (file) { | |
80 | last = split(file, parts, "/") | |
81 | out = parts[last] | |
82 | } else { | |
83 | out = "" | |
84 | } | |
85 | print out | |
86 | } | |
87 | ' | |
88 | } | |
438d0d5f | 89 | |
6339a4f8 | 90 | produce_weather() { |
438d0d5f SK |
91 | metar -d "$WEATHER_STATION_ID" 2>&1 \ |
92 | | awk ' | |
93 | /METAR pattern not found in NOAA data/ { | |
94 | failures++ | |
95 | } | |
96 | ||
97 | /^Temperature/ { | |
98 | celsius = $3; | |
99 | fahrenheit = (celsius * (9 / 5)) + 32; | |
100 | temperature = fahrenheit | |
101 | } | |
102 | ||
103 | END { | |
104 | if (failures > 0) { | |
105 | temperature = "--" | |
106 | } | |
107 | print temperature "°F" | |
108 | }' | |
109 | } | |
110 | ||
6339a4f8 | 111 | produce_datetime() { |
438d0d5f SK |
112 | date +'%a %b %d %H:%M:%S' |
113 | } | |
114 | ||
6339a4f8 | 115 | consume() { |
438d0d5f SK |
116 | pipe="$1" |
117 | tail -f "$pipe" \ | |
118 | | stdbuf -o L awk \ | |
365549a9 SK |
119 | -v opt_debug=0 \ |
120 | -v opt_mpd_song_max_chars=10 \ | |
438d0d5f | 121 | ' |
365549a9 SK |
122 | /^in:MPD_STATE/\ |
123 | { | |
124 | split_msg_parts() | |
125 | db["mpd_state"] = $1 | |
126 | db["mpd_curr_song_time"] = $2 | |
127 | db["mpd_curr_song_percent"] = $3 | |
128 | } | |
129 | ||
130 | /^in:MPD_SONG/\ | |
438d0d5f | 131 | { |
365549a9 SK |
132 | split_msg_parts() |
133 | db["mpd_curr_song_name"] = msg_body | |
438d0d5f SK |
134 | } |
135 | ||
365549a9 | 136 | /^in:WEATHER/\ |
438d0d5f | 137 | { |
365549a9 SK |
138 | split_msg_parts() |
139 | db["weather_temperature"] = msg_body | |
438d0d5f SK |
140 | } |
141 | ||
365549a9 | 142 | /^in:DATE_TIME/\ |
438d0d5f | 143 | { |
365549a9 SK |
144 | split_msg_parts() |
145 | db["datetime"] = msg_body | |
146 | } | |
147 | ||
148 | /^out:BAR/\ | |
149 | { | |
150 | split_msg_parts() | |
438d0d5f SK |
151 | print make_bar() |
152 | } | |
153 | ||
365549a9 SK |
154 | |
155 | function split_msg_parts() { | |
156 | msg_head = $1 | |
157 | sub("^" msg_head " +", "") | |
158 | msg_body = $0 | |
159 | debug(msg_head, msg_body) | |
438d0d5f SK |
160 | } |
161 | ||
365549a9 SK |
162 | function make_bar( position, bar, sep, i, j) { |
163 | position[++i] = make_status_mpd() | |
438d0d5f SK |
164 | position[++i] = db["weather_temperature"] |
165 | position[++i] = db["datetime"] | |
166 | bar = "" | |
167 | sep = "" | |
168 | for (j = 1; j <= i; j++) { | |
169 | bar = bar sep position[j] | |
170 | sep = " " | |
171 | } | |
172 | return bar | |
173 | } | |
365549a9 SK |
174 | |
175 | function make_status_mpd( state, status) { | |
176 | state = db["mpd_state"] | |
177 | ||
178 | if (state == "play") { | |
179 | status = make_status_mpd_state_known("▶") | |
180 | } else if (state == "pause") { | |
181 | status = make_status_mpd_state_known("❚❚") | |
182 | } else if (state == "stop") { | |
183 | status = make_status_mpd_state_known("⬛") | |
184 | } else { | |
185 | status = make_status_mpd_state_unknown("--") | |
186 | } | |
187 | ||
188 | return sprintf("[%s]", status) | |
189 | } | |
190 | ||
191 | function make_status_mpd_state_known(symbol) { | |
192 | return sprintf(\ | |
193 | "%s %s %s %s", | |
194 | symbol, | |
195 | db["mpd_curr_song_time"], | |
196 | db["mpd_curr_song_percent"], | |
197 | substr(db["mpd_curr_song_name"], 1, opt_mpd_song_max_chars)\ | |
198 | ) | |
199 | } | |
200 | ||
201 | function make_status_mpd_state_unknown(symbol) { | |
202 | return sprintf("%s", symbol) | |
203 | } | |
204 | ||
205 | function debug(location, msg) { | |
206 | if (opt_debug) { | |
207 | print_error(location, msg) | |
208 | } | |
209 | } | |
210 | ||
211 | function print_error(location, msg) { | |
212 | print(location " ==> " msg) > "/dev/stderr" | |
213 | } | |
438d0d5f SK |
214 | ' |
215 | } | |
216 | ||
6339a4f8 | 217 | produce_bar_req() { |
438d0d5f SK |
218 | echo '' |
219 | } | |
220 | ||
221 | spawn() { | |
222 | cmd="$1" | |
223 | pipe="$2" | |
365549a9 | 224 | msg_head="$3" |
438d0d5f SK |
225 | interval="$4" |
226 | while true; do | |
365549a9 | 227 | echo "${msg_head} $($cmd)" > "$pipe" |
438d0d5f SK |
228 | sleep "$interval" |
229 | done & | |
230 | } | |
231 | ||
232 | main() { | |
233 | dir_bin="$1" | |
234 | dir_data="$2" | |
235 | pipe="$dir_data/pipe" | |
236 | ||
237 | WEATHER_STATION_ID='KJFK' | |
238 | ||
239 | rm -f "$pipe" | |
240 | mkfifo "$pipe" | |
241 | ||
6339a4f8 SK |
242 | spawn produce_datetime "$pipe" 'in:DATE_TIME' 1 |
243 | spawn produce_weather "$pipe" 'in:WEATHER' $(( 30 * 60 )) | |
365549a9 SK |
244 | spawn produce_mpd_state "$pipe" 'in:MPD_STATE' 1 |
245 | spawn produce_mpd_song "$pipe" 'in:MPD_SONG' 1 | |
6339a4f8 SK |
246 | spawn produce_bar_req "$pipe" 'out:BAR' 1 |
247 | consume "$pipe" | |
438d0d5f SK |
248 | } |
249 | ||
250 | main $@ |