12777ee89Sespie#!/usr/bin/perl -w 22777ee89Sespie 32777ee89Sespie#use strict vars; 42777ee89Sespie 52777ee89Sespie#use Term::ReadKey qw( ReadMode ReadKey ); 62777ee89Sespie#my $x; 72777ee89Sespie#ReadMode 3; 82777ee89Sespie#print "Read 1\n"; 92777ee89Sespie#$x = ReadKey(0); 102777ee89Sespie#print "X=$x\n"; 112777ee89Sespie#print "Read 2\n"; 122777ee89Sespie#$x = ReadKey(0); 132777ee89Sespie#print "X=$x\n"; 142777ee89Sespie#ReadMode 0; 152777ee89Sespie#__END__; 162777ee89Sespie 172777ee89Sespiemy $interactive = ( @ARGV && $ARGV[0] =~ /interactive/ ); 182777ee89Sespie 192777ee89SespieBEGIN { print "1..8\n"; } 202777ee89SespieEND { print "not ok 1\n" unless $loaded } 212777ee89Sespieuse Term::ReadKey; 222777ee89Sespie 232777ee89Sespie$loaded = 1; 242777ee89Sespieprint "ok 1\n"; 252777ee89Sespie 262777ee89Sespieuse Fcntl; 272777ee89Sespie 282777ee89Sespieif ( not exists $ENV{COLUMNS} ) 292777ee89Sespie{ 302777ee89Sespie $ENV{COLUMNS} = 80; 312777ee89Sespie $ENV{LINES} = 24; 322777ee89Sespie} 332777ee89Sespie 342777ee89Sespieif ( $^O =~ /Win32/i ) 352777ee89Sespie{ 362777ee89Sespie sysopen( IN, 'CONIN$', O_RDWR ) or die "Unable to open console input:$!"; 372777ee89Sespie sysopen( OUT, 'CONOUT$', O_RDWR ) or die "Unable to open console output:$!"; 382777ee89Sespie} 392777ee89Sespieelse 402777ee89Sespie{ 412777ee89Sespie 422777ee89Sespie if ( open( IN, "</dev/tty" ) ) 432777ee89Sespie { 442777ee89Sespie *OUT = *IN; 452777ee89Sespie die "Foo" unless -t OUT; 462777ee89Sespie } 472777ee89Sespie else 482777ee89Sespie { 492777ee89Sespie 502777ee89Sespie # Okay we are going to cheat a skip 512777ee89Sespie foreach my $skip ( 2 .. 8 ) 522777ee89Sespie { 532777ee89Sespie print "ok $skip # skip /dev/tty is absent\n"; 542777ee89Sespie } 552777ee89Sespie exit; 562777ee89Sespie } 572777ee89Sespie} 582777ee89Sespie 592777ee89Sespie*IN = *IN; # Make single-use warning go away 602777ee89Sespie$| = 1; 612777ee89Sespie 62*99fd0875Safresh1# Bad filehandle: IN at ../lib/Term/ReadKey.pm line 377 with \IN and harness 63*99fd0875Safresh1my $size1 = join( ",", GetTerminalSize( -t \IN ? \IN : "IN" ) ); 642777ee89Sespiemy $size2 = join( ",", GetTerminalSize("IN") ); 652777ee89Sespiemy $size3 = join( ",", GetTerminalSize(*IN) ); 662777ee89Sespiemy $size4 = join( ",", GetTerminalSize( \*IN ) ); 672777ee89Sespie 682777ee89Sespieif ( ( $size1 eq $size2 ) && ( $size2 eq $size3 ) && ( $size3 eq $size4 ) ) 692777ee89Sespie{ 702777ee89Sespie print "ok 2\n"; 712777ee89Sespie} 722777ee89Sespieelse 732777ee89Sespie{ 742777ee89Sespie print "not ok 2\n"; 752777ee89Sespie} 762777ee89Sespie 772777ee89Sespiesub makenicelist 782777ee89Sespie{ 792777ee89Sespie my (@list) = @_; 802777ee89Sespie my ( $i, $result ); 812777ee89Sespie $result = ""; 822777ee89Sespie for ( $i = 0 ; $i < @list ; $i++ ) 832777ee89Sespie { 842777ee89Sespie $result .= ", " if $i > 0; 852777ee89Sespie $result .= "and " if $i == @list - 1 and @list > 1; 862777ee89Sespie $result .= $list[$i]; 872777ee89Sespie } 882777ee89Sespie $result; 892777ee89Sespie} 902777ee89Sespie 912777ee89Sespiesub makenice 922777ee89Sespie{ 932777ee89Sespie my ($char) = $_[0]; 942777ee89Sespie if ( ord($char) < 32 ) { $char = "^" . pack( "c", ord($char) + 64 ) } 952777ee89Sespie elsif ( ord($char) > 126 ) { $char = ord($char) } 962777ee89Sespie $char; 972777ee89Sespie} 982777ee89Sespie 992777ee89Sespiesub makeunnice 1002777ee89Sespie{ 1012777ee89Sespie my ($char) = $_[0]; 1022777ee89Sespie $char =~ s/^\^(.)$/pack("c",ord($1)-64)/eg; 1032777ee89Sespie $char =~ s/(\d{1,3})/pack("c",$1+0)/eg; 1042777ee89Sespie $char; 1052777ee89Sespie} 1062777ee89Sespie 1072777ee89Sespiemy $response; 1082777ee89Sespie 1092777ee89Sespieeval { 1102777ee89Sespie 1112777ee89Sespie if ( &Term::ReadKey::termoptions() == 1 ) 1122777ee89Sespie { 1132777ee89Sespie $response = 1142777ee89Sespie "Term::ReadKey is using TERMIOS, as opposed to TERMIO or SGTTY.\n"; 1152777ee89Sespie } 1162777ee89Sespie elsif ( &Term::ReadKey::termoptions() == 2 ) 1172777ee89Sespie { 1182777ee89Sespie $response = 1192777ee89Sespie "Term::ReadKey is using TERMIO, as opposed to TERMIOS or SGTTY.\n"; 1202777ee89Sespie } 1212777ee89Sespie elsif ( &Term::ReadKey::termoptions() == 3 ) 1222777ee89Sespie { 1232777ee89Sespie $response = 1242777ee89Sespie "Term::ReadKey is using SGTTY, as opposed to TERMIOS or TERMIO.\n"; 1252777ee89Sespie } 1262777ee89Sespie elsif ( &Term::ReadKey::termoptions() == 4 ) 1272777ee89Sespie { 1282777ee89Sespie $response = 1292777ee89Sespie"Term::ReadKey is trying to make do with stty; facilites may be limited.\n"; 1302777ee89Sespie } 1312777ee89Sespie elsif ( &Term::ReadKey::termoptions() == 5 ) 1322777ee89Sespie { 1332777ee89Sespie $response = "Term::ReadKey is using Win32 functions.\n"; 1342777ee89Sespie } 1352777ee89Sespie else 1362777ee89Sespie { 1372777ee89Sespie $response = 1382777ee89Sespie "Term::ReadKey could not find any way to manipulate the terminal.\n"; 1392777ee89Sespie } 1402777ee89Sespie 1412777ee89Sespie print "ok 3\n"; 1422777ee89Sespie}; 1432777ee89Sespie 1442777ee89Sespieprint "not ok 3\n" if $@; 1452777ee89Sespie 1462777ee89Sespieprint $response if $interactive; 1472777ee89Sespie 1482777ee89Sespieeval { 1492777ee89Sespie push( @modes, "O_NODELAY" ) if &Term::ReadKey::blockoptions() & 1; 1502777ee89Sespie push( @modes, "poll()" ) if &Term::ReadKey::blockoptions() & 2; 1512777ee89Sespie push( @modes, "select()" ) if &Term::ReadKey::blockoptions() & 4; 1522777ee89Sespie push( @modes, "Win32" ) if &Term::ReadKey::blockoptions() & 8; 1532777ee89Sespie 1542777ee89Sespie print "ok 4\n"; 1552777ee89Sespie}; 1562777ee89Sespie 1572777ee89Sespieprint "not ok 4\n" if $@; 1582777ee89Sespie 1592777ee89Sespieif ($interactive) 1602777ee89Sespie{ 1612777ee89Sespie if ( &Term::ReadKey::blockoptions() == 0 ) 1622777ee89Sespie { 1632777ee89Sespie print "No methods found to implement non-blocking reads.\n"; 1642777ee89Sespie print 1652777ee89Sespie" (If your computer supports poll(), you might like to read through ReadKey.xs)\n"; 1662777ee89Sespie } 1672777ee89Sespie else 1682777ee89Sespie { 1692777ee89Sespie print "Non-blocking reads possible via ", makenicelist(@modes), ".\n"; 1702777ee89Sespie print $modes[0] . " will be used. " if @modes > 0; 1712777ee89Sespie print $modes[1] . " will be used for timed reads." 1722777ee89Sespie if @modes > 1 1732777ee89Sespie and $modes[0] eq "O_NODELAY"; 1742777ee89Sespie print "\n"; 1752777ee89Sespie } 1762777ee89Sespie} 1772777ee89Sespie 1782777ee89Sespieeval { 1792777ee89Sespie @size = GetTerminalSize(OUT); 1802777ee89Sespie print "ok 5\n"; 1812777ee89Sespie}; 1822777ee89Sespie 1832777ee89Sespieprint "not ok 5\n" if $@; 1842777ee89Sespie 1852777ee89Sespieif ($interactive) 1862777ee89Sespie{ 1872777ee89Sespie if ( !@size ) 1882777ee89Sespie { 1892777ee89Sespie print 1902777ee89Sespie "GetTerminalSize was incapable of finding the size of your terminal."; 1912777ee89Sespie } 1922777ee89Sespie else 1932777ee89Sespie { 1942777ee89Sespie print "Using GetTerminalSize, it appears that your terminal is\n"; 1952777ee89Sespie print "$size[0] characters wide by $size[1] high.\n\n"; 1962777ee89Sespie } 1972777ee89Sespie 1982777ee89Sespie} 1992777ee89Sespie 2002777ee89Sespieeval { 2012777ee89Sespie @speeds = GetSpeed(); 2022777ee89Sespie print "ok 6\n"; 2032777ee89Sespie}; 2042777ee89Sespie 2052777ee89Sespieprint "not ok 6\n" if $@; 2062777ee89Sespie 2072777ee89Sespieif ($interactive) 2082777ee89Sespie{ 2092777ee89Sespie if (@speeds) 2102777ee89Sespie { 2112777ee89Sespie print "Apparently, you are connected at ", join( "/", @speeds ), 2122777ee89Sespie " baud.\n"; 2132777ee89Sespie } 2142777ee89Sespie else 2152777ee89Sespie { 2162777ee89Sespie print "GetSpeed couldn't tell your connection baud rate.\n\n"; 2172777ee89Sespie } 2182777ee89Sespie print "\n"; 2192777ee89Sespie} 2202777ee89Sespie 2212777ee89Sespieeval { 2222777ee89Sespie %chars = GetControlChars(IN); 2232777ee89Sespie print "ok 7\n"; 2242777ee89Sespie}; 2252777ee89Sespie 2262777ee89Sespieprint "not ok 7\n" if $@; 2272777ee89Sespie 2282777ee89Sespie%origchars = %chars; 2292777ee89Sespie 2302777ee89Sespieif ($interactive) 2312777ee89Sespie{ 2322777ee89Sespie for $c ( keys %chars ) { $chars{$c} = makenice( $chars{$c} ) } 2332777ee89Sespie 2342777ee89Sespie print "Control chars = (", 2352777ee89Sespie join( ', ', map( "$_ => $chars{$_}", keys %chars ) ), ")\n"; 2362777ee89Sespie} 2372777ee89Sespie 2382777ee89Sespieeval { 2392777ee89Sespie SetControlChars( %origchars, IN ); 2402777ee89Sespie print "ok 8\n"; 2412777ee89Sespie}; 2422777ee89Sespie 2432777ee89Sespieprint "not ok 8\n" if $@; 2442777ee89Sespie 2452777ee89Sespie#SetControlChars("FOOFOO"=>"Q"); 2462777ee89Sespie#SetControlChars("INTERRUPT"=>"\x5"); 2472777ee89Sespie 2482777ee89SespieEND { ReadMode 0, IN; } # Just if something goes weird 2492777ee89Sespie 2502777ee89Sespieexit(0) unless $interactive; 2512777ee89Sespie 2522777ee89Sespieprint "\nAnd now for the interactive tests.\n"; 2532777ee89Sespie 2542777ee89Sespieprint 2552777ee89Sespie "\nThis is ReadMode 1. It's guarranteed to give you cooked input. All the\n"; 2562777ee89Sespieprint "signals and editing characters may be used as usual.\n"; 2572777ee89Sespie 2582777ee89SespieReadMode 1, IN; 2592777ee89Sespie 2602777ee89Sespieprint "\nYou may enter some text here: "; 2612777ee89Sespie 2622777ee89Sespie$t = ReadLine 0, IN; 2632777ee89Sespie 2642777ee89Sespiechop $t; 2652777ee89Sespie 2662777ee89Sespieprint "\nYou entered `$t'.\n"; 2672777ee89Sespie 2682777ee89SespieReadMode 2, IN; 2692777ee89Sespie 2702777ee89Sespieprint 2712777ee89Sespie "\nThis is ReadMode 2. It's just like #1, but echo is turned off. Great\n"; 2722777ee89Sespieprint "for passwords.\n"; 2732777ee89Sespie 2742777ee89Sespieprint "\nYou may enter some invisible text here: "; 2752777ee89Sespie 2762777ee89Sespie$t = ReadLine 0, IN; 2772777ee89Sespie 2782777ee89Sespiechop $t; 2792777ee89Sespie 2802777ee89Sespieprint "\nYou entered `$t'.\n"; 2812777ee89Sespie 2822777ee89SespieReadMode 3, IN; 2832777ee89Sespie 2842777ee89Sespieprint 2852777ee89Sespie "\nI won't demonstrate ReadMode 3 here. It's your standard cbreak mode,\n"; 2862777ee89Sespieprint 2872777ee89Sespie "with editing characters disabled, single character at a time input, but\n"; 2882777ee89Sespieprint "with the control characters still enabled.\n"; 2892777ee89Sespie 2902777ee89Sespieprint "\n"; 2912777ee89Sespie 2922777ee89Sespieprint 2932777ee89Sespie"I'm now putting the terminal into ReadMode 4 and using non-blocking reads.\n"; 2942777ee89Sespieprint 2952777ee89Sespie "All signals should be disabled, including xon-xoff. You should only be\n"; 2962777ee89Sespieprint "able to exit this loop via 'q'.\n"; 2972777ee89Sespie 2982777ee89SespieReadMode 4, IN; 2992777ee89Sespie$k = ""; 3002777ee89Sespie 3012777ee89Sespie#$in = *STDIN; 3022777ee89Sespie$in = \*IN; # or *IN or "IN" 3032777ee89Sespiewhile ( $k ne "q" ) 3042777ee89Sespie{ 3052777ee89Sespie print "Press a key, or \"q\" to stop: "; 3062777ee89Sespie $count = 0; 3072777ee89Sespie 3082777ee89Sespie #print "IN = $in\n"; 3092777ee89Sespie $count++ while !defined( $k = ReadKey( -1, $in ) ); 3102777ee89Sespie 3112777ee89Sespie #print "IN2 = $in\n"; 3122777ee89Sespie print "\nYou pressed `", makenice($k), 3132777ee89Sespie "' after the loop rolled over $count times\n"; 3142777ee89Sespie} 3152777ee89SespieReadMode 0, IN; 3162777ee89Sespie 3172777ee89Sespieprint "\nHere is a similar loop which times out after two seconds:\n"; 3182777ee89Sespie 3192777ee89SespieReadMode 4, IN; 3202777ee89Sespie$k = ""; 3212777ee89Sespie 3222777ee89Sespie#$in = *STDIN; 3232777ee89Sespie$in = \*IN; # or *IN or "IN" 3242777ee89Sespiewhile ( $k ne "q" ) 3252777ee89Sespie{ 3262777ee89Sespie print "Press a key, or \"q\" to stop: "; 3272777ee89Sespie $count = 0; 3282777ee89Sespie 3292777ee89Sespie #print "IN = $in\n"; 3302777ee89Sespie print "Timeout! " while !defined( $k = ReadKey( 2, $in ) ); 3312777ee89Sespie 3322777ee89Sespie #print "IN2 = $in\n"; 3332777ee89Sespie print "\nYou pressed `", makenice($k), "'\n"; 3342777ee89Sespie} 3352777ee89Sespie 3362777ee89Sespieprint 3372777ee89Sespie "\nLastly, ReadMode 5, which also affects output (except under Win32).\n\n"; 3382777ee89Sespie 3392777ee89SespieReadMode 5, IN; 3402777ee89Sespie 3412777ee89Sespieprint 3422777ee89Sespie"This should be a diagonal line (except under Win32): *\n*\n*\n\*\n*\n*\r\n\r\n"; 3432777ee89Sespieprint "And this should be a moving spot:\r\n\r\n"; 3442777ee89Sespie 3452777ee89Sespie$width = ( GetTerminalSize(OUT) )[0]; 3462777ee89Sespie$width /= 2; 3472777ee89Sespie$width--; 3482777ee89Sespieif ( $width < 10 ) { $width = 10; } 3492777ee89Sespie 3502777ee89Sespiefor ( $i = 0 ; $i < 20 ; $i += .15 ) 3512777ee89Sespie{ 3522777ee89Sespie print "\r"; 3532777ee89Sespie print( " " x ( ( cos($i) + 1 ) * $width ) ); 3542777ee89Sespie print "*"; 3552777ee89Sespie select( undef, undef, undef, 0.01 ); 3562777ee89Sespie print "\r"; 3572777ee89Sespie print( " " x ( ( cos($i) + 1 ) * $width ) ); 3582777ee89Sespie print " "; 3592777ee89Sespie} 3602777ee89Sespieprint "\r "; 3612777ee89Sespie 3622777ee89Sespieprint "\n\r\n"; 3632777ee89Sespie 3642777ee89SespieReadMode 0, IN; 3652777ee89Sespie 3662777ee89Sespieprint "That's all, folks!\n"; 3672777ee89Sespie 368