非阻塞键盘读取 - C / C ++

时间:2012-02-24 10:27:04

标签: c++ c nonblocking keyboard-events

我现在正在使用以下功能。但我需要改进的是它会从键盘上读取输入(在终端上)即使它没有被按下。我需要知道什么时候没有按下(空闲),以便switch case块落入default部分。此时,read()函数等待,直到有来自用户的输入。任何人都可以根据修改以下代码提出建议吗? 注意:我是一名Java程序员,并且仍在学习C / C ++,所以可能很难在脑子里学到一点点。谢谢你们..

编辑:我找到了这个链接,似乎有一些与我在fcntl(STDIN_FILENO,F_SETFL,flags | O_NONBLOCK);行上寻找的内容有关。但是因为我几乎不知道C中的任何内容,所以我完全不知道它在说什么 http://www.codeguru.com/forum/showthread.php?t=367082

int kfd = 0;
struct termios cooked, raw;
char c;
bool dirty = false;

//get the console in raw mode
tcgetattr(kfd, &cooked);
memcpy(&raw, &cooked, sizeof(struct termios));
raw.c_lflag &=~ (ICANON | ECHO);
// Setting a new line, then end of file
raw.c_cc[VEOL] = 1;
raw.c_cc[VEOF] = 2;
tcsetattr(kfd, TCSANOW, &raw);

puts("Reading from keyboard");
puts("=====================");
puts("Use arrow keys to navigate");

while(true){
//get the next event from the keyboard
if(read(kfd, &c, 1) < 0)
{
  perror("read():");
  exit(-1);
}

linear_ = angular_ = 0;
ROS_DEBUG("value: 0x%02X\n", c);

switch(c)
{
  case KEYCODE_L:
    ROS_DEBUG("LEFT");
    angular_ = -1.0;
    dirty = true;
    break;
  case KEYCODE_R:
    ROS_DEBUG("RIGHT");
    angular_ = 1.0;
    dirty = true;
    break;
  case KEYCODE_U:
    ROS_DEBUG("UP");
    linear_ = 1.0;
    dirty = true;
    break;
  case KEYCODE_D:
    ROS_DEBUG("DOWN");
    linear_ = -1.0;
    dirty = true;
    break;
  default:
    ROS_DEBUG("RELEASE");
    linear_ = 0;
    angular_ = 0;
    dirty = true;
    break;
}

1 个答案:

答案 0 :(得分:1)

OP似乎回答了他们的问题:

  

我想我解决了我的问题。请,任何人,验证并告诉我这是否是正确的方法,或者是完成它的完整方式(我是否缺少任何其他添加步骤,例如重新将其重新设置 - 如果有意义的话)。< / p>      

所以我发现在进入while循环之前添加这3行:

flags = fcntl(0, F_GETFL, 0); /* get current file status flags */
flags |= O_NONBLOCK;          /* turn off blocking flag */
fcntl(0, F_SETFL, flags);         /* set up non-blocking read */