wassup 0.1.2 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e0460f6c9734dcfa48fe6d0561d1de6d5c81d1d49a6f8f6e89cfe8dbb54bb78a
4
- data.tar.gz: f017aea6ab05afe32a5c21ba470f4aa82400d08a54d666172596c27c9f74659c
3
+ metadata.gz: 432db97778e804dfdfe02ec44d382aa7e7a275745c8b2ae73b4dd579bf215ae7
4
+ data.tar.gz: 99ccf1045dbad2b6431df2a55be38c643204b3389a0da7a3ecc06d7ede6d0218
5
5
  SHA512:
6
- metadata.gz: 0a4d4e533f3519c77053a5388a00ad584b84203ae18926e7a105a05a72bbe27b68fac844c22ec152baa394b1dcdf1aafc6ae30bbe1b51c80f6a415baf70540c0
7
- data.tar.gz: 447c01199ef5ee734f9836d30d1ee7fe24fdf01d6652b7499d1c053f4903cfba6e63ee979b26122b44b3ef0ba4c213a2ae0f9dc196effe3537d5cf00a2ef9bb7
6
+ metadata.gz: 264ec05425e3078e3ae97089dc890884b8c9aeff6ac6a10c6a49e6bf85c75dda370fb9135c665118e7fa4efdae1407865ae681074a462291b96eee2b700222c5
7
+ data.tar.gz: c8f13c8cd5f63e494e5408f5cc318a523d6ccc2922f227c7c630d4cc18e865367392a0e1038f6ae79abadf6e1c161edc535dc0908b216adbe91dc80f8f29318b
data/.gitignore CHANGED
@@ -10,4 +10,6 @@
10
10
  # rspec failure tracking
11
11
  .rspec_status
12
12
 
13
+ *.gem
14
+
13
15
  *.swp
data/README.md CHANGED
@@ -1,7 +1,13 @@
1
- # Wassup
1
+ <h3 align="center">
2
+ <img height="200" alt="Wassup logo" src="https://user-images.githubusercontent.com/401294/145626927-7eb0fda5-c62a-47c8-9422-074b178fd8ef.png" />
3
+ </h3>
2
4
 
