免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 12726 | 回复: 0

Linux下非阻塞地检测键盘输入的方法 (整理) [复制链接]

论坛徽章:
0
发表于 2007-05-14 13:29 |显示全部楼层
下面的代码实现了以下特性:
1. getchar获得输入字符不需要按回车
2. 非阻塞得检测键盘输入
3. 输入的字符不回显


  1. #include <stdio.h>
  2. #include <string.h>
  3. #include <sys/time.h>
  4. #include <sys/types.h>
  5. #include <unistd.h>
  6. #include <termios.h>
  7. #include <unistd.h>

  8. static struct termios ori_attr, cur_attr;

  9. static __inline
  10. int tty_reset(void)
  11. {
  12.         if (tcsetattr(STDIN_FILENO, TCSANOW, &ori_attr) != 0)
  13.                 return -1;

  14.         return 0;
  15. }


  16. static __inline
  17. int tty_set(void)
  18. {
  19.        
  20.         if ( tcgetattr(STDIN_FILENO, &ori_attr) )
  21.                 return -1;
  22.        
  23.         memcpy(&cur_attr, &ori_attr, sizeof(cur_attr) );
  24.         cur_attr.c_lflag &= ~ICANON;
  25. //        cur_attr.c_lflag |= ECHO;
  26.         cur_attr.c_lflag &= ~ECHO;
  27.         cur_attr.c_cc[VMIN] = 1;
  28.         cur_attr.c_cc[VTIME] = 0;

  29.         if (tcsetattr(STDIN_FILENO, TCSANOW, &cur_attr) != 0)
  30.                 return -1;

  31.         return 0;
  32. }

  33. static __inline
  34. int kbhit(void)
  35. {
  36.                   
  37.         fd_set rfds;
  38.         struct timeval tv;
  39.         int retval;

  40.         /* Watch stdin (fd 0) to see when it has input. */
  41.         FD_ZERO(&rfds);
  42.         FD_SET(0, &rfds);
  43.         /* Wait up to five seconds. */
  44.         tv.tv_sec  = 0;
  45.         tv.tv_usec = 0;

  46.         retval = select(1, &rfds, NULL, NULL, &tv);
  47.         /* Don't rely on the value of tv now! */

  48.         if (retval == -1) {
  49.                 perror("select()");
  50.                 return 0;
  51.         } else if (retval)
  52.                 return 1;
  53.         /* FD_ISSET(0, &rfds) will be true. */
  54.         else
  55.                 return 0;
  56.         return 0;
  57. }


  58. int main()
  59. {
  60.         int tty_set_flag;
  61.         tty_set_flag = tty_set();
  62.         while(1) {

  63.                 if( kbhit() ) {
  64.                         const int key = getchar();
  65.                         printf("%c pressed\n", key);
  66.                         if(key == 'q')
  67.                                 break;
  68.                 } else {
  69.                         fprintf(stderr, "<no key detected>\n");
  70.                 }
  71.         }

  72.         if(tty_set_flag == 0)
  73.                 tty_reset();
  74.         return 0;
  75. }




复制代码
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP