rbcurse 0.1.3 → 1.1.1
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG +126 -0
- data/Manifest.txt +53 -20
- data/README.markdown +423 -0
- data/Rakefile +3 -1
- data/examples/keytest.rb +177 -0
- data/examples/mpad2.rb +156 -0
- data/examples/newtesttabp.rb +121 -0
- data/examples/rfe.rb +48 -10
- data/examples/rfe_renderer.rb +4 -4
- data/examples/rvimsplit.rb +376 -0
- data/examples/sqlc.rb +97 -106
- data/examples/sqlm.rb +446 -0
- data/examples/test1.rb +4 -4
- data/examples/test2.rb +12 -12
- data/examples/testchars.rb +140 -0
- data/examples/testkeypress.rb +9 -4
- data/examples/testmulticomp.rb +72 -0
- data/examples/testscroller.rb +136 -0
- data/examples/testscrolllb.rb +86 -0
- data/examples/testscrollp.rb +87 -0
- data/examples/testscrollta.rb +80 -0
- data/examples/testscrolltable.rb +166 -0
- data/examples/testsplit.rb +87 -0
- data/examples/testsplit2.rb +123 -0
- data/examples/testsplit3.rb +215 -0
- data/examples/testsplit3_1.rb +244 -0
- data/examples/testsplit3a.rb +215 -0
- data/examples/testsplit3b.rb +237 -0
- data/examples/testsplitta.rb +148 -0
- data/examples/testsplittv.rb +142 -0
- data/examples/testsplittvv.rb +144 -0
- data/examples/testtable.rb +1 -1
- data/examples/testtabp.rb +3 -2
- data/examples/testtestw.rb +69 -0
- data/examples/testtodo.rb +5 -3
- data/examples/testtpane.rb +203 -0
- data/examples/testtpane2.rb +145 -0
- data/examples/testtpanetable.rb +199 -0
- data/examples/viewtodo.rb +5 -3
- data/lib/rbcurse.rb +1 -1
- data/lib/rbcurse/celleditor.rb +2 -2
- data/lib/rbcurse/colormap.rb +5 -5
- data/lib/rbcurse/defaultlistselectionmodel.rb +3 -3
- data/lib/rbcurse/io.rb +663 -0
- data/lib/rbcurse/listeditable.rb +306 -0
- data/lib/rbcurse/listkeys.rb +15 -15
- data/lib/rbcurse/listscrollable.rb +168 -27
- data/lib/rbcurse/mapper.rb +35 -13
- data/lib/rbcurse/rchangeevent.rb +28 -0
- data/lib/rbcurse/rform.rb +845 -0
- data/lib/rbcurse/rlistbox.rb +144 -34
- data/lib/rbcurse/rmessagebox.rb +10 -5
- data/lib/rbcurse/rmulticontainer.rb +325 -0
- data/lib/rbcurse/rmultitextview.rb +306 -0
- data/lib/rbcurse/rscrollform.rb +369 -0
- data/lib/rbcurse/rscrollpane.rb +511 -0
- data/lib/rbcurse/rsplitpane.rb +820 -0
- data/lib/rbcurse/rtabbedpane.rb +737 -109
- data/lib/rbcurse/rtabbedwindow.rb +326 -0
- data/lib/rbcurse/rtable.rb +220 -64
- data/lib/rbcurse/rtextarea.rb +340 -181
- data/lib/rbcurse/rtextview.rb +237 -101
- data/lib/rbcurse/rviewport.rb +203 -0
- data/lib/rbcurse/rwidget.rb +919 -95
- data/lib/rbcurse/scrollable.rb +7 -7
- data/lib/rbcurse/selectable.rb +4 -4
- data/lib/rbcurse/table/tablecellrenderer.rb +3 -0
- data/lib/rbcurse/undomanager.rb +181 -0
- data/lib/rbcurse/vieditable.rb +100 -0
- data/lib/ver/window.rb +471 -21
- metadata +66 -22
- data/README.txt +0 -312
- data/examples/testd.db +0 -0
- data/examples/todocsv.csv +0 -28
data/examples/viewtodo.rb
CHANGED
@@ -2,14 +2,16 @@ $LOAD_PATH << "/Users/rahul/work/projects/rbcurse/"
|
|
2
2
|
require 'rubygems'
|
3
3
|
require 'ncurses'
|
4
4
|
require 'logger'
|
5
|
-
#require 'ver/keyboard'
|
6
5
|
require 'rbcurse'
|
7
6
|
require 'rbcurse/rcombo'
|
8
7
|
require 'rbcurse/rtable'
|
9
|
-
#require 'rbcurse/table/tablecellrenderer'
|
10
8
|
require 'rbcurse/keylabelprinter'
|
11
9
|
require 'rbcurse/applicationheader'
|
12
10
|
require 'rbcurse/action'
|
11
|
+
require 'yaml' # 1.9 2009-10-05 13:11
|
12
|
+
###############################
|
13
|
+
## THIS WONT WORK SINCE I've changed to format of yaml file to array from hash
|
14
|
+
##############################
|
13
15
|
|
14
16
|
class TodoList
|
15
17
|
def initialize file
|
@@ -379,7 +381,7 @@ class TodoApp
|
|
379
381
|
@window.wrefresh
|
380
382
|
Ncurses::Panel.update_panels
|
381
383
|
begin
|
382
|
-
while((ch = @window.getchar()) != ?\C-q )
|
384
|
+
while((ch = @window.getchar()) != ?\C-q.getbyte(0) )
|
383
385
|
colcount = tcm.column_count-1
|
384
386
|
s = keycode_tos ch
|
385
387
|
#status_row.text = "Pressed #{ch} , #{s}"
|
data/lib/rbcurse.rb
CHANGED
data/lib/rbcurse/celleditor.rb
CHANGED
@@ -11,8 +11,7 @@ require 'logger'
|
|
11
11
|
# so it can display itself. Otherwise it is not added to the forms widget list, so the
|
12
12
|
# form has no idea tha this widget exists.
|
13
13
|
#
|
14
|
-
# Tested with Field, combo and checkbox
|
15
|
-
# TODO test and integrate with tables.
|
14
|
+
# Tested with Field, combo and checkbox, tables.
|
16
15
|
#
|
17
16
|
module RubyCurses
|
18
17
|
class CellEditor
|
@@ -98,6 +97,7 @@ module RubyCurses
|
|
98
97
|
widget.visible = true
|
99
98
|
widget.form = parent.form
|
100
99
|
#$log.debug " prepare editor value #{widget.display_length} displlen #{widget.maxlen}"
|
100
|
+
$log.debug " prepare editor form: #{widget.form} "
|
101
101
|
#widget.display_length = widget.display_length -1
|
102
102
|
widget.bgcolor = 'yellow'
|
103
103
|
widget.color = 'black'
|
data/lib/rbcurse/colormap.rb
CHANGED
@@ -91,15 +91,15 @@ include ColorMap
|
|
91
91
|
|
92
92
|
while((ch = @window.getchar()) != KEY_F1 )
|
93
93
|
next if ch == -1
|
94
|
-
break if ch == ?q
|
94
|
+
break if ch == ?q.getbyte(0)
|
95
95
|
case ch
|
96
|
-
when ?r
|
96
|
+
when ?r.getbyte(0)
|
97
97
|
attr |= Ncurses::A_REVERSE
|
98
|
-
when ?b
|
98
|
+
when ?b.getbyte(0)
|
99
99
|
attr |= Ncurses::A_BOLD
|
100
|
-
when ?n
|
100
|
+
when ?n.getbyte(0)
|
101
101
|
attr = Ncurses::A_NORMAL
|
102
|
-
when ?u
|
102
|
+
when ?u.getbyte(0)
|
103
103
|
attr |= Ncurses::A_UNDERLINE
|
104
104
|
else
|
105
105
|
i = ch.chr.to_i
|
@@ -11,7 +11,7 @@ module RubyCurses
|
|
11
11
|
@selected_indices=[]
|
12
12
|
@anchor_selection_index = -1
|
13
13
|
@lead_selection_index = -1
|
14
|
-
@selection_mode =
|
14
|
+
@selection_mode = 'multiple'
|
15
15
|
$log.debug " created DefaultListSelectionModel XXX"
|
16
16
|
end
|
17
17
|
|
@@ -36,8 +36,8 @@ module RubyCurses
|
|
36
36
|
end
|
37
37
|
## TODO should go in sorted, and no dupes
|
38
38
|
def add_selection_interval ix0, ix1
|
39
|
-
$log.debug " def add_selection_interval #{ix0}, ix1"
|
40
|
-
if @selection_mode !=
|
39
|
+
$log.debug " def add_selection_interval #{ix0}, #{ix1}, mode: #{@selection_mode} "
|
40
|
+
if @selection_mode != 'multiple'
|
41
41
|
clear_selection
|
42
42
|
end
|
43
43
|
@anchor_selection_index = ix0
|
data/lib/rbcurse/io.rb
ADDED
@@ -0,0 +1,663 @@
|
|
1
|
+
#*******************************************************
|
2
|
+
# Some common io routines for getting data or putting
|
3
|
+
# at some point
|
4
|
+
# Arunachalesha
|
5
|
+
# 2010-03-06 12:10
|
6
|
+
# Some are outdated.
|
7
|
+
# Current are:
|
8
|
+
# * rbgetstr (and those it calls)
|
9
|
+
# * display_cmenu and create_mitem
|
10
|
+
#*******************************************************#
|
11
|
+
module Io
|
12
|
+
|
13
|
+
# from which line to print in footer_win
|
14
|
+
LINEONE = 1
|
15
|
+
FOOTER_COLOR_PAIR = 6
|
16
|
+
MAIN_WINDOW_COLOR_PAIR = 5
|
17
|
+
ERROR_COLOR_PAIR = 7
|
18
|
+
|
19
|
+
|
20
|
+
# complex version of get_string that allows for trappng of control character
|
21
|
+
# such as C-c and C-h and TAB for completion
|
22
|
+
# validints contains int codes not chars.
|
23
|
+
# TODO We should put a field there, make it visible and mv it to after the prompt
|
24
|
+
# and handle all editing events on it.
|
25
|
+
# @return status_code, string (0 if okay, 7 if help asked for, -1 for abort
|
26
|
+
#def rbgetstr(win, r, c, prompt, maxlen, default, labels, validints=[], helptext="")
|
27
|
+
def rbgetstr(win, r, c, prompt, maxlen, config={})
|
28
|
+
#win ||= @target_window
|
29
|
+
$log.debug " inside rbgetstr #{win} r:#{r} c:#{c} p:#{prompt} m:#{maxlen} "
|
30
|
+
raise "rbgetstr got no window. io.rb" if win.nil?
|
31
|
+
ins_mode = false
|
32
|
+
default = config[:default] || ""
|
33
|
+
prompt = "#{prompt} [#{default}]: " unless default
|
34
|
+
len = prompt.length
|
35
|
+
|
36
|
+
# clear the area of len+maxlen
|
37
|
+
color = $datacolor
|
38
|
+
str = default
|
39
|
+
clear_this win, r, c, color, len+maxlen+1
|
40
|
+
print_this(win, prompt+str, color, r, c)
|
41
|
+
len = prompt.length + str.length
|
42
|
+
#x mylabels=["^G~Help ", "^C~Cancel"]
|
43
|
+
#x mylabels += labels if !labels.nil?
|
44
|
+
begin
|
45
|
+
Ncurses.echo();
|
46
|
+
#x print_key_labels( 0, 0, mylabels)
|
47
|
+
#curpos = 0
|
48
|
+
curpos = str.length
|
49
|
+
prevchar = 0
|
50
|
+
entries = nil
|
51
|
+
#win.mvwgetnstr(LINEONE-3,askstr.length,yn,maxlen)
|
52
|
+
while true
|
53
|
+
#ch=win.mvwgetch(r, len) # get to right of prompt - WHY NOT WORKING ???
|
54
|
+
ch=win.getchar()
|
55
|
+
$log.debug " rbgetstr got ch:#{ch}, str:#{str}. "
|
56
|
+
case ch
|
57
|
+
when 3 # -1 # C-c
|
58
|
+
return -1, nil
|
59
|
+
when 10, 13
|
60
|
+
break
|
61
|
+
when ?\C-h.getbyte(0), ?\C-?.getbyte(0), 127 # delete previous character/backspace
|
62
|
+
len -= 1 if len > prompt.length
|
63
|
+
curpos -= 1 if curpos > 0
|
64
|
+
str.slice!(curpos)
|
65
|
+
clear_this win, r, c, color, len+maxlen+1
|
66
|
+
#print_this(win, prompt+str, color, r, c)
|
67
|
+
when 330 # delete character on cursor
|
68
|
+
#len -= 1 if len > prompt.length
|
69
|
+
#curpos -= 1 if curpos > 0
|
70
|
+
str.slice!(curpos) #rescue next
|
71
|
+
clear_this win, r, c, color, len+maxlen+1
|
72
|
+
when ?\C-g.getbyte(0)
|
73
|
+
#x print_footer_help(helptext)
|
74
|
+
helptext = config[:helptext] || "No help provided"
|
75
|
+
print_help(win, r, c, color, helptext)
|
76
|
+
return 7, nil
|
77
|
+
when KEY_LEFT
|
78
|
+
curpos -= 1 if curpos > 0
|
79
|
+
len -= 1 if len > prompt.length
|
80
|
+
win.wmove r, c+len # since getchar is not going back on del and bs
|
81
|
+
next
|
82
|
+
when KEY_RIGHT
|
83
|
+
if curpos < str.length
|
84
|
+
curpos += 1 #if curpos < str.length
|
85
|
+
len += 1
|
86
|
+
win.wmove r, c+len # since getchar is not going back on del and bs
|
87
|
+
end
|
88
|
+
next
|
89
|
+
when ?\M-i.getbyte(0)
|
90
|
+
ins_mode = !ins_mode
|
91
|
+
next
|
92
|
+
when 9 # TAB
|
93
|
+
if config
|
94
|
+
if prevchar == 9
|
95
|
+
if !entries.nil? and !entries.empty?
|
96
|
+
str = entries.delete_at(0)
|
97
|
+
end
|
98
|
+
else
|
99
|
+
tabc = config[:tab_completion] unless tabc
|
100
|
+
next unless tabc
|
101
|
+
entries = tabc.call(str)
|
102
|
+
$log.debug " tab got #{entries} "
|
103
|
+
str = entries.delete_at(0) unless entries.nil? or entries.empty?
|
104
|
+
end
|
105
|
+
end
|
106
|
+
else
|
107
|
+
#if validints.include?ch
|
108
|
+
#print_status("Found in validints")
|
109
|
+
#return ch, nil
|
110
|
+
#else
|
111
|
+
if ch < 0 || ch > 255
|
112
|
+
Ncurses.beep
|
113
|
+
next
|
114
|
+
end
|
115
|
+
# if control char, beep
|
116
|
+
if ch.chr =~ /[[:cntrl:]]/
|
117
|
+
Ncurses.beep
|
118
|
+
next
|
119
|
+
end
|
120
|
+
# we need to trap KEY_LEFT and RIGHT and what of UP for history ?
|
121
|
+
#end
|
122
|
+
#str << ch.chr
|
123
|
+
if ins_mode
|
124
|
+
str[curpos] = ch.chr
|
125
|
+
else
|
126
|
+
str.insert(curpos, ch.chr)
|
127
|
+
end
|
128
|
+
len += 1
|
129
|
+
curpos += 1
|
130
|
+
break if str.length > maxlen
|
131
|
+
end
|
132
|
+
print_this(win, prompt+str, color, r, c)
|
133
|
+
win.wmove r, c+len # more for arrow keys, curpos may not be end
|
134
|
+
prevchar = ch
|
135
|
+
end
|
136
|
+
str = default if str == ""
|
137
|
+
ensure
|
138
|
+
Ncurses.noecho();
|
139
|
+
#x restore_application_key_labels # must be done after using print_key_labels
|
140
|
+
end
|
141
|
+
return 0, str
|
142
|
+
end
|
143
|
+
def clear_this win, r, c, color, len
|
144
|
+
print_this(win, "%-*s" % [len," "], color, r, c)
|
145
|
+
end
|
146
|
+
def print_help(win, r, c, color, helptext)
|
147
|
+
print_this(win, "%-*s" % [helptext.length+2," "], color, r, c)
|
148
|
+
print_this(win, "%s" % helptext, color, r, c)
|
149
|
+
sleep(5)
|
150
|
+
end
|
151
|
+
# @table_width is a constant in caller based on which we decide where to show
|
152
|
+
# key_labels and error messages.
|
153
|
+
# WHEN WE CREATE A PANEL BWLOW we can do away wit that. FIXME XXX
|
154
|
+
# return true for y, false for n
|
155
|
+
# e.g.
|
156
|
+
# <code>
|
157
|
+
# ret = @main.askyesno(nil, "Are you sure you wish to proceed?")
|
158
|
+
# </code>
|
159
|
+
# 2008-10-09 18:27 added call to print_footer_help
|
160
|
+
def askyesno(win, askstr, default = "N", helptext="Helptext for this question")
|
161
|
+
win ||= @footer_win
|
162
|
+
askstr = "#{askstr} [#{default}]: "
|
163
|
+
len = askstr.length
|
164
|
+
|
165
|
+
clear_error # 2008-10-13 20:26
|
166
|
+
print_this(win, askstr, 4, LINEONE, 0)
|
167
|
+
labels=["?~Help "," ~ ", "N~No ", "Y~Yes "]
|
168
|
+
print_key_labels( 0, 0, labels)
|
169
|
+
win.refresh
|
170
|
+
#Ncurses.echo();
|
171
|
+
yn=''
|
172
|
+
#win.mvwgetnstr(Ncurses.LINES-3,askstr.length,yn,maxlen)
|
173
|
+
while true
|
174
|
+
ch=win.mvwgetch(LINEONE,askstr.length)
|
175
|
+
if ch < 0 || ch > 255
|
176
|
+
next
|
177
|
+
end
|
178
|
+
yn = ch.chr
|
179
|
+
yn = default if yn == '' or ch == 10 # KEY_ENTER
|
180
|
+
yn.downcase!
|
181
|
+
break if yn =~/[yn]/
|
182
|
+
if yn == '?'
|
183
|
+
print_footer_help(helptext)
|
184
|
+
print_key_labels( 0, 0, labels)
|
185
|
+
next
|
186
|
+
end
|
187
|
+
Ncurses.beep
|
188
|
+
end
|
189
|
+
#Ncurses.noecho();
|
190
|
+
clear_error # 2008-11-06 19:27
|
191
|
+
restore_application_key_labels # must be done after using print_key_labels
|
192
|
+
win.refresh
|
193
|
+
return yn == 'y'
|
194
|
+
end
|
195
|
+
|
196
|
+
# return y or n or c
|
197
|
+
|
198
|
+
def askyesnocancel(win, askstr, default = "N")
|
199
|
+
win ||= @footer_win
|
200
|
+
askstr = "#{askstr} [#{default}]: "
|
201
|
+
len = askstr.length
|
202
|
+
|
203
|
+
clear_error # 2008-10-13 20:26
|
204
|
+
print_this(win, askstr, 4, LINEONE, 0)
|
205
|
+
labels=["N~No ", "Y~Yes ","C~Cancel"," ~ "]
|
206
|
+
print_key_labels( 0, 0, labels)
|
207
|
+
win.refresh
|
208
|
+
yn=''
|
209
|
+
#win.mvwgetnstr(LINEONE,askstr.length,yn,maxlen)
|
210
|
+
while true
|
211
|
+
ch=win.mvwgetch(LINEONE,askstr.length)
|
212
|
+
yn = ch.chr
|
213
|
+
yn = default if yn == '' or ch == 10 # KEY_ENTER
|
214
|
+
yn.downcase!
|
215
|
+
break if yn =~/[ync]/
|
216
|
+
Ncurses.beep
|
217
|
+
end
|
218
|
+
restore_application_key_labels # must be done after using print_key_labels
|
219
|
+
return yn
|
220
|
+
end
|
221
|
+
|
222
|
+
# return single digit from given choices
|
223
|
+
# e.g.
|
224
|
+
# <code>
|
225
|
+
# labels=["N~No ", "Y~Yes ","C~Cancel"," ~ ","S~SurpiseMe","G~GoAway! "]
|
226
|
+
# ret = @main.askchoice(nil, "Are you sure you wish to proceed?","N",labels,"NYCSG")
|
227
|
+
# @main.clear_error
|
228
|
+
# </code>
|
229
|
+
|
230
|
+
def askchoice(win, askstr, default, labels, validchars, config={})
|
231
|
+
win ||= @footer_win
|
232
|
+
askstr = "#{askstr} [#{default}]: "
|
233
|
+
len = askstr.length
|
234
|
+
helptext = config.fetch("helptext", "No helptext provided for this action")
|
235
|
+
|
236
|
+
clear_error # 2008-10-13 20:26
|
237
|
+
print_this(win, askstr, 4, LINEONE, 0)
|
238
|
+
#labels=["N~No ", "Y~Yes ","C~Cancel"," ~ "]
|
239
|
+
print_key_labels( 0, 0, labels)
|
240
|
+
yn=''
|
241
|
+
validchars.downcase!
|
242
|
+
#win.mvwgetnstr(LINEONE-3,askstr.length,yn,maxlen)
|
243
|
+
while true
|
244
|
+
ch=win.mvwgetch(LINEONE,askstr.length)
|
245
|
+
yn = ch.chr
|
246
|
+
# 2008-10-31 18:08
|
247
|
+
if ch == ?\C-g or yn == '?'
|
248
|
+
print_footer_help(helptext)
|
249
|
+
print_key_labels( 0, 0, labels)
|
250
|
+
next
|
251
|
+
end
|
252
|
+
yn = default if yn == '' or ch == 10 # KEY_ENTER
|
253
|
+
yn.downcase!
|
254
|
+
break if validchars.include?yn
|
255
|
+
Ncurses.beep
|
256
|
+
end
|
257
|
+
restore_application_key_labels # must be done after using print_key_labels
|
258
|
+
return yn
|
259
|
+
end
|
260
|
+
def get_string(win, askstr, maxlen=20, default="", labels=nil )
|
261
|
+
win ||= @footer_win
|
262
|
+
askstr = "#{askstr} [#{default}]: "
|
263
|
+
len = askstr.length
|
264
|
+
|
265
|
+
clear_error # 2008-11-06 19:25
|
266
|
+
print_this(win, askstr, 4, LINEONE, 0)
|
267
|
+
#labels=["N~No ", "Y~Yes ","C~Cancel"," ~ "]
|
268
|
+
mylabels = ["^G~Help ", "^C~Cancel"]
|
269
|
+
mylabels = (mylabels + labels) if !labels.nil?
|
270
|
+
|
271
|
+
print_key_labels( 0, 0, mylabels)
|
272
|
+
Ncurses.echo();
|
273
|
+
yn=''
|
274
|
+
begin
|
275
|
+
Signal.trap("INT"){ return nil }
|
276
|
+
win.mvwgetnstr(LINEONE,askstr.length,yn,maxlen)
|
277
|
+
rescue
|
278
|
+
yn=''
|
279
|
+
ensure
|
280
|
+
Ncurses.noecho();
|
281
|
+
clear_error # 2008-11-02 11:51
|
282
|
+
restore_application_key_labels # must be done after using print_key_labels
|
283
|
+
end
|
284
|
+
yn = default if yn == "" # 2008-10-31 18:59
|
285
|
+
return yn
|
286
|
+
end
|
287
|
+
|
288
|
+
|
289
|
+
##
|
290
|
+
# prints given text to window, in color at x and y coordinates
|
291
|
+
# @param [Window] window to write to
|
292
|
+
# @param [String] text to print
|
293
|
+
# @param [int] color such as $datacolor or $promptcolor
|
294
|
+
# @param [int] x
|
295
|
+
# @param [int] y
|
296
|
+
# @see Window#printstring
|
297
|
+
# Consider using Window#printstring
|
298
|
+
def print_this(win, text, color, x, y)
|
299
|
+
if(win == nil)
|
300
|
+
raise "win nil in printthis"
|
301
|
+
end
|
302
|
+
#$log.debug " printthis #{win} , #{text} , #{x} , #{y} "
|
303
|
+
color=Ncurses.COLOR_PAIR(color);
|
304
|
+
win.attron(color);
|
305
|
+
#win.mvprintw(x, y, "%-40s" % text);
|
306
|
+
win.mvprintw(x, y, "%s" % text);
|
307
|
+
win.attroff(color);
|
308
|
+
win.refresh
|
309
|
+
end
|
310
|
+
# prints error in footer_win only
|
311
|
+
def print_error(text)
|
312
|
+
clear_error
|
313
|
+
print_in_middle(@footer_win, LINEONE, 10, 80, text, Ncurses.COLOR_PAIR(ERROR_COLOR_PAIR))
|
314
|
+
end
|
315
|
+
# prints status in footer_win only
|
316
|
+
def print_status(text)
|
317
|
+
text = text[text.length-80..-1] if text.length > 80
|
318
|
+
print_error(text)
|
319
|
+
end
|
320
|
+
# clear previous error, call inside getch loop after each ch.
|
321
|
+
def clear_error
|
322
|
+
print_this(@footer_win, "%-*s" % [Ncurses.COLS," "], 5, LINEONE, 0)
|
323
|
+
end
|
324
|
+
# This is only for the menu program, in which we print current action/menu string in the
|
325
|
+
# key labels below.
|
326
|
+
# Its a dirty hack edpending on:
|
327
|
+
# * String CurRow present in key labels
|
328
|
+
# * field_init_proc called this method to set it.
|
329
|
+
def print_action(text)
|
330
|
+
print_this(@footer_win, " %-10s" % ("["+text+"]"), FOOTER_COLOR_PAIR, @action_posy, @action_posx)
|
331
|
+
end
|
332
|
+
|
333
|
+
# the old historical program which prints a string in middle of whereever
|
334
|
+
# thanks to this i was using stdscr which must never be used
|
335
|
+
|
336
|
+
def print_in_middle(win, starty, startx, width, string, color)
|
337
|
+
if(win == nil)
|
338
|
+
raise "window is nil"
|
339
|
+
end
|
340
|
+
x = Array.new
|
341
|
+
y = Array.new
|
342
|
+
Ncurses.getyx(win, y, x);
|
343
|
+
if(startx != 0)
|
344
|
+
x[0] = startx;
|
345
|
+
end
|
346
|
+
if(starty != 0)
|
347
|
+
y[0] = starty;
|
348
|
+
end
|
349
|
+
if(width == 0)
|
350
|
+
width = 80;
|
351
|
+
end
|
352
|
+
length = string.length;
|
353
|
+
temp = (width - length)/ 2;
|
354
|
+
x[0] = startx + temp.floor;
|
355
|
+
win.attron(color);
|
356
|
+
win.mvprintw(y[0], x[0], "%s", string);
|
357
|
+
win.attroff(color);
|
358
|
+
win.refresh();
|
359
|
+
end
|
360
|
+
# splits that bad hack array into even and odd arrays
|
361
|
+
# and prints on last 2 lines
|
362
|
+
|
363
|
+
def print_key_labels(posy, posx, arr)
|
364
|
+
## paint so-called key bindings from key_labels
|
365
|
+
posx = 0
|
366
|
+
even = []
|
367
|
+
odd = []
|
368
|
+
arr.each_index { |i|
|
369
|
+
if i % 2 == 0
|
370
|
+
even << arr[i]
|
371
|
+
else
|
372
|
+
odd << arr[i]
|
373
|
+
end
|
374
|
+
}
|
375
|
+
posy = LINEONE+1
|
376
|
+
print_key_labels_row(posy, posx, even)
|
377
|
+
posy = LINEONE+2
|
378
|
+
print_key_labels_row(posy, posx, odd)
|
379
|
+
# 2008-09-29 21:58
|
380
|
+
@footer_win.wrefresh # needed else secod row not shown after askchoice XXX
|
381
|
+
end
|
382
|
+
|
383
|
+
def print_key_labels_row(posy, posx, arr)
|
384
|
+
#clear first
|
385
|
+
my_form_win = @footer_win
|
386
|
+
# first clear the line
|
387
|
+
print_this(my_form_win, "%-*s" % [Ncurses.COLS," "], FOOTER_COLOR_PAIR, posy, 0)
|
388
|
+
padding = 8
|
389
|
+
padding = 4 if arr.length > 5
|
390
|
+
padding = 0 if arr.length > 7
|
391
|
+
arr.each_index { |i|
|
392
|
+
kl = arr[i].split('~')
|
393
|
+
if kl[0].strip !="" # don't print that white blank space for fillers
|
394
|
+
color_pair=2
|
395
|
+
my_form_win.attron(Ncurses.COLOR_PAIR(color_pair))
|
396
|
+
my_form_win.mvprintw(posy, posx, "%s" % kl[0] );
|
397
|
+
my_form_win.attroff(Ncurses.COLOR_PAIR(color_pair))
|
398
|
+
end
|
399
|
+
color_pair=FOOTER_COLOR_PAIR
|
400
|
+
posx = posx + kl[0].length
|
401
|
+
my_form_win.attron(Ncurses.COLOR_PAIR(color_pair))
|
402
|
+
lab = sprintf(" %s %*s" , kl[1], padding, " ");
|
403
|
+
# hack
|
404
|
+
if kl[1].strip == "CurRow"
|
405
|
+
@action_posx = posx
|
406
|
+
@action_posy = posy
|
407
|
+
end
|
408
|
+
my_form_win.mvprintw(posy, posx, lab)
|
409
|
+
my_form_win.attroff(Ncurses.COLOR_PAIR(color_pair))
|
410
|
+
posx = posx + lab.length
|
411
|
+
}
|
412
|
+
end
|
413
|
+
|
414
|
+
# since it must always be @header_win, we should remove the first param
|
415
|
+
# why should user have any direct access to those 2 windows.
|
416
|
+
def old_print_header(win, htext, posy = 0, posx = 0)
|
417
|
+
win.attron(Ncurses.COLOR_PAIR(6))
|
418
|
+
win.mvprintw(posy, posx, "%-*s" % [Ncurses.COLS, htext] );
|
419
|
+
win.attroff(Ncurses.COLOR_PAIR(6))
|
420
|
+
end
|
421
|
+
def print_header(htext, posy = 0, posx = 0)
|
422
|
+
win = @header_win
|
423
|
+
win.attron(Ncurses.COLOR_PAIR(6))
|
424
|
+
win.mvprintw(posy, posx, "%-*s" % [Ncurses.COLS, htext] );
|
425
|
+
win.attroff(Ncurses.COLOR_PAIR(6))
|
426
|
+
end
|
427
|
+
|
428
|
+
# since it must always be @header_win, we should remove the first param
|
429
|
+
# why should user have any direct access to those 2 windows.
|
430
|
+
def old_print_top_right(win, htext)
|
431
|
+
hlen = htext.length
|
432
|
+
win.attron(Ncurses.COLOR_PAIR(6))
|
433
|
+
win.mvprintw(0, Ncurses.COLS-hlen, htext );
|
434
|
+
win.attroff(Ncurses.COLOR_PAIR(6))
|
435
|
+
#win.refresh
|
436
|
+
end
|
437
|
+
def print_top_right(htext)
|
438
|
+
hlen = htext.length
|
439
|
+
win = @header_win
|
440
|
+
win.attron(Ncurses.COLOR_PAIR(6))
|
441
|
+
win.mvprintw(0, Ncurses.COLS-hlen, htext );
|
442
|
+
win.attroff(Ncurses.COLOR_PAIR(6))
|
443
|
+
#win.refresh
|
444
|
+
end
|
445
|
+
# prints labels defined by user in the DSL.
|
446
|
+
#
|
447
|
+
# Array of labels with:
|
448
|
+
#
|
449
|
+
# * position = [y,x] i.e, row, column
|
450
|
+
# * text = "label text"
|
451
|
+
# * color_pair = 6 (optional, default 6)
|
452
|
+
|
453
|
+
def print_screen_labels(my_form_win, labelarr)
|
454
|
+
table_width = @table_width || Ncurses.LINES-1
|
455
|
+
return if labelarr.nil?
|
456
|
+
labelarr.each{ |lhash|
|
457
|
+
posy, posx = lhash["position"]
|
458
|
+
posy = table_width + posy if posy < 0
|
459
|
+
posx = Ncurses.COLS + posy if posx < 0
|
460
|
+
|
461
|
+
text = lhash["text"]
|
462
|
+
color_pair = lhash["color_pair"] || 6
|
463
|
+
my_form_win.attron(Ncurses.COLOR_PAIR(color_pair))
|
464
|
+
my_form_win.mvprintw(posy, posx, "%-s" % text );
|
465
|
+
my_form_win.attroff(Ncurses.COLOR_PAIR(color_pair))
|
466
|
+
}
|
467
|
+
end
|
468
|
+
|
469
|
+
@deprecated
|
470
|
+
def print_headers(form_hash)
|
471
|
+
header = form_hash["header"]
|
472
|
+
header_top_left = form_hash["header_top_left"] || ""
|
473
|
+
header_top_center = form_hash["header_top_center"] || ""
|
474
|
+
header_top_right = form_hash["header_top_right"] || ""
|
475
|
+
posy = 0
|
476
|
+
posx = 0
|
477
|
+
htext = " <APP NAME> <VERSION> MAIN MENU"
|
478
|
+
|
479
|
+
posy, posx, htext = header if !header.nil?
|
480
|
+
print_header(htext + " %15s " % header_top_left + " %20s" % header_top_center , posy, posx)
|
481
|
+
print_top_right(header_top_right)
|
482
|
+
@header_win.wrefresh();
|
483
|
+
end
|
484
|
+
|
485
|
+
|
486
|
+
# 2008-10-09 18:27 askyesno and ask_string can be passed some text
|
487
|
+
# to be popped up when a user enters ?
|
488
|
+
@deprecated
|
489
|
+
def print_footer_help(helptext)
|
490
|
+
print_this(@footer_win, "%-*s" % [Ncurses.COLS," "], 6, LINEONE+1, 0)
|
491
|
+
print_this(@footer_win, "%-*s" % [Ncurses.COLS," "], 6, LINEONE+2, 0)
|
492
|
+
print_this(@footer_win, "%s" % helptext, 6, LINEONE+1, 0)
|
493
|
+
sleep(5)
|
494
|
+
end
|
495
|
+
def print_help_page(filename = "TODO")
|
496
|
+
#require 'transactionviewer'
|
497
|
+
#tp = TransactionViewer.new(nil)
|
498
|
+
#tp.run
|
499
|
+
require 'panelreader'
|
500
|
+
tp = PanelReader.new()
|
501
|
+
tp.view_file(filename)
|
502
|
+
|
503
|
+
#require 'padreader'
|
504
|
+
#tp = PadReader.new()
|
505
|
+
#tp.view_file(filename)
|
506
|
+
end
|
507
|
+
#def newaskyesno(win, askstr, default = "N", helptext="Helptext for this question")
|
508
|
+
##
|
509
|
+
# user may pass in actions for each key along with other config values in config hash.
|
510
|
+
# config can contain default, helptext, labels and 'y', 'n'
|
511
|
+
@deprecated
|
512
|
+
def newaskyesno(win, askstr, config = {})
|
513
|
+
win ||= @footer_win
|
514
|
+
default = config.fetch("default", "N")
|
515
|
+
helptext = config.fetch("helptext", "This is helptext for this action")
|
516
|
+
askstr = "#{askstr} [#{default}]: "
|
517
|
+
len = askstr.length
|
518
|
+
|
519
|
+
clear_error # 2008-10-13 20:26
|
520
|
+
print_this(win, askstr, 4, LINEONE, 0)
|
521
|
+
labels=config.fetch("labels", ["?~Help "," ~ ", "N~No ", "Y~Yes "])
|
522
|
+
print_key_labels( 0, 0, labels)
|
523
|
+
win.refresh
|
524
|
+
yn=''
|
525
|
+
#win.mvwgetnstr(Ncurses.LINES-3,askstr.length,yn,maxlen)
|
526
|
+
while true
|
527
|
+
ch=win.mvwgetch(LINEONE,askstr.length)
|
528
|
+
if ch < 0 || ch > 255
|
529
|
+
next
|
530
|
+
end
|
531
|
+
yn = ch.chr
|
532
|
+
yn = default if yn == '' or ch == 10 # KEY_ENTER
|
533
|
+
yn.downcase!
|
534
|
+
break if yn =~/[yn]/
|
535
|
+
if yn == '?'
|
536
|
+
print_footer_help(helptext)
|
537
|
+
print_key_labels( 0, 0, labels)
|
538
|
+
next
|
539
|
+
end
|
540
|
+
Ncurses.beep
|
541
|
+
end # while
|
542
|
+
|
543
|
+
begin
|
544
|
+
config[yn].call if config.include? yn
|
545
|
+
ensure
|
546
|
+
restore_application_key_labels # must be done after using print_key_labels
|
547
|
+
win.refresh
|
548
|
+
end
|
549
|
+
|
550
|
+
return yn == 'y'
|
551
|
+
end
|
552
|
+
|
553
|
+
#def add_item hotkey, label, desc,action
|
554
|
+
#
|
555
|
+
## A *simple* way of creating menus that will appear in a single row.
|
556
|
+
# This copies the menu at the bottom of "most" upon pressing ":".
|
557
|
+
# hotkey is the key to invoke an item (a single digit letter)
|
558
|
+
#
|
559
|
+
# label is an action name
|
560
|
+
#
|
561
|
+
# desc is a description displayed after an item is chosen. Usually, its like:
|
562
|
+
#+ "Folding has been enabled" or "Searches will now be case sensitive"
|
563
|
+
#
|
564
|
+
# action may be a Proc or a symbol which will be called if item selected
|
565
|
+
#+ action may be another menu, so recursive menus can be built, but each
|
566
|
+
#+ should fit in a line, its a simple system.
|
567
|
+
|
568
|
+
CMenuItem = Struct.new( :hotkey, :label, :desc, :action )
|
569
|
+
|
570
|
+
|
571
|
+
## An encapsulated form of yesterday's Most Menu
|
572
|
+
# It keeps the internals away from the user.
|
573
|
+
# Its not really OOP in the sense that the PromptMenu is not a MenuItem. That's how it is in
|
574
|
+
# our Menu system, and that led to a lot of painful coding (at least for me). This is quite
|
575
|
+
# simple. A submenu contains a PromptMenu in its action object and is evaluated in a switch.
|
576
|
+
# A recursive loop handles submenus.
|
577
|
+
#
|
578
|
+
# Prompting of menu options with suboptions etc.
|
579
|
+
# A block of code or symbol or proc is executed for any leaf node
|
580
|
+
# This allows us to define different menus for different objects on the screen, and not have to map
|
581
|
+
# all kinds of control keys for operations, and have the user remember them. Only one key invokes the menu
|
582
|
+
# and the rest are ordinary characters.
|
583
|
+
class PromptMenu
|
584
|
+
include Io
|
585
|
+
attr_reader :text
|
586
|
+
attr_reader :options
|
587
|
+
def initialize caller, text="Choose:"
|
588
|
+
@caller = caller
|
589
|
+
@text = text
|
590
|
+
@options = []
|
591
|
+
end
|
592
|
+
def add menuitem
|
593
|
+
@options << menuitem
|
594
|
+
end
|
595
|
+
def create_mitem *args
|
596
|
+
item = CMenuItem.new(*args.flatten)
|
597
|
+
end
|
598
|
+
# Display the top level menu and accept user input
|
599
|
+
# Calls actions or symbols upon selection, or traverses submenus
|
600
|
+
# @return retvalue of last call or send, or 0
|
601
|
+
# @param win window
|
602
|
+
# @param r, c row and col to display on
|
603
|
+
# @param color text color (use $datacolor if in doubt)
|
604
|
+
# @param menu array of CMenuItem structs
|
605
|
+
def display win, r, c, color
|
606
|
+
menu = @options
|
607
|
+
$log.debug " DISP MENU "
|
608
|
+
ret = 0
|
609
|
+
while true
|
610
|
+
str = @text.dup
|
611
|
+
h = {}
|
612
|
+
valid = []
|
613
|
+
menu.each{ |item|
|
614
|
+
str << "(%c) %s " % [ item.hotkey, item.label ]
|
615
|
+
h[item.hotkey] = item
|
616
|
+
valid << item.hotkey
|
617
|
+
}
|
618
|
+
#$log.debug " valid are #{valid} "
|
619
|
+
color = $datacolor
|
620
|
+
print_this(win, str, color, r, c)
|
621
|
+
ch=win.getchar()
|
622
|
+
#$log.debug " got ch #{ch} "
|
623
|
+
next if ch < 0 or ch > 255
|
624
|
+
ch = ch.chr
|
625
|
+
index = valid.index ch
|
626
|
+
if index.nil?
|
627
|
+
clear_this win, r, c, color, str.length
|
628
|
+
print_this(win, "Not valid. Valid are #{valid}", color, r,c)
|
629
|
+
sleep 1
|
630
|
+
next
|
631
|
+
end
|
632
|
+
#$log.debug " index is #{index} "
|
633
|
+
item = h[ch]
|
634
|
+
desc = item.desc
|
635
|
+
#desc ||= "Could not find desc for #{ch} "
|
636
|
+
desc ||= ""
|
637
|
+
clear_this win, r, c, color, str.length
|
638
|
+
print_this(win, desc, color, r,c)
|
639
|
+
action = item.action
|
640
|
+
case action
|
641
|
+
#when Array
|
642
|
+
when PromptMenu
|
643
|
+
# submenu
|
644
|
+
menu = action.options
|
645
|
+
str = "%s: " % action.text
|
646
|
+
when Proc
|
647
|
+
ret = action.call
|
648
|
+
break
|
649
|
+
when Symbol
|
650
|
+
ret = @caller.send(action)
|
651
|
+
break
|
652
|
+
else
|
653
|
+
$log.debug " Unidentified flying class #{action.class} "
|
654
|
+
break
|
655
|
+
end
|
656
|
+
end # while
|
657
|
+
return ret # ret val of last send or call
|
658
|
+
end
|
659
|
+
end # class PromptMenu
|
660
|
+
|
661
|
+
### ADD HERE ###
|
662
|
+
|
663
|
+
end # module
|