3
- A scriptable terminal dashboard
5
+ [![License](https://img.shields.io/badge/license-MIT-green.svg?style=flat)](https://github.com/fastlane/fastlane/blob/master/LICENSE)
6
+ [![Gem](https://img.shields.io/gem/v/wassup.svg?style=flat)](https://rubygems.org/gems/wassup)
4
7
 
8
+ **Wassup** is a scriptable terminal dashboard. Configure panes and content logic in a `Supfile` and then run `wassup`.
9
+
10
+ <hr/>
5
11
 
6
12
  https://user-images.githubusercontent.com/401294/144465499-a8903d4c-f003-4550-b47c-f70c17cc02d8.mov
7
13
 
@@ -8,10 +8,10 @@ add_pane do |pane|
8
8
  pane.title = "Time Update - Every Second"
9
9
 
10
10
  pane.interval = 1
11
- pane.content do
12
- [
13
- `date`
14
- ]
11
+ pane.content do |content|
12
+ date = `date`
13
+
14
+ content.add_row(date)
15
15
  end
16
16
  end
17
17
 
@@ -24,11 +24,11 @@ add_pane do |pane|
24
24
  pane.highlight = false
25
25
  pane.title = "Time Update - Every 5 Seconds"
26
26
 
27
- pane.interval = 5
28
- pane.content do
29
- [
30
- `date`
31
- ]
27
+ pane.interval = 30
28
+ pane.content do |content|
29
+ date = `date`
30
+
31
+ content.add_row(date)
32
32
  end
33
33
  end
34
34
 
@@ -42,13 +42,72 @@ add_pane do |pane|
42
42
  pane.title = "Maybe Error - Every 10 Seconds"
43
43
 
44
44
  pane.interval = 10
45
- pane.content do
45
+ pane.content do |content|
46
46
  if [true, false].sample
47
47
  raise "An error occured! Oh no!"
48
48
  end
49
49
 
50
- [
51
- "[fg=cyan]No error occured[fg=white]"
52
- ]
50
+ output = "[fg=cyan]No error occured[fg=white]"
51
+
52
+ content.add_row(output)
53
+ end
54
+ end
55
+
56
+ add_pane do |pane|
57
+ pane.height = 0.25
58
+ pane.width = 0.35
59
+ pane.top = 0.25
60
+ pane.left = 0.25
61
+
62
+ pane.highlight = false
63
+ pane.title = "Multiple Contents"
64
+
65
+ pane.interval = 10
66
+ pane.content do |content|
67
+ content.add_row("Line 1 of page 1", page: "Page 1")
68
+ content.add_row("Line 2 of page 1", page: "Page 1")
69
+ content.add_row("Line 1 of page 2", page: "Page 2")
70
+ content.add_row("Line 2 of page 2", page: "Page 2")
71
+ end
72
+ end
73
+
74
+ add_pane do |pane|
75
+ pane.height = 0.25
76
+ pane.width = 0.6
77
+ pane.top = 0.5
78
+ pane.left = 0
79
+
80
+ pane.highlight = false
81
+ pane.title = "Time Update - Slow Reload"
82
+
83
+ pane.interval = 30
84
+ pane.show_refresh = true
85
+ pane.content do |content|
86
+ sleep 10
87
+
88
+ date = `date`
89
+
90
+ content.add_row(date)
91
+ end
92
+ end
93
+
94
+ require 'stringio'
95
+ foo = StringIO.new
96
+ $stdout = foo
97
+
98
+ add_pane do |pane|
99
+ pane.height = 1
100
+ pane.width = 0.4
101
+ pane.top = 0.0
102
+ pane.left = 0.6
103
+
104
+ pane.highlight = false
105
+ pane.title = "STDOUT"
106
+
107
+ pane.interval = 4
108
+ pane.content do |content|
109
+ $stdout.string.split("\n").each do |line|
110
+ content.add_row(line)
111
+ end
53
112
  end
54
113
  end
@@ -21,8 +21,9 @@ add_pane do |pane|
21
21
 
22
22
  pane.title = "Stats: fastlane-community"
23
23
 
24
- pane.interval = 1
25
- pane.content do
24
+ pane.interval = 2
25
+ pane.show_refresh = false
26
+ pane.content do |builder|
26
27
  days_1 = 0
27
28
  days_7 = 0
28
29
  days_30 = 0
@@ -41,13 +42,11 @@ add_pane do |pane|
41
42
  days_365 +=1 if days <= 365
42
43
  end
43
44
 
44
- [
45
- "Opened today: #{days_1}",
46
- "Opened 7 days: #{days_7}",
47
- "Opened 30 days: #{days_30}",
48
- "Opened 60 days: #{days_60}",
49
- "Opened 365 days: #{days_365}"
50
- ]
45
+ builder.add_row("Opened today: #{days_1}")
46
+ builder.add_row("Opened 7 days: #{days_7}")
47
+ builder.add_row("Opened 30 days: #{days_30}")
48
+ builder.add_row("Opened 60 days: #{days_60}")
49
+ builder.add_row("Opened 365 days: #{days_365}")
51
50
  end
52
51
  end
53
52
 
@@ -64,8 +63,9 @@ add_pane do |pane|
64
63
 
65
64
  pane.title = "Stats: fastlane/fastlane"
66
65
 
67
- pane.interval = 1
68
- pane.content do
66
+ pane.interval = 2
67
+ pane.show_refresh = false
68
+ pane.content do |builder|
69
69
  days_1 = 0
70
70
  days_7 = 0
71
71
  days_30 = 0
@@ -86,14 +86,12 @@ add_pane do |pane|
86
86
  days_60_plus +=1 if days > 60
87
87
  end
88
88
 
89
- [
90
- "Opened today: #{days_1}",
91
- "Opened 7 days: #{days_7}",
92
- "Opened 30 days: #{days_30}",
93
- "Opened 45 days: #{days_45}",
94
- "Opened 60 days: #{days_60}",
95
- "More than 60 days: #{days_60_plus}",
96
- ]
89
+ builder.add_row("Opened today: #{days_1}")
90
+ builder.add_row("Opened 7 days: #{days_7}")
91
+ builder.add_row("Opened 30 days: #{days_30}")
92
+ builder.add_row("Opened 45 days: #{days_45}")
93
+ builder.add_row("Opened 60 days: #{days_60}")
94
+ builder.add_row("More than 60 days: #{days_60_plus}")
97
95
  end
98
96
  end
99
97
 
@@ -111,7 +109,8 @@ add_pane do |pane|
111
109
  pane.title = "Circle CI - fastlane/fastlane"
112
110
 
113
111
  pane.interval = 60 * 5
114
- pane.content do
112
+ pane.show_refresh = true
113
+ pane.content do |builder|
115
114
  resp = RestClient::Request.execute(
116
115
  method: :get,
117
116
  url: "https://circleci.com/api/v2/project/github/fastlane/fastlane/pipeline",
@@ -125,7 +124,7 @@ add_pane do |pane|
125
124
  end.map do |item|
126
125
  id = item["id"]
127
126
  number = item["number"]
128
- message = item["vcs"]["commit"]["subject"]
127
+ message = (item["vcs"]["commit"] || {})["subject"]
129
128
  login = item["trigger"]["actor"]["login"]
130
129
 
131
130
  resp = RestClient::Request.execute(
@@ -145,7 +144,10 @@ add_pane do |pane|
145
144
  status = "[fg=yellow]#{status}[fg=white]"
146
145
  end
147
146
 
148
- ["#{number} (#{status}) by #{login} - #{message}", [item, workflow]]
147
+ display = "#{number} (#{status}) by #{login} - #{message}"
148
+ object = [item, workflow]
149
+
150
+ builder.add_row(display, object)
149
151
  end
150
152
  end
151
153
  pane.selection do |data|
@@ -179,7 +181,8 @@ add_pane do |pane|
179
181
  pane.title = "Open PRs - fastlane-community"
180
182
 
181
183
  pane.interval = 60 * 5
182
- pane.content do
184
+ pane.show_refresh = true
185
+ pane.content do |builder|
183
186
  fastlane_community_prs = []
184
187
 
185
188
  resp = RestClient::Request.execute(
@@ -213,13 +216,9 @@ add_pane do |pane|
213
216
  days = (Time.now - date).to_i / (24 * 60 * 60)
214
217
  days_formatted = '%3.3s' % days.to_s
215
218
 
216
- ["[fg=yellow]#{number_formatted}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}",pr]
219
+ display = "[fg=yellow]#{number_formatted}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}"
220
+ builder.add_row(display, pr, page: name)
217
221
  end
218
-
219
- {
220
- title: name,
221
- content: prs
222
- }
223
222
  end
224
223
  end
225
224
  pane.selection do |data|
@@ -243,7 +242,8 @@ add_pane do |pane|
243
242
  pane.title = "Open PRs - fastlane/fastlane"
244
243
 
245
244
  pane.interval = 60 * 5
246
- pane.content do
245
+ pane.show_refresh = true
246
+ pane.content do |builder|
247
247
  fastlane_prs = []
248
248
 
249
249
  resp = RestClient::Request.execute(
@@ -264,7 +264,8 @@ add_pane do |pane|
264
264
  days = (Time.now - date).to_i / (24 * 60 * 60)
265
265
  days_formatted = '%3.3s' % days.to_s
266
266
 
267
- ["[fg=yellow]##{number}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}",pr]
267
+ display = "[fg=yellow]##{number}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}"
268
+ builder.add_row(display, pr)
268
269
  end
269
270
  end
270
271
  pane.selection do |data|
data/lib/wassup/app.rb CHANGED
@@ -34,6 +34,7 @@ module Wassup
34
34
  highlight: pane_builder.highlight,
35
35
  focus_number: number,
36
36
  interval: pane_builder.interval,
37
+ show_refresh: pane_builder.show_refresh,
37
38
  content_block: pane_builder.content_block,
38
39
  selection_blocks: pane_builder.selection_blocks
39
40
  )
@@ -74,7 +75,7 @@ module Wassup
74
75
 
75
76
  begin
76
77
 
77
- @hidden_pane = Pane.new(0, 0, 0, 0, highlight: false, focus_number: 0, interval: nil, content_block: nil, selection_blocks: nil)
78
+ @hidden_pane = Pane.new(0, 0, 0, 0, highlight: false, focus_number: 0, interval: nil, show_refresh: false, content_block: nil, selection_blocks: nil)
78
79
  @hidden_pane.focus_handler = @focus_handler
79
80
  @focused_pane = @hidden_pane
80
81
 
data/lib/wassup/pane.rb CHANGED
@@ -6,10 +6,10 @@ module Wassup
6
6
  class Pane
7
7
  attr_accessor :win
8
8
  attr_accessor :subwin
9
- attr_accessor :data_lines
10
- attr_accessor :data_objects
11
9
  attr_accessor :top
12
10
 
11
+ attr_accessor :contents
12
+
13
13
  attr_accessor :title
14
14
 
15
15
  attr_accessor :focused
@@ -30,13 +30,37 @@ module Wassup
30
30
  attr_accessor :selection_blocks
31
31
 
32
32
  attr_accessor :content_thread
33
+ attr_accessor :show_refresh
33
34
 
34
35
  attr_accessor :selected_view_index
35
- attr_accessor :all_view_data_objects
36
36
 
37
37
  attr_accessor :win_height, :win_width, :win_top, :win_left
38
38
 
39
- def initialize(height, width, top, left, title: nil, highlight: true, focus_number: nil, interval:, content_block:, selection_blocks:)
39
+ class Content
40
+ class Row
41
+ attr_accessor :display
42
+ attr_accessor :object
43
+
44
+ def initialize(display, object)
45
+ @display = display
46
+ @object = object || display
47
+ end
48
+ end
49
+
50
+ attr_accessor :title
51
+ attr_accessor :data
52
+
53
+ def initialize(title = nil)
54
+ @title = title
55
+ @data = []
56
+ end
57
+
58
+ def add_row(display, object = nil)
59
+ @data << Row.new(display, object)
60
+ end
61
+ end
62
+
63
+ def initialize(height, width, top, left, title: nil, highlight: true, focus_number: nil, interval:, show_refresh:, content_block:, selection_blocks:)
40
64
  self.win_height = Curses.lines * height
41
65
  self.win_width = Curses.cols * width
42
66
  self.win_top = Curses.lines * top
@@ -52,11 +76,11 @@ module Wassup
52
76
  self.virtual_scroll = true
53
77
 
54
78
  self.top = 0
55
- self.data_lines = []
56
- self.data_objects = []
79
+
80
+ self.contents = []
81
+ self.show_refresh = show_refresh
57
82
 
58
83
  self.selected_view_index = 0
59
- self.all_view_data_objects = [] # Array of array
60
84
 
61
85
  self.win.refresh
62
86
  self.subwin.refresh
@@ -77,16 +101,16 @@ module Wassup
77
101
  self.subwin = nil
78
102
  end
79
103
 
80
- if (@all_view_data_objects || []).size > 1
104
+ if (self.contents || []).size > 1
81
105
  top_bump = 4
82
106
 
83
- view_title = (self.all_view_data_objects[self.selected_view_index] || {})[:title]
107
+ view_title = self.contents[self.selected_view_index].title || "<No Title>"
84
108
  view_title += " " * 100
85
109
 
86
110
  self.win.setpos(2, 2)
87
111
  self.win.addstr(view_title[0...self.win.maxx()-3])
88
112
 
89
- subtitle = "(#{self.selected_view_index + 1} out of #{self.all_view_data_objects.size})"
113
+ subtitle = "(#{self.selected_view_index + 1} out of #{self.contents.size})"
90
114
  subtitle += " " * 100
91
115
  self.win.setpos(3, 2)
92
116
  self.win.addstr(subtitle[0...self.win.maxx()-3])
@@ -120,28 +144,52 @@ module Wassup
120
144
  end
121
145
  end
122
146
 
147
+ def data_lines
148
+ return [] if self.selected_view_index.nil?
149
+ content = (self.contents || [])[self.selected_view_index]
150
+
151
+ if content.nil?
152
+ return []
153
+ else
154
+ content.data.map(&:display)
155
+ end
156
+ end
157
+
158
+ def refreshing?
159
+ return !self.content_thread.nil?
160
+ end
161
+
123
162
  def refresh(force: false)
124
- return if !needs_refresh? && !force
163
+ if force
164
+ self.last_refreshed = nil
165
+ end
166
+
167
+ return if !needs_refresh?
125
168
 
126
169
  thread = self.content_thread
127
170
  if !thread.nil?
128
171
  if thread.status == "sleep" || thread.status == "run" || thread.status == "aborting"
172
+ self.update_refresh
129
173
  return
130
174
  elsif thread.status == nil
131
- self.add_line("thread status is nil")
132
175
  return
133
176
  elsif thread.status == false
134
- content = thread.value
135
- if content.is_a?(Ope)
136
- self.refresh_content([
137
- "[fg=red]Error during refersh[fg=white]",
138
- "[fg=red]at #{Time.now}[fg=while]",
139
- "",
140
- "[fg=yellow]Will try again next interval[fg=white]"
141
- ])
142
- else
143
- self.refresh_content(content)
177
+ rtn = thread.value
178
+ if rtn.is_a?(Ope)
179
+ content = Wassup::Pane::Content.new
180
+
181
+ content.add_row("[fg=red]Error during refersh[fg=white]")
182
+ content.add_row("[fg=red]at #{Time.now}[fg=while]")
183
+ content.add_row("")
184
+ content.add_row("[fg=yellow]Will try again next interval[fg=white]")
185
+
186
+ self.refresh_content([content])
187
+ elsif rtn.is_a?(Wassup::PaneBuilder::ContentBuilder)
188
+ self.refresh_content(rtn.contents)
144
189
  end
190
+
191
+ self.update_box
192
+ self.update_title
145
193
  else
146
194
  # This shouldn't happen
147
195
  # TODO: also fix this
@@ -151,26 +199,21 @@ module Wassup
151
199
  the_block = self.content_block
152
200
  self.content_thread = Thread.new {
153
201
  begin
154
- content = the_block.call()
202
+ builder = Wassup::PaneBuilder::ContentBuilder.new(self.contents)
203
+ content = the_block.call(builder)
204
+
205
+ builder
155
206
  rescue => ex
156
207
  next Ope.new(ex)
157
208
  end
158
209
  }
210
+ self.update_box
211
+ self.update_title
159
212
  end
160
213
  end
161
214
 
162
- def refresh_content(content)
163
- return unless content.is_a?(Array)
164
- return if content.first.nil?
165
-
166
- if content.first.is_a?(Hash)
167
- self.all_view_data_objects = content
168
- else
169
- self.all_view_data_objects = [
170
- content
171
- ]
172
- end
173
-
215
+ def refresh_content(contents)
216
+ self.contents = contents
174
217
  self.load_current_view()
175
218
  self.last_refreshed = Time.now
176
219
 
@@ -179,33 +222,54 @@ module Wassup
179
222
 
180
223
  def load_current_view
181
224
  self.setup_subwin()
182
- view_content = self.all_view_data_objects[self.selected_view_index]
183
225
 
184
226
  # this might be bad
185
227
  self.highlighted_line = nil
228
+ self.virtual_reload()
229
+ end
230
+
231
+ def title=(title)
232
+ @title = title
233
+ self.update_box()
234
+ self.update_title()
235
+ end
236
+
237
+ attr_accessor :refresh_char_count
238
+ def refresh_char
239
+ return "" unless self.show_refresh
186
240
 
187
- require 'pp'
188
- if view_content.is_a?(Hash) && view_content[:content]
189
- view_content = view_content[:content]
241
+ if self.refresh_char_count.nil?
242
+ self.refresh_char_count = 0
190
243
  end
191
244
 
192
- @data_lines = []
193
- @data_objects = []
194
- view_content.each do |item|
195
- if item.is_a?(String)
196
- @data_objects << item
197
- self.add_line(item)
198
- elsif item.is_a?(Array)
199
- @data_objects << item[1]
200
- self.add_line(item[0])
245
+ if self.refreshing?
246
+ array = ['\\', '|', '/', '|']
247
+ rtn = array[self.refresh_char_count]
248
+
249
+ self.refresh_char_count += 1
250
+ if self.refresh_char_count >= array.size
251
+ self.refresh_char_count = 0
201
252
  end
253
+
254
+ return rtn
255
+ else
256
+ return ""
202
257
  end
203
258
  end
204
259
 
205
- def title=(title)
206
- @title = title
207
- self.update_box()
208
- self.update_title()
260
+ attr_accessor :last_refresh_char_at
261
+ def update_refresh
262
+ return unless self.should_box
263
+
264
+ self.last_refresh_char_at ||= Time.now
265
+
266
+ if Time.now - self.last_refresh_char_at >= 0.15
267
+ self.win.setpos(0, 1)
268
+ self.win.addstr(self.refresh_char)
269
+ self.win.refresh
270
+
271
+ self.last_refresh_char_at = Time.now
272
+ end
209
273
  end
210
274
 
211
275
  def update_title
@@ -236,16 +300,6 @@ module Wassup
236
300
  self.win.refresh
237
301
  end
238
302
 
239
- def add_line(text)
240
- data_lines << text
241
-
242
- if self.virtual_scroll
243
- self.virtual_reload
244
- else
245
- self.load_thing
246
- end
247
- end
248
-
249
303
  # Load the file into memory and
250
304
  # put the first part on the curses display.
251
305
  def load_thing
@@ -258,8 +312,9 @@ module Wassup
258
312
  end
259
313
 
260
314
  def virtual_reload
261
- return if self.data_lines.nil?
315
+ return if self.data_lines.nil? || self.data_lines.empty?
262
316
 
317
+ # TODO: This errored out but might be because thread stuff???
263
318
  self.data_lines[self.top..(self.top+self.subwin.maxy-1)].each_with_index do |line, idx|
264
319
 
265
320
  write_full_line = false
@@ -267,65 +322,49 @@ module Wassup
267
322
 
268
323
  max_char = self.subwin.maxx()-3
269
324
 
270
- # if false && write_full_line || should_highlight
271
- # if should_highlight
272
- # self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::HIGHLIGHT))
273
- # else
274
- # self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
275
- # end
276
- #
277
- # short_line = line[0...max_char]
278
- #
279
- # self.subwin.setpos(idx, 0)
280
- # self.subwin.addstr(short_line)
281
- # self.subwin.clrtoeol()
282
- #
283
- # self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
284
- # else
285
- self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
286
-
287
- splits = line.split(/\[.*?\]/) # returns ["hey something", "other thing", "okay"]
288
- scans = line.scan(/\[.*?\]/) #returns ["red", "white"]
289
- scans = scans.map do |str|
290
- if str.start_with?('[fg=')
291
- str = str.gsub('[fg=', '').gsub(']','')
292
- Wassup::Color.new(str)
293
- else
294
- str
295
- end
296
- end
297
-
298
- all_parts = splits.zip(scans).flatten.compact
299
-
300
- char_count = 0
301
-
302
- if should_highlight
303
- self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::HIGHLIGHT))
304
- end
305
-
306
- all_parts.each do |part|
307
- if part.is_a?(Wassup::Color)
308
- #color = Curses.color_pair([1,2,3,4].sample)
309
- if !should_highlight
310
- self.subwin.attrset(Curses.color_pair(part.color_pair))
311
- end
312
- else
313
- new_char_count = char_count + part.size
314
- if new_char_count >= max_char
315
- part = part[0...(max_char - char_count)]
316
- end
317
-
318
- self.subwin.setpos(idx, char_count)
319
- self.subwin.addstr(part)
320
-
321
- char_count += part.size
322
- end
323
-
324
- end
325
-
326
- self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
327
- self.subwin.clrtoeol()
328
- #end
325
+ self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
326
+
327
+ splits = line.split(/\[.*?\]/) # returns ["hey something", "other thing", "okay"]
328
+ scans = line.scan(/\[.*?\]/) #returns ["red", "white"]
329
+ scans = scans.map do |str|
330
+ if str.start_with?('[fg=')
331
+ str = str.gsub('[fg=', '').gsub(']','')
332
+ Wassup::Color.new(str)
333
+ else
334
+ str
335
+ end
336
+ end
337
+
338
+ all_parts = splits.zip(scans).flatten.compact
339
+
340
+ char_count = 0
341
+
342
+ if should_highlight
343
+ self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::HIGHLIGHT))
344
+ end
345
+
346
+ all_parts.each do |part|
347
+ if part.is_a?(Wassup::Color)
348
+ #color = Curses.color_pair([1,2,3,4].sample)
349
+ if !should_highlight
350
+ self.subwin.attrset(Curses.color_pair(part.color_pair))
351
+ end
352
+ else
353
+ new_char_count = char_count + part.size
354
+ if new_char_count >= max_char
355
+ part = part[0...(max_char - char_count)]
356
+ end
357
+
358
+ self.subwin.setpos(idx, char_count)
359
+ self.subwin.addstr(part)
360
+
361
+ char_count += part.size
362
+ end
363
+
364
+ end
365
+
366
+ self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
367
+ self.subwin.clrtoeol()
329
368
  end
330
369
  self.subwin.refresh
331
370
  end
@@ -387,7 +426,7 @@ module Wassup
387
426
  def scroll_left
388
427
  self.selected_view_index -= 1
389
428
  if self.selected_view_index < 0
390
- self.selected_view_index = self.all_view_data_objects.size - 1
429
+ self.selected_view_index = self.contents.size - 1
391
430
  end
392
431
 
393
432
  self.load_current_view
@@ -395,7 +434,7 @@ module Wassup
395
434
 
396
435
  def scroll_right
397
436
  self.selected_view_index += 1
398
- if self.selected_view_index >= self.all_view_data_objects.size
437
+ if self.selected_view_index >= self.contents.size
399
438
  self.selected_view_index = 0
400
439
  end
401
440
 
@@ -465,7 +504,9 @@ module Wassup
465
504
  else
466
505
  selection_block = self.selection_blocks[input]
467
506
  if !selection_block.nil? && !self.highlighted_line.nil?
468
- data = @data_objects[self.highlighted_line]
507
+ content = self.contents[self.selected_view_index]
508
+ row = content.data[self.highlighted_line]
509
+ data = row.object || row.display
469
510
  selection_block.call(data)
470
511
  end
471
512
  end
@@ -10,10 +10,56 @@ module Wassup
10
10
 
11
11
  attr_accessor :title
12
12
 
13
+ attr_accessor :show_refresh
14
+
13
15
  attr_accessor :interval
14
16
  attr_accessor :content_block
15
17
  attr_accessor :selection_blocks
16
18
 
19
+ class ContentBuilder
20
+ attr_accessor :contents
21
+
22
+ def initialize(contents)
23
+ @contents = contents
24
+ @need_to_clear = true
25
+ @show_refresh = true
26
+ end
27
+
28
+ def clear=(clear)
29
+ @need_to_clear = clear
30
+ end
31
+
32
+ def add_row(display, object=nil, page:nil)
33
+ if @need_to_clear
34
+ @need_to_clear = false
35
+ self.contents = []
36
+ end
37
+
38
+ content = nil
39
+
40
+ # Create contents if none
41
+ if page.nil?
42
+ if self.contents.empty?
43
+ content = Pane::Content.new
44
+ self.contents << content
45
+ else
46
+ content = self.contents.first
47
+ end
48
+ elsif page.is_a?(String)
49
+ content = self.contents.find do |content|
50
+ content.title == page
51
+ end
52
+
53
+ if content.nil?
54
+ content = Pane::Content.new(page)
55
+ self.contents << content
56
+ end
57
+ end
58
+
59
+ content.add_row(display, object)
60
+ end
61
+ end
62
+
17
63
  def initialize()
18
64
  @height = 1
19
65
  @weight = 1
@@ -1,3 +1,3 @@
1
1
  module Wassup
2
- VERSION = "0.1.2"
2
+ VERSION = "0.2.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: wassup
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.2
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Josh Holtz
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-12-03 00:00:00.000000000 Z
11
+ date: 2021-12-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: curses
@@ -63,7 +63,7 @@ licenses:
63
63
  metadata:
64
64
  homepage_uri: https://github.com/joshdholtz/wassup
65
65
  source_code_uri: https://github.com/joshdholtz/wassup
66
- post_install_message:
66
+ post_install_message:
67
67
  rdoc_options: []
68
68
  require_paths:
69
69
  - lib
@@ -78,8 +78,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
78
78
  - !ruby/object:Gem::Version
79
79
  version: '0'
80
80
  requirements: []
81
- rubygems_version: 3.2.3
82
- signing_key:
81
+ rubygems_version: 3.0.3.1
82
+ signing_key:
83
83
  specification_version: 4
84
84
  summary: A scriptable terminal dashboard
85
85
  test_files: []