File: Widgets.pod

package info (click to toggle)
libcurses-widgets-perl 1.2-1
  • links: PTS
  • area: main
  • in suites: woody
  • size: 140 kB
  • ctags: 29
  • sloc: perl: 1,359; makefile: 34
file content (674 lines) | stat: -rw-r--r-- 21,963 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
=head1 NAME

Curses::Widgets -- Curses-based widgets and functions

=head1 Doc/Module Version info

$Id: Widgets.pod,v 1.2 2000/03/17 00:30:03 corliss Exp corliss $

=head1 SYNOPSIS

	use Curses::Widgets;

	--or--

	use Curses::Widgets qw( :standard );	# same as above
	use Curses::Widgets qw( :functions );	# just functions
	use Curses::Widgets qw( :all );	 	# everything

=head1 REQUIREMENTS

Requires the Curses module, Curses or nCurses libraries.  You must still 
'use Curses;' in your script as well.

=head1 DESCRIPTION

This module provides a standard library of functions and widgets for use in
creating Curses-based interfaces.  Should work reliably with both Curses and
nCurses libraries.

Current widgets include:

	Text field (txt_field)
	List box (list_box)
	Button sets (buttons)
	Calendar (calendar)
	Message box (msg_box)
	Input box (input_box)

Extra functions include:

	select_colour
	line_split
	grab_key
	init_scr

Note that all of the widgets strictly use named parameters, while the
functions use unamed arguments.  All of them either return values, or modify
references that were passed as arguments.

Also note, for purpose of screen geometry, that all values passed for
specifying 'cols' and 'lines' refers only to the dimensions of the actual
content area, and does not include the border decorations.  You will typically
need to plan for an additional 2 for both 'cols' and 'lines' to account for
these.

=head1 EXPORTED

=head2 Default

=over 4

=item *
txt_field

=item *
buttons

=item *
list_box

=item *
calendar

=item *
msg_box

=item *
input_box

=item *
select_colour

=item *
init_scr

=back

=head2 OK

=over 4

=item *
line_split

=item *
grab_key

=back

=head1 WIDGETS

=head2 Text field

The text field widget creates a derived window (which uses coordinates
relative to the passed window) with a border surrounding the text.  When used
interactively, it handles its own input, passing back only the keys it
doesn't know how to handle, as well as the final content string and cursor
position.

If border decorations are enabled (they are, by default), the widget provides 
an arrow superimposed on the border to indicate whether there is content that 
can be scrolled to in that direction.  The arrow only appears when the content 
exceeds the display area.  The field is underlined if border decorations are
turned off.

Currently, this widget will handle any normal characters to be inserted into
the content string, and the following keys:

	Key		Curses Constant
	-------------------------------
	backspace	KEY_BACKSPACE
	delete		KEY_DC
	left arrow	KEY_LEFT
	right arrow	KEY_RIGHT
	up arrow	KEY_UP
	down arrow	KEY_DOWN
	page up		KEY_PPAGE
	home		KEY_HOME,KEY_FIND
	end		KEY_END,KEY_SEARCH

All parameters are passed as named parameters:

	Parameter	Commments
	-----------------------------------
	window		object handle to parent
			window for the widget
	ypos		integer, optional,
			default is 1
	xpos		integer, optional,
			default is 1
	lines		integer, optional,
			default is 1
	cols		integer, optional,
			default is $COLS - 2
	content		string, optional,
			default is "\n"
	password	integer, optional
			default is 0
	pos		integer, optional
			default is 0
	border		string, optional
			default is 'red'
	decorations	integer, optional
			default is 1
	edit		integer, optional
			default is 1
	hz_scroll	integer, optional
			default is 0
	function	reference, optional
	draw_only	integer, optional
			default is 0
	l_limit		integer, optional
	c_limit		integer, optional
	title		string, optional
	regex		string, optional,
			default is "\t"
	cursor_disable	integer, optional
			default is 0

'window' is a object handle to a predefined window or subwindow.  A quick
tip for debugging:  if either 'xpos', 'ypos', 'lines', or 'cols' cause any
portion of the window to extend passed the boundaries of the parent window,
the module will print an error message to STDERR, and immediately exit the
routine--no attempt will be made to draw or activate the widget.

'border' is the English name of the common console colours.  See the
'select_colour' function for a list of available colours.

'content' is a string containing the text you wish to fill the field with.

'password' will cause all text to show up as asterixs when printed.  This is
obviously intended for input that needs visual feedback, while maintaining
content security.

'pos' refers to the cursor position for use in interactive mode, so that input
can be inserted or appended to the content string.  This is ignored if passed
in conjunction with the draw_only parameter.  Valid settings are 0 -
length($string), or -1 to place the cursor at the end of the string.

'decorations' enables or disables the border/title/arrow decorations on the
field.  When disabled, the field will be underlined, to give some visual
indication of the size of the field.

'edit' turns on or off editing capabilities in the widget.  The field is still
navigable with all special keys, but no cursor will be printed, and the
content will not be affected by typed input.

'hz_scroll' enables horizontal scrolling in the text field, instead of the
normal behaviour of splitting on white space and presenting a new line.  This
will only work with one line widgets.  If you call this widget with any value
of 'lines' greater than one, horizontal scrolling will automatically be
disabled.

'function' is a scalar reference to a subroutine that can be called by the
widget when it times out, waiting for input.  For this to work, it assumes a
halfdelay(10) has been called, or on some other interval.

'l_limit' and 'c_limit' are completely optional, and can be used
together, if desired.  Both are integers, and can limit the content in
the text field.  Which ever limit is hit first will be honoured.

'title' is an optional string that will be superimposed over the
top-left border in reverse video.

'regex' is a string of all the characters that you wish to use to shift
focus off the text field, and return the contents.  By default, the tab
character is used ("\t").  This string is interpolated inside of
character class brackets, so don't include regex specific punctuation.
If you wish both new lines and tabs to shift focus, you would use
"\t\n".

'cursor_disable' disables the internal routine that prints it's own cursor.
It's best used when you are passing it a background function that updates
another portion of the screen, otherwise, when that update occurs, the cursor
would disappear from the field.  However, if you don't have such a function,
the cursor will appear right next to the software cursor, giving it the
appearance of a two character cursor.  In those situations, you should use
this option to disable the software cursor.

The memory allocated for the window is released when the widget routine exits.

	B<Example (non-Interactive)>

	txt_field( 'window'	=> $window,
		   'ypos'	=> 2,
		   'xpos'	=> $COLS - 5,
		   'lines'	=> $LINES - 10,
		   'cols'	=> $COLS - 10,
		   'content'	=> $note,
		   'border'	=> 'red',
		   'draw_only'	=> 1);
	
	B<(Interactive)>

	($key, $rtrnd_note, $pos) = txt_field( 'window'	=> $window,
					 'ypos'		=> 2,
					 'xpos'		=> $COLS - 5,
					 'lines'	=> $LINES - 10,
					 'cols'		=> $COLS - 10,
					 'content'	=> $note,
					 'border'	=> 'green',
					 'pos'		=> length($note),
					 'function'	=> \&clock);

=head2 List box

The list box widget creates a derived window that holds a scrollable list of
items, surounded by a border.  When called interactively, it handles it's own
input for navigation.  Any keys not used for navigation are returned, as well
as the currently selected item, unless the 'regex' option is used.  If so, it
will only return if the key matches the regex.

	Key		Curses Constant
	-------------------------------
	up arrow	KEY_UP
	down arrow	KEY_DOWN
	page up		KEY_PPAGE
	page down	KEY_PPAGE

The widget provides an arrow superimposed on the border to indicate whether
there is content that can be scrolled to in that direction.  The arrow only
appears when the content exceeds the display area.

All parameters are passed as named parameters:

	Parameter	Commments
	-----------------------------------
	window		object handle to parent
			window for the widget
	ypos		integer, optional,
			default is 1
	xpos		integer, optional,
			default is 1
	lines		integer, optional,
			default is 1
	cols		integer, optional,
			default is $COLS - 2
	list		hash or array reference
	border		string, optional
			default is 'red'
	selected	integer, optional,
			default is first element
	function	reference, optional
	draw_only	integer, optional
			default is 0
	title		string, optional
	regex		string, optional
	sort		string, optional
			default is 'numeric'

