初学者:Pyqt 4 将触摸键盘连接到浏览器小部件



有人可以帮我连接这些点吗?仍在学习如何编程,我正在尝试通过在 PYQT 中制作一个简单的 GUI 来学习 OOP。

我正在尝试但不知道如何连接两个小部件。一个是 Web 浏览器示例,第二个是触摸键盘示例。触摸浏览器小部件中的行以添加 url 时需要调用触摸键盘。

我的浏览器小部件的代码:

import sys
from PyQt4.QtGui import QApplication
from PyQt4.QtCore import QUrl
from PyQt4.QtWebKit import QWebView
from PyQt4.QtGui import QGridLayout, QLineEdit, QWidget
class UrlInput(QLineEdit):
def __init__(self, browser):
super(UrlInput, self).__init__()
self.browser = browser
# add event listener on "enter" pressed
self.returnPressed.connect(self._return_pressed)
def _return_pressed(self):
url = QUrl(self.text())
# load url into browser frame
browser.load(url)
if __name__ == "__main__":
app = QApplication(sys.argv)
# create grid layout
grid = QGridLayout()
browser = QWebView()
browser.load(QUrl('http://google.com'))
url_input = UrlInput(browser)
# url_input at row 1 column 0 of our grid
grid.addWidget(url_input, 1, 0)
# browser frame at row 2 column 0 of our grid
grid.addWidget(browser, 2, 0)
# main app window
main_frame = QWidget()
main_frame.setLayout(grid)
main_frame.show()
# close app when user closes window
sys.exit(app.exec_())

键盘触摸代码:

from PyQt4 import QtGui, QtCore
from decimal import Decimal

# applicationle widgets
SIP_WIDGETS = [QtGui.QLineEdit]

class MyFlatPushButton(QtGui.QPushButton):
def __init__(self, caption, min_size=(50, 20)):
self.MIN_SIZE = min_size
QtGui.QPushButton.__init__(self, caption)
self.setFocusPolicy(QtCore.Qt.NoFocus)
def sizeHint(self):
return QtCore.QSize(self.MIN_SIZE[0], self.MIN_SIZE[1])

