您的位置:首页 > 移动开发 > Objective-C

QObject源码分析

2016-05-22 10:08 471 查看
/**
*QObject.h
* QObjectData存放着当前对象,父对象,子对象链表,元对象,元对象数据,以及一些标志位
*/
class Q_CORE_EXPORT QObjectData {
public:
virtual ~QObjectData() = 0;
QObject *q_ptr;                         /*QObject指针*/
QObject *parent;                        /*父对象指针*/
QObjectList children;                   /*子对象链表*/

uint isWidget : 1;                      /*是否为Widget,为1位,0和1*/
uint blockSig : 1;                      /*是否信号阻塞,为1位,0和1*/
uint wasDeleted : 1;                    /*是否已经删除,为1位,0和1*/
uint isDeletingChildren : 1;            /*是否子对象链表删除,为1位,0和1*/
uint sendChildEvents : 1;               /*发送子对象事件,为1位,0和1*/
uint receiveChildEvents : 1;            /*接收子对象事件,为1位,0和1*/
uint isWindow : 1; //for QWindow        /*是否为Window,为1位,0和1*/
uint unused : 25;                       /*未使用*/
int postedEvents;                       /*发布事件*/
QDynamicMetaObjectData *metaObject;     /*动态元对象数据*/
QMetaObject *dynamicMetaObject() const; //assert dynamic  /*元对象*/
};

/**
*QObject_p.h
*ExtraData结构存放着用户数据,属性名,属性值,定时器运行时间,事件过滤,对象名
*QObjectPrivate存放着QObjectConnectionListVector,向量中存放着链表,链表中存放着信号与槽
*也存放ExtraData,QThreadData,QObjectConnectionListVector
*/
class Q_CORE_EXPORT QObjectPrivate : public QObjectData
{
Q_DECLARE_PUBLIC(QObject)
public:
struct ExtraData
{
ExtraData() {}
#ifndef QT_NO_USERDATA
QVector<QObjectUserData *> userData;            /*用户数据*/
#endif
QList<QByteArray> propertyNames;                /*属性名*/
QList<QVariant> propertyValues;                 /*属性值*/
QVector<int> runningTimers;                     /*定时器运行时间*/
QList<QPointer<QObject> > eventFilters;         /*事件过滤链表*/
QString objectName;                             /*对象名*/
};

typedef void (*StaticMetaCallFunction)(QObject *, QMetaObject::Call, int, void **);

/*信号槽*/
struct Connection
{
QObject *sender;                                    /*发送者*/
QObject *receiver;                                  /*接收者*/
union {
StaticMetaCallFunction callFunction;
QtPrivate::QSlotObjectBase *slotObj;
};
// The next pointer for the singly-linked ConnectionList
Connection *nextConnectionList;                     /*下一个链表指针*/
//senders linked list
Connection *next;                                   /*下一个Connection对象指针*/
Connection **prev;                                  /*上一个Connection对象双重指针*/
QAtomicPointer<const int> argumentTypes;            /*参数类型模板*/
QAtomicInt ref_;
ushort method_offset;
ushort method_relative;
uint signal_index : 27; // In signal range (see QObjectPrivate::signalIndex())      /*信号索引*/
ushort connectionType : 3; // 0 == auto, 1 == direct, 2 == queued, 4 == blocking    /*信号槽链接类型*/
ushort isSlotObject : 1;
ushort ownArgumentTypes : 1;                                                        /*自己的参数类型*/
Connection() : nextConnectionList(0), ref_(2), ownArgumentTypes(true) {
//ref_ is 2 for the use in the internal lists, and for the use in QMetaObject::Connection
}
~Connection();
int method() const { Q_ASSERT(!isSlotObject); return method_offset + method_relative; }
void ref() { ref_.ref(); }
void deref() {
if (!ref_.deref()) {
Q_ASSERT(!receiver);
delete this;
}
}
};
// ConnectionList is a singly-linked list
/*Connection链表*/
struct ConnectionList {
ConnectionList() : first(0), last(0) {}
Connection *first;
Connection *last;
};
/*发送者*/
struct Sender
{
QObject *sender;
int signal;
int ref;
};

QObjectPrivate(int version = QObjectPrivateVersion);
virtual ~QObjectPrivate();
void deleteChildren();

void setParent_helper(QObject *);
void moveToThread_helper();
void setThreadData_helper(QThreadData *currentData, QThreadData *targetData);
void _q_reregisterTimers(void *pointer);

bool isSender(const QObject *receiver, const char *signal) const;
QObjectList receiverList(const char *signal) const;
QObjectList senderList() const;

void addConnection(int signal, Connection *c);
void cleanConnectionLists();

static inline Sender *setCurrentSender(QObject *receiver,
Sender *sender);
static inline void resetCurrentSender(QObject *receiver,
Sender *currentSender,
Sender *previousSender);

static QObjectPrivate *get(QObject *o) {
return o->d_func();
}

int signalIndex(const char *signalName, const QMetaObject **meta = 0) const;
inline bool isSignalConnected(uint signalIdx) const;

// To allow abitrary objects to call connectNotify()/disconnectNotify() without making
// the API public in QObject. This is used by QQmlNotifierEndpoint.
inline void connectNotify(const QMetaMethod &signal);
inline void disconnectNotify(const QMetaMethod &signal);

template <typename Func1, typename Func2>
static inline QMetaObject::Connection connect(const typename QtPrivate::FunctionPointer<Func1>::Object *sender, Func1 signal,
const typename QtPrivate::FunctionPointer<Func2>::Object *receiverPrivate, Func2 slot,
Qt::ConnectionType type = Qt::AutoConnection);

template <typename Func1, typename Func2>
static inline bool disconnect(const typename QtPrivate::FunctionPointer<Func1>::Object *sender, Func1 signal,
const typename QtPrivate::FunctionPointer<Func2>::Object *receiverPrivate, Func2 slot);

static QMetaObject::Connection connectImpl(const QObject *sender, int signal_index,
const QObject *receiver, void **slot,
QtPrivate::QSlotObjectBase *slotObj, Qt::ConnectionType type,
const int *types, const QMetaObject *senderMetaObject);
static QMetaObject::Connection connect(const QObject *sender, int signal_index, QtPrivate::QSlotObjectBase *slotObj, Qt::ConnectionType type);
static bool disconnect(const QObject *sender, int signal_index, void **slot);
public:
ExtraData *extraData;    // extra data set by the user
QThreadData *threadData; // id of the thread that owns the object

QObjectConnectionListVector *connectionLists;

Connection *senders;     // linked list of connections connected to this object
Sender *currentSender;   // object currently activating the object
mutable quint32 connectedSignals[2];

union {
QObject *currentChildBeingDeleted;
QAbstractDeclarativeData *declarativeData; //extra data used by the declarative module
};

// these objects are all used to indicate that a QObject was deleted
// plus QPointer, which keeps a separate list
QAtomicPointer<QtSharedPointer::ExternalRefCountData> sharedRefcount;
};

/**
*QObect.cpp
*用向量保存着ConnectionList
*/
class QObjectConnectionListVector : public QVector<QObjectPrivate::ConnectionList>
{
public:
bool orphaned; //the QObject owner of this vector has been destroyed while the vector was inUse
bool dirty; //some Connection have been disconnected (their receiver is 0) but not removed from the list yet
int inUse; //number of functions that are currently accessing this object or its connections
QObjectPrivate::ConnectionList allsignals;

QObjectConnectionListVector()
: QVector<QObjectPrivate::ConnectionList>(), orphaned(false), dirty(false), inUse(0)
{ }

QObjectPrivate::ConnectionList &operator[](int at)
{
if (at < 0)
return allsignals;
return QVector<QObjectPrivate::ConnectionList>::operator[](at);
}
};

/**
*QObject.cpp
*/
class Q_CORE_EXPORT QObject
{
Q_DECLARE_PRIVATE(QObject) /*得到QObjectData指针*/
/*
Q_DECLARE_PRIVATE宏定义为:
#define Q_DECLARE_PRIVATE(Class) \
inline Class##Private* d_func() { return reinterpret_cast<Class##Private *>(qGetPtrHelper(d_ptr)); } \
inline const Class##Private* d_func() const { return reinterpret_cast<const Class##Private *>(qGetPtrHelper(d_ptr)); } \
friend class Class##Private;
*/
/*构造函数实例化QObjectPrivate对象并初始化*/
QObject::QObject(QObject *parent)
: d_ptr(new QObjectPrivate)
{
Q_D(QObject);
d_ptr->q_ptr = this; /*QObjectData*/
d->threadData = (parent && !parent->thread()) ? parent->d_func()->threadData : QThreadData::current(); /*QObjectPrivate*/
d->threadData->ref();
if (parent) {
QT_TRY {
if (!check_parent_thread(parent, parent ? parent->d_func()->threadData : 0, d->threadData))
parent = 0;
setParent(parent);
} QT_CATCH(...) {
d->threadData->deref();
QT_RETHROW;
}
}
qt_addObject(this);
if (Q_UNLIKELY(qtHookData[QHooks::AddQObject]))
reinterpret_cast<QHooks::AddQObjectCallback>(qtHookData[QHooks::AddQObject])(this);
}

};
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: