wassup 0.1.1 → 0.1.2
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 +4 -4
- data/.github/FUNDING.yml +3 -0
- data/README.md +37 -3
- data/examples/basic/Supfile +28 -0
- data/examples/debug/Supfile +54 -0
- data/examples/josh-fastlane/README.md +14 -0
- data/examples/josh-fastlane/Supfile +23 -6
- data/examples/josh-fastlane/demo.png +0 -0
- data/lib/wassup/app.rb +13 -6
- data/lib/wassup/color.rb +76 -0
- data/lib/wassup/pane.rb +132 -34
- data/lib/wassup/pane_builder.rb +15 -3
- data/lib/wassup/version.rb +1 -1
- data/lib/wassup.rb +1 -0
- metadata +8 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e0460f6c9734dcfa48fe6d0561d1de6d5c81d1d49a6f8f6e89cfe8dbb54bb78a
|
4
|
+
data.tar.gz: f017aea6ab05afe32a5c21ba470f4aa82400d08a54d666172596c27c9f74659c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0a4d4e533f3519c77053a5388a00ad584b84203ae18926e7a105a05a72bbe27b68fac844c22ec152baa394b1dcdf1aafc6ae30bbe1b51c80f6a415baf70540c0
|
7
|
+
data.tar.gz: 447c01199ef5ee734f9836d30d1ee7fe24fdf01d6652b7499d1c053f4903cfba6e63ee979b26122b44b3ef0ba4c213a2ae0f9dc196effe3537d5cf00a2ef9bb7
|
data/.github/FUNDING.yml
ADDED
data/README.md
CHANGED
@@ -1,8 +1,42 @@
|
|
1
1
|
# Wassup
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
3
|
+
A scriptable terminal dashboard
|
4
|
+
|
5
|
+
|
6
|
+
https://user-images.githubusercontent.com/401294/144465499-a8903d4c-f003-4550-b47c-f70c17cc02d8.mov
|
7
|
+
|
8
|
+
## Example `Supfile`
|
9
|
+
|
10
|
+
```rb
|
11
|
+
require 'json'
|
12
|
+
require 'rest-client'
|
13
|
+
|
14
|
+
add_pane do |pane|
|
15
|
+
pane.height = 0.5
|
16
|
+
pane.width = 00.5
|
17
|
+
pane.top = 0
|
18
|
+
pane.left = 0
|
19
|
+
|
20
|
+
pane.highlight = true
|
21
|
+
pane.title = "Open PRs - fastlane/fastlane"
|
22
|
+
|
23
|
+
pane.interval = 60 * 5
|
24
|
+
pane.content do
|
25
|
+
resp = RestClient.get "https://api.github.com/repos/fastlane/fastlane/pulls"
|
26
|
+
json = JSON.parse(resp)
|
27
|
+
json.map do |pr|
|
28
|
+
display = "##{pr["number"]} pr["title"]"
|
29
|
+
|
30
|
+
# First element is displayed
|
31
|
+
# Second element is passed to pane.selection
|
32
|
+
[display, pr["html_url"]]
|
33
|
+
end
|
34
|
+
end
|
35
|
+
pane.selection do |url|
|
36
|
+
`open #{url}`
|
37
|
+
end
|
38
|
+
end
|
39
|
+
```
|
6
40
|
|
7
41
|
## Installation
|
8
42
|
|
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'json'
|
2
|
+
require 'rest-client'
|
3
|
+
|
4
|
+
add_pane do |pane|
|
5
|
+
pane.height = 0.5
|
6
|
+
pane.width = 0.5
|
7
|
+
pane.top = 0
|
8
|
+
pane.left = 0
|
9
|
+
|
10
|
+
pane.highlight = true
|
11
|
+
pane.title = "Open PRs - fastlane/fastlane"
|
12
|
+
|
13
|
+
pane.interval = 60 * 5
|
14
|
+
pane.content do
|
15
|
+
resp = RestClient.get "https://api.github.com/repos/fastlane/fastlane/pulls"
|
16
|
+
json = JSON.parse(resp)
|
17
|
+
json.map do |pr|
|
18
|
+
display = "##{pr["number"]} #{pr["title"]}"
|
19
|
+
|
20
|
+
# First element is displayed
|
21
|
+
# Second element is passed to pane.selection
|
22
|
+
[display, pr["html_url"]]
|
23
|
+
end
|
24
|
+
end
|
25
|
+
pane.selection do |url|
|
26
|
+
`open #{url}`
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
add_pane do |pane|
|
2
|
+
pane.height = 0.25
|
3
|
+
pane.width = 0.25
|
4
|
+
pane.top = 0
|
5
|
+
pane.left = 0
|
6
|
+
|
7
|
+
pane.highlight = false
|
8
|
+
pane.title = "Time Update - Every Second"
|
9
|
+
|
10
|
+
pane.interval = 1
|
11
|
+
pane.content do
|
12
|
+
[
|
13
|
+
`date`
|
14
|
+
]
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
add_pane do |pane|
|
19
|
+
pane.height = 0.25
|
20
|
+
pane.width = 0.25
|
21
|
+
pane.top = 0.25
|
22
|
+
pane.left = 0
|
23
|
+
|
24
|
+
pane.highlight = false
|
25
|
+
pane.title = "Time Update - Every 5 Seconds"
|
26
|
+
|
27
|
+
pane.interval = 5
|
28
|
+
pane.content do
|
29
|
+
[
|
30
|
+
`date`
|
31
|
+
]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
add_pane do |pane|
|
36
|
+
pane.height = 0.25
|
37
|
+
pane.width = 0.35
|
38
|
+
pane.top = 0
|
39
|
+
pane.left = 0.25
|
40
|
+
|
41
|
+
pane.highlight = false
|
42
|
+
pane.title = "Maybe Error - Every 10 Seconds"
|
43
|
+
|
44
|
+
pane.interval = 10
|
45
|
+
pane.content do
|
46
|
+
if [true, false].sample
|
47
|
+
raise "An error occured! Oh no!"
|
48
|
+
end
|
49
|
+
|
50
|
+
[
|
51
|
+
"[fg=cyan]No error occured[fg=white]"
|
52
|
+
]
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
# Josh's _fastlane_ Example
|
2
|
+
|
3
|
+
## Purpose
|
4
|
+
I need to view a lot of different _fastlane_ things at one glance between _fastlane_'s two organizations:
|
5
|
+
- https://github.com/fastlane
|
6
|
+
- https://github.com/fastlane-community
|
7
|
+
|
8
|
+
I mainly need to watch PRs on https://github.com/fastlane/fastlane/ but also all PRs from all the repos in https://github.com/fastlane-community
|
9
|
+
|
10
|
+
I also like to see some stats on PR count (and eventually issues and hot/trending issues)
|
11
|
+
|
12
|
+
It's also nice to have a quick glace of CircleCI jobs
|
13
|
+
|
14
|
+