class SoftInputWidget(QtGui.QDialog):
def __init__(self, parent_object, keyboard_type='default'):
QtGui.QDialog.__init__(self)
self.setWindowFlags(QtCore.Qt.Tool | QtCore.Qt.WindowStaysOnTopHint | QtCore.Qt.FramelessWindowHint)
self.INPUT_WIDGET = None
self.PARENT_OBJECT = parent_object
self.signalMapper = QtCore.QSignalMapper(self)
self.NO_ORD_KEY_LIST = list()
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Left)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Up)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Right)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Down)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Backspace)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Enter)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Tab)
self.NO_ORD_KEY_LIST.append(QtCore.Qt.Key_Escape)
self.do_layout(keyboard_type)
self.signalMapper.mapped[int].connect(self.buttonClicked)
def do_layout(self, keyboard_type='default'):
"""
@param   keyboard_type:
@return:
"""
gl = QtGui.QVBoxLayout()
self.setFont(self.PARENT_OBJECT.font())
number_widget_list = []
sym_list = range(0, 10)
for sym in sym_list:
button = MyFlatPushButton(str(sym))
button.KEY_CHAR = ord(str(sym))
number_widget_list.append(button)
button = MyFlatPushButton('*')
button.KEY_CHAR = ord('*')
number_widget_list.append(button)
# alphabets
alpha_widget_list = []
sym_list = ['q', 'w', 'e', 'r', 't', 'z', 'u', 'i', 'o', 'p','@',
'new_row',
'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', '-', '/',
'new_row',
'y', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', ':']
for sym in sym_list:
if sym == 'new_row':
alpha_widget_list.append('new_row')
else:
button = MyFlatPushButton(sym)
button.KEY_CHAR = ord(sym)
alpha_widget_list.append(button)

# back space
control_widget_list = []
# close
button = MyFlatPushButton('Esc')
button.KEY_CHAR = QtCore.Qt.Key_Escape
control_widget_list.append(button)
control_widget_list.append('sep')
button = MyFlatPushButton('Del')
button.setToolTip('Backspace')
button.KEY_CHAR = QtCore.Qt.Key_Backspace
control_widget_list.append(button)
control_widget_list.append('sep')
# tab
button = MyFlatPushButton('TAB')
button.KEY_CHAR = QtCore.Qt.Key_Tab
control_widget_list.append(button)
control_widget_list.append('sep')
# space
button = MyFlatPushButton('Space', min_size=(70, 30))
button.KEY_CHAR = QtCore.Qt.Key_Space
control_widget_list.append(button)
control_widget_list.append('sep')

# enter
button = MyFlatPushButton('ENTER', min_size=(60, 30))
button.KEY_CHAR = QtCore.Qt.Key_Enter
control_widget_list.append(button)
control_widget_list.append('sep')
alist = list()
alist.append((QtCore.Qt.Key_Left, 'Left'))
alist.append((QtCore.Qt.Key_Right, 'Right'))
alist.append((QtCore.Qt.Key_Up, 'Up'))
alist.append((QtCore.Qt.Key_Down, 'Down'))
for key in alist:
button = MyFlatPushButton(key[1])
button.KEY_CHAR = key[0]
control_widget_list.append(button)
MAX_COL = 10
col = 0
tlist = list()
if keyboard_type == 'numeric':
widget_list = number_widget_list
elif keyboard_type == 'alpha':
widget_list = alpha_widget_list
else:
widget_list = list()
widget_list.extend(number_widget_list)
widget_list.append('new_row')
widget_list.extend(alpha_widget_list)
widget_list.append('new_row')
widget_list.extend(control_widget_list)
for widget in widget_list:
if widget == 'new_row':
col = MAX_COL
elif widget == 'sep':
tlist.append(self.get_vline())
continue
else:
tlist.append(widget)
widget.clicked.connect(self.signalMapper.map)
self.signalMapper.setMapping(widget, widget.KEY_CHAR)
if col == MAX_COL:
col = 0
v = QtGui.QHBoxLayout()
v.addStretch()
v.setSpacing(2)
map(v.addWidget, tlist)
v.addStretch()
gl.addLayout(v)
tlist = []
else:
col += 1
v = QtGui.QHBoxLayout()
v.setSpacing(5)
v.addStretch()
map(v.addWidget, tlist)
v.addStretch()
gl.addLayout(v)
gl.setContentsMargins(0, 0, 0, 0)
gl.setSpacing(3)
gl.setSizeConstraint(gl.SetFixedSize)
self.setLayout(gl)

#moguce za iskoristi za back botun
def reject(self):
self.buttonClicked(QtCore.Qt.Key_Escape)
def buttonClicked(self, char_ord):
w = self.INPUT_WIDGET
if char_ord in self.NO_ORD_KEY_LIST:
keyPress = QtGui.QKeyEvent(QtCore.QEvent.KeyPress, char_ord, QtCore.Qt.NoModifier, '')
else:
keyPress = QtGui.QKeyEvent(QtCore.QEvent.KeyPress, char_ord, QtCore.Qt.NoModifier, chr(char_ord))
# send keypress event to widget
QtGui.QApplication.sendEvent(w, keyPress)
# line edit returnPressed event is triggering twice for press and release both
# that is why do not send release event for special key
if char_ord not in self.NO_ORD_KEY_LIST:
keyRelease = QtGui.QKeyEvent(QtCore.QEvent.KeyPress, char_ord, QtCore.Qt.NoModifier, '')
QtGui.QApplication.sendEvent(w, keyRelease)
# hide on enter or esc button click
if char_ord in (QtCore.Qt.Key_Enter, QtCore.Qt.Key_Escape):
self.hide()
def show_input_panel(self, widget):
self.INPUT_WIDGET = widget
self.show()
self.update_panel_position()
def update_panel_position(self):
widget = self.INPUT_WIDGET
if not widget: return
widget_rect = widget.rect()
widget_bottom = widget.mapToGlobal(QtCore.QPoint(widget.frameGeometry().x(), widget.frameGeometry().y())).y()
screen_height = QtGui.qApp.desktop().availableGeometry().height()
input_panel_height = self.geometry().height() + 5
if (screen_height - widget_bottom) > input_panel_height:
# display input panel at bottom of widget
panelPos = QtCore.QPoint(widget_rect.left(), widget_rect.bottom() + 2)
else:
# display input panel at top of widget
panelPos = QtCore.QPoint(widget_rect.left(), widget_rect.top() - input_panel_height)
panelPos = widget.mapToGlobal(panelPos)
self.move(panelPos)
def _get_line(self, vertical=True):
line = QtGui.QFrame()
line.setContentsMargins(0, 0, 0, 0)
if vertical is True:
line.setFrameShape(line.VLine)
else:
line.setFrameShape(line.HLine)
line.setFrameShadow(line.Sunken)
return line
def get_hline(self):
return self._get_line(vertical=False)
def get_vline(self):
return self._get_line()

class TouchInterface(QtCore.QObject):
def __init__(self, PARENT_WIDGET):
QtCore.QObject.__init__(self)
self._PARENT_WIDGET = PARENT_WIDGET
self._input_panel_all = SoftInputWidget(PARENT_WIDGET, 'default')
# self._input_panel_numeric = SoftInputWidget(PARENT_WIDGET, 'numeric')
def childEvent(self, event):
if event.type() == QtCore.QEvent.ChildAdded:
if isinstance(event.child(), *SIP_WIDGETS):
event.child().installEventFilter(self)
def eventFilter(self, widget, event):
if self._PARENT_WIDGET.focusWidget() == widget and event.type() == QtCore.QEvent.MouseButtonPress:
if hasattr(widget, 'keyboard_type'):
if widget.keyboard_type == 'default':
self._input_panel_all.show_input_panel(widget)
# elif widget.keyboard_type == 'numeric':
#  self._input_panel_numeric.show_input_panel(widget)
return False

class TouchInputWidget(QtGui.QWidget):
def __init__(self):
QtGui.QWidget.__init__(self)
self.touch_interface = TouchInterface(self)
def childEvent(self, event):
self.touch_interface.childEvent(event)
def eventFilter(self, widget, event):
return self.touch_interface.eventFilter(widget, event)

class ExampleWidget(TouchInputWidget):
def __init__(self):
TouchInputWidget.__init__(self)
#self.txtNumeric = QtGui.QLineEdit()
# actiate touch input
# self.txtNumeric.keyboard_type = 'numeric'
self.txtText = QtGui.QLineEdit()
# activate touch input
self.txtText.keyboard_type = 'default'
gl = QtGui.QVBoxLayout()
# gl.addWidget(self.txtNumeric)
gl.addWidget(self.txtText)
self.setWindowTitle('Touch Input Demo')
self.setLayout(gl)
if __name__ == '__main__':
app = QtGui.QApplication([])
ExampleWidget().show()
app.exec_()

我不太确定我是否理解您的需求,从那里我看到您只想在单击 QLineEdit 时显示一些键盘。如果这是你需要的,我会告诉你使用信号并覆盖一些默认方法,并在其中实现想要的行为。

看看这个小例子,看看它是否有意义,以及是否可以将这种推理用于您的应用程序中。

import sys
from PyQt5.QtCore import pyqtSignal
from PyQt5.QtWidgets import QApplication
from PyQt5.QtWidgets import QHBoxLayout
from PyQt5.QtWidgets import QLineEdit
from PyQt5.QtWidgets import QMainWindow
from PyQt5.QtWidgets import QPushButton
from PyQt5.QtWidgets import QWidget
class MainWindow(QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
self.central_widget = QWidget()
self.cw_layout = QHBoxLayout()
self.central_widget.setLayout(self.cw_layout)
self.setCentralWidget(self.central_widget)
self.line = LineEdit()
self.kb = KeyBoard()
self.cw_layout.addWidget(self.line)
self.create_connections()
def create_connections(self):
self.line.signal_evoke_kb.connect(self.show_kb)
def show_kb(self):
if self.kb.isHidden():
self.kb.show()
else:
self.kb.hide()

class LineEdit(QLineEdit):
signal_evoke_kb = pyqtSignal()
def __init__(self):
super(LineEdit, self).__init__()
def mousePressEvent(self, QMouseEvent):
super(LineEdit, self).mousePressEvent(QMouseEvent)
self.signal_evoke_kb.emit()
class KeyBoard(QWidget):
def __init__(self):
super(KeyBoard, self).__init__()
self.layout = QHBoxLayout()
for key in ['q','w','e','r','t','y']:
self.layout.addWidget(QPushButton(key))
self.setLayout(self.layout)

if __name__ == "__main__":
app = QApplication(sys.argv)
mw = MainWindow()
mw.show()
sys.exit(app.exec_())

我正在使用 PyQt5,所以您可能只需要更改导入。

最新更新