问题是当我按下'shift'键盘上的其他键时。这是我正在使用的代码(原始代码的功劳归于Nghia Ho)
#include <GL/freeglut.h>
#include <iostream>
#include <cmath>
#include "Camera.h"
using namespace std;
void Display();
void Reshape (int w, int h);
void Keyboard(unsigned char key, int x, int y);
void KeyboardUp(unsigned char key, int x, int y);
void MouseMotion(int x, int y);
void Mouse(int button, int state, int x, int y);
void Timer(int value);
void Idle();
void Grid();
Camera g_camera;
bool g_key[256];
bool g_shift_down = false;
bool g_fps_mode = false;
int g_viewport_width = 0;
int g_viewport_height = 0;
bool g_mouse_left_down = false;
bool g_mouse_right_down = false;
// Movement settings
const float g_translation_speed = 0.05;
const float g_rotation_speed = M_PI/180*0.2;
int main (int argc, char **argv) {
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE | GLUT_DEPTH);
glutInitWindowSize(640, 480);
glutCreateWindow("FPS demo by Nghia Ho - Hit SPACEBAR to toggle FPS mode");
glutIgnoreKeyRepeat(1);
glutDisplayFunc(Display);
glutIdleFunc(Display);
glutReshapeFunc(Reshape);
glutMouseFunc(Mouse);
glutMotionFunc(MouseMotion);
glutPassiveMotionFunc(MouseMotion);
glutKeyboardFunc(Keyboard);
glutKeyboardUpFunc(KeyboardUp);
glutIdleFunc(Idle);
glutTimerFunc(1, Timer, 0);
glutMainLoop();
return 0;
}
void Grid()
{
glPushMatrix();
glColor3f(1,1,1);
for(int i=-50; i < 50; i++) {
glBegin(GL_LINES);
glVertex3f(i, 0, -50);
glVertex3f(i, 0, 50);
glEnd();
}
for(int i=-50; i < 50; i++) {
glBegin(GL_LINES);
glVertex3f(-50, 0, i);
glVertex3f(50, 0, i);
glEnd();
}
glPopMatrix();
}
void Display (void) {
glClearColor (0.0,0.0,0.0,1.0); //clear the screen to black
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); //clear the color buffer and the depth buffer
glLoadIdentity();
g_camera.Refresh();
glColor3f(0,1,0);
glutWireTeapot(0.5);
Grid();
glutSwapBuffers(); //swap the buffers
}
void Reshape (int w, int h) {
g_viewport_width = w;
g_viewport_height = h;
glViewport (0, 0, (GLsizei)w, (GLsizei)h); //set the viewport to the current window specifications
glMatrixMode (GL_PROJECTION); //set the matrix to projection
glLoadIdentity ();
gluPerspective (60, (GLfloat)w / (GLfloat)h, 0.1 , 100.0); //set the perspective (angle of sight, width, height, ,depth)
glMatrixMode (GL_MODELVIEW); //set the matrix back to model
}
void Keyboard(unsigned char key, int x, int y)
{
if(key == 27) {
exit(0);
}
if(key == ' ') {
g_fps_mode = !g_fps_mode;
if(g_fps_mode) {
glutSetCursor(GLUT_CURSOR_NONE);
glutWarpPointer(g_viewport_width/2, g_viewport_height/2);
}
else {
glutSetCursor(GLUT_CURSOR_LEFT_ARROW);
}
}
if(glutGetModifiers() == GLUT_ACTIVE_SHIFT) {
g_shift_down = true;
}
else {
g_shift_down = false;
}
g_key[key] = true;
}
void KeyboardUp(unsigned char key, int x, int y)
{
g_key[key] = false;
}
void Timer(int value)
{
if(g_fps_mode) {
if(g_key['w'] || g_key['W']) {
g_camera.Move(g_translation_speed);
}
else if(g_key['s'] || g_key['S']) {
g_camera.Move(-g_translation_speed);
}
else if(g_key['a'] || g_key['A']) {
g_camera.Strafe(g_translation_speed);
}
else if(g_key['d'] || g_key['D']) {
g_camera.Strafe(-g_translation_speed);
}
else if(g_mouse_left_down) {
g_camera.Fly(-g_translation_speed);
}
else if(g_mouse_right_down) {
g_camera.Fly(g_translation_speed);
}
}
glutTimerFunc(1, Timer, 0);
}
void Idle()
{
Display();
}
void Mouse(int button, int state, int x, int y)
{
if(state == GLUT_DOWN) {
if(button == GLUT_LEFT_BUTTON) {
g_mouse_left_down = true;
}
else if(button == GLUT_RIGHT_BUTTON) {
g_mouse_right_down = true;
}
}
else if(state == GLUT_UP) {
if(button == GLUT_LEFT_BUTTON) {
g_mouse_left_down = false;
}
else if(button == GLUT_RIGHT_BUTTON) {
g_mouse_right_down = false;
}
}
}
void MouseMotion(int x, int y)
{
// This variable is hack to stop glutWarpPointer from triggering an event callback to Mouse(...)
// This avoids it being called recursively and hanging up the event loop
static bool just_warped = false;
if(just_warped) {
just_warped = false;
return;
}
if(g_fps_mode) {
int dx = x - g_viewport_width/2;
int dy = y - g_viewport_height/2;
if(dx) {
g_camera.RotateYaw(g_rotation_speed*dx);
}
if(dy) {
g_camera.RotatePitch(g_rotation_speed*dy);
}
glutWarpPointer(g_viewport_width/2, g_viewport_height/2);
just_warped = true;
}
}
奇怪的是,当我按任何其他键时,它第一次修复它,但它没有第二次修复它 万分感谢!
答案 0 :(得分:3)
问题是,GLUT键盘功能不会给你键代码,即按下了哪个键和修饰符的数字表示,而是字符代码,即由那个字母形成的字母代码。当然,大写字符具有与其小写字母不同的字符代码。持有班次当然会改变大小写。
实际上,GLUT并不是特别适合您想要的那种输入。使用GLFW或SDL进行此操作要简单得多。但是在您的特定情况下,有一个简单的解决方案:在“按下键”数组中进行索引之前,只需将所有传入的字符代码转换为小写:
#include <ctype.h> /* for tolower */
/* ... */
void Keyboard(unsigned char key, int x, int y)
{
key = tolower(key); /* <--- */
if(key == 27) {
exit(0);
}
if(key == ' ') {
g_fps_mode = !g_fps_mode;
if(g_fps_mode) {
glutSetCursor(GLUT_CURSOR_NONE);
glutWarpPointer(g_viewport_width/2, g_viewport_height/2);
}
else {
glutSetCursor(GLUT_CURSOR_LEFT_ARROW);
}
}
if(glutGetModifiers() == GLUT_ACTIVE_SHIFT) {
g_shift_down = true;
}
else {
g_shift_down = false;
}
g_key[key] = true;
}