|
@@ -3,6 +3,8 @@ require 'rest-client'
|
|
3
3
|
require 'json'
|
4
4
|
require 'colorize'
|
5
5
|
|
6
|
+
require 'curses'
|
7
|
+
|
6
8
|
fastlane_community_prs = []
|
7
9
|
fastlane_prs = []
|
8
10
|
|
@@ -135,17 +137,32 @@ add_pane do |pane|
|
|
135
137
|
workflow = json["items"].first
|
136
138
|
status = workflow["status"]
|
137
139
|
|
138
|
-
|
140
|
+
if status == "failed"
|
141
|
+
status = "[fg=red]#{status}[fg=white]"
|
142
|
+
elsif status == "success"
|
143
|
+
status = "[fg=green]#{status}[fg=white]"
|
144
|
+
else
|
145
|
+
status = "[fg=yellow]#{status}[fg=white]"
|
146
|
+
end
|
147
|
+
|
148
|
+
["#{number} (#{status}) by #{login} - #{message}", [item, workflow]]
|
139
149
|
end
|
140
150
|
end
|
141
151
|
pane.selection do |data|
|
142
|
-
|
143
|
-
|
144
|
-
|
152
|
+
workflow = data[1]
|
153
|
+
|
154
|
+
slug = workflow["project_slug"]
|
155
|
+
pipeline_number = workflow["pipeline_number"]
|
156
|
+
workflow_id = workflow["id"]
|
145
157
|
|
146
158
|
url = "https://app.circleci.com/pipelines/#{slug}/#{pipeline_number}/workflows/#{workflow_id}"
|
147
159
|
`open #{url}`
|
148
160
|
end
|
161
|
+
pane.selection('o') do |data|
|
162
|
+
pipeline = data[0]
|
163
|
+
url = pipeline["vcs"]["review_url"]
|
164
|
+
`open #{url}`
|
165
|
+
end
|
149
166
|
end
|
150
167
|
|
151
168
|
#
|
@@ -196,7 +213,7 @@ add_pane do |pane|
|
|
196
213
|
days = (Time.now - date).to_i / (24 * 60 * 60)
|
197
214
|
days_formatted = '%3.3s' % days.to_s
|
198
215
|
|
199
|
-
["#{number_formatted} #{days_formatted}d ago #{title}",pr]
|
216
|
+
["[fg=yellow]#{number_formatted}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}",pr]
|
200
217
|
end
|
201
218
|
|
202
219
|
{
|
@@ -247,7 +264,7 @@ add_pane do |pane|
|
|
247
264
|
days = (Time.now - date).to_i / (24 * 60 * 60)
|
248
265
|
days_formatted = '%3.3s' % days.to_s
|
249
266
|
|
250
|
-
["##{number} #{days_formatted}d ago #{title}",pr]
|
267
|
+
["[fg=yellow]##{number}[fg=cyan] #{days_formatted}d ago[fg=white] #{title}",pr]
|
251
268
|
end
|
252
269
|
end
|
253
270
|
pane.selection do |data|
|
Binary file
|
data/lib/wassup/app.rb
CHANGED
@@ -10,10 +10,12 @@ module Wassup
|
|
10
10
|
|
11
11
|
Curses.stdscr.scrollok true
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
13
|
+
Wassup::Color.init
|
14
|
+
|
15
|
+
# Determines the colors in the 'attron' below
|
16
|
+
|
17
|
+
#Curses.init_pair(Curses::COLOR_BLUE,Curses::COLOR_BLUE,Curses::COLOR_BLACK)
|
18
|
+
#Curses.init_pair(Curses::COLOR_RED,Curses::COLOR_RED,Curses::COLOR_BLACK)
|
17
19
|
|
18
20
|
app = App.new(path: path)
|
19
21
|
end
|
@@ -33,7 +35,7 @@ module Wassup
|
|
33
35
|
focus_number: number,
|
34
36
|
interval: pane_builder.interval,
|
35
37
|
content_block: pane_builder.content_block,
|
36
|
-
|
38
|
+
selection_blocks: pane_builder.selection_blocks
|
37
39
|
)
|
38
40
|
pane.focus_handler = @focus_handler
|
39
41
|
@panes[number.to_s] = pane
|
@@ -44,7 +46,12 @@ module Wassup
|
|
44
46
|
@focused_pane = nil
|
45
47
|
@panes = {}
|
46
48
|
|
49
|
+
# TODO: this could maybe get replaced with selection_blocks now
|
47
50
|
@focus_handler = Proc.new do |input|
|
51
|
+
if input == "q"
|
52
|
+
exit
|
53
|
+
end
|
54
|
+
|
48
55
|
if (pane = @panes[input.to_s])
|
49
56
|
@focused_pane.focused = false
|
50
57
|
|
@@ -67,7 +74,7 @@ module Wassup
|
|
67
74
|
|
68
75
|
begin
|
69
76
|
|
70
|
-
@hidden_pane = Pane.new(0, 0, 0, 0, highlight: false, focus_number: 0, interval: nil, content_block: nil,
|
77
|
+
@hidden_pane = Pane.new(0, 0, 0, 0, highlight: false, focus_number: 0, interval: nil, content_block: nil, selection_blocks: nil)
|
71
78
|
@hidden_pane.focus_handler = @focus_handler
|
72
79
|
@focused_pane = @hidden_pane
|
73
80
|
|
data/lib/wassup/color.rb
ADDED
@@ -0,0 +1,76 @@
|
|
1
|
+
require 'curses'
|
2
|
+
|
3
|
+
module Wassup
|
4
|
+
class Color
|
5
|
+
attr_accessor :color_pair
|
6
|
+
|
7
|
+
module Pair
|
8
|
+
BLACK = 0
|
9
|
+
BLUE = 1
|
10
|
+
CYAN = 2
|
11
|
+
GREEN = 3
|
12
|
+
MAGENTA = 4
|
13
|
+
RED = 5
|
14
|
+
WHITE = 15
|
15
|
+
YELLOW = 7
|
16
|
+
|
17
|
+
NORMAL = 20
|
18
|
+
HIGHLIGHT = 21
|
19
|
+
|
20
|
+
BORDER = 20
|
21
|
+
BORDER_FOCUS = 7
|
22
|
+
|
23
|
+
TITLE = 20
|
24
|
+
TITLE_FOCUS = 20
|
25
|
+
end
|
26
|
+
|
27
|
+
def self.init
|
28
|
+
Curses.use_default_colors()
|
29
|
+
|
30
|
+
Curses.init_pair(Pair::NORMAL, Pair::WHITE, 0) #white foreground, black background
|
31
|
+
Curses.init_pair(Pair::HIGHLIGHT, 0, Pair::WHITE) # black foreground, white background
|
32
|
+
|
33
|
+
# Curses.init_pair(Pair::BORDER, Pair::WHITE, 0) #white foreground, black background
|
34
|
+
# Curses.init_pair(Pair::BORDER_FOCUS, Pair::MAGENTA, 0) #white foreground, black background
|
35
|
+
#
|
36
|
+
# Curses.init_pair(Pair::TITLE, Pair::WHITE, 0) #white foreground, black background
|
37
|
+
# Curses.init_pair(Pair::TITLE_FOCUS, Pair::WHITE, 0) #white foreground, black background
|
38
|
+
|
39
|
+
Curses.init_pair(Pair::BLACK, Curses::COLOR_BLACK, 0)
|
40
|
+
Curses.init_pair(Pair::BLUE, Curses::COLOR_BLUE, 0)
|
41
|
+
Curses.init_pair(Pair::CYAN, Curses::COLOR_CYAN, 0)
|
42
|
+
Curses.init_pair(Pair::GREEN, Curses::COLOR_GREEN, 0)
|
43
|
+
Curses.init_pair(Pair::MAGENTA, Curses::COLOR_MAGENTA, 0)
|
44
|
+
Curses.init_pair(Pair::RED, Curses::COLOR_RED, 0)
|
45
|
+
Curses.init_pair(Pair::WHITE, Pair::WHITE, 0)
|
46
|
+
Curses.init_pair(Pair::YELLOW, Curses::COLOR_YELLOW, 0)
|
47
|
+
end
|
48
|
+
|
49
|
+
def initialize(string_name)
|
50
|
+
@color_pair = case string_name
|
51
|
+
when "black"
|
52
|
+
Pair::BLACK
|
53
|
+
when "blue"
|
54
|
+
Pair::BLUE
|
55
|
+
when "cyan"
|
56
|
+
Pair::CYAN
|
57
|
+
when "green"
|
58
|
+
Pair::GREEN
|
59
|
+
when "magenta"
|
60
|
+
Pair::MAGENTA
|
61
|
+
when "red"
|
62
|
+
Pair::RED
|
63
|
+
when "white"
|
64
|
+
Pair::WHITE
|
65
|
+
when "yellow"
|
66
|
+
Pair::YELLOW
|
67
|
+
else
|
68
|
+
if string_name.to_i.to_s == string_name
|
69
|
+
string_name.to_i
|
70
|
+
else
|
71
|
+
Pair::WHITE
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
data/lib/wassup/pane.rb
CHANGED
@@ -27,14 +27,16 @@ module Wassup
|
|
27
27
|
attr_accessor :interval
|
28
28
|
attr_accessor :last_refreshed
|
29
29
|
attr_accessor :content_block
|
30
|
-
attr_accessor :
|
30
|
+
attr_accessor :selection_blocks
|
31
|
+
|
32
|
+
attr_accessor :content_thread
|
31
33
|
|
32
34
|
attr_accessor :selected_view_index
|
33
35
|
attr_accessor :all_view_data_objects
|
34
36
|
|
35
37
|
attr_accessor :win_height, :win_width, :win_top, :win_left
|
36
38
|
|
37
|
-
def initialize(height, width, top, left, title: nil, highlight: true, focus_number: nil, interval:, content_block:,
|
39
|
+
def initialize(height, width, top, left, title: nil, highlight: true, focus_number: nil, interval:, content_block:, selection_blocks:)
|
38
40
|
self.win_height = Curses.lines * height
|
39
41
|
self.win_width = Curses.cols * width
|
40
42
|
self.win_top = Curses.lines * top
|
@@ -63,7 +65,7 @@ module Wassup
|
|
63
65
|
|
64
66
|
self.interval = interval
|
65
67
|
self.content_block = content_block
|
66
|
-
self.
|
68
|
+
self.selection_blocks = selection_blocks || {}
|
67
69
|
end
|
68
70
|
|
69
71
|
def setup_subwin
|
@@ -111,11 +113,53 @@ module Wassup
|
|
111
113
|
return Time.now - self.interval > self.last_refreshed
|
112
114
|
end
|
113
115
|
|
114
|
-
|
115
|
-
|
116
|
+
class Ope
|
117
|
+
attr_accessor :error
|
118
|
+
def initialize(error)
|
119
|
+
@error = error
|
120
|
+
end
|
121
|
+
end
|
116
122
|
|
117
|
-
|
123
|
+
def refresh(force: false)
|
124
|
+
return if !needs_refresh? && !force
|
125
|
+
|
126
|
+
thread = self.content_thread
|
127
|
+
if !thread.nil?
|
128
|
+
if thread.status == "sleep" || thread.status == "run" || thread.status == "aborting"
|
129
|
+
return
|
130
|
+
elsif thread.status == nil
|
131
|
+
self.add_line("thread status is nil")
|
132
|
+
return
|
133
|
+
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)
|
144
|
+
end
|
145
|
+
else
|
146
|
+
# This shouldn't happen
|
147
|
+
# TODO: also fix this
|
148
|
+
return
|
149
|
+
end
|
150
|
+
else
|
151
|
+
the_block = self.content_block
|
152
|
+
self.content_thread = Thread.new {
|
153
|
+
begin
|
154
|
+
content = the_block.call()
|
155
|
+
rescue => ex
|
156
|
+
next Ope.new(ex)
|
157
|
+
end
|
158
|
+
}
|
159
|
+
end
|
160
|
+
end
|
118
161
|
|
162
|
+
def refresh_content(content)
|
119
163
|
return unless content.is_a?(Array)
|
120
164
|
return if content.first.nil?
|
121
165
|
|
@@ -128,8 +172,9 @@ module Wassup
|
|
128
172
|
end
|
129
173
|
|
130
174
|
self.load_current_view()
|
131
|
-
|
132
175
|
self.last_refreshed = Time.now
|
176
|
+
|
177
|
+
self.content_thread = nil
|
133
178
|
end
|
134
179
|
|
135
180
|
def load_current_view
|
@@ -164,6 +209,8 @@ module Wassup
|
|
164
209
|
end
|
165
210
|
|
166
211
|
def update_title
|
212
|
+
return unless self.should_box
|
213
|
+
|
167
214
|
title = self.title || "<No Title>"
|
168
215
|
full_title = "#{self.focus_number} - #{title}"
|
169
216
|
|
@@ -182,9 +229,9 @@ module Wassup
|
|
182
229
|
def update_box
|
183
230
|
return unless self.should_box
|
184
231
|
|
185
|
-
self.win.
|
232
|
+
self.win.attrset(self.focused ? Curses.color_pair(Wassup::Color::Pair::BORDER_FOCUS) : Curses.color_pair(Wassup::Color::Pair::BORDER))
|
186
233
|
self.win.box()
|
187
|
-
self.win.
|
234
|
+
self.win.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
|
188
235
|
|
189
236
|
self.win.refresh
|
190
237
|
end
|
@@ -215,19 +262,70 @@ module Wassup
|
|
215
262
|
|
216
263
|
self.data_lines[self.top..(self.top+self.subwin.maxy-1)].each_with_index do |line, idx|
|
217
264
|
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
265
|
+
write_full_line = false
|
266
|
+
should_highlight = self.focused && self.highlight && (idx + self.top) == self.highlighted_line
|
267
|
+
|
268
|
+
max_char = self.subwin.maxx()-3
|
269
|
+
|
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
|
231
329
|
end
|
232
330
|
self.subwin.refresh
|
233
331
|
end
|
@@ -327,10 +425,10 @@ module Wassup
|
|
327
425
|
self.top += 1
|
328
426
|
str = self.data_lines[self.top + self.subwin.maxy - 1]
|
329
427
|
if str
|
330
|
-
self.subwin.
|
428
|
+
self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
|
331
429
|
self.subwin.setpos(self.subwin.maxy - 1, 0)
|
332
430
|
self.subwin.addstr(str)
|
333
|
-
self.subwin.
|
431
|
+
self.subwin.attrset(Curses.color_pair(Wassup::Color::Pair::NORMAL))
|
334
432
|
end
|
335
433
|
return true
|
336
434
|
else
|
@@ -348,27 +446,27 @@ module Wassup
|
|
348
446
|
|
349
447
|
if input == "j"
|
350
448
|
if virtual_scroll
|
351
|
-
virtual_scroll_down
|
449
|
+
self.virtual_scroll_down
|
352
450
|
else
|
353
451
|
scroll_down
|
354
452
|
end
|
355
453
|
elsif input == "k"
|
356
454
|
if virtual_scroll
|
357
|
-
virtual_scroll_up
|
455
|
+
self.virtual_scroll_up
|
358
456
|
else
|
359
457
|
scroll_up
|
360
458
|
end
|
361
459
|
elsif input == "h"
|
362
|
-
scroll_left
|
460
|
+
self.scroll_left
|
363
461
|
elsif input == "l"
|
364
|
-
scroll_right
|
365
|
-
elsif input == "
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
if !
|
462
|
+
self.scroll_right
|
463
|
+
elsif input == "r"
|
464
|
+
self.refresh(force: true)
|
465
|
+
else
|
466
|
+
selection_block = self.selection_blocks[input]
|
467
|
+
if !selection_block.nil? && !self.highlighted_line.nil?
|
370
468
|
data = @data_objects[self.highlighted_line]
|
371
|
-
|
469
|
+
selection_block.call(data)
|
372
470
|
end
|
373
471
|
end
|
374
472
|
end
|
data/lib/wassup/pane_builder.rb
CHANGED
@@ -12,13 +12,25 @@ module Wassup
|
|
12
12
|
|
13
13
|
attr_accessor :interval
|
14
14
|
attr_accessor :content_block
|
15
|
-
attr_accessor :
|
15
|
+
attr_accessor :selection_blocks
|
16
|
+
|
17
|
+
def initialize()
|
18
|
+
@height = 1
|
19
|
+
@weight = 1
|
20
|
+
@top = 0
|
21
|
+
@left = 0
|
22
|
+
|
23
|
+
@highlight = false
|
24
|
+
@interval = 60 * 5
|
25
|
+
|
26
|
+
@selection_blocks = {}
|
27
|
+
end
|
16
28
|
|
17
29
|
def content(&block)
|
18
30
|
self.content_block = block
|
19
31
|
end
|
20
|
-
def selection(&block)
|
21
|
-
self.
|
32
|
+
def selection(input=10, &block)
|
33
|
+
self.selection_blocks[input] = block
|
22
34
|
end
|
23
35
|
end
|
24
36
|
end
|
data/lib/wassup/version.rb
CHANGED
data/lib/wassup.rb
CHANGED
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.
|
4
|
+
version: 0.1.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Josh Holtz
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-12-
|
11
|
+
date: 2021-12-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: curses
|
@@ -32,6 +32,7 @@ executables:
|
|
32
32
|
extensions: []
|
33
33
|
extra_rdoc_files: []
|
34
34
|
files:
|
35
|
+
- ".github/FUNDING.yml"
|
35
36
|
- ".gitignore"
|
36
37
|
- ".rspec"
|
37
38
|
- ".travis.yml"
|
@@ -44,9 +45,14 @@ files:
|
|
44
45
|
- bin/console
|
45
46
|
- bin/setup
|
46
47
|
- bin/wassup
|
48
|
+
- examples/basic/Supfile
|
49
|
+
- examples/debug/Supfile
|
50
|
+
- examples/josh-fastlane/README.md
|
47
51
|
- examples/josh-fastlane/Supfile
|
52
|
+
- examples/josh-fastlane/demo.png
|
48
53
|
- lib/wassup.rb
|
49
54
|
- lib/wassup/app.rb
|
55
|
+
- lib/wassup/color.rb
|
50
56
|
- lib/wassup/pane.rb
|
51
57
|
- lib/wassup/pane_builder.rb
|
52
58
|
- lib/wassup/version.rb
|