Qt 事件处理 快捷键(重写eventFilter的函数,使用Qt::ControlModifier判断)
2017-06-15 20:42
1071 查看
CTRL+Enter发送信息的实现
在现在的即时聊天程序中,一般都设置有快捷键来实现一些常用的功能,类似QQ可以用CTRL+Enter来实现信息的发送。
在QT4中,所有的事件都继承与QEvent这个类,以下是用QEvent来实现快捷键的功能。
首先所有QT类的基类QObject有一个成员函数installEventFilter,这个函数是用来将一个事件处理器和该QObject绑定起来,所以就有了我下面的想法。
首先在chat类定义一个eventFilter,该函数是一个虚函数,可以由子类进行更改。所以声明eventFilter如下:
virtual bool eventFilter(QObject *obj, QEvent *e);
看了下QT文档对于这个函数的声明的解释,大概意思就是如果你要过滤某个事件就返回false,如果要使用某个事件就返回true。
我想在这个函数中加入对Enter键和Ctrl+Enter组合键的判断,具体查看QKeyEvent类的文档
QKeyEvent类中有函数key和modifier,key函数返回的是发生时间的按键值,modifier返回的而是修饰键,QT所支持的修饰键如下:
Constant Value Description
Qt::NoModifier 0x00000000 No modifier key is pressed.
Qt::ShiftModifier 0x02000000 A Shift key on the keyboard is pressed.
Qt::ControlModifier 0x04000000 A Ctrl key on the keyboard is pressed.
Qt::AltModifier 0x08000000 An Alt key on the keyboard is pressed.
Qt::MetaModifier 0x10000000 A Meta key on the keyboard is pressed.
Qt::KeypadModifier 0x20000000 A keypad button is pressed.
Qt::GroupSwitchModifier 0x40000000 X11 only. A Mode_switch key on the keyboard is pressed.
所以可以重写eventFilter函数来实现快捷键的功能,可以根据QKeyEvent的key和modifire来分别是Enter还是Ctrl+enter被按下。
重写eventFilter的函数如下:
[cpp] view plain copy
bool Window::eventFilter(QObject *obj, QEvent *e)
{
Q_ASSERT(obj == ui.inputMsgEdit);
if (e->type() == QEvent::KeyPress)
{
QKeyEvent *event = static_cast(e);
if (event->key() == Qt::Key_Return && (event->modifiers() & Qt::ControlModifier))
{
sendMessage();
return true;
}
}
return false;
}
然后把这个过滤器用installEventFilter函数安装在聊天窗口的输入框上(QTextEdit),这样就实现快捷键的功能了。
三键组合Shift + Ctrl + A的实现
只要在窗体中相应keyPressEvent事件函数即可。
[cpp] view plain copy
void Window::keyPressEvent(QKeyEvent *e)
{
if (e->modifiers() == (Qt::ShiftModifier | Qt::ControlModifier) && e->key() == Qt::Key_A)
{
//pressed
}
}
键盘按住Ctrl键 + 鼠标左键的实现
在窗体中相应mousePressEvent事件函数在其中检测Ctrl键是否按住即可。
[cpp] view plain copy
void Window::mousePressEvent(QMouseEvent *e)
{
// 获取鼠标在点击窗体上的坐标
QPoint pos = e->pos();
if (e->button() == LeftButton)
{
if ( QApplication::keyboardModifiers () == Qt::ControlModifier)
{
//pressed
}
}
}
一个例子:
[cpp] view plain copy
#include "mainwindow.h"
#include <QKeyEvent>
#include <QMessageBox>
#include <QDebug>
#include <QShortcut>
#include <QPushButton>
#include <QHBoxLayout>
#include <QAction>
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent)
{
// 设置窗口布局
QWidget *mainWidget = new QWidget(this);
QPushButton *button1 = new QPushButton("MessageBoxA", this);
QPushButton *button2 = new QPushButton("MessageBoxB", this);
QHBoxLayout *layout = new QHBoxLayout(this);
layout->addWidget(button1);
layout->addWidget(button2);
mainWidget->setLayout(layout);
this->setCentralWidget(mainWidget);
this->resize(200, 100);
this->setWindowTitle("Test");
// 创建QAction并设置快捷键
QAction *actionA = new QAction(this);
actionA->setShortcut(QKeySequence(tr("Ctrl+A")));
// actionA->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_A));
QAction *actionB = new QAction(this);
actionB->setShortcut(QKeySequence(tr("Ctrl+B")));
// actionA->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_B));
// 给button添加快捷键
// this->addAction(actionA);// 没用
button1->addAction(actionA);// 必须将快捷键添加到按钮上,同时使keyPressEvent失效,无法捕捉到Ctrl+A
button2->addAction(actionB);
// 设置快捷键相应
connect(actionA, &QAction::triggered, this, &MainWindow::button1_click);
connect(actionB, &QAction::triggered, this, &MainWindow::button2_click);
// 设置按钮点击事件相应
connect(button1, &QPushButton::clicked, this, &MainWindow::button1_click);
connect(button2, &QPushButton::clicked, this, &MainWindow::button2_click);
// 占用快捷键,使keyPressEvent函数失效
QShortcut *shortCut1 = new QShortcut(QKeySequence(tr("Delete")), this);
QShortcut *shortCut2 = new QShortcut(QKeySequence(tr("Return")), this);
// QShortcut *shortCut2 = new QShortcut(tr("Return"), this);
}
MainWindow::~MainWindow()
{
}
// 如果快捷键被设置,keyPressevent就无法处理相应的按钮事件
void MainWindow::keyPressEvent(QKeyEvent *event)
{
switch (event->key())
{
case Qt::Key_0:
{
qDebug() << Qt::Key_0;
QMessageBox::about(NULL, "0", "0");
break;
}
case Qt::Key_Return:// 被占用,失效
{
qDebug() << Qt::Key_Return;
QMessageBox::about(NULL, "return", "return");
break;
}
case Qt::Key_Delete:// 被占用,失效
{
qDebug() << Qt::Key_Delete;
QMessageBox::about(NULL, "Delete", "Delete");
break;
}
case QKeySequence::Delete:// 捕获不到,不能有这种方式处理
{
qDebug() << QKeySequence::Delete;
QMessageBox::about(NULL, "QKeySequence::Delete", "QKeySequence::Delete");
break;
}
case Qt::Key_F1:
{
qDebug() << Qt::Key_F1;
QMessageBox::about(NULL, "F1", "F1");
break;
}
case Qt::Key_O:// 处理组合快捷按钮
{
if (event->modifiers() & Qt::ControlModifier)
{
QMessageBox::about(NULL, "Ctr+O", "Ctr+O");
}
break;
}
case Qt::Key_A:// 被窗口button占用,失效,不能处理
{
if (event->modifiers() & Qt::ControlModifier)
{
QMessageBox::about(NULL, "Ctr+A", "Ctr+A");
}
break;
}
default:
{
qDebug() << event->key();
}
}
// if (event->key() == Qt::Key_O)
// {
// if (event->modifiers() & Qt::ControlModifier)
// {
// QMessageBox::about(NULL, "Ctr+O", "Ctr+O");
// }
// }
}
void MainWindow::keyReleaseEvent(QKeyEvent *event)
{
}
void MainWindow::button1_click()
{
QMessageBox::about(NULL, "MessageBoxA", "MessageBoxA");
}
void MainWindow::button2_click()
{
QMessageBox::about(NULL, "MessageBoxB", "MessageBoxB");
}
http://blog.csdn.net/caoshangpa/article/details/77933937
原文链接:http://blog.csdn.net/yang382197207/article/details/45363967
原文链接:http://blog.csdn.net/xj626852095/article/details/12039093
在现在的即时聊天程序中,一般都设置有快捷键来实现一些常用的功能,类似QQ可以用CTRL+Enter来实现信息的发送。
在QT4中,所有的事件都继承与QEvent这个类,以下是用QEvent来实现快捷键的功能。
首先所有QT类的基类QObject有一个成员函数installEventFilter,这个函数是用来将一个事件处理器和该QObject绑定起来,所以就有了我下面的想法。
首先在chat类定义一个eventFilter,该函数是一个虚函数,可以由子类进行更改。所以声明eventFilter如下:
virtual bool eventFilter(QObject *obj, QEvent *e);
看了下QT文档对于这个函数的声明的解释,大概意思就是如果你要过滤某个事件就返回false,如果要使用某个事件就返回true。
我想在这个函数中加入对Enter键和Ctrl+Enter组合键的判断,具体查看QKeyEvent类的文档
QKeyEvent类中有函数key和modifier,key函数返回的是发生时间的按键值,modifier返回的而是修饰键,QT所支持的修饰键如下:
Constant Value Description
Qt::NoModifier 0x00000000 No modifier key is pressed.
Qt::ShiftModifier 0x02000000 A Shift key on the keyboard is pressed.
Qt::ControlModifier 0x04000000 A Ctrl key on the keyboard is pressed.
Qt::AltModifier 0x08000000 An Alt key on the keyboard is pressed.
Qt::MetaModifier 0x10000000 A Meta key on the keyboard is pressed.
Qt::KeypadModifier 0x20000000 A keypad button is pressed.
Qt::GroupSwitchModifier 0x40000000 X11 only. A Mode_switch key on the keyboard is pressed.
所以可以重写eventFilter函数来实现快捷键的功能,可以根据QKeyEvent的key和modifire来分别是Enter还是Ctrl+enter被按下。
重写eventFilter的函数如下:
[cpp] view plain copy
bool Window::eventFilter(QObject *obj, QEvent *e)
{
Q_ASSERT(obj == ui.inputMsgEdit);
if (e->type() == QEvent::KeyPress)
{
QKeyEvent *event = static_cast(e);
if (event->key() == Qt::Key_Return && (event->modifiers() & Qt::ControlModifier))
{
sendMessage();
return true;
}
}
return false;
}
然后把这个过滤器用installEventFilter函数安装在聊天窗口的输入框上(QTextEdit),这样就实现快捷键的功能了。
三键组合Shift + Ctrl + A的实现
只要在窗体中相应keyPressEvent事件函数即可。
[cpp] view plain copy
void Window::keyPressEvent(QKeyEvent *e)
{
if (e->modifiers() == (Qt::ShiftModifier | Qt::ControlModifier) && e->key() == Qt::Key_A)
{
//pressed
}
}
键盘按住Ctrl键 + 鼠标左键的实现
在窗体中相应mousePressEvent事件函数在其中检测Ctrl键是否按住即可。
[cpp] view plain copy
void Window::mousePressEvent(QMouseEvent *e)
{
// 获取鼠标在点击窗体上的坐标
QPoint pos = e->pos();
if (e->button() == LeftButton)
{
if ( QApplication::keyboardModifiers () == Qt::ControlModifier)
{
//pressed
}
}
}
一个例子:
[cpp] view plain copy
#include "mainwindow.h"
#include <QKeyEvent>
#include <QMessageBox>
#include <QDebug>
#include <QShortcut>
#include <QPushButton>
#include <QHBoxLayout>
#include <QAction>
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent)
{
// 设置窗口布局
QWidget *mainWidget = new QWidget(this);
QPushButton *button1 = new QPushButton("MessageBoxA", this);
QPushButton *button2 = new QPushButton("MessageBoxB", this);
QHBoxLayout *layout = new QHBoxLayout(this);
layout->addWidget(button1);
layout->addWidget(button2);
mainWidget->setLayout(layout);
this->setCentralWidget(mainWidget);
this->resize(200, 100);
this->setWindowTitle("Test");
// 创建QAction并设置快捷键
QAction *actionA = new QAction(this);
actionA->setShortcut(QKeySequence(tr("Ctrl+A")));
// actionA->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_A));
QAction *actionB = new QAction(this);
actionB->setShortcut(QKeySequence(tr("Ctrl+B")));
// actionA->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_B));
// 给button添加快捷键
// this->addAction(actionA);// 没用
button1->addAction(actionA);// 必须将快捷键添加到按钮上,同时使keyPressEvent失效,无法捕捉到Ctrl+A
button2->addAction(actionB);
// 设置快捷键相应
connect(actionA, &QAction::triggered, this, &MainWindow::button1_click);
connect(actionB, &QAction::triggered, this, &MainWindow::button2_click);
// 设置按钮点击事件相应
connect(button1, &QPushButton::clicked, this, &MainWindow::button1_click);
connect(button2, &QPushButton::clicked, this, &MainWindow::button2_click);
// 占用快捷键,使keyPressEvent函数失效
QShortcut *shortCut1 = new QShortcut(QKeySequence(tr("Delete")), this);
QShortcut *shortCut2 = new QShortcut(QKeySequence(tr("Return")), this);
// QShortcut *shortCut2 = new QShortcut(tr("Return"), this);
}
MainWindow::~MainWindow()
{
}
// 如果快捷键被设置,keyPressevent就无法处理相应的按钮事件
void MainWindow::keyPressEvent(QKeyEvent *event)
{
switch (event->key())
{
case Qt::Key_0:
{
qDebug() << Qt::Key_0;
QMessageBox::about(NULL, "0", "0");
break;
}
case Qt::Key_Return:// 被占用,失效
{
qDebug() << Qt::Key_Return;
QMessageBox::about(NULL, "return", "return");
break;
}
case Qt::Key_Delete:// 被占用,失效
{
qDebug() << Qt::Key_Delete;
QMessageBox::about(NULL, "Delete", "Delete");
break;
}
case QKeySequence::Delete:// 捕获不到,不能有这种方式处理
{
qDebug() << QKeySequence::Delete;
QMessageBox::about(NULL, "QKeySequence::Delete", "QKeySequence::Delete");
break;
}
case Qt::Key_F1:
{
qDebug() << Qt::Key_F1;
QMessageBox::about(NULL, "F1", "F1");
break;
}
case Qt::Key_O:// 处理组合快捷按钮
{
if (event->modifiers() & Qt::ControlModifier)
{
QMessageBox::about(NULL, "Ctr+O", "Ctr+O");
}
break;
}
case Qt::Key_A:// 被窗口button占用,失效,不能处理
{
if (event->modifiers() & Qt::ControlModifier)
{
QMessageBox::about(NULL, "Ctr+A", "Ctr+A");
}
break;
}
default:
{
qDebug() << event->key();
}
}
// if (event->key() == Qt::Key_O)
// {
// if (event->modifiers() & Qt::ControlModifier)
// {
// QMessageBox::about(NULL, "Ctr+O", "Ctr+O");
// }
// }
}
void MainWindow::keyReleaseEvent(QKeyEvent *event)
{
}
void MainWindow::button1_click()
{
QMessageBox::about(NULL, "MessageBoxA", "MessageBoxA");
}
void MainWindow::button2_click()
{
QMessageBox::about(NULL, "MessageBoxB", "MessageBoxB");
}
http://blog.csdn.net/caoshangpa/article/details/77933937
原文链接:http://blog.csdn.net/yang382197207/article/details/45363967
原文链接:http://blog.csdn.net/xj626852095/article/details/12039093
相关文章推荐
- Qt5事件处理机制:“函数样式转换”:位于“.”运算符右边时非法/不允许使用此类型名
- Qt提升子部件的办法&如何重写提升后部件的事件处理函数
- 使用“事件监听/链式事件处理方式”实现window.onload同时调用多个函数
- js使用函数绑定技术改变事件处理程序的作用域
- Qt 事件处理 快捷键
- 事件处理函数OnEnter OnExit 使用一例
- Qt使用一个事件队列对所有发出的事件进行维护(QObject的event()函数相当于dispatch函数),用EventLabel 继承QLabel作为例子(简单明了) good
- 多个Button使用同一个事件处理方法时判断是哪个Button发生了事件
- jq 数组操作、事件处理和相关处理函数的使用
- Qt ------ 覆盖eventFilter(),捕获组件事件,事件处理
- 在vc下和gcc下不同函数名,可使用宏来判断处理
- (转载)Qt 的线程与事件循环——可打印threadid进行观察槽函数到底是在哪个线程里执行,学习moveToThread的使用)
- js使用函数绑定技术改变事件处理程序的作用域
- Qt中使用事件过滤器来处理键盘焦点
- QT重写控件函数并添加鼠标单击事件
- Qt 事件处理 快捷键
- Qt中如何禁掉所有UI操作以及注意事项(处理各个widget的eventFilter这一层,但是感觉不好,为什么不使用QApplication呢)
- Qt 的线程与事件循环——可打印threadid进行观察槽函数到底是在哪个线程里执行,学习moveToThread的使用)
- QT 槽函数使用记录 —— 进度条弹窗事件
- Effective C# 原则35:选择重写函数而不是使用事件句柄(译)