【问题标题】:Get an input in Ruby在 Ruby 中获取输入
【发布时间】:2016-03-22 04:13:58
【问题描述】:

我正在写一个终端游戏。它每秒重写游戏场。我希望用户通过按键进行交互。这是我想出的一个简化示例:

require 'io/console'

move = true

thr = Thread.new do
  while move do
    puts "Foo"
    sleep(1)
  end
end

loop do
  input = $stdin.getch
  if input == "a"
    move = false
    break
  end
end

看起来它有效。但是我有一个来自thr 的奇怪输出,它搞乱了整个游戏领域:

【问题讨论】:

  • 如果您正在制作游戏,您可能希望使用curses 库并有一个事件循环来检查键盘的可读状态。这里没有线程的原因。
  • 线程如何正确输出?
  • 当我尝试你的代码时,“Foo”总是写在行的开头,而不是像你的情况那样插入。这可能是因为终端设置不同。 puts 在字符串的末尾写一个换行符,您使用的终端将换行符解释为一个换行符。当你写puts "Foo\r"时输出如何?
  • user1934428 puts "Foo\r" 工作正常

标签: ruby input getch


【解决方案1】:

puts 在将字符串输出到屏幕后自动附加一个换行符 (\n)。这在大多数情况下很有用,但并非总是如此。

如果您不想换行,请使用print

print "Foo"

在这种情况下,您可能还想清除现有行;你可以用\r(用于“回车”)来做到这一点:

print "Foo\r"

这会将光标移回第 0 列。请注意,它不会清除任何字符 - 它只是将光标移回第 0 列,因此它可以覆盖字符。比如这个:

print "Hello\r"
print "Foo\r"

将导致:

Foolo

因为Foo 只输出三个字符——比屏幕上的少两个。为了解决这个问题,我们需要添加空格:

print "Foo  \r"

还有\b(退格)将光标向后移动一个字符:

print "Foo"
print "\b\bee"

将导致:

Fee

所有这些操作起来都相当乏味,这正是curses 库存在的原因;-) 它将所有这些包装在处理擦除正确内容的包装函数中,它最初是为 ASCII 游戏开发的像这样 ;-) 我建议你使用它!

【讨论】:

  • 感谢您的详细解释。回车解决了我的问题。我想下次我会使用 curses 库。有一些教程会很棒。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-06-11
  • 2011-12-08
  • 2011-10-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-10-15
相关资源
最近更新 更多