我是 C++ 编程的初学者,两周以来,我正在编写一个脚本,以便在同一个键盘上为 2 名玩家玩太空射击游戏。
对于游戏显示,我使用 NCURSES,对于键盘输入,我使用 X11。首先,我在键盘输入方面一直存在问题。
我们和朋友一起写了这个函数:
//earlier in the script :
Display *dpy;
if (NULL==(dpy=XOpenDisplay(NULL))) {
perror("Connexion problem");
exit(1);
}
XGrabKeyboard(dpy, DefaultRootWindow(dpy), True, GrabModeAsync, GrabModeAsync, CurrentTime);
//the function (keysPressed is just an array to store keyboard inputs) :
void getKBinput(bool (&keysPressed)[128], Display* dpy){
XEvent ev;
int kc;
if (XPending(dpy)){
XNextEvent(dpy, &ev);
switch (ev.type) {
case KeyPress:
kc = ((XKeyPressedEvent*)&ev)->keycode;
keysPressed[kc] = true;
break;
case KeyRelease:
kc = ((XKeyReleasedEvent*)&ev)->keycode;
keysPressed[kc] = false;
break;
case Expose:
while (XCheckTypedEvent(dpy, Expose, &ev));
break;
case ButtonPress:
case ButtonRelease:
case MotionNotify:
case ConfigureNotify:
default:
break;
}
}
}
}
//later in the script :
XUngrabKeyboard(dpy, CurrentTime);
if (XCloseDisplay(dpy)) {
perror("You can't deconnect to the server");
exit(1);
}
我在循环中使用这个函数来移动每艘宇宙飞船,具体取决于玩家按下每帧的内容。
但是,当我使用特定键的混合时,程序不会处理某些键(因此他没有将它们注册在布尔数组 keysPressed 中)。
例如,当玩家1同时按下“D”键和“C”键时,玩家2不能使用“向上”键或“!”键。(但玩家 2 可以同时使用“左”键和“下”键,没有问题)。
为了更好地了解这个脚本在做什么,我在一个外部文件中重写了这部分以打印按下的键和释放的键:
#include <X11/Xlib.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char **argv){
Display *dpy;
XEvent ev;
char * s;
unsigned int kc;
int quit = 0;
if (NULL==(dpy=XOpenDisplay(NULL))) {
perror(argv[0]);
exit(1);
}
XAutoRepeatOff(dpy);
XGrabKeyboard(dpy, DefaultRootWindow(dpy), True, GrabModeAsync, GrabModeAsync, CurrentTime);
for (;!quit;) {
XNextEvent(dpy, &ev);
switch (ev.type) {
case KeyPress:
kc = ((XKeyPressedEvent*)&ev)->keycode;
s = XKeysymToString(XKeycodeToKeysym(dpy, kc, 0));
if (s) printf("KEY PRESS:%s\n", s);
if (!strcmp(s, "q")) quit=~0;
break;
case KeyRelease:
kc = ((XKeyReleasedEvent*)&ev)->keycode;
s = XKeysymToString(XKeycodeToKeysym(dpy, kc, 0));
if (s) printf("KEY RELEASE:%s\n", s);
case Expose:
while (XCheckTypedEvent(dpy, Expose, &ev));
break;
case ButtonPress:
case ButtonRelease:
case MotionNotify:
case ConfigureNotify:
default:
break;
}
}
XUngrabKeyboard(dpy, CurrentTime);
XAutoRepeatOn(dpy);
if (XCloseDisplay(dpy)) {
perror(argv[0]);
exit(1);
}
return 0;
}
这证实了我的问题。因为我的电脑很旧(而且一些键工作得非常糟糕),所以我在其他电脑上测试了这个脚本,使其落在相同的输出上。
我在 x11 文档中进行了搜索(可能不正确?),一个解锁键之间每个混合的功能或其他绕过此限制的方法。我什么也没找到。我应该使用其他库进行键盘输入吗?
对不起我糟糕的英语(和潜在的错误),我尽力让人们理解。感谢您的阅读。