Don't declare type 'id' in the global namespace in a public header
It's not necessary, and it breaks the qttools build (where we have a global variable named 'id'), and thus will most certainly build a lot of existing user code. Amends e47c22480fe84c100019cd92d0296f0dd2a7f3f1. Change-Id: I97a91c2cb23fdae65143cf14c81570cf88d529d5 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
This commit is contained in:
parent
c164b75c17
commit
aa0a53fc19
@ -530,7 +530,7 @@ inline QDebug operator<<(QDebug debug, QKeyCombination combination)
|
||||
|
||||
QT_END_NAMESPACE
|
||||
Q_FORWARD_DECLARE_CF_TYPE(CFString);
|
||||
typedef struct objc_object *id;
|
||||
struct objc_object;
|
||||
Q_FORWARD_DECLARE_OBJC_CLASS(NSObject);
|
||||
QT_FOR_EACH_CORE_FOUNDATION_TYPE(QT_FORWARD_DECLARE_CF_TYPE)
|
||||
QT_FOR_EACH_MUTABLE_CORE_FOUNDATION_TYPE(QT_FORWARD_DECLARE_MUTABLE_CF_TYPE)
|
||||
@ -555,7 +555,10 @@ QT_BEGIN_NAMESPACE
|
||||
}
|
||||
|
||||
// Defined in qcore_mac_objc.mm
|
||||
Q_CORE_EXPORT QDebug operator<<(QDebug, id obj);
|
||||
#if defined(__OBJC__)
|
||||
Q_CORE_EXPORT QDebug operator<<(QDebug, id);
|
||||
#endif
|
||||
Q_CORE_EXPORT QDebug operator<<(QDebug, objc_object *);
|
||||
Q_CORE_EXPORT QDebug operator<<(QDebug, const NSObject *);
|
||||
Q_CORE_EXPORT QDebug operator<<(QDebug, CFStringRef);
|
||||
|
||||
|
@ -10,3 +10,7 @@ qt_internal_add_test(tst_qdebug
|
||||
PUBLIC_LIBRARIES
|
||||
Qt::Concurrent
|
||||
)
|
||||
|
||||
if (APPLE)
|
||||
target_compile_options(tst_qdebug PRIVATE -x objective-c++)
|
||||
endif()
|
||||
|
@ -52,6 +52,10 @@ struct ConvertsToQVariant {
|
||||
};
|
||||
static_assert(!QTypeTraits::has_ostream_operator_v<QDebug, ConvertsToQVariant>);
|
||||
|
||||
#if defined(Q_OS_DARWIN)
|
||||
#include <objc/runtime.h>
|
||||
#include <Foundation/Foundation.h>
|
||||
#endif
|
||||
|
||||
class tst_QDebug: public QObject
|
||||
{
|
||||
@ -88,6 +92,12 @@ private slots:
|
||||
void threadSafety() const;
|
||||
void toString() const;
|
||||
void noQVariantEndlessRecursion() const;
|
||||
#if defined(Q_OS_DARWIN)
|
||||
void objcInCppMode_data() const;
|
||||
void objcInCppMode() const;
|
||||
void objcInObjcMode_data() const;
|
||||
void objcInObjcMode() const;
|
||||
#endif
|
||||
};
|
||||
|
||||
void tst_QDebug::assignment() const
|
||||
@ -873,6 +883,69 @@ void tst_QDebug::noQVariantEndlessRecursion() const
|
||||
qDebug() << var;
|
||||
}
|
||||
|
||||
#if defined(Q_OS_DARWIN)
|
||||
|
||||
@interface MyObjcClass : NSObject
|
||||
@end
|
||||
|
||||
@implementation MyObjcClass : NSObject
|
||||
- (NSString *)description
|
||||
{
|
||||
return @"MyObjcClass is the best";
|
||||
}
|
||||
@end
|
||||
|
||||
void tst_QDebug::objcInCppMode_data() const
|
||||
{
|
||||
QTest::addColumn<objc_object *>("object");
|
||||
QTest::addColumn<QString>("message");
|
||||
|
||||
QTest::newRow("nil") << static_cast<objc_object*>(nullptr) << QString::fromLatin1("(null)");
|
||||
|
||||
// Not an NSObject subclass
|
||||
auto *nsproxy = reinterpret_cast<objc_object *>(class_createInstance(objc_getClass("NSProxy"), 0));
|
||||
QTest::newRow("NSProxy") << nsproxy << QString::fromLatin1("<NSProxy: 0x%1>").arg(uintptr_t(nsproxy), 1, 16);
|
||||
|
||||
// Plain NSObject
|
||||
auto *nsobject = reinterpret_cast<objc_object *>(class_createInstance(objc_getClass("NSObject"), 0));
|
||||
QTest::newRow("NSObject") << nsobject << QString::fromLatin1("<NSObject: 0x%1>").arg(uintptr_t(nsobject), 1, 16);
|
||||
|
||||
auto str = QString::fromLatin1("foo");
|
||||
QTest::newRow("NSString") << reinterpret_cast<objc_object*>(str.toNSString()) << str;
|
||||
|
||||
// Custom debug description
|
||||
QTest::newRow("MyObjcClass") << reinterpret_cast<objc_object*>([[MyObjcClass alloc] init])
|
||||
<< QString::fromLatin1("MyObjcClass is the best");
|
||||
}
|
||||
|
||||
void tst_QDebug::objcInCppMode() const
|
||||
{
|
||||
QFETCH(objc_object *, object);
|
||||
QFETCH(QString, message);
|
||||
|
||||
MessageHandlerSetter mhs(myMessageHandler);
|
||||
{ qDebug() << object; }
|
||||
|
||||
QCOMPARE(s_msg, message);
|
||||
}
|
||||
|
||||
void tst_QDebug::objcInObjcMode_data() const
|
||||
{
|
||||
objcInCppMode_data();
|
||||
}
|
||||
|
||||
void tst_QDebug::objcInObjcMode() const
|
||||
{
|
||||
QFETCH(objc_object *, object);
|
||||
QFETCH(QString, message);
|
||||
|
||||
MessageHandlerSetter mhs(myMessageHandler);
|
||||
{ qDebug() << static_cast<id>(object); }
|
||||
|
||||
QCOMPARE(s_msg, message);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Should compile: instentiation of unrelated operator<< should not cause cause compilation
|
||||
// error in QDebug operators (QTBUG-47375)
|
||||
class TestClassA {};
|
||||
|
Loading…
x
Reference in New Issue
Block a user