rbhex-core 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (108) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +20 -0
  3. data/CHANGELOG +2000 -0
  4. data/LICENSE +56 -0
  5. data/README.md +44 -0
  6. data/examples/abasiclist.rb +179 -0
  7. data/examples/alpmenu.rb +50 -0
  8. data/examples/app.sample +19 -0
  9. data/examples/atree.rb +100 -0
  10. data/examples/bline.rb +136 -0
  11. data/examples/common/file.rb +45 -0
  12. data/examples/data/README.markdown +9 -0
  13. data/examples/data/brew.txt +38 -0
  14. data/examples/data/color.2 +37 -0
  15. data/examples/data/gemlist.txt +60 -0
  16. data/examples/data/lotr.txt +12 -0
  17. data/examples/data/ports.txt +136 -0
  18. data/examples/data/table.txt +37 -0
  19. data/examples/data/tasks.csv +88 -0
  20. data/examples/data/tasks.txt +27 -0
  21. data/examples/data/todo.txt +10 -0
  22. data/examples/data/todo.txt.bak +10 -0
  23. data/examples/data/todocsv.csv +28 -0
  24. data/examples/data/unix1.txt +21 -0
  25. data/examples/data/unix2.txt +11 -0
  26. data/examples/dbdemo.rb +502 -0
  27. data/examples/dirtree.rb +94 -0
  28. data/examples/newtabbedwindow.rb +100 -0
  29. data/examples/newtesttabp.rb +92 -0
  30. data/examples/tabular.rb +146 -0
  31. data/examples/tasks.rb +178 -0
  32. data/examples/term2.rb +84 -0
  33. data/examples/testbuttons.rb +296 -0
  34. data/examples/testcombo.rb +102 -0
  35. data/examples/testfields.rb +195 -0
  36. data/examples/testkeypress.rb +72 -0
  37. data/examples/testlistbox.rb +170 -0
  38. data/examples/testmessagebox.rb +140 -0
  39. data/examples/testprogress.rb +116 -0
  40. data/examples/testree.rb +106 -0
  41. data/examples/testwsshortcuts.rb +66 -0
  42. data/examples/testwsshortcuts2.rb +128 -0
  43. data/lib/rbhex.rb +6 -0
  44. data/lib/rbhex/core/docs/index.txt +73 -0
  45. data/lib/rbhex/core/include/action.rb +80 -0
  46. data/lib/rbhex/core/include/actionmanager.rb +49 -0
  47. data/lib/rbhex/core/include/appmethods.rb +214 -0
  48. data/lib/rbhex/core/include/bordertitle.rb +48 -0
  49. data/lib/rbhex/core/include/chunk.rb +203 -0
  50. data/lib/rbhex/core/include/io.rb +553 -0
  51. data/lib/rbhex/core/include/listbindings.rb +74 -0
  52. data/lib/rbhex/core/include/listcellrenderer.rb +140 -0
  53. data/lib/rbhex/core/include/listeditable.rb +317 -0
  54. data/lib/rbhex/core/include/listscrollable.rb +663 -0
  55. data/lib/rbhex/core/include/listselectable.rb +271 -0
  56. data/lib/rbhex/core/include/multibuffer.rb +83 -0
  57. data/lib/rbhex/core/include/orderedhash.rb +77 -0
  58. data/lib/rbhex/core/include/ractionevent.rb +73 -0
  59. data/lib/rbhex/core/include/rchangeevent.rb +27 -0
  60. data/lib/rbhex/core/include/rhistory.rb +95 -0
  61. data/lib/rbhex/core/include/rinputdataevent.rb +47 -0
  62. data/lib/rbhex/core/include/vieditable.rb +172 -0
  63. data/lib/rbhex/core/include/widgetmenu.rb +66 -0
  64. data/lib/rbhex/core/system/colormap.rb +165 -0
  65. data/lib/rbhex/core/system/keyboard.rb +150 -0
  66. data/lib/rbhex/core/system/keydefs.rb +30 -0
  67. data/lib/rbhex/core/system/ncurses.rb +236 -0
  68. data/lib/rbhex/core/system/panel.rb +162 -0
  69. data/lib/rbhex/core/system/window.rb +913 -0
  70. data/lib/rbhex/core/util/ansiparser.rb +119 -0
  71. data/lib/rbhex/core/util/app.rb +1228 -0
  72. data/lib/rbhex/core/util/basestack.rb +410 -0
  73. data/lib/rbhex/core/util/bottomline.rb +1859 -0
  74. data/lib/rbhex/core/util/colorparser.rb +77 -0
  75. data/lib/rbhex/core/util/focusmanager.rb +31 -0
  76. data/lib/rbhex/core/util/padreader.rb +192 -0
  77. data/lib/rbhex/core/util/rcommandwindow.rb +604 -0
  78. data/lib/rbhex/core/util/rdialogs.rb +574 -0
  79. data/lib/rbhex/core/util/viewer.rb +149 -0
  80. data/lib/rbhex/core/util/widgetshortcuts.rb +506 -0
  81. data/lib/rbhex/core/version.rb +5 -0
  82. data/lib/rbhex/core/widgets/applicationheader.rb +103 -0
  83. data/lib/rbhex/core/widgets/box.rb +58 -0
  84. data/lib/rbhex/core/widgets/divider.rb +310 -0
  85. data/lib/rbhex/core/widgets/keylabelprinter.rb +194 -0
  86. data/lib/rbhex/core/widgets/rcombo.rb +253 -0
  87. data/lib/rbhex/core/widgets/rcontainer.rb +415 -0
  88. data/lib/rbhex/core/widgets/rlink.rb +30 -0
  89. data/lib/rbhex/core/widgets/rlist.rb +696 -0
  90. data/lib/rbhex/core/widgets/rmenu.rb +958 -0
  91. data/lib/rbhex/core/widgets/rmenulink.rb +22 -0
  92. data/lib/rbhex/core/widgets/rmessagebox.rb +387 -0
  93. data/lib/rbhex/core/widgets/rprogress.rb +118 -0
  94. data/lib/rbhex/core/widgets/rtabbedpane.rb +634 -0
  95. data/lib/rbhex/core/widgets/rtabbedwindow.rb +70 -0
  96. data/lib/rbhex/core/widgets/rtextarea.rb +960 -0
  97. data/lib/rbhex/core/widgets/rtextview.rb +739 -0
  98. data/lib/rbhex/core/widgets/rtree.rb +768 -0
  99. data/lib/rbhex/core/widgets/rwidget.rb +3277 -0
  100. data/lib/rbhex/core/widgets/scrollbar.rb +143 -0
  101. data/lib/rbhex/core/widgets/statusline.rb +113 -0
  102. data/lib/rbhex/core/widgets/tabular.rb +264 -0
  103. data/lib/rbhex/core/widgets/tabularwidget.rb +1142 -0
  104. data/lib/rbhex/core/widgets/textpad.rb +995 -0
  105. data/lib/rbhex/core/widgets/tree/treecellrenderer.rb +150 -0
  106. data/lib/rbhex/core/widgets/tree/treemodel.rb +428 -0
  107. data/rbhex-core.gemspec +32 -0
  108. metadata +172 -0
