【问题标题】:How to access the PC Keyboard Buffer for Detecting multiple key press and key release?如何访问 PC 键盘缓冲区以检测多个按键和按键释放?
【发布时间】:2016-06-15 10:03:50
【问题描述】:

我正在用 C 语言为 PC 制作一个风琴合成器软件,因为我必须检测多个按键和按键释放,以便相应地同时播放音符。所以,我认为访问键盘缓冲区会有所帮助。但我不知道该怎么做。所以任何人都可以建议这样做的方法或一些新的想法来检测多个按键。为了检测单个按键和按键释放,我使用 kbhit() 和 getch() 函数制作了以下 C 代码:-

#include<stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<time.h>

void keypress(char);
void delay(int);

int flag=0;

int main()
{
    char c;

    while(1)
    {
        if(kbhit())
        {
            c=getch();

            printf("\nCharacter:%c",c);

            getch();

            keypress(c);

            printf("\nKey Released");

        }
    }

    return 0;
}

void keypress(char ch)
{
    char c;

    delay(50);

    if(kbhit())
    {
        c=getch();

        if(c==ch)
        {
            keypress(c);
        }

    }
}

void delay(int milliSeconds)
{
    clock_t final_time = milliSeconds + clock();
    while (final_time > clock());
}

但它有一些问题,例如:-

1). 未检测到多个按键

2).它会产生非常小的延迟

那么任何人都可以建议改进代码以解决上述问题或一些用于检测多个按键和按键释放的新技术。

平台:-Windows 8.1

如果解决方案对平台友好,那就太好了。

谢谢!

【问题讨论】:

  • 您的意思是要像钢琴键盘一样使用 PC 键盘,同时按住多个键?您不妨考虑 WINAPI 函数GetKeyboardState
  • 这是 DOS 编程,不是 Windows。

标签: c


【解决方案1】:

这显示了如何使用 Windows GetAsyncKeyState 函数。它不需要在 GUI 中 - 此控制台应用程序如图所示工作。您可以检查位状态标志as documented 以确定操作。例如,按下某个键时会自动重复。您可能也不需要检查每个键。

#include <stdio.h>
#include <windows.h>

int main(void)
{
    unsigned short buff[256] = {0};
    unsigned short kval;
    int i;
    while (1) {
        for(i=0; i<256; i++) {
            kval = GetAsyncKeyState(i);
            if(kval != buff[i]) {
                printf("%02X:%04X ", i, kval);
                buff[i] = kval;
            }
        }
    }
    return 0;
}

在这个测试中,第一行是在我按下任何键之前输出的。当我按下并释放'A'时,输出了第二行。

0D:0001 26:0001 45:0001 53:0001 54:0001 0D:0000 26:0000 45:0000 53:0000 54:0000
41:8001 41:8000 41:0000

注意:与user32.lib链接。

【讨论】:

    【解决方案2】:

    当您包含 conio.h 时,该解决方案已经绑定到 Windows(或 MS/DOS)平台。

    在这里,我假设您实际上并不需要命令行程序,最好的方法是构建一个具有事件循环的 Windows GUI 程序并直接处理 WM_KEYDOWNWM_KEYUP 消息,以便在键在键盘上按下时释放。为避免丢失键状态更改的任何风险,您甚至可以始终使用GetKeyboardState API 函数来加载键盘上所有键的当前状态。

    我知道这更像是一个精确答案的暗示,但详细的答案对于 SO 帖子来说太长了。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-09-20
      • 2019-03-05
      • 2017-03-22
      • 1970-01-01
      • 2018-01-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多