All previously described parameters maintain their same use and warnings.

'list' can be either a hash reference or an array reference.  If a hash is
passed, the value will be displayed, but the key will be returned as the
selected entry.  The list will also be numerically sorted according to key
value when displayed.

If 'list' is an array reference, the list will be displayed in array order,
and the index number of the element will be returned as the selected value.

'regex' works in the same manner as the the equivalent option in txt_field.

'sort' determines the type of sort used on the key values of lists passed as
hashes (it has no affect on lists passed as lists).  It defaults to a
'numeric' sort, but if you wish it to use an 'alphabetic' sort, you just need
to set it accordingly.

	B<Example (non-Interactive)>

	list_box( 'window'	=> $main,
		  'ypos'	=> 2,
		  'lines'	=> 10,
		  'cols'	=> 25,
		  'list'	=> \%list,
		  'border'	=> 'red',
		  'selected'	=> 1,
		  'draw_only'	=> 1);

	b<(Interactive)>

	($input, $selected) = list_box( 'window'	=> $main,
					'ypos'		=> 2,
					'xpos'		=> 5,
					'lines'		=> 10,
					'cols'		=> 25,
					'list'		=> \@list,
					'border'	=> 'green',
					'selected'	=> $last,
					'function'	=> \&clock);

=head2 Button set

The button bar creates a derived window as well, printing the passed 
buttons, and handles the key strokes to navigate amongst them,
while passing any other keystrokes and the currently selected button.  The
button set can be rendered either vertically or horizontally, and the
keystrokes that can be used for navigation depend upon that.  Like the
list_box, if the 'regex' option is used, it will only return on matching
values.

	Key		Curses Constant
	-------------------------------
	left arrow	KEY_LEFT
	right arrow	KEY_RIGHT
	up arrow	KEY_UP
	down arrow	KEY_DOWN

All parameters are passed as named parameters:

	Parameter	Commments
	-----------------------------------
	window		object handle to parent
			window for the widget
	buttons		reference
	ypos		integer, optional,
			default is 1
	xpos		integer, optional,
			default is 1
	active_button	integer, optional
	function	reference, optional
	vertical	integer, optional
	draw_only	integer, optional
			default is 0
	spacing		integer, default is 2
	regex		string, optional

Again, all previously described parameters remain the same.  Boundary checking
is still done for the entire bar, and if it exceeds them it will simply be 
skipped without drawing, while sending an error message stating as much to 
STDERR.

'buttons' is an array reference with each element a separate button.
'active_button' is the element's positional reference.  'spacing' is the
number of whitespace used to separate the buttons (spaces in horizontal mode,
lines in vertical mode).

If 'vertical' is passed with a Perlish true value the button set will be
rendered as a vertical set.

	B<Example (non-Interactive)>

	buttons( 'window'	=> $win_bar,
		 'buttons'	=> \@buttons,
		 'active_button'=> 2,
		 'draw_only'	=> 1);

	b<(Interactive)>

	($input, $selected) = buttons( 'windows'	=> $win_bar,
				       'buttons'	=> \@buttons,
				       'active_button'	=> $last,
				       'function'	=> \&clock);

=head2 Calendar

The calendar widget creates a fully navigable calendar in a derived, bordered
window.  The calendar controls its own input until it captures a keystroke it
doesn't explicitly handle.  In that case, it returns the key.  Like the
button_bar and list_box, though, this widget has a regex function.

	Key		Curses Constant
	-------------------------------
	left arrow	KEY_LEFT
	right arrow	KEY_RIGHT
	up arrow	KEY_UP
	down arrow	KEY_DOWN
	home		KEY_HOME
	page up		KEY_PPAGE
	page down	KEY_NPAGE

The home key, in this case, moves the selected date to the the current date.
The page up and down keys move the calendar from month to month.

