本文介绍了事件 - 仅捕获 Qt.Key_Delete的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想为 QTableWidget 更改 Key_Delete 的行为,但是由于使用了 Designer,我不想在带有表单的 py 文件中进行任何更改.因此,不要像这样重新实现 QTableWidget 就像这个答案:如何在 PyQt 中为 Qt-Designer 小部件实现 MousePressEvent 我这样做:

I would like to change behavior of Key_Delete for QTableWidget, but because of using Designer I don't want to make any changes in py file with form. So instead of reimplementing QTableWidget like it is this answer: How to implement MousePressEvent for a Qt-Designer Widget in PyQt I do something like this:

class MyForm(QtGui.QMainWindow):
def __init__(self, parent=None):
    QtGui.QWidget.__init__(self, parent)
    self.ui = Ui_MainWindow()
    self.ui.setupUi(self)

    self.ui.tableWidget.__class__.keyPressEvent = self.test

def test(self,event):
    if event.key() == Qt.Key_Delete:
        print "test"

    return QTableWidget.keyPressEvent(self, event)

问题是我不知道如何保持 Qt.Key_Delete 以外的其他键的原始行为.我已经像这样更改了最后一行:

The problem is that I don't know how to keep original behavior of other keys than Qt.Key_Delete.I have already changed last line like this:

return QtGui.QTableWidget.keyPressEvent(self, event)
return QtGui.QTableWidget.event(self, event)

但它不起作用.

推荐答案

首先:但它不起作用"通常不够描述.你期望什么行为?你看到的行为是什么?是否有任何错误消息?

First: "but it doesn't work" is usually not descriptive enough. What behavior did you expect? What was the behavior you saw instead? Were there any error messages?

不过,我可以很容易地看出这里有一些错误.

I can easily see a few mistakes in here, though.

  1. 您正在覆盖方法 QTableWidget.keyPressEvent,该方法需要 2 个参数:(QTableWidget 实例,事件).但是在您上面显示的代码中,您用来覆盖它的函数只需要一个参数(第一个参数self"不计算在内,因为它是自动提供的).

  1. You're overriding the method QTableWidget.keyPressEvent, which expects 2 arguments: (QTableWidget instance, event). But in the code you show above, the function you are using to override it only takes 1 argument (the first argument, 'self', does not count since it is automatically supplied).

由于您已设置 QTableWidget.keyPressEvent = self.test,并且您还尝试从 in self.test() 调用此函数,因此您创建了一个无限递归函数.

Since you have set QTableWidget.keyPressEvent = self.test, and you are also trying to call this function from within self.test(), you have created an infinitely recursive function.

当您调用 QTableWidget.keyPressEvent 时,您传入的第一个参数 (self) 是 QMainWindow 对象.然而正如我上面提到的,这个函数需要一个 QTableWidget 作为它的第一个参数.

When you call QTableWidget.keyPressEvent, the first argument you have passed in (self) is a QMainWindow object. However as I mentioned above, this function expects a QTableWidget as its first argument.

由于您在 class 级别重写此方法,所有 QTableWidget 将被迫使用相同的 keyPressEvent 函数(这将是非常有问题的).相反,您应该只覆盖特定小部件的方法:self.ui.tableWidget.keyPressEvent = self.test(还要注意 tableWidget.keyPressEvent 的签名与 QTableWidget.keyPressEvent 不同)

Since you are overriding this method at the class level, ALL QTableWidgets will be forced to use the same keyPressEvent function (this would be very problematic). Instead, you should override just your specific widget's method: self.ui.tableWidget.keyPressEvent = self.test (also note that the signature for tableWidget.keyPressEvent is different from QTableWidget.keyPressEvent)

示例:

from PyQt4 import QtCore, QtGui
app = QtGui.QApplication([])
win = QtGui.QMainWindow()
win.show()

table = QtGui.QTableWidget()
win.setCentralWidget(table)
def test(event):
    if event.key() == QtCore.Qt.Key_Delete:
        print "delete"
    return QtGui.QTableWidget.keyPressEvent(table, event)
table.keyPressEvent = test

最后,另一种(可能更简洁)的方法是创建 QTableWdget 的子类,然后在 Designer 中将表格小部件提升"到您的新类.

Finally, another (possibly cleaner) approach would be to create a subclass of QTableWdget and, within Designer, 'promote' the table widget to your new class.

这篇关于事件 - 仅捕获 Qt.Key_Delete的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

07-04 03:32