如何在使用stty -icanon时阅读返回

时间:2014-03-26 11:17:28

标签: bash stty

设置stty -icanon时间0 min 0后我有一个循环,以防止读取阻塞。

它可以正常工作,除了它无法读取输入/返回键。

有没有办法在这种模式下读取回车键,或者我的代码可以写成任何其他方式?

相关代码

tput smcup
Draw
if [ -t 0 ]; then stty -icanon time 0 min 0; fi
count=0
keypress=''
while [ "$keypress" != "q" ]; do
        sleep 0.1
        (( count = count + 1 ))
        rows=$(tput lines)
        columns=$(tput cols)
        Draw
        read  keypress
        name=$name$keypress
        echo $name
        if [[ $oldcolumns != $columns || $oldrows != $rows ]];then
                Draw
                oldcolumns=$columns
                oldrows=$rows
        elif [[ $count -eq 1  ]]; then
#               Draw
                count=0
        fi
done

if [ -t 0 ]; then stty sane; fi
tput rmcup
#rm tail.tmp
echo "Thanks for using this script."
exit 0

1 个答案:

答案 0 :(得分:2)

您可以通过阅读

执行此操作
  • 取消设置IFS
  • 不使用任何行分隔符
  • 一次只读一个字符

IFS= read -t 0.01 -d '' -n1 keypress

例如,我们输入 a space ,然后 return

$ IFS= read -t 0.01 -s -d '' -n1 keypress ; echo "\"$keypress\""
"a"
$ IFS= read -t 0.01 -s -d '' -n1 keypress ; echo "\"$keypress\""
" "
$ IFS= read -t 0.01 -s -d '' -n1 keypress ; echo "\"$keypress\""
"
"
$ 

我在上面的例子中添加了-s标志来抑制read的回显输入,因此它不会混淆输出的内容。这不是上述工作所必需的。

编辑:

在我看到你的评论之前,我没有意识到你有效地想要非阻塞模式。这更难。我能想到的最好的办法是在你的读命令中输入一个小的(10毫秒)超时。这会导致事件循环中延迟10毫秒的不幸影响,这可能是也可能是不可接受的。对我来说,更小的超时会导致bash表现不佳,并且0超时似乎根本不起作用。