All parameters are passed as named parameters:

	Parameter	Commments
	-----------------------------------
	window		object handle to parent
			window for the widget
	ypos		integer, optional,
			default is 1
	xpos		integer, optional,
			default is 1
	date_disp	reference
	border		string, optional
			default is 'red'
	function	reference, optional
	draw_only	integer, optional
			default is 0
	t_colour	string, optional
			default is 'yellow'
	e_colour	string, optional
			default is 'red'
	events		reference
	regex		string, optional

'date_disp' is an array reference that holds the desired date to display (in
day, month, year format).  If date_disp is not passed (or an empty list
reference is given instead), it will be initialised with the current date.
Should the widget be called in interactive mode, the reference will be
modified to display the last date navigated to by the user.  The first 
element, [0], is the day, the second, [1], the month, and the third, [2], 
the year.

't_colour' highlights the current date in the desired colour.  If colour is
not available, then the current date will be displayed in bold.  'e_colour'
will highlight each date found in the 'events' array ref in the desired
colour.  Date formats for the 'event' array must be 'dd/mm/yyyy', with no
leading zeros.

	B<Example (non-Interactive)>

	calendar( 'window'	=> $main,
		  'date_disp'	=> \@date,
		  'border'	=> 'red',
		  'draw_only'	=> 1);

	B<(Interactive)>

	$input = calendar( 'window'	=> $main,
			   'date_disp'	=> \@date,
			   'border'	=> 'blue',
			   'function'	=> \&clock);

=head2 Message Box

The msg_box displays the passed message in a new window that erases once
acknowledged.  It automatically scales and centers itself according to the
console and the passed message.

	Parameter	Commments
	-----------------------------------
	title		string, optional
	message		string, optional
	border		string, optional
			defaults to 'blue'
	function	reference, optional
	mode		integer, optional

All previously described options remain the same.  It only responds to the 
ENTER or space key.  Mode refers to the buttons drawn with the message.  By
default, it only draws an OK button, but if set to 2, it will display both an
OK and a CANCEL button.  In that instance, the widget will return a 1 if OK
was selected, or a 0 if CANCEL was selected.

	B<Example>

	msg_box( 'title'	=> "Critical Error!",
		 'message'	=> "Now, you've done it!",
		 'border'	=> "red");

Note that there is a minimum needed console size for this to work, which is
currently 5 rows by 14 columns.  If the console size is at least that size,
the message box will render.  Also note, though, that both the message and the
title may get chomped down to alloted window space, if you pass it more than
it can display.

Further, if the function parameter is used, and the passed function updates
the screen, you may see the message box disappear, though it is still trapping
key strokes.  To avoid this behaviour, refresh the current screen before
calling this function.

=head2 Input Box

The input_box displays a dialog box with a prompt, a one-line input field, 
and a two buttons, B<OK> and B<CANCEL>.  Like the msg_box, this widget
automatically scales and centers itself according to the prompt.

Unlike the msg_box, however, this widget returns two values; the first being
the value of the text field, the second being a 1 if the B<OK> button was
pressed, or a 0 if the B<CANCEL> button was pressed.  Hitting B<ENTER> while
in the text field is a shortcut for pressing the B<OK> button.

	Parameter	Commments
	-----------------------------------
	title		string, optional
	prompt		string, optional
	cols		integer, optional
	border		string, optional
			defaults to 'blue'
	f_colour	string, optional
			defaults to 'yellow'
	c_limit		defaults to 4096
	content		string, optional
	function	reference, optional

'cols' overrides the internally calculated width requirements (formerly
determined by the prompt width) to the specified setting.  This forces the
field width to be cols - 2 in width as well.

'f_colour' is the colour to use for the text field border when it has the
focus.  It will use the same colour set in 'border'

This widget requires a minimum console size for this to work, which is 8 rows
by 24 columns.  Both the title and the prompt may be chomped to accomodate
available screen space.

'c_limit' is simply passed to the text widget to restrict the length of the
typed string.  Horizontal scrolling is enabled.

	B<Example>

	($field, $button) = input_box( 'title'		=> 'Password',
				       'prompt'		=> 'Enter Password:',
				       'border'		=> 'blue');

If the function parameter is used, and the passed function updates
the screen, you may see the message box disappear, though it is still trapping
key strokes.  To avoid this behaviour, refresh the current screen before
calling this function.

