Programmer's Note

コード読み書きの備忘録。

Rubyでバッファリングなしのキー入力を試す

Rubyでバッファリングなしのキー入力読み込みを試す。

普通の標準入力の getc を使った場合は、 入力された文字はターミナルに出力されつつ、バッファリングされて、 Enterが押されて初めて文字列がプログラムに送られる。

例:

ソース: t_getc.rb
while c = STDIN.getc
    print c
end

実行:
$ ruby t_getc.rb
abcdefg[RETURN]
abcdefg

しかし、プログラムでダイレクトにキー入力を拾いたい。 (例えばエディタを作るときのカーソル移動とか)

cursesライブラリを使うという方法もあるが、 これはターミナルが全クリアされてうまくない。

調べると"io/console"というライブラリがあったのでこれを使う。 使い方は簡単。

ソース: t_getch.rb
require 'io/console'

while c = STDIN.getch
    print c
end

実行:
$ ruby t_getch.rb
abcdefg             

入力した時点で文字が表示される。 そしてENTER押しても改行されなく、同じ行の先頭にカーソルが移る。 ENTERが押されたときに、キーコードとしてはCR(13)が入り、 printでターミナルに送られるが、これはターミナル側ではカーソルを行頭に移すことを意味するからだ。

このプログラムには罠があって、C-cを押してもプログラムが終了しない。 以下のように実装しないと、毎回killコマンドを打つするはめになる。

ソース:  t_getch.rb
require 'io/console'

while c = STDIN.getch
    exit if c == ?\C-c
    print c
end

以上。