1 /****************************************************************************
3 ** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/legal
6 ** This file is part of the QtQml module of the Qt Toolkit.
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia. For licensing terms and
14 ** conditions see http://qt.digia.com/licensing. For further information
15 ** use the contact form at http://qt.digia.com/contact-us.
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 2.1 requirements
23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
25 ** In addition, as a special exception, Digia gives you certain additional
26 ** rights. These rights are described in the Digia Qt LGPL Exception
27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
29 ** GNU General Public License Usage
30 ** Alternatively, this file may be used under the terms of the GNU
31 ** General Public License version 3.0 as published by the Free Software
32 ** Foundation and appearing in the file LICENSE.GPL included in the
33 ** packaging of this file. Please review the following information to
34 ** ensure the GNU General Public License version 3.0 requirements will be
35 ** met: http://www.gnu.org/copyleft/gpl.html.
40 ****************************************************************************/
42 #ifndef QQUICKVISUALDATAMODEL_P_P_H
43 #define QQUICKVISUALDATAMODEL_P_P_H
45 #include "qquickvisualdatamodel_p.h"
47 #include "qquickvisualadaptormodel_p.h"
49 #include <QtQml/qqmlcontext.h>
50 #include <QtQml/qqmlincubator.h>
52 #include <private/qqmlopenmetaobject_p.h>
58 // This file is not part of the Qt API. It exists purely as an
59 // implementation detail. This header file may change from version to
60 // version without notice, or even be removed.
67 typedef QQuickListCompositor Compositor;
69 class QQuickVisualDataModelAttachedMetaObject;
71 class QQuickVisualDataModelItemMetaType : public QQmlRefCount
74 QQuickVisualDataModelItemMetaType(QV8Engine *engine, QQuickVisualDataModel *model, const QStringList &groupNames);
75 ~QQuickVisualDataModelItemMetaType();
77 void initializeMetaObject();
78 void initializeConstructor();
80 int parseGroups(const QStringList &groupNames) const;
81 int parseGroups(const v8::Local<v8::Value> &groupNames) const;
83 static void release_index(v8::Persistent<v8::Value> object, void *parameter);
84 static void release_model(v8::Persistent<v8::Value> object, void *parameter);
86 static v8::Handle<v8::Value> get_model(v8::Local<v8::String>, const v8::AccessorInfo &info);
87 static v8::Handle<v8::Value> get_groups(v8::Local<v8::String>, const v8::AccessorInfo &info);
88 static void set_groups(
89 v8::Local<v8::String>, v8::Local<v8::Value> value, const v8::AccessorInfo &info);
90 static v8::Handle<v8::Value> get_member(v8::Local<v8::String>, const v8::AccessorInfo &info);
91 static void set_member(
92 v8::Local<v8::String>, v8::Local<v8::Value> value, const v8::AccessorInfo &info);
93 static v8::Handle<v8::Value> get_index(v8::Local<v8::String>, const v8::AccessorInfo &info);
95 QQmlGuard<QQuickVisualDataModel> model;
97 QV8Engine * const v8Engine;
98 QQuickVisualDataModelAttachedMetaObject *metaObject;
99 const QStringList groupNames;
100 v8::Persistent<v8::ObjectTemplate> constructor;
103 class QQuickVisualAdaptorModel;
104 class QVDMIncubationTask;
106 class QQuickVisualDataModelItem : public QObject, public QV8ObjectResource
109 Q_PROPERTY(int index READ modelIndex NOTIFY modelIndexChanged)
110 Q_PROPERTY(QObject *model READ modelObject CONSTANT)
111 V8_RESOURCE_TYPE(VisualDataItemType)
113 QQuickVisualDataModelItem(QQuickVisualDataModelItemMetaType *metaType, int modelIndex);
114 ~QQuickVisualDataModelItem();
116 void referenceObject() { ++objectRef; }
117 bool releaseObject() { return --objectRef == 0 && !(groups & Compositor::PersistedFlag); }
118 bool isObjectReferenced() const { return objectRef != 0 || (groups & Compositor::PersistedFlag); }
120 bool isReferenced() const {
123 || ((groups & Compositor::UnresolvedFlag) && (groups & Compositor::GroupMask));
128 QObject *modelObject() { return this; }
131 QQmlComponent *component,
133 QQmlContextData *context,
134 QQmlContextData *forContext);
135 void destroyObject();
137 static QQuickVisualDataModelItem *dataForObject(QObject *object);
139 int groupIndex(Compositor::Group group);
141 int modelIndex() const { return index; }
142 void setModelIndex(int idx) { index = idx; emit modelIndexChanged(); }
144 virtual v8::Handle<v8::Value> get() { return engine->newQObject(this); }
146 virtual void setValue(const QString &role, const QVariant &value) { Q_UNUSED(role); Q_UNUSED(value); }
147 virtual bool resolveIndex(const QQuickVisualAdaptorModel &, int) { return false; }
149 QQuickVisualDataModelItemMetaType * const metaType;
150 QQmlContextData *contextData;
152 QQuickVisualDataModelAttached *attached;
153 QVDMIncubationTask *incubationTask;
161 void modelIndexChanged();
164 void objectDestroyed(QObject *);
168 class QQuickVisualDataModelPrivate;
169 class QVDMIncubationTask : public QQmlIncubator
172 QVDMIncubationTask(QQuickVisualDataModelPrivate *l, IncubationMode mode)
173 : QQmlIncubator(mode)
177 virtual void statusChanged(Status);
178 virtual void setInitialState(QObject *);
180 QQuickVisualDataModelItem *incubating;
181 QQuickVisualDataModelPrivate *vdm;
182 int index[QQuickListCompositor::MaximumGroupCount];
186 class QQuickVisualDataGroupEmitter
189 virtual ~QQuickVisualDataGroupEmitter() {}
190 virtual void emitModelUpdated(const QQuickChangeSet &changeSet, bool reset) = 0;
191 virtual void createdPackage(int, QQuickPackage *) {}
192 virtual void initPackage(int, QQuickPackage *) {}
193 virtual void destroyingPackage(QQuickPackage *) {}
195 QIntrusiveListNode emitterNode;
198 typedef QIntrusiveList<QQuickVisualDataGroupEmitter, &QQuickVisualDataGroupEmitter::emitterNode> QQuickVisualDataGroupEmitterList;
200 class QQuickVisualDataGroupPrivate : public QObjectPrivate
203 Q_DECLARE_PUBLIC(QQuickVisualDataGroup)
205 QQuickVisualDataGroupPrivate() : group(Compositor::Cache), defaultInclude(false) {}
207 static QQuickVisualDataGroupPrivate *get(QQuickVisualDataGroup *group) {
208 return static_cast<QQuickVisualDataGroupPrivate *>(QObjectPrivate::get(group)); }
210 void setModel(QQuickVisualDataModel *model, Compositor::Group group);
211 bool isChangedConnected();
212 void emitChanges(QV8Engine *engine);
213 void emitModelUpdated(bool reset);
215 void createdPackage(int index, QQuickPackage *package);
216 void initPackage(int index, QQuickPackage *package);
217 void destroyingPackage(QQuickPackage *package);
219 bool parseIndex(const v8::Local<v8::Value> &value, int *index, Compositor::Group *group) const;
221 QQmlV8Function *args, Compositor::Group *group, int *index, int *count, int *groups) const;
223 Compositor::Group group;
224 QQmlGuard<QQuickVisualDataModel> model;
225 QQuickVisualDataGroupEmitterList emitters;
226 QQuickChangeSet changeSet;
231 class QQuickVisualDataModelParts;
233 class QQuickVisualDataModelPrivate : public QObjectPrivate, public QQuickVisualDataGroupEmitter
235 Q_DECLARE_PUBLIC(QQuickVisualDataModel)
237 QQuickVisualDataModelPrivate(QQmlContext *);
238 ~QQuickVisualDataModelPrivate();
240 static QQuickVisualDataModelPrivate *get(QQuickVisualDataModel *m) {
241 return static_cast<QQuickVisualDataModelPrivate *>(QObjectPrivate::get(m));
245 void connectModel(QQuickVisualAdaptorModel *model);
247 QObject *object(Compositor::Group group, int index, bool asynchronous);
248 QQuickVisualDataModel::ReleaseFlags release(QObject *object);
249 QString stringValue(Compositor::Group group, int index, const QString &name);
250 void emitCreatedPackage(QVDMIncubationTask *incubationTask, QQuickPackage *package);
251 void emitInitPackage(QVDMIncubationTask *incubationTask, QQuickPackage *package);
252 void emitCreatedItem(QVDMIncubationTask *incubationTask, QQuickItem *item) {
253 emit q_func()->createdItem(incubationTask->index[m_compositorGroup], item); }
254 void emitInitItem(QVDMIncubationTask *incubationTask, QQuickItem *item) {
255 emit q_func()->initItem(incubationTask->index[m_compositorGroup], item); }
256 void emitDestroyingPackage(QQuickPackage *package);
257 void emitDestroyingItem(QQuickItem *item) { emit q_func()->destroyingItem(item); }
258 void removeCacheItem(QQuickVisualDataModelItem *cacheItem);
260 void updateFilterGroup();
262 void addGroups(Compositor::iterator from, int count, Compositor::Group group, int groupFlags);
263 void removeGroups(Compositor::iterator from, int count, Compositor::Group group, int groupFlags);
264 void setGroups(Compositor::iterator from, int count, Compositor::Group group, int groupFlags);
267 const QVector<Compositor::Insert> &inserts,
268 QVarLengthArray<QVector<QQuickChangeSet::Insert>, Compositor::MaximumGroupCount> *translatedInserts,
269 QHash<int, QList<QQuickVisualDataModelItem *> > *movedItems = 0);
270 void itemsInserted(const QVector<Compositor::Insert> &inserts);
272 const QVector<Compositor::Remove> &removes,
273 QVarLengthArray<QVector<QQuickChangeSet::Remove>, Compositor::MaximumGroupCount> *translatedRemoves,
274 QHash<int, QList<QQuickVisualDataModelItem *> > *movedItems = 0);
275 void itemsRemoved(const QVector<Compositor::Remove> &removes);
277 const QVector<Compositor::Remove> &removes, const QVector<Compositor::Insert> &inserts);
278 void itemsChanged(const QVector<Compositor::Change> &changes);
279 template <typename T> static v8::Local<v8::Array> buildChangeList(const QVector<T> &changes);
281 void emitModelUpdated(const QQuickChangeSet &changeSet, bool reset);
283 bool insert(Compositor::insert_iterator &before, const v8::Local<v8::Object> &object, int groups);
285 static void group_append(QQmlListProperty<QQuickVisualDataGroup> *property, QQuickVisualDataGroup *group);
286 static int group_count(QQmlListProperty<QQuickVisualDataGroup> *property);
287 static QQuickVisualDataGroup *group_at(QQmlListProperty<QQuickVisualDataGroup> *property, int index);
289 void releaseIncubator(QVDMIncubationTask *incubationTask);
290 void incubatorStatusChanged(QVDMIncubationTask *incubationTask, QQmlIncubator::Status status);
291 void setInitialState(QVDMIncubationTask *incubationTask, QObject *o);
293 QQuickVisualAdaptorModel m_adaptorModel;
294 QQuickListCompositor m_compositor;
295 QQmlComponent *m_delegate;
296 QQuickVisualDataModelItemMetaType *m_cacheMetaType;
297 QQmlContext *m_context;
298 QQuickVisualDataModelParts *m_parts;
299 QQuickVisualDataGroupEmitterList m_pendingParts;
301 QList<QQuickVisualDataModelItem *> m_cache;
302 QList<QVDMIncubationTask *> m_finishedIncubating;
303 QList<QByteArray> m_watchedRoles;
305 QString m_filterGroup;
310 QQuickListCompositor::Group m_compositorGroup;
312 bool m_delegateValidated : 1;
314 bool m_transaction : 1;
315 bool m_incubatorCleanupScheduled : 1;
319 QQuickVisualDataGroup *m_cacheItems;
320 QQuickVisualDataGroup *m_items;
321 QQuickVisualDataGroup *m_persistedItems;
323 QQuickVisualDataGroup *m_groups[Compositor::MaximumGroupCount];
327 class QQuickVisualPartsModel : public QQuickVisualModel, public QQuickVisualDataGroupEmitter
330 Q_PROPERTY(QString filterOnGroup READ filterGroup WRITE setFilterGroup NOTIFY filterGroupChanged RESET resetFilterGroup)
332 QQuickVisualPartsModel(QQuickVisualDataModel *model, const QString &part, QObject *parent = 0);
333 ~QQuickVisualPartsModel();
335 QString filterGroup() const;
336 void setFilterGroup(const QString &group);
337 void resetFilterGroup();
338 void updateFilterGroup();
339 void updateFilterGroup(Compositor::Group group, const QQuickChangeSet &changeSet);
342 bool isValid() const;
343 QQuickItem *item(int index, bool asynchronous=false);
344 ReleaseFlags release(QQuickItem *item);
345 QString stringValue(int index, const QString &role);
346 QList<QByteArray> watchedRoles() const { return m_watchedRoles; }
347 void setWatchedRoles(QList<QByteArray> roles);
349 int indexOf(QQuickItem *item, QObject *objectContext) const;
351 void emitModelUpdated(const QQuickChangeSet &changeSet, bool reset);
353 void createdPackage(int index, QQuickPackage *package);
354 void initPackage(int index, QQuickPackage *package);
355 void destroyingPackage(QQuickPackage *package);
358 void filterGroupChanged();
361 QQuickVisualDataModel *m_model;
362 QHash<QObject *, QQuickPackage *> m_packaged;
364 QString m_filterGroup;
365 QList<QByteArray> m_watchedRoles;
366 Compositor::Group m_compositorGroup;
370 class QMetaPropertyBuilder;
372 class QQuickVisualDataModelPartsMetaObject : public QQmlOpenMetaObject
375 QQuickVisualDataModelPartsMetaObject(QObject *parent)
376 : QQmlOpenMetaObject(parent) {}
378 virtual void propertyCreated(int, QMetaPropertyBuilder &);
379 virtual QVariant initialValue(int);
382 class QQuickVisualDataModelParts : public QObject
386 QQuickVisualDataModelParts(QQuickVisualDataModel *parent);
388 QQuickVisualDataModel *model;
389 QList<QQuickVisualPartsModel *> models;
392 class QQuickVisualDataModelAttachedMetaObject : public QAbstractDynamicMetaObject, public QQmlRefCount
395 QQuickVisualDataModelAttachedMetaObject(
396 QQuickVisualDataModelItemMetaType *metaType, QMetaObject *metaObject);
397 ~QQuickVisualDataModelAttachedMetaObject();
399 void objectDestroyed(QObject *);
400 int metaCall(QObject *, QMetaObject::Call, int _id, void **);
403 QQuickVisualDataModelItemMetaType * const metaType;
404 QMetaObject * const metaObject;
405 const int memberPropertyOffset;
406 const int indexPropertyOffset;