=head1 FUNCTIONS

=head2 select_colour

Usage:  B<select_colour($window, foreground [, background])>

This function sets the character attributes for all subsequent characters to
the specified colour, for the specified window.  The first two arguments are
required, the first being an object handle to the window, and the second a 
string denoting the desired foreground colour.  A background colour can also
be given, but if not, it defaults to black.

Valid colours are black, cyan, green, magenta, red, white, blue, and yellow.  
All attributes stay in effect until another set is declared, or all 
attributes are reset via B<attrset(0)>.

	B<Example>

	select_colour($main, 'yellow');

=head2 init_scr

Usage: B<init_scr($miny, $minx)>

This function tests the terminal for both minimum dimensions and
interactivity.  If either condition is detected to be unsatisfactory, it
produces a warning on STDERR, and returns a false condition.  If it tests
okay, however, it will return a handle to a new Curses object.  It will also
set the default keypad, halfdelay, noecho, and cbreak options.

The miny and minx, minimum lines and columns, respectively, are optional.  If
omitted, the standard console size of 25 lines by 80 columns will be checked
for.

	B<Example>

	$mwh = init_scr(40, 80);

=head2 line_split (not exported by default)

Usage:  B<line_split(string, line_length)>

This function returns the submitted string as a list, each element being
a separate line.  It accounts for not only column limits, but whitespace
as well, splitting a sentence by whitespace, so as to not break words.

	B<Example>

	@lines = line_split($note, 80);

=head2 grab_key (not exported by default)

Usage:  B<grab_key($wh [, \&func_ref])>

This function returns the pressed key, calling the passed function reference
while waiting.

Only the first argument is mandatory, that being the object handle for the
window gathering the key strokes.  The function reference passed will be
called while waiting for a key to pressed, but only works if you've
initialised the console for half-blocking mode.  Ie., to call that function
every half a second:

	halfdelay(5);

=head1 Troubleshooting

Curses::Widgets will never intentionally kill your script.  It does do some
basic checks before executing some routines, and if it finds something amiss,
it will use the B<warn> function to report the error.

When testing scripts that use this module, you'd be well advised to pipe
STDERR to a file, so that it doesn't mess with the current display.  Checking
that file later will show you what specific areas of the script have problems.
Otherwise, the display might become corrupted, and cause perfectly valid
function calls to B<appear> screwey, when it was only the fact that the STDERR
moved the cursor location before the next STDOUT output could be rendered.

You should also consider overloading the __DIE__ signal handler, to make sure
that Curses returns your terminal to a usable state in case of fatal errors.

If you run into problems that appear to be the fault of the module, please
send me the STDERR output and a script that demonstrates the problem.

=head1 HISTORY

See the Changelog for in depth change history.  So far, I haven't broken
any of the default exported functions, so most scripts should run
unmodified.

2000/02/21 -- v1.1 Improved error handling/reporting, misc bug fixes, and
		major feature additions to the input_box, txt_field, list_box,
		and calendar.  Added init_scr function
2000/01/15 -- v1.0 Version promotion for first stable release
2000/01/15 -- v0.10 Degugging, added input_box, msg_box widgets
1999/11/17 -- v0.9 Internal calendar generation, improved error handling/
		reporting, added spacing argument to button bar, removed
		init_colours function
1999/06/17 -- v0.8 Added line_split function, title options, minor rewrites
1999/04/14 -- v0.7 Added l_limit/c_limit to text field
1999/02/02 -- v0.6 Colour-capability detection added, up/down charactersadded
		for content out-of-view indication, additional debugging
1999/01/11 -- v0.5 Debugging
1999/01/10 -- v0.4 Special key support added, special character constants 
		used, new select_colour function
1999/01/03 -- v0.3 rewrite/optimisation
1998/12/30 -- v0.2 rewrite/optimisation
1998/12/29 -- v0.1 Initial release (text field, list box, buttons, calendar)

=head1 AUTHOR

All bug reports, gripes, adulations, and comments can be sent to Arthur
Corliss, at B<corliss@odinicfoundation.org>.