ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/AnyEvent-ReadLine-Gnu/Gnu.pm
Revision: 1.6
Committed: Fri May 11 00:30:20 2012 UTC (12 years ago) by root
Branch: MAIN
Changes since 1.5: +1 -1 lines
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 =head1 NAME
2    
3     AnyEvent::ReadLine::Gnu - event-based interface to Term::ReadLine::Gnu
4    
5     =head1 SYNOPSIS
6    
7     use AnyEvent::ReadLine::Gnu;
8    
9     # works always, prints message to stdout
10     AnyEvent::ReadLine::Gnu->print ("message\n");
11    
12     # now initialise readline
13 root 1.2 my $rl = new AnyEvent::ReadLine::Gnu prompt => "hi> ", on_line => sub {
14 root 1.1 # called for each line entered by the user
15     AnyEvent::ReadLine::Gnu->print ("you entered: $_[0]\n");
16     };
17    
18     # asynchronously print something
19     my $t = AE::timer 1, 1, sub {
20     $rl->hide;
21     print "async message 1\n"; # mind the \n
22     $rl->show;
23    
24     # the same, but shorter:
25     $rl->print ("async message 2\n");
26     };
27    
28     # do other eventy stuff...
29     AE::cv->recv;
30    
31     =head1 DESCRIPTION
32    
33     The L<Term::ReadLine> module family is bizarre (and you are encouraged not
34     to look at its sources unless you want to go blind). It does support
35     event-based operations, somehow, but it's hard to figure out.
36    
37     It also has some utility functions for printing messages asynchronously,
38     something that, again, isn't obvious how to do.
39    
40     This module has figured it all out for you, once and for all.
41    
42     =over 4
43    
44     =cut
45    
46     package AnyEvent::ReadLine::Gnu;
47    
48     use common::sense;
49     use AnyEvent;
50    
51     BEGIN {
52     # we try our best
53     local $ENV{PERL_RL} = "Gnu";
54    
55     require Term::ReadLine;
56     require Term::ReadLine::Gnu;
57     }
58    
59     use base Term::ReadLine::;
60    
61 root 1.2 our $VERSION = '0.2';
62 root 1.1
63     =item $rl = new AnyEvent::ReadLine::Gnu key => value...
64    
65     Creates a new AnyEvent::ReadLine object.
66    
67     Actually, it only configures readline and provides a convenient way to
68     call the show and hide methods, as well as readline methods - this is a
69     singleton.
70    
71     The returned object is the standard L<Term::ReadLine::Gnu> object, all
72     methods that are documented (or working) for that module should work on
73     this object.
74    
75     Once initialised, this module will also restore the terminal settings on a
76     normal program exit.
77    
78     The following key-value pairs are supported:
79    
80     =over 4
81    
82     =item on_line => $cb->($string)
83    
84     The only mandatory parameter - passes the callback that will receive lines
85     that are completed by the user.
86    
87 root 1.2 The string will be in locale-encoding (a multibyte character string). For
88     example, in an utf-8 using locale it will be utf-8. There is no portable
89     way known to the author to convert this into e.g. a unicode string.
90    
91 root 1.1 =item prompt => $string
92    
93     The prompt string to use, defaults to C<< > >>.
94    
95     =item name => $string
96    
97     The readline application name, defaults to C<$0>.
98    
99     =item in => $glob
100    
101     The input filehandle (should be a glob): defaults to C<*STDIN>.
102    
103     =item out => $glob
104    
105     The output filehandle (should be a glob): defaults to C<*STDOUT>.
106    
107     =back
108    
109     =cut
110    
111     our $self;
112     our $prompt;
113     our $cb;
114     our $hidden;
115     our $rw;
116     our ($in, $out);
117    
118     our $saved_point;
119     our $saved_line;
120    
121 root 1.2 # we postpone calling the user clalback here because readline
122     # still has the input buffer at this point, so calling hide and
123     # show might not have the desired effect.
124     sub on_line {
125     my $line = shift;
126     my $point = $self->{point};
127    
128     AE::postpone sub {
129     $cb->($line, $point);
130     };
131     }
132    
133 root 1.1 sub new {
134     my ($class, %arg) = @_;
135    
136     $in = $arg{in} || *STDIN;
137     $out = $arg{out} || *STDOUT;
138     $prompt = $arg{prompt} || "> ";
139 root 1.2 $cb = $arg{on_line} || $arg{cb}
140     or do { require Carp; Carp::croak ("AnyEvent::ReadLine::Gnu->new on_line callback argument mandatry, but missing") };
141 root 1.1
142     $self = $class->SUPER::new ($arg{name} || $0, $in, $out);
143    
144 root 1.2 $self->CallbackHandlerInstall ($prompt, \&on_line);
145 root 1.1 # set the unadorned prompt
146     $self->rl_set_prompt ($prompt);
147 root 1.5 $self->redisplay;
148 root 1.1
149     $hidden = 1;
150     $self->show;
151    
152     $self
153     }
154    
155     =item $rl->hide
156    
157     =item AnyEvent::ReadLine::Gnu->hide
158    
159     These methods I<hide> the readline prompt and text. Basically, it removes
160     the readline feedback from your terminal.
161    
162     It is safe to call even when AnyEvent::ReadLine::Gnu has not yet been
163     initialised.
164    
165     This is immensely useful in an event-based program when you want to output
166     some stuff to the terminal without disturbing the prompt - just C<hide>
167     readline, output your thing, then C<show> it again.
168    
169     Since user input will not be processed while readline is hidden, you
170     should call C<show> as soon as possible.
171    
172     =cut
173    
174     sub hide {
175     return if !$self || $hidden++;
176    
177     undef $rw;
178    
179     $saved_point = $self->{point};
180     $saved_line = $self->{line_buffer};
181    
182     $self->rl_set_prompt ("");
183     $self->{line_buffer} = "";
184     $self->rl_redisplay;
185     }
186    
187     =item $rl->show
188    
189     =item AnyEvent::ReadLine::Gnu->show
190    
191     Undos any hiding. Every call to C<hide> has to be followed to a call to
192     C<show>. The last call will redisplay the readline prompt, current input
193     line and cursor position. Keys entered while the prompt was hidden will be
194     processed again.
195    
196     =cut
197    
198     sub show {
199     return if !$self || --$hidden;
200    
201     if (defined $saved_point) {
202     $self->rl_set_prompt ($prompt);
203     $self->{line_buffer} = $saved_line;
204     $self->{point} = $saved_point;
205     $self->redisplay;
206     }
207    
208     $rw = AE::io $in, 0, sub {
209     $self->rl_callback_read_char;
210     };
211     }
212    
213     =item $rl->print ($string, ...)
214    
215     =item AnyEvent::ReadLine::Gnu->print ($string, ...)
216    
217     Prints the given strings to the terminal, by first hiding the readline,
218     printing the message, and showing it again.
219    
220 root 1.2 This function can be called even when readline has never been initialised.
221 root 1.1
222     The last string should end with a newline.
223    
224     =cut
225    
226     sub print {
227     shift;
228    
229     hide;
230     my $out = $out || *STDOUT;
231     print $out @_;
232     show;
233     }
234    
235     END {
236     return unless $self;
237    
238     $self->hide;
239     $self->callback_handler_remove;
240     }
241    
242     1;
243    
244     =back
245    
246 root 1.3 =head1 CAVEATS
247    
248     There are some issues with readline that can be problematic in event-based
249     programs:
250    
251     =over 4
252    
253     =item blocking I/O
254    
255     Readline uses blocking terminal I/O. Under most circumstances, this does
256     not cause big delays, but ttys have the potential to block programs
257     indefinitely (e.g. on XOFF).
258    
259     =item unexpected disk I/O
260    
261 root 1.4 By default, readline does filename completion on TAB, and reads its
262     config files.
263 root 1.3
264 root 1.5 Tab completion can be disabled by calling C<< $rl->unbind_key (9) >>.
265    
266 root 1.4 =item tty settings
267 root 1.3
268     After readline has been initialised, it will mangle the termios tty
269     settings. This does not normally affect output very much, but should be
270     taken into consideration.
271    
272 root 1.4 =item output intermixing
273    
274     Your program might wish to print messages (for example, log messages) to
275     STDOUT or STDERR. This will usually cause confusion, unless readline is
276     hidden with the hide method.
277    
278 root 1.3 =back
279    
280     Oh, and the above list is probably not complete.
281    
282 root 1.1 =head1 AUTHOR, CONTACT, SUPPORT
283    
284     Marc Lehmann <schmorp@schmorp.de>
285 root 1.6 http://software.schmorp.de/pkg/AnyEvent-ReadLine-Gnu.html
286 root 1.1
287 root 1.5 =head1 SEE ALSO
288    
289     L<rltelnet> - a simple tcp_connect-with-readline program using this module.
290    
291 root 1.1 =cut
292