最近在学QT编程,写了个简单的推箱子游戏,debug的过程中一个问题困扰了我很久。。研究了很久,终于发现了原因,但是一些细节的东西还是不知道QT到底是怎么运行的。特记之,以备后续学习重温之用。
背景:
实现用方向键控制小人的运动,需要重新实现主窗口的keyPressEvent()函数。
问题:
玩第一关通过之后,会把原先存在的一个pushButton->show()出来提示按下进入下一关。鼠标按下之后可以显示第二关的界面,同时pushButton->hide(),但是发现方向键无作用,qdebug发现方向键无法进入自定义的按键事件函数,而其他的键如A~Z, 空格等等按键可以,而且必须要重新刷新界面才可以令方向键进入按键事件。(此时的方向键其实是有作用的,只不过方向键的事件是被隐藏的按键接收了,主窗口并没有接收到)
分析:
其实上面已经有简单的分析,如上所说,在我们看来的方向键无作用,其实是作用被隐藏了,我们知道当界面上有按键存在,且按键为焦点时,此时你按下方向键焦点会在各个button之间选择,按键信息也被置为焦点的按键接收,若按键是隐藏的,则我们看不到焦点的变化,这个导致用户误认为按键无作用。
解决方法:
既然原因已经明了,我们只需要在按下按钮之后,把Focus设置为主窗口,在主窗口的类函数里面用this->setFocus()则可以解决问题。
另外说明一下为什么方向键看起来没有作用,而其他键都有作用呢。这是因为QT的消息传递机制,在我们按下方向键时,pushButton类是可以接收并处理这类消息的,当我们按下其他的按键,pushButton无法处理,则把该消息传递给它的父窗口,我们重新实现的是主窗口的keypressEvent函数,可以处理这类消息,所以用qDebug是可以发现按键有反应。
初学QT,有啥写错的请多多指教哈~~
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
void keyPressEvent(QKeyEvent *);
void paintEvent(QPaintEvent *);
~MainWindow();
public slots:
void enterNextLevel();
private slots:
void on_btnNextLevel_clicked();
private:
Ui::MainWindow *ui;
int nXpeople;
int nYpeople;
int nLevel;//当前level
bool bIndex;//判断是否进入下一关
QPushButton *btnNextLevel;
};
构造函数:
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
this->setGeometry(300,300,320,320);
this->setWindowTitle(tr("推箱子游戏"));
ui->btnNextLevel->hide();
memcpy(&anMap, &anMap[1][0][0], sizeof(anMap)/4);
nLevel = 1;
bIndex = false;
}