@@ -0,0 +1,634 @@
1
+ =begin
2
+ * Name: newtabbedpane.rb
3
+ * Description : This is radically simplified tabbedpane. The earlier version
4
+ was too complex with multiple forms and pads, and a scrollform. This uses
5
+ the external form and has some very simple programming to handle the whole thing.
6
+ * Author: rkumar (http://github.com/rkumar/rbcurse/)
7
+ * Date: 2011-10-20
8
+ * License: Same as Ruby's License (http://www.ruby-lang.org/LICENSE.txt)
9
+ * Last update: 2014-03-28 20:39
10
+
11
+ == CHANGES
12
+ As of 1.5.0, this replaces the earlier TabbedPane which
13
+ now lies in lib/rbhex/deprecated/widgets
14
+ in the rbhex repo.
15
+ == TODO
16
+ on start first buttons bottom should not be lined.
17
+ Alt-1-9 to goto tabs
18
+ add remove tabs at any time - started, untested
19
+ events for tab add/remove/etc
20
+ =end
21
+ require 'rbhex'
22
+ ##
23
+ module RubyCurses
24
+ class TabbedPane < Widget
25
+ dsl_property :title, :title_attrib
26
+ # what kind of buttons, if this is a window, :ok :ok_camcel :ok_apply_cancel
27
+ dsl_accessor :button_type
28
+ attr_reader :button_row
29
+ # index of tab that is currently open
30
+ attr_reader :current_tab
31
+
32
+
33
+ def initialize form=nil, config={}, &block
34
+ @_events ||= []
35
+ @_events.push(:PRESS)
36
+ @button_gap = 2
37
+ init_vars
38
+ super
39
+ @focusable = true
40
+ @editable = true
41
+ @col_offset = 2
42
+ raise ArgumentError, "NewTabbedPane : row or col not set: r: #{@row} c: #{@col} " unless @row && @col
43
+ end
44
+
45
+ # Add a tab
46
+ # @param String name of tab, may have ampersand for hotkey/accelerator
47
+ def tab title, config={}, &block
48
+ #@tab_components[title]=[]
49
+ #@tabs << Tab.new(title, self, config, &block)
50
+ insert_tab @tabs.count, title, config, &block
51
+ self
52
+ end
53
+ alias :add_tab :tab
54
+
55
+ # a shortcut for binding a command to a press of an action button
56
+ # The block will be passed
57
+ # This is only relevant if you have asked for buttons to be created, which is
58
+ # only relevant in a TabbedWindow
59
+ # ActionEvent has source event and action_command
60
+ def command *args, &block
61
+ bind :PRESS, *args, &block
62
+ end
63
+
64
+ # -------------- tab maintenance commands ------------------ #
65
+
66
+ # insert a tab at index, with title
67
+ def insert_tab index, title, config={}, &block
68
+ @tabs.insert(index, Tab.new(title, self, config, &block) )
69
+ end
70
+ # remove given tab
71
+ def remove_tab tab
72
+ @tabs.delete tab
73
+ self
74
+ end
75
+ # remove all tabs
76
+ def remove_all
77
+ @tabs = []
78
+ self
79
+ end
80
+ # remove tab at given index, defaulting to current
81
+ def remove_tab_at index = @current_tab
82
+ @tabs.delete_at index
83
+ end
84
+
85
+ def repaint
86
+ @current_tab ||= 0
87
+ @button_row ||= @row + 2
88
+ @separator_row = @button_row + 1 # hope we have it by now, where to print separator
89
+ @separator_row0 = @button_row - 1 unless @button_row == @row + 1
90
+ @separator_row2 = @row + @height - 3 # hope we have it by now, where to print separator
91
+ #return unless @repaint_required
92
+ if @buttons.empty?
93
+ _create_buttons
94
+ @components = @buttons.dup
95
+ @components.push(*@tabs[@current_tab].items)
96
+ create_action_buttons
97
+ @components.push(*@action_buttons)
98
+ elsif @tab_changed
99
+ @components = @buttons.dup
100
+ @components.push(*@tabs[@current_tab].items)
101
+ @components.push(*@action_buttons)
102
+ @tab_changed = false
103
+ end
104
+ # if some major change has happened then repaint everything
105
+ if @repaint_required
106
+ $log.debug " NEWTAB repaint graphic #{@graphic} "
107
+ print_borders unless @suppress_borders # do this once only, unless everything changes
108
+ print_separator1
109
+ @components.each { |e| e.repaint_all(true); e.repaint }
110
+ else
111
+ @components.each { |e| e.repaint }
112
+ end # if repaint_required
113
+ print_border if (@suppress_borders == false && @repaint_all) # do this once only, unless everything changes
114
+ @repaint_required = false
115
+ end
116
+ def handle_key ch
117
+ $log.debug " NEWTABBED handle_key #{ch} "
118
+ return if @components.empty?
119
+ _multiplier = ($multiplier == 0 ? 1 : $multiplier )
120
+
121
+ # should this go here 2011-10-19
122
+ unless @_entered
123
+ $log.warn "WARN: calling ON_ENTER since in this situation it was not called"
124
+ on_enter
125
+ end
126
+ #if ch == KEY_TAB
127
+ #$log.debug "NEWTABBED GOTO NEXT"
128
+ #return goto_next_component
129
+ #elsif ch == KEY_BTAB
130
+ #return goto_prev_component
131
+ #end
132
+ comp = @current_component
133
+ $log.debug " NEWTABBED handle_key #{ch}: #{comp}"
134
+ if comp
135
+ ret = comp.handle_key(ch)
136
+ $log.debug " NEWTABBED handle_key#{ch}: #{comp} returned #{ret} "
137
+ if ret != :UNHANDLED
138
+ comp.repaint # NOTE: if we don;t do this, then it won't get repainted. I will have to repaint ALL
139
+ # in repaint of this.
140
+ return ret
141
+ end
142
+ $log.debug "XXX NEWTABBED key unhandled by comp #{comp.name} "
143
+ else
144
+ Ncurses.beep
145
+ $log.warn "XXX NEWTABBED key unhandled NULL comp"
146
+ end
147
+ case ch
148
+ when ?\C-c.getbyte(0)
149
+ $multiplier = 0
150
+ return 0
151
+ when ?0.getbyte(0)..?9.getbyte(0)
152
+ $log.debug " VIM coming here to set multiplier #{$multiplier} "
153
+ $multiplier *= 10 ; $multiplier += (ch-48)
154
+ return 0
155
+ end
156
+ ret = process_key ch, self
157
+ # allow user to map left and right if he wants
158
+ if ret == :UNHANDLED
159
+ case ch
160
+ when KEY_UP, KEY_BTAB
161
+ # form will pick this up and do needful
162
+ return goto_prev_component #unless on_first_component?
163
+ when KEY_LEFT
164
+ # if i don't check for first component, key will go back to form,
165
+ # but not be processes. so focussed remain here, but be false.
166
+ # In case of returnign an unhandled TAB, on_leave will happen and cursor will move to
167
+ # previous component outside of this.
168
+ return goto_prev_component unless on_first_component?
169
+ when KEY_RIGHT, KEY_TAB
170
+ return goto_next_component #unless on_last_component?
171
+ when KEY_DOWN
172
+ if on_a_button?
173
+ return goto_first_item
174
+ else
175
+ return goto_next_component #unless on_last_component?
176
+ end
177
+ else
178
+ #@_entered = false
179
+ return :UNHANDLED
180
+ end
181
+ end
182
+
183
+ $multiplier = 0
184
+ return 0
185
+ end
186
+ # on enter processing
187
+ # Very often the first may be a label !
188
+ def on_enter
189
+ # if BTAB, the last comp
190
+ if $current_key == KEY_BTAB
191
+ @current_component = @components.last
192
+ else
193
+ @current_component = @components.first
194
+ end
195
+ return unless @current_component
196
+ $log.debug " NEWTABBED came to ON_ENTER #{@current_component} "
197
+ set_form_row
198
+ @_entered = true
199
+ end
200
+ def on_leave
201
+ @_entered = false
202
+ super
203
+ end
204
+ # takes focus to first item (after buttons)
205
+ def goto_first_item
206
+ bc = @buttons.count
207
+ @components[bc..-1].each { |c|
208
+ if c.focusable
209
+ leave_current_component
210
+ @current_component = c
211
+ set_form_row
212
+ break
213
+ end
214
+ }
215
+ end
216
+
217
+ # takes focus to last item
218
+ def goto_last_item
219
+ bc = @buttons.count
220
+ f = nil
221
+ @components[bc..-1].each { |c|
222
+ if c.focusable
223
+ f = c
224
+ end
225
+ }
226
+ if f
227
+ leave_current_component
228
+ @current_component = f
229
+ set_form_row
230
+ end
231
+ end
232
+ # take focus to the next component or item
233
+ # Called from DOWN, RIGHT or Tab
234
+ def goto_next_component
235
+ if @current_component != nil
236
+ leave_current_component
237
+ if on_last_component?
238
+ @_entered = false
239
+ return :UNHANDLED
240
+ end
241
+ @current_index = @components.index(@current_component)
242
+ index = @current_index + 1
243
+ index.upto(@components.length-1) do |i|
244
+ f = @components[i]
245
+ if f.focusable
246
+ @current_index = i
247
+ @current_component = f
248
+ return set_form_row
249
+ end
250
+ end
251
+ end
252
+ @_entered = false
253
+ return :UNHANDLED
254
+ end
255
+ # take focus to prev component or item
256
+ # Called from LEFT, UP or Back Tab
257
+ def goto_prev_component
258
+ if @current_component != nil
259
+ leave_current_component
260
+ if on_first_component?
261
+ @_entered = false
262
+ return :UNHANDLED
263
+ end
264
+ @current_index = @components.index(@current_component)
265
+ index = @current_index -= 1
266
+ index.downto(0) do |i|
267
+ f = @components[i]
268
+ if f.focusable
269
+ @current_index = i
270
+ @current_component = f
271
+ return set_form_row
272
+ end
273
+ end
274
+ end
275
+ return :UNHANDLED
276
+ end
277
+ # private
278
+ def set_form_row
279
+ return :UNHANDLED if @current_component.nil?
280
+ $log.debug " NEWTABBED on enter sfr #{@current_component} "
281
+ @current_component.on_enter
282
+ @current_component.set_form_row # why was this missing in vimsplit. is it
283
+ # that on_enter does a set_form_row
284
+ @current_component.set_form_col # XXX
285
+ @current_component.repaint
286
+ # XXX compo should do set_form_row and col if it has that
287
+ end
288
+ # private
289
+ def set_form_col
290
+ return if @current_component.nil?
291
+ $log.debug " #{@name} NEWTABBED set_form_col calling sfc for #{@current_component.name} "
292
+ @current_component.set_form_col
293
+ end
294
+ # leave the component we are on.
295
+ # This should be followed by all containers, so that the on_leave action
296
+ # of earlier comp can be displayed, such as dimming components selections
297
+ def leave_current_component
298
+ @current_component.on_leave
299
+ # NOTE this is required, since repaint will just not happen otherwise
300
+ # Some components are erroneously repainting all, after setting this to true so it is
301
+ # working there.
302
+ @current_component.repaint_required true
303
+ $log.debug " after on_leave VIMS XXX #{@current_component.focussed} #{@current_component.name}"
304
+ @current_component.repaint
305
+ end
306
+
307
+ # is focus on first component
308
+ def on_first_component?
309
+ @current_component == @components.first
310
+ end
311
+ # is focus on last component
312
+ def on_last_component?
313
+ @current_component == @components.last
314
+ end
315
+ # returns true if user on an action button
316
+ # @return true or false
317
+ def on_a_button?
318
+ @components.index(@current_component) < @buttons.count
319
+ end
320
+ # set focus on given component
321
+ # Sometimes you have the handle to component, and you want to move focus to it
322
+ def goto_component comp
323
+ return if comp == @current_component
324
+ leave_current_component
325
+ @current_component = comp
326
+ set_form_row
327
+ end
328
+ # set current tab to given tab
329
+ # @return self
330
+ def set_current_tab t
331
+ return if @current_tab == t
332
+ @current_tab = t
333
+ goto_component @components[t]
334
+ @tab_changed = true
335
+ @repaint_required = true
336
+ self
337
+ end
338
+
339
+ def DEPRECATED_handle_key ch # :nodoc
340
+ map_keys unless @keys_mapped
341
+ ret = process_key ch, self
342
+ @multiplier = 0
343
+ return :UNHANDLED if ret == :UNHANDLED
344
+ return 0
345
+ end
346
+
347
+ # Put all the housekeeping stuff at the end
348
+ private
349
+ def init_vars
350
+ @buttons = []
351
+ @tabs = []
352
+ #@tab_components = {}
353
+ @bottombuttons = []
354
+ #
355
+ # I'll keep current tabs comps in this to simplify
356
+ @components = []
357
+ @_entered = false
358
+ end
359
+
360
+ def map_keys
361
+ @keys_mapped = true
362
+ #bind_key(?q, :myproc)
363
+ #bind_key(32, :myproc)
364
+ end
365
+
366
+ # creates the tab buttons (which are radio buttons)
367
+ def _create_buttons
368
+ $log.debug "XXX: INSIDE create_buttons col_offset #{@col_offset} "
369
+ v = Variable.new
370
+ r = @button_row # @row + 1
371
+ col = @col + @col_offset
372
+ @tabs.each_with_index { |t, i|
373
+ txt = t.text
374
+ @buttons << TabButton.new(nil) do
375
+ variable v
376
+ text txt
377
+ name txt
378
+ #value txt
379
+ row r
380
+ col col
381
+ surround_chars ['','']
382
+ selected_background 'green'
383
+ selected_foreground 'white'
384
+
385
+ end
386
+ b = @buttons.last
387
+ b.command do
388
+ set_current_tab i
389
+ end
390
+ b.form = @form
391
+ b.override_graphic @graphic
392
+ col += txt.length + @button_gap
393
+ }
394
+ end # _create_buttons
395
+ private
396
+ def print_borders
397
+ width = @width
398
+ height = @height-1
399
+ window = @graphic
400
+ startcol = @col
401
+ startrow = @row
402
+ @color_pair = get_color($datacolor)
403
+ $log.debug "NTP #{name}: window.print_border #{startrow}, #{startcol} , h:#{height}, w:#{width} , @color_pair, @attr "
404
+ window.print_border startrow, startcol, height, width, @color_pair, @attr
405
+ print_title
406
+ end
407
+ def print_separator1
408
+
409
+ width = @width
410
+ height = @height-1
411
+ window = @graphic
412
+ startcol = @col
413
+ startrow = @row
414
+ @color_pair = get_color($datacolor)
415
+ r = @separator_row
416
+ c = @col + @col_offset
417
+
418
+ urcorner = []
419
+ #window.printstring r, c, '-' * (@width-2), @color_pair, @attr
420
+ window.mvwhline( r, @col+1, Ncurses::ACS_HLINE, @width-2)
421
+ @buttons.each_with_index do |b, i|
422
+ l = b.text.length
423
+ if b.selected?
424
+ if false #c == @col + @col_offset
425
+ cc = c
426
+ ll = l+1
427
+ else
428
+ cc = c-1
429
+ ll = l+2
430
+ end
431
+ #rr = r -1 #unless rr == @col
432
+ window.printstring r, cc, " "*ll, @color_pair, @attr
433
+ #window.printstring r, cc-1, FFI::NCurses::ACS_HLINE.chr*ll, @color_pair, @attr
434
+ #window.printstring r-2, cc, FFI::NCurses::ACS_HLINE.chr*ll, @color_pair, @attr
435
+ window.mvwaddch r, cc-1, FFI::NCurses::ACS_LRCORNER unless cc-1 <= @col
436
+ window.mvwaddch r, c+l+1, FFI::NCurses::ACS_LLCORNER
437
+ else
438
+ window.mvwaddch r, c+l+1, FFI::NCurses::ACS_BTEE
439
+ end
440
+
441
+ #window.printstring r-2, c, FFI::NCurses::ACS_HLINE*l, @color_pair, @attr
442
+ #tt = b.text
443
+ #window.printstring r, c, tt, @color_pair, @attr
444
+ c += l + 1
445
+ #window.mvwaddch r, c, '+'.ord
446
+ window.mvwaddch r-1, c, FFI::NCurses::ACS_VLINE
447
+ window.mvwaddch r-2, c, FFI::NCurses::ACS_URCORNER #ACS_TTEE
448
+ #window.mvwaddch r-2, c+1, '/'.ord
449
+ urcorner << c
450
+ c+=@button_gap
451
+ end
452
+ window.mvwhline( @separator_row0, @col + 1, Ncurses::ACS_HLINE, c-@col-1-@button_gap)
453
+ window.mvwhline( @separator_row2, @col + 1, Ncurses::ACS_HLINE, @width-2)
454
+ urcorner.each do |c|
455
+ window.mvwaddch r-2, c, FFI::NCurses::ACS_URCORNER #ACS_TTEE
456
+ end
457
+ end
458
+ def print_title
459
+ return unless @title
460
+ _title = @title
461
+ if @title.length > @width - 2
462
+ _title = @title[0..@width-2]
463
+ end
464
+ @graphic.printstring( @row, @col+(@width-_title.length)/2, _title,
465
+ @color_pair, @title_attrib) unless @title.nil?
466
+ end
467
+
468
+ #
469
+ # Decides which buttons are to be created
470
+ # create the buttons at the bottom OK/ APPLY/ CANCEL
471
+
472
+ def create_action_buttons
473
+ return unless @button_type
474
+ case @button_type.to_s.downcase
475
+ when "ok"
476
+ make_buttons ["&OK"]
477
+ when "ok_cancel" #, "input", "list", "field_list"
478
+ make_buttons %w[&OK &Cancel]
479
+ when "ok_apply_cancel" #, "input", "list", "field_list"
480
+ make_buttons %w[&OK &Apply &Cancel]
481
+ when "yes_no"
482
+ make_buttons %w[&Yes &No]
483
+ when "yes_no_cancel"
484
+ make_buttons ["&Yes", "&No", "&Cancel"]
485
+ when "custom"
486
+ raise "Blank list of buttons passed to custom" if @buttons.nil? or @buttons.size == 0
487
+ make_buttons @buttons
488
+ else
489
+ $log.warn "No buttontype passed for creating tabbedpane. Not creating any"
490
+ #make_buttons ["&OK"]
491
+ end
492
+ end
493
+
494
+ # actually creates the action buttons
495
+ def make_buttons names
496
+ @action_buttons = []
497
+ $log.debug "XXX: came to NTP make buttons FORM= #{@form.name} names #{names} "
498
+ total = names.inject(0) {|total, item| total + item.length + 4}
499
+ bcol = center_column total
500
+
501
+ # this craps out when height is zero
502
+ brow = @row + @height-2
503
+ brow = FFI::NCurses.LINES-2 if brow < 0
504
+ $log.debug "XXX: putting buttons :on #{brow} : #{@row} , #{@height} "
505
+ button_ct=0
506
+ tpp = self
507
+ names.each_with_index do |bname, ix|
508
+ text = bname
509
+ #underline = @underlines[ix] if !@underlines.nil?
510
+
511
+ button = Button.new nil do
512
+ text text
513
+ name bname
514
+ row brow
515
+ col bcol
516
+ #underline underline
517
+ highlight_background $reversecolor
518
+ color $datacolor
519
+ bgcolor $datacolor
520
+ end
521
+ @action_buttons << button
522
+ button.form = @form
523
+ button.override_graphic @graphic
524
+ index = button_ct
525
+ tpp = self
526
+ button.command { |form| @selected_index = index; @stop = true;
527
+ # ActionEvent has source event and action_command
528
+ fire_handler :PRESS, ActionEvent.new(tpp, index, button.text)
529
+ #throw(:close, @selected_index)
530
+ }
531
+ button_ct += 1
532
+ bcol += text.length+6
533
+ end
534
+ end
535
+ def center_column textlen
536
+ width = @col + @width
537
+ return (width-textlen)/2
538
+ end
539
+
540
+ ## ADD ABOVE
541
+ end # class
542
+
543
+ class Tab
544
+ attr_accessor :text
545
+ attr_reader :config
546
+ attr_reader :items
547
+ attr_accessor :parent_component
548
+ attr_accessor :index
549
+ attr_accessor :button # so you can set an event on it 2011-10-4
550
+ attr_accessor :row_offset
551
+ attr_accessor :col_offset
552
+ def initialize text, parent_component, aconfig={}, &block
553
+ @text = text
554
+ @items = []
555
+ @config = aconfig
556
+ @parent_component = parent_component
557
+ @row_offset ||= 2
558
+ @col_offset ||= 2
559
+ @config.each_pair { |k,v| variable_set(k,v) }
560
+ instance_eval &block if block_given?
561
+ end
562
+ def item widget
563
+ widget.form = @parent_component.form
564
+ widget.override_graphic @parent_component.form.window
565
+ # these will fail if TP put inside some other container. NOTE
566
+ widget.row ||= 0
567
+ widget.col ||= 0
568
+ # If we knew it was only widget we could expand it
569
+ if widget.kind_of?(RubyCurses::Container) #|| widget.respond_to?(:width)
570
+ widget.width ||= @parent_component.width-3
571
+ end
572
+ # Darn ! this was setting Label to fully height
573
+ if widget.kind_of?(RubyCurses::Container) #|| widget.respond_to?(:height)
574
+ widget.height ||= @parent_component.height-3
575
+ end
576
+ # i don't know button_offset as yet
577
+ widget.row += @row_offset + @parent_component.row + 1
578
+ widget.col += @col_offset + @parent_component.col
579
+ @items << widget
580
+ end
581
+ end # class tab
582
+ class TabButton < RadioButton
583
+ attr_accessor :display_tab_on_traversal
584
+ def getvalue_for_paint
585
+ @text
586
+ end
587
+ def selected?
588
+ @variable.value == @value
589
+ end
590
+
591
+ end
592
+
593
+ end # module
594
+ if __FILE__ == $PROGRAM_NAME
595
+ require 'rbhex/core/util/app'
596
+ require 'rbhex/core/widgets/rcontainer'
597
+ App.new do
598
+ #r = Container.new nil, :row => 1, :col => 2, :width => 40, :height => 10, :title => "A container"
599
+ r = Container.new nil, :suppress_borders => true
600
+ f1 = field "name", :maxlen => 20, :display_length => 20, :bgcolor => :white,
601
+ :color => :black, :text => "abc", :label => ' Name: '
602
+ f2 = field "email", :display_length => 20, :bgcolor => :white,
603
+ :color => :blue, :text => "me@google.com", :label => 'Email: '
604
+ f3 = radio :group => :grp, :text => "red", :value => "RED", :color => :red
605
+ f4 = radio :group => :grp, :text => "blue", :value => "BLUE", :color => :blue
606
+ f5 = radio :group => :grp, :text => "green", :value => "GREEN", :color => :green
607
+ r.add(f1)
608
+ r.add(f2)
609
+ r.add(f3,f4,f5)
610
+ TabbedPane.new @form, :row => 3, :col => 5, :width => 60, :height => 20 do
611
+ title "User Setup"
612
+ button_type :ok_apply_cancel
613
+ tab "&Profile" do
614
+ item Field.new nil, :row => 2, :col => 2, :text => "enter your name", :label => ' Name: '
615
+ item Field.new nil, :row => 3, :col => 2, :text => "enter your email", :label => 'Email: '
616
+ end
617
+ tab "&Settings" do
618
+ item CheckBox.new nil, :row => 2, :col => 2, :text => "Use HTTPS", :mnemonic => 'u'
619
+ item CheckBox.new nil, :row => 3, :col => 2, :text => "Quit with confirm", :mnemonic => 'q'
620
+ end
621
+ tab "&Term" do
622
+ radio = Variable.new
623
+ item RadioButton.new nil, :row => 2, :col => 2, :text => "&xterm", :value => "xterm", :variable => radio
624
+ item RadioButton.new nil, :row => 3, :col => 2, :text => "sc&reen", :value => "screen", :variable => radio
625
+ radio.update_command() {|rb| ENV['TERM']=rb.value }
626
+ end
627
+ tab "Conta&iner" do
628
+ item r
629
+ end
630
+
631
+ end
632
+ end # app
633
+
634
+ end