TCL Flush忽略退格

时间:2013-03-14 14:28:23

标签: tcl user-input flush

在tcl中执行刷新以捕获用户输入时,有没有办法忽略退格?

我正在执行一项功能,我将变量中的用户输入捕获到稍后用于另一个命令的变量中。所以我执行以下功能。

puts -nonewline "What is the username? "
flush stdout
set usrnm [gets stdin]

所以,假设我使用该命令,只要我不使用退格键,一切都按照我预期的方式工作,但是如果我使用退格键,则添加“\ x7F”作为字符。是否有办法让退格区不被视为角色?

2 个答案:

答案 0 :(得分:0)

这似乎取决于你的终端;当我尝试使用这些键序列的代码时:

  • 退格 B'/ KBD> C 返回
  • B'/ KBD> C 退格 d 返回

然后我在string length变量中得到长度为3的字符串(通过usrnm测量)。当终端正常处于熟化模式时(通常默认),这是我所期望的。由于\x7f可能不是用户名中的有效字符,我猜你可以过滤掉它:

set usrnm [string map {\x7f ""} $usrnm]

绝对确定该字符不存在的唯一方法是将终端置于原始模式(也可能是无回声)并自行完成所有字符输入处理。相对于问题的大小,这是一项巨大的工作;后置滤波器对我来说似乎更明智(我仍然想知道你的终端是什么)。


[编辑]:要将终端恢复到熟化模式,请执行以下操作:

exec stty -raw <@stdin

答案 1 :(得分:0)

我最近遇到了这个,我编写了一个处理char 127字符(退格)的过程。如果需要进行任何其他输入清理,您也可以在此处执行此操作,例如删除特殊字符。我觉得这可以更优雅,但确实有效。

proc cleanInput {str} {
    set return ""
    for {set i 0} {$i < [string length $str]} {incr i} {
        set char [string index $str $i]
        set asc [scan $char %c]
        if {$asc == 127} { #backspace
            if {[string length $return] > 0} {
                set return [string range $return 0 [expr "[string length $return] - 2"]]
            }
        } else {
            append return $char
        }
    }
    return $return
}