如何使用 Haskell 中的 readline 在任何按键上擦除终端中的一行?
How to erase a line in terminal on any keypress with readline in Haskell?
我正在使用 Haskell bindings 到 readline
库来读取用户的输入。
我想要实现的是提供一个预填值,只需按 return 键即可提交,但如果用户开始输入,我想自动删除预填文本。 (这样用户就不必担心删除预填充值。)
我认为可以使用 rl_getc_function
挂钩来完成。但是,Haskell 绑定不公开此功能。
有什么方法可以实现所需的行为吗?
终于想出了一个办法,但是不太好,感觉有点hack。
它的工作原理是将所有键重新绑定到一个自定义函数,该函数首先擦除该行,然后重置所有这些处理程序以再次实际插入该字符。为了不丢失触发按键,它被推回输入。
main :: IO ()
main = do
-- create a copy of current keymap
keymap <- getKeymap >>= copyKeymap
-- bind (hopefully all) regular keys to a helper function
forM_ (map toEnum [32..256]) $ \key ->
bindKey key $ \ _ _ -> do
-- delete all text on line
getEnd >>= deleteText 0
-- set cursor to start of line
setPoint 0
redisplay
-- reset keymap to the original one
setKeymap keymap
-- push pressed key back to input
setPendingInput key
return 0
setStartupHook (Just $ insertText "prefilled text")
readline "prompt> "
这个的主要痛点是确定要重新绑定哪些键。我用了一种科学的试错方法:下限是space(低于这个值的是不可打印的,可能有一些特殊的功能,我不想弄乱它)。上限设置为 256 - 任何更多都会导致段错误,使用较小的数字会使函数无法处理某些 unicode 输入。
即使在这个范围内,如果用户开始在 CJK. It definitely does not work correctly if the user types something by using a dead key.
中输入内容,它也可能无法正常工作
我正在使用 Haskell bindings 到 readline
库来读取用户的输入。
我想要实现的是提供一个预填值,只需按 return 键即可提交,但如果用户开始输入,我想自动删除预填文本。 (这样用户就不必担心删除预填充值。)
我认为可以使用 rl_getc_function
挂钩来完成。但是,Haskell 绑定不公开此功能。
有什么方法可以实现所需的行为吗?
终于想出了一个办法,但是不太好,感觉有点hack。
它的工作原理是将所有键重新绑定到一个自定义函数,该函数首先擦除该行,然后重置所有这些处理程序以再次实际插入该字符。为了不丢失触发按键,它被推回输入。
main :: IO ()
main = do
-- create a copy of current keymap
keymap <- getKeymap >>= copyKeymap
-- bind (hopefully all) regular keys to a helper function
forM_ (map toEnum [32..256]) $ \key ->
bindKey key $ \ _ _ -> do
-- delete all text on line
getEnd >>= deleteText 0
-- set cursor to start of line
setPoint 0
redisplay
-- reset keymap to the original one
setKeymap keymap
-- push pressed key back to input
setPendingInput key
return 0
setStartupHook (Just $ insertText "prefilled text")
readline "prompt> "
这个的主要痛点是确定要重新绑定哪些键。我用了一种科学的试错方法:下限是space(低于这个值的是不可打印的,可能有一些特殊的功能,我不想弄乱它)。上限设置为 256 - 任何更多都会导致段错误,使用较小的数字会使函数无法处理某些 unicode 输入。
即使在这个范围内,如果用户开始在 CJK. It definitely does not work correctly if the user types something by using a dead key.
中输入内容,它也可能无法正常工作