start to delay a bit objects creation.

use a component incubator to create objects whuile the event loop is running

load applets ui only when they get a view

it will have to be cleaned out a lot, by moving the loading logic into AppletInterface
This commit is contained in:
Marco Martin 2013-02-19 17:27:04 +01:00
parent f4f22df3a3
commit 26b5b98e0a
7 changed files with 115 additions and 14 deletions

View File

@ -34,7 +34,6 @@
//#include "private/declarative/dataenginebindings_p.h"
class QmlObjectPrivate
{
public:
@ -66,6 +65,7 @@ public:
QString qmlPath;
QQmlEngine* engine;
QQmlIncubator incubator;
QQmlComponent* component;
QObject *root;
bool delay : 1;
@ -127,6 +127,7 @@ QmlObject::QmlObject(QObject *parent)
d(new QmlObjectPrivate(this))
{
d->engine = new QQmlEngine(this);
d->engine->setIncubationController(new QmlObjectIncubationController(0));
//d->engine->setNetworkAccessManagerFactory(new PackageAccessManagerFactory());
}
@ -185,14 +186,14 @@ void QmlObject::completeInitialization()
return;
}
QQmlIncubator incubator;
d->component->create(incubator);
d->component->create(d->incubator);
while (!incubator.isReady() && incubator.status() != QQmlIncubator::Error) {
while (!d->incubator.isReady() && d->incubator.status() != QQmlIncubator::Error) {
QCoreApplication::processEvents(QEventLoop::AllEvents, 50);
}
d->root = incubator.object();
d->root = d->incubator.object();
//d->root = d->component->create();
if (!d->root) {
d->errorPrint();

View File

@ -21,7 +21,12 @@
#define QMLOBJECT_H
#include <QObject>
#include <QQmlIncubationController>
#include <QWindow>
#include <QAnimationDriver>
#include <QGuiApplication>
#include <QScreen>
class QQmlEngine;
class QQmlComponent;
@ -29,6 +34,53 @@ class QQmlComponent;
class QmlObjectPrivate;
class QmlObjectIncubationController : public QObject, public QQmlIncubationController
{
Q_OBJECT
public:
QmlObjectIncubationController(QObject *parent)
: QQmlIncubationController(),
QObject(parent)
{
// Allow incubation for 1/3 of a frame.
m_incubation_time = qMax(1, int(1000 / QGuiApplication::primaryScreen()->refreshRate()) / 3);
}
protected:
virtual bool event(QEvent *e)
{
if (e->type() == QEvent::User) {
incubate();
return true;
}
return QObject::event(e);
}
public slots:
void incubate()
{
if (incubatingObjectCount()) {
incubateFor(m_incubation_time * 2);
if (incubatingObjectCount()) {
QCoreApplication::postEvent(this, new QEvent(QEvent::User));
}
}
}
void animationStopped() { incubate(); }
protected:
virtual void incubatingObjectCountChanged(int count)
{
if (count) {
QCoreApplication::postEvent(this, new QEvent(QEvent::User));
}
}
private:
int m_incubation_time;
};
/**
* @class QmlObject plasma/declarativewidget.h <Plasma/QmlObject>
*

View File

@ -68,6 +68,10 @@ AppletInterface::AppletInterface(DeclarativeAppletScript *script, QQuickItem *pa
this, SIGNAL(locationChanged()));
connect(m_appletScriptEngine, SIGNAL(contextChanged()),
this, SIGNAL(contextChanged()));
m_creationTimer = new QTimer(this);
m_creationTimer->setSingleShot(true);
connect(m_creationTimer, &QTimer::timeout, m_appletScriptEngine, &DeclarativeAppletScript::delayedInit);
}
AppletInterface::~AppletInterface()
@ -89,6 +93,9 @@ void AppletInterface::setUiObject(QObject *object)
QQmlExpression expr(m_appletScriptEngine->engine()->rootContext(), object, "parent");
QQmlProperty prop(object, "anchors.fill");
prop.write(expr.evaluate());
geometryChanged(QRectF(), QRectF(x(), y(), width(), height()));
emit busyChanged();
}
QObject *AppletInterface::uiObject() const
@ -138,7 +145,7 @@ void AppletInterface::setTitle(const QString &title)
bool AppletInterface::isBusy() const
{
return m_busy;
return !m_uiObject || m_busy;
}
void AppletInterface::setBusy(bool busy)
@ -505,4 +512,22 @@ void AppletInterface::geometryChanged(const QRectF &newGeometry, const QRectF &o
}
}
void AppletInterface::itemChange(ItemChange change, const ItemChangeData &value)
{
if (change == QQuickItem::ItemSceneChange) {
//we have a window: create the
if (value.window && !m_uiObject && !m_creationTimer->isActive()) {
m_appletScriptEngine->delayedInit();
/*Experiment on even more delayed, doesn't seem to be good
QTime time = QTime::currentTime();
qsrand((uint)time.msec());
const int interval = qrand() % ((1000 + 1) - 50) + 50;
//QTimer::singleShot(interval, m_appletScriptEngine, SLOT(delayedInit()));
m_creationTimer->start(interval);*/
}
}
QQuickItem::itemChange(change, value);
}
#include "moc_appletinterface.cpp"

View File

@ -228,6 +228,7 @@ Q_SIGNALS:
protected:
void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry);
void itemChange(ItemChange change, const ItemChangeData &value);
DeclarativeAppletScript *m_appletScriptEngine;
@ -244,6 +245,8 @@ private:
QWeakPointer<QObject> m_uiObject;
QWeakPointer<QObject> m_compactUiObject;
QTimer *m_creationTimer;
Plasma::BackgroundHints m_backgroundHints;
bool m_busy : 1;
bool m_expanded : 1;

View File

@ -98,7 +98,15 @@ bool DeclarativeAppletScript::init()
connect(applet(), SIGNAL(activate()),
this, SLOT(activate()));
//FIXME: everything should be delayed
if (pc) {
delayedInit();
}
return true;
}
bool DeclarativeAppletScript::delayedInit()
{
m_qmlObject = new QmlObject(applet());
m_qmlObject->setInitializationDelayed(true);
//FIXME: what replaced this?
@ -146,9 +154,10 @@ bool DeclarativeAppletScript::init()
m_interface->setUiObject(m_qmlObject->rootObject());
qDebug() << "Graphic object created:" << a << a->property("graphicObject");
qDebug() << "Graphic object created:" << applet() << applet()->property("graphicObject");
//Create the ToolBox
Plasma::Containment *pc = qobject_cast<Plasma::Containment *>(applet());
if (pc) {
Plasma::Package pkg = Plasma::PluginLoader::self()->loadPackage("Plasma/Generic");
pkg.setPath("org.kde.toolbox");
@ -175,7 +184,7 @@ bool DeclarativeAppletScript::init()
}
}
return !a->failedToLaunch();
return !applet()->failedToLaunch();
}
QString DeclarativeAppletScript::filePath(const QString &type, const QString &file) const

View File

@ -56,6 +56,7 @@ public Q_SLOTS:
void executeAction(const QString &name);
void activate();
void configChanged();
bool delayedInit();
protected:
bool init();

View File

@ -21,7 +21,8 @@ import QtQuick 2.0
import org.kde.plasma.core 0.1 as PlasmaCore
import org.kde.plasma.components 0.1 as PlasmaComponents
Row {
Item {
id: root
width: 640
height: 48
@ -31,13 +32,13 @@ Row {
Connections {
target: plasmoid
onAppletAdded: {
var container = appletContainerComponent.createObject(root)
container.visible = true
var container = appletContainerComponent.createObject(row)
print("Applet added in test panel: " + applet)
applet.parent = container
container.applet = applet
applet.anchors.fill= applet.parent
applet.anchors.fill = applet.parent
applet.visible = true
container.visible = true
}
}
@ -45,12 +46,13 @@ Row {
id: appletContainerComponent
Item {
id: container
visible: false
anchors {
top: parent.top
bottom: parent.bottom
}
width: height
width: height
property Item applet
@ -64,8 +66,16 @@ Row {
}
}
Row {
id: row
anchors {
top: parent.top
bottom: parent.bottom
}
}
Component.onCompleted: {
print("Test Panel loaded")
print(plasmoid)
}
}
}