保定网站建设解决方案,wordpress install.php,建设工程施工合同2017,wordpress进数据库文章目录 前言#xff1a;一、虚拟键盘的实现综合代码 二、为什么选用QWidget而不适用QDialog实现键盘三、从窗体a拉起窗体b后#xff0c;窗体b闪退问题的探讨四、关闭主窗口时子窗口未关闭的问题 前言#xff1a;
本文章主要包含四部分#xff1a;
虚拟键盘的实现#… 文章目录 前言一、虚拟键盘的实现综合代码 二、为什么选用QWidget而不适用QDialog实现键盘三、从窗体a拉起窗体b后窗体b闪退问题的探讨四、关闭主窗口时子窗口未关闭的问题 前言
本文章主要包含四部分
虚拟键盘的实现基于Pyside2)为什么选用QWidget而不适用QDialog实现键盘关于从一个窗体a中拉起另一个窗体b后窗体b闪退的问题探讨关闭主窗口时子窗口未关闭的问题
由于qt5官方的virtualkeyboard库无法适用于公司的应用场景于是需要手写一个virtual keyboard目前是初步实现了但是没有办法全局监听希望后续能有实现全局监听的办法。 已实现功能
作为组件以keyboard.py 形式集成到项目中可切换大小写可按比例附着于屏幕下方项目内多组件共用Keyboard需要作为单例类符合真实键盘键位支持部分特殊字符
待实现功能
全局监听 一、虚拟键盘的实现
从虚拟键盘的交互可以感知其应当作为一个窗体与用户进行交互通常窗体用的较多的是QDialog和QWidget由于QDialog会阻塞其他窗体的交互事件似乎可以通过setModal设置模态或非模态但是笔者尝试后不起作用故这里选择QWidget。 ————— 实现思路
QWidget作为键盘窗体QPushButton作为虚拟键盘的每个按键模拟真实键盘键位为每一行提供一个QHBoxLayout设置一个父layout即QVBoxLayout将所有QHBoxLayout添加进去。通过setGeometry设置窗体位于指定位置使键盘每次出现即附着于屏幕下方设置该类为单例类通过组件点击事件激活虚拟键盘这里重写了QLineEdit的点击事件mouseclickeventkeyboard工具类单例类装饰器
综合代码
代码结构
keyboard.py 键盘实现keyboard_util.py 键盘工具类singleton_util.py 单例类装饰器类enjoy_edit.py QLineEdit示例组件main.py 主程序入口
注代码虽使用PySide2但修改PySide2为PyQt5也可运行 代码已放在github https://github.com/qilin02811/VirtualKeyboard clone后即可运行通过python3 main.py即可运行需安装PySide2环境如果是PyQt5环境应将代码中的依赖修改为PyQt5 示意图
点击文本框后即可拉起键盘并且键盘附着于最下方
二、为什么选用QWidget而不适用QDialog实现键盘
由于QT程序一般有多个窗体我们希望键盘不会被其他窗体阻塞且我们也不希望键盘阻塞其他窗体故上面代码所有窗体均为QWidget而未使用QDialog。 使用QDialog要通过dialog.exec_()来拉起否则不会处理窗口的事件。 并且如果通过exec拉起QDialog必须关闭该dialog后才会响应其他窗体这是实际运行过程中应该避免的。 通过该键盘程序的编写我更倾向于使用QWidget而不是QDialog。
三、从窗体a拉起窗体b后窗体b闪退问题的探讨
由于在窗体a中我通过w QWidget() ,w.show()闪退故考虑使用QDialog q QDialog() q.exec_() 但这样会产生一个问题当处理键盘点击事件完成后想要点击主窗口或其他子窗口事件需要先关闭键盘这不符合我们平常的使用场景我们不希望键盘阻塞其他窗口于是又放弃了QDialog回到QWidget研究闪退问题。
这里给出一段解决闪退问题的示例 发生闪退问题的代码
class ×××(QWidget):def __init__():super().__init()def ×××(self):w QWidget()w.show()未发生闪退问题的代码
class ×××(QWidget):def __init__():super().__init()self.w Nonedef ×××(self):if self.w is None:self.w QWidget(self)self.w.show()推测第一个代码由于w.show()后整个解释器中就不存在w的引用则w.show()后会清除w的实例 第二个代码由于有self.w None的引用故self.w.show()后不会清除self.w的实例
四、关闭主窗口时子窗口未关闭的问题
编写窗体程序时经常出现多个窗体需要逐一关闭的情况我们希望关闭主窗口时能够关闭所有子窗口可以通过重写closeEvent实现
# 逐个关闭所有子widget
def closeEvent(self, event):for widget in QApplication.instance().allWidgets():if widget ! self and isinstance(widget, QWidget):widget.close()event.accept()