QObject Class
QObject 类是所有 Qt 对象的基类。更多
注:该类中的所有函数都是可重入的。
注:这些函数也是线程安全的:
- connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
- connect(const QObject *sender, const char *signal, const char *method, Qt::ConnectionType type) const
- connect(常量 QObject *sender, PointerToMemberFunction signal, 常量 QObject *receiver, PointerToMemberFunction method, Qt::ConnectionType type)
- connect(const QObject *sender, PointerToMemberFunction signal, Functor functor)
- connect(常量 QObject *sender, PointerToMemberFunction signal, 常量 QObject *context, Functor functor, Qt::ConnectionType type)
- disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *method) (常量 QObject *sender, 常量 char *signal, 常量 QObject *receiver, 常量 char *method
- disconnect(const char *signal, const QObject *receiver, const char *method) const
- disconnect(常量 QObject *sender, PointerToMemberFunction signal, 常量 QObject *receiver, PointerToMemberFunction method)
- deleteLater()
属性
- objectName : QString
公共功能
QObject(QObject *parent = nullptr) | |
virtual | ~QObject() |
QBindable<QString> | bindableObjectName() |
bool | blockSignals(bool block) |
const QObjectList & | children() const |
QMetaObject::Connection | connect(const QObject *sender, const char *signal, const char *method, Qt::ConnectionType type = Qt::AutoConnection) const |
bool | disconnect(const QObject *receiver, const char *method = nullptr) const |
bool | disconnect(const char *signal = nullptr, const QObject *receiver = nullptr, const char *method = nullptr) const |
void | dumpObjectInfo() const |
void | dumpObjectTree() const |
QList<QByteArray> | dynamicPropertyNames() const |
virtual bool | event(QEvent *e) |
virtual bool | eventFilter(QObject *watched, QEvent *event) |
T | findChild(QAnyStringView name, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const |
(since 6.7) T | findChild(Qt::FindChildOptions options = Qt::FindChildrenRecursively) const |
QList<T> | findChildren(QAnyStringView name, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const |
(since 6.3) QList<T> | findChildren(Qt::FindChildOptions options = Qt::FindChildrenRecursively) const |
QList<T> | findChildren(const QRegularExpression &re, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const |
bool | inherits(const char *className) const |
void | installEventFilter(QObject *filterObj) |
(since 6.4) bool | isQuickItemType() const |
bool | isWidgetType() const |
bool | isWindowType() const |
void | killTimer(int id) |
(since 6.8) void | killTimer(Qt::TimerId id) |
virtual const QMetaObject * | metaObject() const |
bool | moveToThread(QThread *targetThread) |
QString | objectName() const |
QObject * | parent() const |
QVariant | property(const char *name) const |
void | removeEventFilter(QObject *obj) |
void | setObjectName(const QString &name) |
(since 6.4) void | setObjectName(QAnyStringView name) |
void | setParent(QObject *parent) |
bool | setProperty(const char *name, const QVariant &value) |
(since 6.6) bool | setProperty(const char *name, QVariant &&value) |
bool | signalsBlocked() const |
int | startTimer(int interval, Qt::TimerType timerType = Qt::CoarseTimer) |
int | startTimer(std::chrono::nanoseconds interval, Qt::TimerType timerType = Qt::CoarseTimer) |
QThread * | thread() const |
公共插槽
void | deleteLater() |
信号
void | destroyed(QObject *obj = nullptr) |
void | objectNameChanged(const QString &objectName) |
静态公共成员
QMetaObject::Connection | connect(const QObject *sender, const QMetaMethod &signal, const QObject *receiver, const QMetaMethod &method, Qt::ConnectionType type = Qt::AutoConnection) |
QMetaObject::Connection | connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type = Qt::AutoConnection) |
QMetaObject::Connection | connect(const QObject *sender, PointerToMemberFunction signal, Functor functor) |
QMetaObject::Connection | connect(const QObject *sender, PointerToMemberFunction signal, const QObject *context, Functor functor, Qt::ConnectionType type = Qt::AutoConnection) |
QMetaObject::Connection | connect(const QObject *sender, PointerToMemberFunction signal, const QObject *receiver, PointerToMemberFunction method, Qt::ConnectionType type = Qt::AutoConnection) |
bool | disconnect(const QMetaObject::Connection &connection) |
bool | disconnect(const QObject *sender, const QMetaMethod &signal, const QObject *receiver, const QMetaMethod &method) |
bool | disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *method) |
bool | disconnect(const QObject *sender, PointerToMemberFunction signal, const QObject *receiver, PointerToMemberFunction method) |
const QMetaObject | staticMetaObject |
QString | tr(const char *sourceText, const char *disambiguation = nullptr, int n = -1) |
受保护函数
virtual void | childEvent(QChildEvent *event) |
virtual void | connectNotify(const QMetaMethod &signal) |
virtual void | customEvent(QEvent *event) |
virtual void | disconnectNotify(const QMetaMethod &signal) |
bool | isSignalConnected(const QMetaMethod &signal) const |
int | receivers(const char *signal) const |
QObject * | sender() const |
int | senderSignalIndex() const |
virtual void | timerEvent(QTimerEvent *event) |
相关非成员
QObjectList | |
(since 6.8) enum class | TimerId { Invalid } |
T | qobject_cast(QObject *object) |
T | qobject_cast(const QObject *object) |
宏
(since 6.7) | QT_NO_CONTEXTLESS_CONNECT |
QT_NO_NARROWING_CONVERSIONS_IN_CONNECT | |
Q_CLASSINFO(Name, Value) | |
Q_EMIT | |
Q_ENUM(...) | |
Q_ENUM_NS(...) | |
Q_FLAG(...) | |
Q_FLAG_NS(...) | |
Q_GADGET | |
(since 6.3) | Q_GADGET_EXPORT(EXPORT_MACRO) |
Q_INTERFACES(...) | |
Q_INVOKABLE | |
(since 6.0) | Q_MOC_INCLUDE |
Q_NAMESPACE | |
Q_NAMESPACE_EXPORT(EXPORT_MACRO) | |
Q_OBJECT | |
Q_PROPERTY(...) | |
Q_REVISION | |
Q_SET_OBJECT_NAME(Object) | |
Q_SIGNAL | |
Q_SIGNALS | |
Q_SLOT | |
Q_SLOTS |
详细说明
QObject 是 Qt对象模型的核心。该模型的核心功能是一个非常强大的无缝对象通信机制,称为信号(signals)和槽(slot)。您可以使用connect() 将信号连接到槽,然后使用disconnect() 销毁连接。为了避免永无休止的通知循环,您可以使用blockSignals() 暂时屏蔽信号。受保护函数connectNotify() 和disconnectNotify() 可以跟踪连接。
QObjects 以对象树的形式组织自己。创建一个以另一个对象为父对象的 QObject 时,该对象会自动将自己添加到父对象的children() 列表中。父对象拥有该对象的所有权,也就是说,它会在析构函数中自动删除其子对象。您可以使用findChild() 或findChildren() 根据名称和可选类型查找对象。
每个对象都有一个objectName() ,其类名可通过相应的metaObject() 找到(参见QMetaObject::className() )。您可以使用inherits() 函数确定对象的类是否继承了 QObject 继承层次结构中的另一个类。
删除对象时,它会发出destroyed() 信号。您可以捕捉这个信号,以避免对 QObject 的悬空引用。
QObjects 可以通过event() 接收事件,并过滤其他对象的事件。详见installEventFilter() 和eventFilter() 。可以重新实现一个方便的处理程序childEvent() 来捕捉子事件。
最后但并非最不重要的是,QObject 在 Qt 中提供了基本的计时器支持;有关计时器的高级支持,请参阅QChronoTimer 。
请注意,任何实现信号、槽或属性的对象都必须使用Q_OBJECT 宏。您还需要在源文件上运行Meta-Object 编译器。我们强烈建议在 QObject 的所有子类中使用该宏,无论它们是否实际使用了信号、槽和属性,因为不这样做可能会导致某些函数表现出奇怪的行为。
所有 Qt Widget 都继承 QObject。方便函数isWidgetType() 返回一个对象是否实际上是一个 widget。它比qobject_cast<QWidget *>(obj) 或obj->inherits("QWidget") 快得多。
children QObjectList QObjectList 是 <QObject *> 的类型定义。QList
线程亲和性
一个 QObject 实例被称为具有线程亲和性,或者说它生活在某个线程中。当 QObject 收到queued signal 或发布的事件时,槽或事件处理程序将在该对象所在的线程中运行。
注意: 如果 QObject 没有线程亲和性(也就是说,如果thread() 返回 0),或者如果它所处的线程没有正在运行的事件循环,那么它就不能接收队列信号或发布的事件。
默认情况下,QObject 位于创建它的线程中。可以使用thread() 查询对象的线程亲和性,也可以使用moveToThread() 更改对象的线程亲和性。
所有 QObject 必须与其父对象生活在同一个线程中。因此
- setParent如果涉及的两个 QObject 处于不同的线程中,则 () 将会失败。
- 当一个 QObject 被移动到另一个线程时,它的所有子线程也会自动被移动。
- moveToThread如果 QObject 有父对象,则 () 将失败。
- 如果在QThread::run() 中创建了 QObject,它们就不能成为QThread 对象的子对象,因为QThread 并不在调用QThread::run() 的线程中。
注意: QObject 的成员变量不会自动成为其子对象。必须通过传递指向子对象constructor 的指针或调用setParent() 来设置父子关系。如果没有这一步,当调用moveToThread() 时,对象的成员变量将保留在旧线程中。
无复制构造函数或赋值操作符
QObject 既没有复制构造函数,也没有赋值操作符。这是由设计决定的。实际上,它们是被声明的,不过是在private
部分使用宏Q_DISABLE_COPY() 声明的。事实上,所有从 QObject 派生的 Qt 类(直接或间接)都使用这个宏将它们的复制构造函数和赋值操作符声明为私有。其中的道理请参阅 Qt对象模型页面中关于Identity vs Value 的讨论。
这样做的主要后果是,在可能使用 QObject 子类作为值的地方,您应该使用指向 QObject(或您的 QObject 子类)的指针。例如,如果没有复制构造函数,就不能使用 QObject 子类作为值存储在容器类中。您必须存储指针。
自动连接
Qt 的元对象系统提供了一种在 QObject 子类及其子类之间自动连接信号和插槽的机制。只要使用合适的对象名称定义对象,并且槽遵循简单的命名约定,就可以在运行时通过QMetaObject::connectSlotsByName() 函数执行这种连接。
uic 会生成调用该函数的代码,以便在用 Qt Widgets Designer.有关使用 Qt Widgets Designer使用自动连接的更多信息,请参阅本手册的 "在应用程序中使用设计器用户界面文件"部分。 Qt Widgets Designer手册的 "在应用程序中使用设计器用户界面文件 "一节中提供了更多有关使用
动态属性
动态属性可在运行时添加到 QObject 实例或从 QObject 实例中移除。动态属性无需在编译时声明,但具有与静态属性相同的优点,并可使用相同的 API 进行操作--使用property() 读取和setProperty() 写入。
动态属性由 Qt Widgets Designer支持动态属性,标准 Qt Widget 和用户创建的窗体都可以被赋予动态属性。
国际化(I18n)
所有 QObject 子类都支持 Qt 的翻译功能,因此可以将应用程序的用户界面翻译成不同的语言。
另请参阅 QMetaObject,QPointer,QObjectCleanupHandler,Q_DISABLE_COPY() 以及对象树和所有权。
属性文档
[bindable]
objectName : QString
注: 该属性支持QProperty 绑定。
此属性保存此对象的名称
使用findChild() 可以通过名称(和类型)查找对象。使用findChildren() 可以查找一组对象。
qDebug("MyClass::setPrecision():(%s) 无效精度 %f"、 qPrintable(objectName()), newPrecision);
默认情况下,该属性包含一个空字符串。
另请参阅 metaObject() 和QMetaObject::className()。
成员函数文档
[explicit invokable]
QObject::QObject(QObject *parent = nullptr)
构造一个对象,其父对象为parent 。
对象的父对象可视为对象的所有者。例如,dialog box 是其包含的OK 和Cancel 按钮的父对象。
父对象的析构函数会销毁所有子对象。
将parent 设置为nullptr
会构造一个没有父对象的对象。如果该对象是一个部件,它将成为一个顶层窗口。
注: 可通过元对象系统和 QML 调用此函数。参见Q_INVOKABLE 。
另请参阅 parent()、findChild() 和findChildren()。
[virtual noexcept]
QObject::~QObject()
销毁对象并删除其所有子对象。
与该对象的所有往来信号都会自动断开,该对象的所有待发布事件都会从事件队列中删除。不过,通常使用deleteLater() 比直接删除QObject 子类更安全。
警告 所有子对象都会被删除。如果堆栈或全局中有这些对象,程序迟早会崩溃。我们不建议从父对象外部持有指向子对象的指针。如果你仍然这样做,destroyed() 信号将为你提供一个检测对象是否被销毁的机会。
警告: 当QObject 正在处理传递给它的事件时,删除它可能会导致崩溃。如果QObject 存在于与当前执行线程不同的线程中,则不得直接删除。请使用deleteLater() 代替,它会导致事件循环在所有待处理事件都已传递给它后删除对象。
另请参阅 deleteLater()。
[noexcept]
bool QObject::blockSignals(bool block)
如果block 为 true,该对象发出的信号将被阻塞(即发出的信号不会调用与之相连的任何内容)。如果block 为 false,则不会发生这种阻塞。
返回值是signalsBlocked() 之前的值。
请注意,即使该对象的信号被阻塞,也会发出destroyed() 信号。
被阻塞时发出的信号不会被缓冲。
另请参见 signalsBlocked() 和QSignalBlocker 。
[virtual protected]
void QObject::childEvent(QChildEvent *event)
该事件处理程序可在子类中重新实现,以接收子事件。事件将通过event 参数传递。
QEvent::ChildAdded 和 事件会在添加或删除子对象时发送给对象。在这两种情况下,你只能依赖于子对象是 ,或者如果 () 返回 ,则是 。(这是因为,在 的情况下,子对象尚未完全构建,而在 的情况下,子对象可能已经被析构)。QEvent::ChildRemoved QObject isWidgetType true
QWidget ChildAdded ChildRemoved
QEvent::ChildPolished 当打磨子代或添加打磨子代时,会向部件发送事件。如果收到子代已抛光事件,则子代的构造通常已经完成。但这并不能保证,在执行部件的构造函数期间,可能会有多个抛光事件发生。
每个子部件都会收到一个ChildAdded 事件、零个或多个ChildPolished 事件和一个ChildRemoved 事件。
如果子部件在添加后立即被移除,则会省略ChildPolished 事件。如果一个子部件在构建和销毁过程中被多次抛光,您可能会收到多个针对同一子部件的子部件抛光事件,每次都有一个不同的虚拟表。
另请参阅 event() 。
const QObjectList &QObject::children() const
返回子对象列表。QObjectList 类在<QObject>
头文件中的定义如下:
typedef QList<QObject*> QObjectList;
第一个被添加的子对象是列表中的first 对象,最后一个被添加的子对象是列表中的last 对象,即新的子对象被添加到最后。
请注意,当QWidget 的子对象是raised 或lowered 时,列表顺序会发生变化。被提升的 widget 会成为列表中的最后一个对象,而被降低的 widget 会成为列表中的第一个对象。
另请参阅 findChild()、findChildren()、parent() 和setParent()。
[static]
QMetaObject::Connection QObject::connect(const QObject *sender, const QMetaMethod &signal, const QObject *receiver, const QMetaMethod &method, Qt::ConnectionType type = Qt::AutoConnection)
从sender 对象中的signal 到receiver 对象中的method ,创建给定type 的连接。返回一个连接句柄,用于稍后断开连接。
如果无法创建连接,例如参数无效,则连接句柄将无效。可以通过将QMetaObject::Connection 转换为 bool 来检查其是否有效。
该函数的工作方式与connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
相同,但它使用QMetaMethod 来指定信号和方法。
另请参阅 connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)。
[static]
QMetaObject::Connection QObject::connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type = Qt::AutoConnection)
从sender 对象中的signal 到receiver 对象中的method ,创建给定type 的连接。返回一个连接句柄,用于稍后断开连接。
在指定signal 和method 时,必须使用SIGNAL()
和SLOT()
宏:
QLabel *label = new QLabel; QScrollBar *scrollBar = new QScrollBar; QObject::connect(scrollBar, SIGNAL(valueChanged(int)), label, SLOT(setNum(int)));
该示例可确保标签始终显示当前滚动条的值。请注意,信号和槽参数不得包含任何变量名,只能包含类型。例如,以下示例将不起作用并返回 false:
// WRONG QObject::connect(scrollBar, SIGNAL(valueChanged(int value)), label, SLOT(setNum(int value)));
一个信号也可以连接到另一个信号:
class MyWidget : public QWidget { Q_OBJECT public: MyWidget(); signals: void buttonClicked(); private: QPushButton *myButton; }; MyWidget::MyWidget() { myButton = new QPushButton(this); connect(myButton, SIGNAL(clicked()), this, SIGNAL(buttonClicked())); }
在这个例子中,MyWidget
构造函数从一个私有成员变量中转发了一个信号,并以一个与MyWidget
相关的名称提供给用户。
一个信号可以连接多个槽和信号。一个槽可以连接多个信号。
如果一个信号连接了多个槽,那么在信号发出时,这些槽将按照连接的顺序被激活。
如果函数成功地将信号连接到插槽,则会返回一个QMetaObject::Connection ,表示连接句柄。如果无法创建连接,例如QObject 无法验证signal 或method 的存在,或者它们的签名不兼容,则连接句柄将无效。可以通过将句柄转换为 bool 来检查句柄是否有效。
默认情况下,每次连接都会发出一个信号;重复连接会发出两个信号。只需调用一次disconnect() 就能中断所有这些连接。如果通过Qt::UniqueConnection type ,则只有在不重复的情况下才会建立连接。如果已经存在重复连接(相同对象上相同插槽的相同信号),连接将失败,connect 将返回无效的QMetaObject::Connection 。
注意: Qt::UniqueConnections 对 lambdas、非成员函数和函数式不起作用;它们只适用于连接到成员函数。
可选的type 参数描述了要建立的连接类型。特别是,它决定了特定信号是立即传递到槽,还是排队等待稍后传递。如果是队列信号,参数必须是 Qt 元对象系统已知的类型,因为 Qt 需要复制参数,将其存储在幕后事件中。如果您尝试使用队列连接,并收到错误信息
QObject::connect: Cannot queue arguments of type 'MyType' (Make sure 'MyType' is registered using qRegisterMetaType().)
请在建立连接前调用qRegisterMetaType() 注册数据类型。
注意:该函数是线程安全的。
另请参阅 disconnect()、sender()、qRegisterMetaType()、Q_DECLARE_METATYPE() 和基于字符串的连接与基于连接器的连接之间的区别。
[static]
template <typename PointerToMemberFunction, typename Functor> QMetaObject::Connection QObject::connect(const QObject *sender, PointerToMemberFunction signal, Functor functor)
此函数重载 connect()。
创建从sender 对象中的signal 到functor 的连接,并返回连接句柄
信号必须是在标头中声明为信号的函数。槽函数可以是任何可以连接到信号的函数或函数器。如果信号的参数数至少与槽函数的参数数相同,则槽函数可以连接到给定的信号。信号和槽中相应参数的类型之间必须存在隐式转换。
举例说明
void someFunction(); QPushButton *button = new QPushButton; QObject::connect(button, &QPushButton::clicked, someFunction);
也可以使用 Lambda 表达式:
QByteArray page = ...; QTcpSocket *socket = new QTcpSocket; socket->connectToHost("qt-project.org", 80); QObject::connect(socket, &QTcpSocket::connected, [=] () { socket->write("GET " + page + "\r\n"); });
如果发送方被销毁,连接将自动断开。但是,在信号发出时,必须确保函数中使用的任何对象仍然有效。
因此,建议使用 connect() 的重载,它也将QObject 作为接收器/上下文。通过定义QT_NO_CONTEXTLESS_CONNECT
宏,可以禁用无上下文重载。
重载函数可通过qOverload 解决。
注意:该函数是线程安全的。
QMetaObject::Connection QObject::connect(const QObject *sender, const char *signal, const char *method, Qt::ConnectionType type = Qt::AutoConnection) const
此函数重载 connect()。
将signal 从sender 对象连接到此对象的method 。
等价于 connect(sender,signal,this
,method,type)。
每建立一个连接都会发出一个信号,因此重复连接会发出两个信号。您可以使用disconnect() 中断连接。
注意:此函数是线程安全的。
另请参阅 disconnect() 。
[static]
template <typename PointerToMemberFunction, typename Functor> QMetaObject::Connection QObject::connect(const QObject *sender, PointerToMemberFunction signal, const QObject *context, Functor functor, Qt::ConnectionType type = Qt::AutoConnection)
此函数重载 connect()。
从sender 对象中的signal 创建一个给定的type 连接到functor ,以放置在context 的特定事件循环中,并返回该连接的句柄。
注意: Qt::UniqueConnections 对 lambdas、非成员函数和函数式不起作用;只适用于连接到成员函数。
信号必须是在头文件中声明为信号的函数。槽函数可以是任何可以连接到信号的函数或函数器。如果信号的参数数至少与槽函数的参数数相同,则槽函数可以连接到给定的信号。信号和槽中相应参数的类型之间必须存在隐式转换。
举例说明
void someFunction(); QPushButton *button = new QPushButton; QObject::connect(button, &QPushButton::clicked, this, someFunction, Qt::QueuedConnection);
也可以使用 Lambda 表达式:
QByteArray page = ...; QTcpSocket *socket = new QTcpSocket; socket->connectToHost("qt-project.org", 80); QObject::connect(socket, &QTcpSocket::connected, this, [=] () { socket->write("GET " + page + "\r\n"); }, Qt::AutoConnection);
如果发送方或上下文被破坏,连接将自动断开。不过,在信号发出时,必须确保函数中使用的对象仍然有效。
重载函数可通过qOverload 解决。
注意:该函数是线程安全的。
[static]
template <typename PointerToMemberFunction> QMetaObject::Connection QObject::connect(const QObject *sender, PointerToMemberFunction signal, const QObject *receiver, PointerToMemberFunction method, Qt::ConnectionType type = Qt::AutoConnection)
此函数重载 connect()。
从sender 对象中的signal 到receiver 对象中的method ,创建给定type 的连接。返回一个连接句柄,用于稍后断开连接。
信号必须是在标头中声明为信号的函数。槽函数可以是任何可以连接到信号的成员函数。如果信号的参数数至少与槽的参数数相同,且信号和槽中相应参数的类型之间存在隐式转换,则槽可以连接到给定的信号。
举例说明
QLabel *label = new QLabel; QLineEdit *lineEdit = new QLineEdit; QObject::connect(lineEdit, &QLineEdit::textChanged, label, &QLabel::setText);
本例确保标签始终显示当前行编辑文本。
一个信号可以连接多个槽和信号。一个槽可以连接多个信号。
如果一个信号与多个插槽相连,当信号发出时,这些插槽将按照连接的顺序被激活。
如果函数成功地将信号连接到槽,则返回一个连接句柄。如果无法创建连接,例如QObject 无法验证signal 的存在(如果它未被声明为信号),则连接句柄将无效。您可以通过将QMetaObject::Connection 转换为 bool 来检查它是否有效。
默认情况下,每次连接都会发出一个信号;重复连接会发出两个信号。只需调用一次disconnect() 就能中断所有这些连接。如果通过Qt::UniqueConnection type ,则只有在不重复的情况下才会建立连接。如果已经存在重复连接(相同对象上相同插槽的相同信号),连接将失败,connect 将返回无效的QMetaObject::Connection 。
可选的type 参数描述了要建立的连接类型。特别是,它决定了特定信号是立即发送到插槽,还是稍后排队发送。如果是队列信号,参数必须是 Qt 元对象系统已知的类型,因为 Qt 需要复制参数并将其存储在幕后事件中。如果您尝试使用队列连接,并得到错误信息
QObject::connect: Cannot queue arguments of type 'MyType' (Make sure 'MyType' is registered using qRegisterMetaType().)
请确保使用Q_DECLARE_METATYPE
重载函数可通过qOverload 解决。
注意:该函数是线程安全的。
另请参阅 基于字符串的连接与基于函数的连接之间的区别。
[virtual protected]
void QObject::connectNotify(const QMetaMethod &signal)
当该对象中的signal 连接到某些内容时,就会调用该虚函数。
如果要将signal 与某个特定信号进行比较,可以使用QMetaMethod::fromSignal() 如下操作:
if (signal == QMetaMethod::fromSignal(&MyObject::valueChanged)) { // signal is valueChanged }
警告: 该函数违反了面向对象的模块化原则。但是,当您需要执行昂贵的操作时,只有当某物连接到某个信号时,该函数才会有用。
警告:该函数违反了面向对象的模块化原则: 此函数由执行连接的线程调用,而该线程可能与此对象所在的线程不同。调用该函数时,还可能锁定了QObject 内部互斥。因此,不允许从您的重实现中重新输入任何QObject 函数,包括isSignalConnected()。如果您在重实现中锁定了一个互斥项,请确保不要在调用QObject 函数时在其他地方持有该互斥项,否则会导致死锁。
另请参见 connect() 和disconnectNotify()。
[virtual protected]
void QObject::customEvent(QEvent *event)
该事件处理程序可在子类中重新实现,以接收自定义事件。自定义事件是用户定义的事件,其类型值至少与QEvent::Type 枚举中的QEvent::User 项一样大,通常是QEvent 子类。事件通过event 参数传递。
[slot]
void QObject::deleteLater()
计划删除此对象。
当控制返回到事件循环时,对象将被删除。如果调用此函数时事件循环尚未运行(例如,在QCoreApplication::exec() 之前调用了对象的 deleteLater()),那么一旦事件循环启动,对象就会被删除。如果在主事件循环停止后调用 deleteLater(),则不会删除对象。如果在没有运行事件循环的线程中调用 deleteLater(),对象将在线程结束时被销毁。
需要注意的是,进入和离开一个新的事件循环(例如打开一个模态对话框)不会执行延迟删除;要删除对象,控件必须返回到调用 deleteLater() 的事件循环。这不适用于前一个嵌套事件循环仍在运行时删除的对象:一旦新的嵌套事件循环开始,Qt 事件循环就会删除这些对象。
在 Qt 未通过QCoreApplication::exec() 或QEventLoop::exec() 等驱动事件派发器的情况下,延迟删除将不会被自动处理。在这种情况下,为确保延迟删除,可使用以下变通方法:
const auto *eventDispatcher = QThread::currentThread()->eventDispatcher(); QObject::connect(eventDispatcher, &QAbstractEventDispatcher::aboutToBlock, QThread::currentThread(), []{ if (QThread::currentThread()->loopLevel() == 0) QCoreApplication::sendPostedEvents(nullptr, QEvent::DeferredDelete); } );
注意:该函数是线程安全的。
[signal]
void QObject::destroyed(QObject *obj = nullptr)
该信号会在QPointer 的任何实例被通知后,立即在对象obj 销毁前发出,且不能被阻止。
该信号发出后,所有对象的子对象都会立即被销毁。
另请参见 deleteLater() 和QPointer 。
[static]
bool QObject::disconnect(const QMetaObject::Connection &connection)
断开连接。
如果connection 无效或已断开连接,则什么也不做并返回 false。
另请参阅 connect().
[static]
bool QObject::disconnect(const QObject *sender, const QMetaMethod &signal, const QObject *receiver, const QMetaMethod &method)
断开sender 对象中的signal 与receiver 对象中的method 的连接。如果连接成功断开,则返回true
;否则返回false
。
此函数提供了与disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *method)
相同的可能性,但使用QMetaMethod 表示要断开的信号和方法。
此外,如果出现以下情况,该函数将返回 false,并且不返回任何信号和断开的插槽:
- signal 不是发送者类或其父类成员。
- method 不是接收者类或其父类成员。
- signal 实例表示的不是信号。
注意: 在connect() 和相应的 disconnect() 调用中,使用相同的语法、指针到成员函数或基于字符串的SIGNAL
和SLOT
宏。
为避免不匹配,请存储connect() 返回的连接句柄,并在调用disconnect() 时使用。
注意: 如果queued connection 已断开连接,已安排的事件可能仍在传递,导致接收器在连接断开后被调用。
QMetaMethod() 可用作通配符,意思是 "任何信号 "或 "接收对象中的任何插槽"。同样,nullptr
也可用于receiver ,意思是 "任何接收对象"。在这种情况下,方法也应该是 QMetaMethod()。sender 参数永远不应该是nullptr
。
注意: 断开所有信号槽连接也会断开QObject::destroyed() 信号(如果该信号已连接)。这样做会对依赖该信号清理资源的类产生不利影响。建议只断开应用程序代码连接的特定信号。
另请参阅 disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *method)。
[static]
bool QObject::disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *method)
断开sender 对象中的signal 与receiver 对象中的method 的连接。如果连接成功断开,则返回true
;否则返回false
。
当涉及的任何一个对象被销毁时,信号槽连接就会被删除。
如以下示例所示,disconnect() 通常有三种用法。
- 断开与对象信号相连的所有连接:
disconnect(myObject, nullptr, nullptr, nullptr);
相当于非静态重载函数
myObject->disconnect();
- 断开与特定信号的所有连接:
disconnect(myObject, SIGNAL(mySignal()), nullptr, nullptr);
相当于非静态重载函数
myObject->disconnect(SIGNAL(mySignal()));
- 断开特定接收器:
disconnect(myObject, nullptr, myReceiver, nullptr);
相当于非静态重载函数
myObject->disconnect(myReceiver);
注: 在connect() 和相应的 disconnect() 调用中,使用相同的语法、指针到成员函数或基于字符串的SIGNAL
和SLOT
宏。
为避免不匹配,请存储connect() 返回的连接句柄,并在调用disconnect() 时使用它。
注意: 如果queued connection 连接断开,已安排的事件可能仍在发送,导致接收器在连接断开后被调用。
nullptr
可用作通配符,分别表示 "任何信号"、"任何接收对象 "或 "接收对象中的任何槽"。
sender 永远不能是nullptr
。(一次调用中不能断开多个对象的信号连接)。
如果signal 是nullptr
,则会断开receiver 和method 与任何信号的连接。如果不是,则只断开指定信号的连接。
如果receiver 是nullptr
,则会断开与signal 的任何连接。如果不是,则不会断开receiver 以外对象中的插槽连接。
如果method 是nullptr
,则会断开与receiver 相连的任何连接。如果不是,则只有名为method 的插槽会被断开,其他插槽都不会被断开。如果忽略receiver ,则method 必须是nullptr
,因此不能断开所有对象上的特定命名插槽。
注意: 断开所有信号槽连接也会断开QObject::destroyed() 信号(如果该信号已连接)。这样做会对依赖该信号清理资源的类产生不利影响。建议只断开应用程序代码连接的特定信号。
注意:此函数是线程安全的。
另请参见 connect()。
bool QObject::disconnect(const QObject *receiver, const char *method = nullptr) const
该函数重载了 disconnect()。
断开此对象中的所有信号与receiver'method 的连接。
注: 在connect() 和相应的 disconnect() 调用中使用相同的语法,即指针到成员函数或使用SIGNAL
和SLOT
宏的基于字符串的语法。
为避免不匹配,请存储connect() 返回的连接句柄,并在调用disconnect() 时使用。
注意: 如果queued connection 被断开,已安排的事件可能仍在传递,导致接收器在连接断开后被调用。
当涉及的任何一个对象被销毁时,信号槽连接就会被移除。
bool QObject::disconnect(const char *signal = nullptr, const QObject *receiver = nullptr, const char *method = nullptr) const
该函数重载了 disconnect()。
断开signal 与receiver 的method 的连接。
注: 在connect() 和相应的 disconnect() 调用中使用相同的语法,即指针到成员函数或使用SIGNAL
和SLOT
宏的基于字符串的语法。
为避免不匹配,请存储connect() 返回的连接句柄,并在调用disconnect() 时使用它。
注意: 如果queued connection 被断开,已安排的事件可能仍在传递,导致接收器在连接断开后被调用。
当涉及的任何一个对象被销毁时,信号槽连接就会被移除。
注意: 断开所有信号槽连接也会断开QObject::destroyed() 信号(如果已连接)。这样做会对依赖该信号清理资源的类产生不利影响。建议只断开应用程序代码连接的特定信号。
注意:此函数是线程安全的。
[static]
template <typename PointerToMemberFunction> bool QObject::disconnect(const QObject *sender, PointerToMemberFunction signal, const QObject *receiver, PointerToMemberFunction method)
该函数重载了 disconnect()。
断开对象sender 中的signal 与对象receiver 中的method 的连接。如果连接成功断开,则返回true
;否则返回false
。
当涉及的任何一个对象被销毁时,信号槽连接就会被移除。
如以下示例所示,disconnect() 通常有三种用法。
- 断开与对象信号相连的所有连接:
disconnect(myObject, nullptr, nullptr, nullptr);
- 断开与特定信号连接的所有连接:
disconnect(myObject, &MyObject::mySignal(), nullptr, nullptr);
- 断开特定接收器的连接
disconnect(myObject, nullptr, myReceiver, nullptr);
- 断开特定信号与特定插槽的连接:
nullptr
可用作通配符,分别表示 "任何信号"、"任何接收对象 "或 "接收对象中的任何插槽"。
sender 永远不能是nullptr
。(一次调用中不能断开多个对象的信号连接)。
如果signal 是nullptr
,则会断开receiver 和method 与任何信号的连接。如果不是,则只断开指定信号的连接。
如果receiver 是nullptr
,则会断开与signal 连接的任何信号。如果不是,则只断开指定接收器中的插槽。disconnect() 如果使用非空receiver ,也会断开与receiver 作为上下文对象连接的插槽函数。
如果method 是nullptr
,它将断开与receiver 连接的任何功能。如果不是,只有名为method 的槽会被断开连接,其他槽都不会被断开。如果忽略receiver ,则method 必须是nullptr
,因此不能断开所有对象上的特定命名插槽。
注意: 无法使用此重载断开与函数或 lambda 表达式连接的信号。这是因为无法对它们进行比较。相反,请使用使用QMetaObject::Connection 的重载。
注: 除非method 是nullptr
,否则此函数也不会断开使用基于字符串的connect() 版本建立的连接。要断开此类连接,请使用相应的基于字符串的重载 disconnect()。
注意:此函数是线程安全的。
另请参见 connect()。
[virtual protected]
void QObject::disconnectNotify(const QMetaMethod &signal)
当signal 与该对象中的某些内容断开连接时,将调用此虚函数。
有关如何将signal 与特定信号进行比较的示例,请参阅connectNotify() 。
如果所有信号都已从该对象断开(例如disconnect() 的信号参数是nullptr
),则仅调用一次 disconnectNotify(),而signal 将是无效的QMetaMethod (QMetaMethod::isValid() 返回false
)。
警告: 此函数违反了面向对象的模块化原则。不过,它可能有助于优化对昂贵资源的访问。
警告:此函数违反了面向对象的模块化原则: 此函数由执行断开连接的线程调用,该线程可能与此对象所在的线程不同。调用该函数时,还可能锁定了QObject 内部互斥。因此,不允许从您的重实现中重新输入任何QObject 函数,包括isSignalConnected()。如果您在重实现中锁定了一个互斥项,请确保不要在调用QObject 函数时在其他地方持有该互斥项,否则会导致死锁。
另请参见 disconnect() 和connectNotify()。
void QObject::dumpObjectInfo() const
将此对象的信号连接等信息转到调试输出。
注意: 在 Qt 5.9 之前,此函数不是常量。
另请参阅 dumpObjectTree()。
void QObject::dumpObjectTree() const
向调试输出转存子代树。
注意: 在 Qt 5.9 之前,此函数不是常量。
另请参阅 dumpObjectInfo()。
QList<QByteArray> QObject::dynamicPropertyNames() const
返回使用setProperty() 动态添加到对象中的所有属性的名称。
[virtual]
bool QObject::event(QEvent *e)
此虚函数接收对象发生的事件,如果事件e 已被识别和处理,则返回 true。
可以重新实现 event() 函数来定制对象的行为。
请确保调用父事件类实现来处理所有未处理的事件。
例如
class MyClass : public QWidget { Q_OBJECT public: MyClass(QWidget *parent = nullptr); ~MyClass(); bool event(QEvent* ev) override { if (ev->type() == QEvent::PolishRequest) { // overwrite handling of PolishRequest if any doThings(); return true; } else if (ev->type() == QEvent::Show) { // complement handling of Show if any doThings2(); QWidget::event(ev); return true; } // Make sure the rest of events are handled return QWidget::event(ev); } };
另请参见 installEventFilter()、timerEvent()、QCoreApplication::sendEvent() 和QCoreApplication::postEvent()。
[virtual]
bool QObject::eventFilter(QObject *watched, QEvent *event)
如果该对象已安装为watched 对象的事件过滤器,则可过滤事件。
在重新实现此函数时,如果要过滤掉event ,即停止进一步处理,则返回 true;否则返回 false。
示例
classMainWindow :publicQMainWindow {public: MainWindow();protected:booleventFilter(QObject*obj、 QEvent*ev) override;private: QTextEdit*textEdit; }; MainWindow::MainWindow() { textEdit = newQTextEditsetCentralWidget(textEdit); textEdit->installEventFilter(this); }boolMainWindow::eventFilter(QObject*obj、 QEvent*event) {if(obj==textEdit) {if(event->type()==QEvent按键) { QKeyEvent*keyEvent = static_cast<QKeyEvent*>(event); qDebug() << "Ate key press" << keyEvent->key(); return true; }else{return false; } }else{// 将事件传递给父类 returnQMainWindow::eventFilter(obj,event); } }
请注意,在上面的示例中,未处理的事件被传递给了基类的 eventFilter() 函数,因为基类可能为了自己的内部目的而重新实现了 eventFilter()。
某些事件(如QEvent::ShortcutOverride )必须明确接受(通过调用accept() 来接受),以防止传播。
警告 如果在此函数中删除接收器对象,请确保返回 true。否则,Qt 将把事件转发给已删除的对象,程序可能会崩溃。
另请参阅 installEventFilter().
template <typename T> T QObject::findChild(QAnyStringView name, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const
返回该对象的子对象,该子对象可以被转换为 T 类型,并被称为name ,如果没有这样的对象,则返回nullptr
。如果name 参数为空,则匹配所有对象。空且非空的name 只匹配objectName 为空的对象。除非options 指定了 FindDirectChildrenOnly 选项,否则搜索将递归进行。
如果匹配搜索的子对象不止一个,则返回最直接的祖先。如果有多个最直接祖先,则会返回children() 中的第一个子代。在这种情况下,最好使用findChildren() 获取所有子代的完整列表。
此示例返回parentWidget
的子QPushButton
,名为"button1"
,即使该按钮不是父节点的直接子节点:
QPushButton *button = parentWidget->findChild<QPushButton *>("button1");
此示例返回parentWidget
的子QListWidget
:
QListWidget *list = parentWidget->findChild<QListWidget *>();
此示例返回parentWidget
(其直接父节点)的子节点QPushButton
,名为"button1"
:
QPushButton *button = parentWidget->findChild<QPushButton *>("button1", Qt::FindDirectChildrenOnly);
此示例返回QListWidget
的子代parentWidget
,它的直接父代:
QListWidget *list = parentWidget->findChild<QListWidget *>(Qt::FindDirectChildrenOnly);
注意: 在 6.7 之前的 Qt XML 版本中,此函数将name 作为QString
,而不是QAnyStringView
。
另请参阅 findChildren()。
[since 6.7]
template <typename T> T QObject::findChild(Qt::FindChildOptions options = Qt::FindChildrenRecursively) const
这是一个重载函数。
返回该对象可转换为 T 类型的子对象,如果没有该对象,则返回nullptr
。除非options 指定了 FindDirectChildrenOnly 选项,否则搜索将递归进行。
如果匹配搜索的子节点不止一个,则返回最直接的祖先。如果有多个最直接祖先,则会返回children() 中的第一个子代。在这种情况下,最好使用findChildren() 获取所有子代的完整列表。
此函数在 Qt 6.7 中引入。
另请参阅 findChildren()。
template <typename T> QList<T> QObject::findChildren(QAnyStringView name, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const
返回该对象的所有子对象,其name 给定值可转换为 T 类型;如果没有此类对象,则返回空列表。如果name 参数为空,则匹配所有对象;如果参数为空,则只匹配objectName 为空的对象。除非options 指定了 FindDirectChildrenOnly 选项,否则搜索将递归进行。
下面的示例显示了如何查找指定parentWidget
的子QWidget
的列表,该列表名为widgetname
:
此示例将返回作为parentWidget
子目录的所有QPushButton
s:
QList<QPushButton *> allPButtons = parentWidget.findChildren<QPushButton *>();
此示例将返回作为parentWidget
直接子代的所有QPushButton
s:
QList<QPushButton *> childButtons = parentWidget.findChildren<QPushButton *>(Qt::FindDirectChildrenOnly);
注意: 在 6.7 之前的 Qt XML 版本中,此函数将name 作为QString
,而不是QAnyStringView
。
另请参阅 findChild() 。
[since 6.3]
template <typename T> QList<T> QObject::findChildren(Qt::FindChildOptions options = Qt::FindChildrenRecursively) const
这是一个重载函数。
返回该对象的所有可以转换为 T 类型的子对象,如果没有这样的对象,则返回空列表。除非options 指定了 FindDirectChildrenOnly 选项,否则搜索将递归进行。
此函数在 Qt 6.3 中引入。
另请参见 findChild()。
template <typename T> QList<T> QObject::findChildren(const QRegularExpression &re, Qt::FindChildOptions options = Qt::FindChildrenRecursively) const
此函数重载 findChildren()。
返回该对象的子对象(可被转换为 T 类型),且其名称符合正则表达式re ,如果没有这样的对象,则返回空列表。除非options 指定了 FindDirectChildrenOnly 选项,否则搜索将递归进行。
bool QObject::inherits(const char *className) const
如果该对象是一个继承了className 的类的实例,或者是一个继承了className 的QObject 子类的实例,则返回true
;否则返回false
。
类被视为继承自身。
示例
QTimer *timer = new QTimer; // QTimer inherits QObject timer->inherits("QTimer"); // returns true timer->inherits("QObject"); // returns true timer->inherits("QAbstractButton"); // returns false // QVBoxLayout inherits QObject and QLayoutItem QVBoxLayout *layout = new QVBoxLayout; layout->inherits("QObject"); // returns true layout->inherits("QLayoutItem"); // returns true (even though QLayoutItem is not a QObject)
如果您需要确定一个对象是否是一个特定类的实例,以便对其进行转换,可以考虑使用qobject_cast<Type *>(object)来代替。
另请参阅 metaObject() 和qobject_cast()。
void QObject::installEventFilter(QObject *filterObj)
在此对象上安装事件过滤器filterObj 。例如
monitoredObj->installEventFilter(filterObj);
事件过滤器是一个接收发送到此对象的所有事件的对象。过滤器可以停止事件或将事件转发给此对象。事件过滤器filterObj 通过其eventFilter() 函数接收事件。如果事件应被过滤(即停止),则eventFilter() 函数必须返回 true;否则必须返回 false。
如果在一个对象上安装了多个事件过滤器,则先激活最后安装的过滤器。
如果filterObj 已为该对象安装,则该函数会将其移至最后安装的位置。
下面是一个KeyPressEater
类,它可以捕捉被监控对象的按键操作:
classKeyPressEater :publicQObject { Q_OBJECT ...protected:booleventFilter(QObject*obj、 QEvent*event) override; };boolKeyPressEater::eventFilter(QObject*obj、 QEvent*event) {if(event->type()==QEvent按键) { QKeyEvent*keyEvent = static_cast<QKeyEvent*>(event); qDebug("Ate key press %d", keyEvent->key()); return true; }else{// 标准事件处理 returnQObject::eventFilter(obj,event); } }
下面是如何将其安装到两个部件上:
KeyPressEater *keyPressEater = new KeyPressEater(this); QPushButton *pushButton = new QPushButton(this); QListView *listView = new QListView(this); pushButton->installEventFilter(keyPressEater); listView->installEventFilter(keyPressEater);
例如,QShortcut 类使用这种技术来拦截快捷键的按下。
警告 如果您在eventFilter() 函数中删除了接收器对象,请确保返回 true。如果返回 false,Qt 会将事件发送到已删除的对象,程序将崩溃。
请注意,过滤对象必须与此对象处于同一线程。如果filterObj 在不同的线程中,则此函数不会执行任何操作。如果filterObj 或此对象在调用此函数后被移动到不同的线程中,事件过滤器将不会被调用,直到两个对象再次拥有相同的线程亲和性(它不会被删除)。
另请参见 removeEventFilter()、eventFilter() 和event()。
[since 6.4]
bool QObject::isQuickItemType() const
如果对象是QQuickItem ,则返回true
;否则返回false
。
调用此函数等同于调用inherits("QQuickItem")
,只是速度更快。
此函数在 Qt 6.4 中引入。
[protected]
bool QObject::isSignalConnected(const QMetaMethod &signal) const
如果signal 至少连接了一个接收器,则返回true
,否则返回false
。
signal 必须是此对象的信号成员,否则行为未定义。
static const QMetaMethod valueChangedSignal = QMetaMethod::fromSignal(&MyObject::valueChanged); if (isSignalConnected(valueChangedSignal)) { QByteArray data; data = get_the_value(); // expensive operation emit valueChanged(data); }
正如上面的代码片段所示,使用该函数可以避免昂贵的操作或发出无人监听的信号。
警告 在多线程应用程序中,对该函数的连续调用不能保证产生相同的结果。
警告:此函数违反了面向对象原则: 此函数违反了面向对象的模块化原则。特别是,不得从connectNotify() 或disconnectNotify() 的重载中调用此函数,因为这些函数可能会被任何线程调用。
另请参见 receivers()。
bool QObject::isWidgetType() const
如果对象是一个 widget,则返回true
;否则返回false
。
调用该函数等同于调用inherits("QWidget")
,只是速度更快。
bool QObject::isWindowType() const
如果对象是窗口,则返回true
;否则返回false
。
调用该函数等同于调用inherits("QWindow")
,只是速度更快。
void QObject::killTimer(int id)
杀死定时器标识符为id 的定时器。
定时器事件启动时,定时器标识符由startTimer() 返回。
另请参阅 timerEvent() 和startTimer()。
[since 6.8]
void QObject::killTimer(Qt::TimerId id)
这是一个重载函数。
该函数在 Qt 6.8 中引入。
[virtual]
const QMetaObject *QObject::metaObject() const
返回指向此对象元对象的指针。
元对象包含继承于QObject 的类的相关信息,例如类名、超类名、属性、信号和槽。每个包含Q_OBJECT 宏的QObject 子类都有一个元对象。
信号/槽连接机制和属性系统都需要元对象信息。inherits() 函数也使用元对象。
如果没有指向实际对象实例的指针,但仍想访问某个类的元对象,可以使用staticMetaObject 。
示例:
QObject *obj = new QPushButton; obj->metaObject()->className(); // returns "QPushButton" QPushButton::staticMetaObject.className(); // returns "QPushButton"
另请参见 staticMetaObject 。
bool QObject::moveToThread(QThread *targetThread)
更改此对象及其子对象的线程亲和性,成功后返回true
。如果对象有父对象,则不能移动该对象。事件处理将继续在targetThread 中进行。
要将对象移至主线程,可使用QApplication::instance() 获取指向当前应用程序的指针,然后使用QApplication::thread() 获取应用程序所在的线程。例如
myObject->moveToThread(QApplication::instance()->thread());
如果targetThread 为nullptr
,该对象及其子对象的所有事件处理都将停止,因为它们不再与任何线程相关联。
请注意,该对象的所有活动计时器都将重置。定时器首先在当前线程中停止,然后在targetThread 中重新启动(间隔相同)。因此,在线程间不断移动对象可能会无限期推迟定时器事件。
在改变线程亲和性之前,会向该对象发送QEvent::ThreadChange 事件。您可以通过处理该事件来执行任何特殊处理。需要注意的是,发布到此对象的任何新事件都将在targetThread 中处理,前提是它不是nullptr
:当它是nullptr
时,此对象或其子对象将不再与任何线程相关联,因此无法进行任何事件处理。
警告: 此函数对线程不安全;当前线程必须与当前线程亲和性相同。换句话说,此函数只能将对象从当前线程 "推 "到另一个线程,而不能将对象从任意线程 "拉 "到当前线程。但有一个例外:没有线程亲和性的对象可以被 "拉 "到当前线程。
另请参见 thread().
[private signal]
void QObject::objectNameChanged(const QString &objectName)
该信号在对象名称更改后发出。新的对象名称以objectName 的形式传递。
注意: 这是一个私有信号。可以在信号连接中使用,但用户不能发出。
注: 用于属性objectName 的通知信号。
另请参见 QObject::objectName 。
QObject *QObject::parent() const
返回指向父对象的指针。
QVariant QObject::property(const char *name) const
返回对象name 属性的值。
如果不存在此类属性,则返回的变量无效。
有关所有可用属性的信息通过metaObject() 和dynamicPropertyNames() 提供。
另请参阅 setProperty()、QVariant::isValid()、metaObject() 和dynamicPropertyNames()。
[protected]
int QObject::receivers(const char *signal) const
返回连接到signal 的接收器数量。
由于槽和信号都可以用作信号的接收器,而且相同的连接可以多次进行,因此接收器的数量与该信号的连接数相同。
调用此函数时,可以使用SIGNAL()
宏传递特定信号:
if (receivers(SIGNAL(valueChanged(QByteArray))) > 0) { QByteArray data; get_the_value(&data); // expensive operation emit valueChanged(data); }
如上面的代码片段所示,使用该函数可以避免昂贵的操作或发出无人监听的信号。
警告 在多线程应用程序中,对该函数的连续调用不能保证产生相同的结果。
警告:此函数违反了面向对象原则: 此函数违反了面向对象的模块化原则。特别是,不得从connectNotify() 或disconnectNotify() 的重载中调用此函数,因为这些函数可能会被任何线程调用。
另请参见 isSignalConnected()。
void QObject::removeEventFilter(QObject *obj)
从该对象中删除事件过滤器对象obj 。如果未安装此类事件过滤器,则该请求将被忽略。
销毁该对象时,将自动删除该对象的所有事件过滤器。
删除事件过滤器始终是安全的,即使是在事件过滤器激活期间(即从eventFilter() 函数)。
另请参见 installEventFilter()、eventFilter() 和event()。
[protected]
QObject *QObject::sender() const
如果在由信号激活的槽中调用,则返回指向发送信号的对象的指针;否则返回nullptr
。该指针仅在从该对象的线程上下文调用该函数的槽执行期间有效。
如果发送者被销毁,或槽与发送者的信号断开连接,该函数返回的指针将失效。
警告 此函数违反了面向对象的模块化原则。不过,当许多信号连接到一个槽时,访问发送者可能会很有用。
警告:该函数违反了面向对象的模块化原则: 如上所述,当通过Qt::DirectConnection 从不同于此对象的线程调用槽时,此函数的返回值无效。在这种情况下请勿使用此函数。
另请参见 senderSignalIndex()。
[protected]
int QObject::senderSignalIndex() const
返回调用当前执行槽的信号的元方法索引,该信号是sender() 返回的类的成员。如果在信号激活的槽之外调用,则返回-1。
对于带有默认参数的信号,无论connect() 使用了哪个参数,该函数都将返回带有所有参数的索引。例如,信号destroyed(QObject *obj = \nullptr)
将有两个不同的索引(带参数和不带参数),但该函数将始终返回带参数的索引。这不适用于重载不同参数的信号。
警告 此函数违反了面向对象的模块化原则。不过,当许多信号连接到一个插槽时,访问信号索引可能会很有用。
警告:此函数的返回值不符合面向对象的模块化原则: 当通过Qt::DirectConnection 从不同于此对象线程的线程调用槽时,此函数的返回值无效。在这种情况下请勿使用此函数。
另请参阅 sender()、QMetaObject::indexOfSignal() 和QMetaObject::method()。
void QObject::setObjectName(const QString &name)
将对象名称设置为name 。
注: 属性objectName 的设置函数。
另请参阅 objectName() 。
[since 6.4]
void QObject::setObjectName(QAnyStringView name)
这是一个重载函数。
注: 属性objectName 的设置函数。
此函数在 Qt 6.4 中引入。
void QObject::setParent(QObject *parent)
使对象成为parent 的子对象。
bool QObject::setProperty(const char *name, const QVariant &value)
将对象name 属性的值设置为value 。
如果使用Q_PROPERTY 在类中定义了该属性,则成功时返回 true,否则返回 false。如果没有使用Q_PROPERTY 定义该属性,因此元对象中没有列出该属性,则会将其添加为动态属性并返回 false。
有关所有可用属性的信息通过metaObject() 和dynamicPropertyNames() 提供。
可以使用property() 再次查询动态属性,也可以通过将属性值设置为无效的QVariant 来删除动态属性。更改动态属性的值会导致向对象发送QDynamicPropertyChangeEvent 。
注:以"_q_"开头的动态属性保留给内部使用。
另请参阅 property()、metaObject()、dynamicPropertyNames() 和QMetaProperty::write() 。
[since 6.6]
bool QObject::setProperty(const char *name, QVariant &&value)
该函数重载了 setProperty。
此函数在 Qt 6.6 中引入。
[noexcept]
bool QObject::signalsBlocked() const
如果信号被屏蔽,则返回true
;否则返回false
。
默认情况下不屏蔽信号。
另请参阅 blockSignals() 和QSignalBlocker 。
int QObject::startTimer(int interval, Qt::TimerType timerType = Qt::CoarseTimer)
这是一个重载函数,将启动一个类型为timerType 的计时器,超时时间为interval 毫秒。这相当于调用
startTimer(std::chrono::milliseconds{interval}, timerType);
另请参阅 timerEvent(),killTimer(),QChronoTimer, 和QBasicTimer 。
int QObject::startTimer(std::chrono::nanoseconds interval, Qt::TimerType timerType = Qt::CoarseTimer)
这是一个重载函数。
启动计时器并返回计时器标识符,如果无法启动计时器则返回 0。
在调用killTimer() 之前,每隔interval 就会发生一次定时器事件。如果interval 等于std::chrono::duration::zero()
,则每当没有窗口系统事件需要处理时,定时器事件就会发生一次。
当定时器事件发生时,将调用带有QTimerEvent 事件参数类的虚拟timerEvent() 函数。重新实现该函数可获取定时器事件。
如果有多个定时器在运行,可使用QTimerEvent::id() 方法找出哪个定时器被激活。
示例
classMyObject :publicQObject { Q_OBJECTpublic: MyObject(QObject*parent =nullptr);protected:voidtimerEvent(QTimerEvent*event) override; }; MyObject::MyObject(QObject*父对象): QObject(parent) {using namespacestd::chrono_literals; startTimer(50ms); startTimer(5s); startTimer(10min); startTimer(1h); }voidMyObject::timerEvent(QTimerEvent*event){ qDebug() << "Timer ID:" << event->id(); }
请注意,定时器的精度取决于底层操作系统和硬件。
timerType 参数允许您自定义定时器的精度。有关不同定时器类型的信息,请参阅Qt::TimerType 。大多数平台支持 20 毫秒的精度,有些平台则更高。如果 Qt 无法提供所需的定时器事件数量,它会默默地丢弃一些事件。
QTimer 和QChronoTimer 类提供了一个高级编程接口,可使用单次定时器和定时器信号代替事件。还有一个QBasicTimer 类,它比QChronoTimer 更轻量级,但比直接使用定时器 ID 更简便。
注意: 从 Qt 6.8 开始,interval 的类型是std::chrono::nanoseconds
,在此之前是std::chrono::milliseconds
。这一更改向后兼容 Qt 的旧版本。
注: 在 Qt 6.8 中,QObject 改为使用Qt::TimerId 来表示计时器 ID。出于向后兼容的原因,本方法将TimerId 转换为 int,但您可以使用Qt::TimerId 来检查本方法返回的值,例如:
QObject *obj; ... const auto id = Qt::TimerId{obj->startTimer(100ms)}; if (id != Qt::TimerId::Invalid) // The timer has been started successfully
另请参阅 timerEvent(),killTimer(),QChronoTimer, 和QBasicTimer 。
QThread *QObject::thread() const
返回对象所在的线程。
另请参阅 moveToThread()。
[virtual protected]
void QObject::timerEvent(QTimerEvent *event)
该事件处理程序可在子类中重新实现,以接收对象的定时器事件。
QChronoTimer 定时器事件处理程序提供了更高级别的定时器功能接口,以及更多有关定时器的一般信息。定时器事件通过 参数传递。event
另请参阅 startTimer()、killTimer() 和event()。
[static]
QString QObject::tr(const char *sourceText, const char *disambiguation = nullptr, int n = -1)
返回sourceText 的翻译版本,对于包含复数的字符串,可选择基于disambiguation 字符串和n 的值;否则,如果没有合适的翻译字符串,则返回QString::fromUtf8(sourceText)。
举例说明:
void SpreadSheet::setupMenuBar() { QMenu *fileMenu = menuBar()->addMenu(tr("&File")); ...
如果同一个sourceText 被用于同一上下文中的不同角色,则可在disambiguation ( 默认为nullptr
) 中传递额外的标识字符串。
举例说明
MyWindow::MyWindow() { QLabel *senderLabel = new QLabel(tr("Name:")); QLabel *recipientLabel = new QLabel(tr("Name:", "recipient")); ...
有关 Qt 翻译机制的详细描述,请参阅 "编写翻译源代码",有关歧义消除的信息,请参阅 "歧义消除相同文本"部分。
警告: 只有在调用此方法之前安装了所有翻译器时,此方法才是可重入的。不支持在执行翻译时安装或删除翻译器。这样做可能会导致崩溃或其他不良行为。
另请参阅 QCoreApplication::translate() 和Qt 的国际化。
成员变量文档
const QMetaObject QObject::staticMetaObject
该变量存储类的元对象。
元对象包含继承于QObject 的类的相关信息,如类名、超类名、属性、信号和槽等。每个包含Q_OBJECT 宏的类都有一个元对象。
信号/槽连接机制和属性系统都需要元对象信息。inherits() 函数也使用元对象。
如果您有一个指向对象的指针,可以使用metaObject() 获取与该对象相关的元对象。
示例
QPushButton::staticMetaObject.className(); // returns "QPushButton" QObject *obj = new QPushButton; obj->metaObject()->className(); // returns "QPushButton"
另请参见 metaObject()。
相关非成员
template <typename T> T qobject_cast(QObject *object)
template <typename T> T qobject_cast(const QObject *object)
如果对象是 T 类型(或子类),则返回给定的object ,否则返回nullptr
。如果object 是nullptr
,则也会返回nullptr
。
类 T 必须(直接或间接)继承QObject ,并用Q_OBJECT 宏声明。
类将被视为继承自身。
举例说明:
QObject *obj = new QTimer; // QTimer inherits QObject QTimer *timer = qobject_cast<QTimer *>(obj); // timer == (QObject *)obj QAbstractButton *button = qobject_cast<QAbstractButton *>(obj); // button == nullptr
qobject_cast() 函数的行为类似于标准 C++dynamic_cast()
,其优点是不需要 RTTI 支持,并且可以跨动态链接库边界工作。
qobject_cast() 还可以与接口结合使用。
警告 如果没有使用Q_OBJECT 宏声明 T,该函数的返回值将是未定义的。
另请参见 QObject::inherits()。
QObjectList
[since 6.8]
enum class TimerId
用于表示计时器 ID(例如QTimer 和QChronoTimer )。底层类型是int
。您可以使用qToUnderlying() 将 Qt XML::TimerId 转换为int
。
常量 | 值 | 说明 |
---|---|---|
QObject::TimerId::Invalid | 0 | 代表无操作定时器 ID;其用法取决于上下文,例如,这是QObject::startTimer() 返回的值,表示启动定时器失败;而当定时器处于非活动状态时,QChronoTimer::id() 返回此值,即timer.isActive() 返回false 。 |
该枚举在 Qt 6.8 中引入。
另请参阅 QTimer::id()、QChronoTimer::id() 和QObject::startTimer()。
宏文档
[since 6.7]
QT_NO_CONTEXTLESS_CONNECT
定义此宏将禁用QObject::connect() 的重载,该重载将信号连接到函数器,而无需指定QObject 作为接收器/上下文对象(即QObject::connect() 的 3 参数重载)。
使用无上下文重载容易出错,因为很容易连接到依赖于接收端某些本地状态的函数。如果这种本地状态被破坏,连接就不会自动断开。
此外,此类连接总是直接连接,这可能会在多线程场景中造成问题(例如,如果信号是从另一个线程发出的)。
此宏在 Qt 6.7 中引入。
另请参见 QObject::connect 和Qt::ConnectionType 。
QT_NO_NARROWING_CONVERSIONS_IN_CONNECT
当信号和槽使用基于 PMF 的语法连接时,定义此宏将禁用信号携带的参数和槽接受的参数之间的窄化和浮点积分转换。
另请参见 QObject::connect 。
Q_CLASSINFO(Name, Value)
该宏将额外信息与类关联,可使用QObject::metaObject() 获取。额外信息的形式是Name 字符串和Value 字面字符串。
举例说明:
class MyClass : public QObject { Q_OBJECT Q_CLASSINFO("Author", "Pierre Gendron") Q_CLASSINFO("URL", "http://www.my-organization.qc.ca") public: ... };
Qt 在 Qt D-Bus和 Qt Qml模块。例如,在 C++ 中定义QML Object Types时,可以指定一个属性为默认属性:
Q_CLASSINFO("DefaultProperty", "content")
另请参阅 QMetaObject::classInfo()、使用Qt D-Bus Adaptors 和从 C++ 定义 QML 类型。
Q_EMIT
当您想使用第三方信号/插槽机制来使用 Qt Signals and Slots 时,使用该宏来替换emit
关键字,以发射信号。
该宏通常在no_keywords
与.pro
文件中的CONFIG
变量一起指定时使用,但也可在未指定 no_keywords
时使用。
Q_ENUM(...)
该宏用于在元对象系统中注册枚举类型。它必须放在具有Q_OBJECT 、Q_GADGET 或Q_GADGET_EXPORT 宏的类的枚举声明之后。对于命名空间,请使用Q_ENUM_NS() 代替。
例如
class MyClass : public QObject { Q_OBJECT public: MyClass(QObject *parent = nullptr); ~MyClass(); enum Priority { High, Low, VeryHigh, VeryLow }; Q_ENUM(Priority) void setPriority(Priority priority); Priority priority() const; };
使用 Q_ENUM 声明的枚举将在外层QMetaObject 中注册QMetaEnum 。您也可以使用QMetaEnum::fromType() 来获取QMetaEnum 。
已注册的枚举也会自动注册到 Qt XML 元类型系统中,使QMetaType 无需使用Q_DECLARE_METATYPE() 就能知道它们。这将启用一些有用的功能;例如,如果在QVariant 中使用,可以将它们转换为字符串。同样,将它们传递给QDebug 将打印出它们的名称。
请注意,枚举值是以带符号int
的形式存储在元对象系统中的。使用超出int
有效值范围的值注册枚举,将导致溢出,并可能在通过元对象系统访问它们时产生未定义的行为。例如,QML 就是通过元对象系统访问已注册的枚举。
另请参阅 Qt 的属性系统。
Q_ENUM_NS(...)
该宏用于在元对象系统中注册枚举类型。它必须放在具有Q_NAMESPACE 宏的命名空间的枚举声明之后。它的作用与Q_ENUM 相同,只是在名称空间中。
使用 Q_ENUM_NS 声明的枚举,其QMetaEnum 注册在外层QMetaObject 中。您也可以使用QMetaEnum::fromType() 来获取QMetaEnum 。
已注册的枚举也会自动注册到 Qt XML 元类型系统中,使QMetaType 无需使用Q_DECLARE_METATYPE() 就能知道它们。这将启用一些有用的功能;例如,如果在QVariant 中使用,可以将它们转换为字符串。同样,将它们传递给QDebug 将打印出它们的名称。
请注意,枚举值是以带符号int
的形式存储在元对象系统中的。使用超出int
有效值范围的值注册枚举,将导致溢出,并可能在通过元对象系统访问它们时产生未定义的行为。例如,QML 就是通过元对象系统访问已注册的枚举。
另请参阅 Qt 的属性系统。
Q_FLAG(...)
该宏向元对象系统注册一个flags type 。它通常用于类定义中,以声明给定枚举的值可用作标志,并使用比特 OR 运算符进行组合。对于命名空间,请使用Q_FLAG_NS() 代替。
宏必须放在枚举声明之后。标志类型的声明使用Q_DECLARE_FLAGS() 宏。
例如,在QItemSelectionModel 中,SelectionFlags 标志的声明方式如下:
class QItemSelectionModel : public QObject { Q_OBJECT public: ... enum SelectionFlag { NoUpdate = 0x0000, Clear = 0x0001, Select = 0x0002, Deselect = 0x0004, Toggle = 0x0008, Current = 0x0010, Rows = 0x0020, Columns = 0x0040, SelectCurrent = Select | Current, ToggleCurrent = Toggle | Current, ClearAndSelect = Clear | Select }; Q_DECLARE_FLAGS(SelectionFlags, SelectionFlag) Q_FLAG(SelectionFlags) ... }
注意: Q_FLAG 宏负责在元对象系统中注册单个标志值,因此无需在该宏之外使用Q_ENUM() 。
另请参阅 Qt 的属性系统。
Q_FLAG_NS(...)
该宏用于在元对象系统中注册一个flags type 。它用于包含Q_NAMESPACE 宏的命名空间,以声明给定枚举的值可用作标志,并可使用比特 OR 运算符进行组合。它与Q_FLAG 相同,只是在命名空间中使用。
宏必须放在枚举声明之后。
注意: Q_FLAG_NS 宏负责在元对象系统中注册单个标志值,因此无需在该宏之外使用Q_ENUM_NS() 。
另请参阅 Qt 的属性系统。
Q_GADGET
Q_GADGET 宏是Q_OBJECT 宏的精简版,适用于不继承于QObject 但仍希望使用QMetaObject 提供的某些反射功能的类。
注意: 该宏扩展以private
: 访问指定符结束。如果在该宏之后立即声明成员,这些成员也将是私有的。若要在宏之后添加公共(或受保护)成员,请使用public:
(或protected:
)访问指定符。
Q_GADGET 可以有Q_ENUM 、Q_PROPERTY 和Q_INVOKABLE ,但不能有信号或插槽。
Q_GADGET 使一个类成员staticMetaObject
可用。staticMetaObject
属于QMetaObject 类型,可访问用Q_ENUM 声明的枚举。
另请参见 Q_GADGET_EXPORT 。
[since 6.3]
Q_GADGET_EXPORT(EXPORT_MACRO)
Q_GADGET_EXPORT 宏的工作原理与Q_GADGET 宏完全相同。不过,staticMetaObject
变量(参见Q_GADGET )是用所提供的EXPORT_MACRO 限定符来声明的。如果对象需要从动态链接库中导出,但外层类作为一个整体不需要导出(例如,因为它主要由内联函数组成),这个宏就很有用。
注意: 该宏扩展以private
: 访问规范结束。如果在该宏之后立即声明成员,这些成员也将是私有的。要在宏后面添加公共(或受保护)成员,请使用public:
(或protected:
) 访问指定符。
例如
class Point { Q_GADGET_EXPORT(EXPORT_MACRO) Q_PROPERTY(int x MEMBER x) Q_PROPERTY(int y MEMBER y) ~~~
此宏在 Qt 6.3 中引入。
Q_INTERFACES(...)
该宏告诉 Qt 类实现了哪些接口。这在实现插件时使用。
另请参阅 Q_DECLARE_INTERFACE(),Q_PLUGIN_METADATA(), 以及如何创建 Qt 插件。
Q_INVOKABLE
将此宏应用于成员函数的声明,以便通过元对象系统调用这些函数。宏写在返回类型之前,如下例所示:
class Window : public QWidget { Q_OBJECT public: Window(); void normalMethod(); Q_INVOKABLE void invokableMethod(); };
使用 Q_INVOKABLE 标记了invokableMethod()
函数,使其在元对象系统中注册,并能使用QMetaObject::invokeMethod() 进行调用。由于normalMethod()
函数没有以这种方式注册,因此无法使用QMetaObject::invokeMethod() 进行调用。
如果一个可调用的成员函数返回一个指向QObject 或QObject 子类的指针,并且是从 QML 调用的,则适用特殊的所有权规则。更多信息,请参阅QML 和 C++ 之间的数据类型转换(Data Type Conversion Between QML and C++)。
[since 6.0]
Q_MOC_INCLUDE
Q_MOC_INCLUDE 宏可以在类内部或外部使用,并告诉Meta Object 编译器添加一个包含。
// Put this in your code and the generated code will include this header. Q_MOC_INCLUDE("myheader.h")
如果用作属性或信号/插槽参数的类型是向前声明的,那么这个宏就非常有用。
此宏在 Qt 6.0 中引入。
Q_NAMESPACE
Q_NAMESPACE 宏可用于为命名空间添加QMetaObject 功能。
Q_NAMESPACE 可以有Q_CLASSINFO,Q_ENUM_NS,Q_FLAG_NS ,但不能有Q_ENUM,Q_FLAG,Q_PROPERTY,Q_INVOKABLE, 信号或槽。
Q_NAMESPACE 提供一个外部变量staticMetaObject
。staticMetaObject
属于QMetaObject 类型,可访问用Q_ENUM_NS/Q_FLAG_NS 声明的枚举。
例如
namespace test { Q_NAMESPACE ...
另请参见 Q_NAMESPACE_EXPORT 。
Q_NAMESPACE_EXPORT(EXPORT_MACRO)
Q_NAMESPACE_EXPORT 宏可用于为命名空间添加QMetaObject 功能。
它的工作原理与Q_NAMESPACE 宏完全相同。不过,在命名空间中定义的外部staticMetaObject
变量是用所提供的EXPORT_MACRO 限定符声明的。如果需要从动态链接库中导出对象,这将非常有用。
例如
namespace test { Q_NAMESPACE_EXPORT(EXPORT_MACRO) ...
另请参阅 Q_NAMESPACE 和创建共享库。
Q_OBJECT
Q_OBJECT 宏用于启用元对象功能,如动态属性、信号和插槽。
您可以将 Q_OBJECT 宏添加到类定义的任何部分,这些部分需要声明自己的信号和插槽,或使用 Qt 元对象系统提供的其他服务。
注意: 该宏扩展以private
: 访问指定符结束。如果在此宏之后立即声明成员,这些成员也将是私有的。要在宏后面添加公共(或受保护)成员,请使用public:
(或protected:
) 访问指定符。
示例
#include <QObject> class Counter : public QObject { Q_OBJECT // Note. The Q_OBJECT macro starts a private section. // To declare public members, use the 'public:' access modifier. public: Counter() { m_value = 0; } int value() const { return m_value; } public slots: void setValue(int value); signals: void valueChanged(int newValue); private: int m_value; };
注意: 该宏要求类是QObject 的子类。使用Q_GADGET 或Q_GADGET_EXPORT 代替 Q_OBJECT,可以在不是QObject 子类的类中启用元对象系统对枚举的支持。
Q_PROPERTY(...)
该宏用于在继承QObject 的类中声明属性。属性的行为类似于类的数据成员,但它们具有可通过元对象系统访问的附加功能。
Q_PROPERTY(type name (READ getFunction [WRITE setFunction] | MEMBER memberName [(READ getFunction | WRITE setFunction)]) [RESET resetFunction] [NOTIFY notifySignal] [REVISION int | REVISION(int[, int])] [DESIGNABLE bool] [SCRIPTABLE bool] [STORED bool] [USER bool] [BINDABLE bindableProperty] [CONSTANT] [FINAL] [REQUIRED])
属性名称、类型和READ
函数是必需的。类型可以是QVariant 支持的任何类型,也可以是用户定义的类型。其他项目是可选的,但WRITE
函数是常用的。除USER
之外,其他属性默认为 true,而 默认为 false。
例如
Q_PROPERTY(QString title READ title WRITE setTitle USER true)
有关如何使用该宏的更多细节,以及使用该宏的更详细示例,请参阅Qt 的属性系统讨论。
另请参阅 Qt 的属性系统。
Q_REVISION
将此宏应用于成员函数的声明,以便在元对象系统中使用修订号对其进行标记。宏写在返回类型之前,如下例所示:
class Window : public QWidget { Q_OBJECT Q_PROPERTY(int normalProperty READ normalProperty) Q_PROPERTY(int newProperty READ newProperty REVISION(2, 1)) public: Window(); int normalProperty(); int newProperty(); public slots: void normalMethod(); Q_REVISION(2, 1) void newMethod(); };
当使用元对象系统向另一个 API 动态公开对象时,这个宏非常有用,因为你可以匹配另一个 API 的多个版本所期望的版本。请看以下简化示例:
Window window; int expectedRevision = 0; const QMetaObject *windowMetaObject = window.metaObject(); for (int i=0; i < windowMetaObject->methodCount(); i++) if (windowMetaObject->method(i).revision() <= expectedRevision) exposeMethod(windowMetaObject->method(i)); for (int i=0; i < windowMetaObject->propertyCount(); i++) if (windowMetaObject->property(i).revision() <= expectedRevision) exposeProperty(windowMetaObject->property(i));
使用与上例相同的 Window 类,只有当预期版本为2.1
或更高时,才会在此代码中公开 newProperty 和 newMethod。
如果没有标记,所有方法都会被认为处于修订版0
中,因此Q_REVISION(0)
或Q_REVISION(0, 0)
标记无效,会被忽略。
您可以向Q_REVISION
传递一个或两个整数参数。如果只传递一个参数,则仅表示次版本。这意味着主版本未指定。如果传递两个参数,第一个参数表示主要版本,第二个参数表示次要版本。
元对象系统本身不使用该标记。目前只有QtQml 模块使用。
有关更通用的字符串标记,请参见QMetaMethod::tag()
另请参见 QMetaMethod::revision()。
Q_SET_OBJECT_NAME(Object)
该宏将Object 指定为objectName "对象"。
Object 是否是指针并不重要,宏会自己计算出来。
另请参见 QObject::objectName()。
Q_SIGNAL
这是一个附加宏,允许将单个函数标记为信号。它非常有用,尤其是当您使用的第三方源代码解析器不理解signals
或Q_SIGNALS
组时。
当您想使用第三方信号/插槽机制来使用 Qt Signals 和 Slots 时,使用该宏来替换类声明中的signals
关键字。
该宏通常在no_keywords
与.pro
文件中的CONFIG
变量一起指定时使用,但也可在未指定 no_keywords
时使用。
Q_SIGNALS
当您想使用第三方信号/插槽机制来使用 Qt Signals and Slots 时,使用该宏来替换类声明中的signals
关键字。
该宏通常在no_keywords
与.pro
文件中的CONFIG
变量一起指定时使用,但也可在未指定 no_keywords
时使用。
Q_SLOT
这是一个附加宏,允许将单个函数标记为槽。它非常有用,尤其是当您使用的第三方源代码解析器不理解slots
或Q_SLOTS
组时。
当您想使用第三方信号/槽机制来使用 Qt Signals and Slots 时,使用该宏来替换类声明中的slots
关键字。
该宏通常在no_keywords
与.pro
文件中的CONFIG
变量一起指定时使用,但也可在未指定 no_keywords
时使用。
Q_SLOTS
当您想使用第三方信号/插槽机制来使用 Qt Signals and Slots 时,使用该宏来替换类声明中的slots
关键字。
该宏通常在no_keywords
与.pro
文件中的CONFIG
变量一起指定时使用,但也可在未指定 no_keywords
时使用。
© 2025 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.