on xenial help sign in
Don't use context properties but properties on the delegates

This increases a bit the requirements for delegates of the LVWPH but since we control them it's not really a problem. In ::layout the setContextProperty calls accounted for around 45% according to callgrind, now it's around 10% only.

commitfdf9a7e891efb9bd733f5c6b899d07bd2e3383ea authorAlbert Astals Cid <albert.astals@canonical.com> dateThu 17 Mar 2016, 15:21 (11 years ago) parent7659185
6 files changed+26−34
plugins/Dash/listviewwithpageheader.cpp+13−16 qml/Dash/DashCategoryBase.qml+3−11 qml/Dash/GenericScopeView.qml+2−2 tests/plugins/Dash/listviewwithpageheadersectiontest.cpp+2−2 tests/plugins/Dash/listviewwithpageheadertestsection.qml+2−1 tests/plugins/Dash/tst_ListViewWithPageHeaderQML.qml+4−2
plugins/Dash/listviewwithpageheader.cpp+13−16
@@ -97,6 +97,7 @@
9797#include <qqmlengine.h>
9898#pragma GCC diagnostic push
9999#pragma GCC diagnostic ignored "-pedantic"
100+#include <private/qqmlcontext_p.h>
100101#include <private/qqmldelegatemodel_p.h>
101102#include <private/qqmlglobal_p.h>
102103#include <private/qquickitem_p.h>
@@ -750,8 +751,6 @@ QQuickItem *ListViewWithPageHeader::getSectionItem(const QString &sectionText)
750751
751752 QQmlContext *creationContext = m_sectionDelegate->creationContext();
752753 QQmlContext *context = new QQmlContext(creationContext ? creationContext : qmlContext(this));
753− context->setContextProperty(QStringLiteral("section"), sectionText);
754− context->setContextProperty(QStringLiteral("delegateIndex"), -1);
755754 QObject *nobj = m_sectionDelegate->beginCreate(context);
756755 if (nobj) {
757756 QQml_setParent_noEvent(context, nobj);
@@ -759,6 +758,8 @@ QQuickItem *ListViewWithPageHeader::getSectionItem(const QString &sectionText)
759758 if (!sectionItem) {
760759 delete nobj;
761760 } else {
761+ sectionItem->setProperty("text", sectionText);
762+ sectionItem->setProperty("delegateIndex", -1);
762763 sectionItem->setZ(2);
763764 QQml_setParent_noEvent(sectionItem, m_clipItem);
764765 sectionItem->setParentItem(m_clipItem);
@@ -792,8 +793,7 @@ void ListViewWithPageHeader::updateSectionItem(int modelIndex)
792793 if (!item->sectionItem()) {
793794 item->setSectionItem(getSectionItem(sectionText));
794795 } else {
795− QQmlContext *context = QQmlEngine::contextForObject(item->sectionItem())->parentContext();
796− context->setContextProperty(QStringLiteral("section"), sectionText);
796+ item->sectionItem()->setProperty("text", sectionText);
797797 }
798798 } else {
799799 if (item->sectionItem()) {
@@ -914,8 +914,7 @@ ListViewWithPageHeader::ListItem *ListViewWithPageHeader::createItem(int modelIn
914914 polish();
915915 }
916916 if (listItem->sectionItem()) {
917− QQmlContext *context = QQmlEngine::contextForObject(listItem->sectionItem())->parentContext();
918− context->setContextProperty(QStringLiteral("delegateIndex"), modelIndex);
917+ listItem->sectionItem()->setProperty("delegateIndex", modelIndex);
919918 }
920919 adjustMinYExtent();
921920 m_contentHeightDirty = true;
@@ -939,9 +938,10 @@ void ListViewWithPageHeader::itemCreated(int modelIndex, QObject *object)
939938 return;
940939
941940 item->setParentItem(m_clipItem);
941+ // FIXME Why do we need the refreshExpressions call?
942942 QQmlContext *context = QQmlEngine::contextForObject(item)->parentContext();
943− context->setContextProperty(QStringLiteral("ListViewWithPageHeader"), this);
944− context->setContextProperty(QStringLiteral("heightToClip"), QVariant::fromValue<int>(0));
943+ QQmlContextPrivate::get(context)->data->refreshExpressions();
944+ item->setProperty("heightToClip", QVariant::fromValue<int>(0));
945945 if (modelIndex == m_asyncRequestedIndex) {
946946 createItem(modelIndex, false);
947947 refill();
@@ -1107,8 +1107,7 @@ void ListViewWithPageHeader::onModelUpdated(const QQmlChangeSet &changeSet, bool
11071107 for (int i = 0; i < m_visibleItems.count(); ++i) {
11081108 ListItem *item = m_visibleItems[i];
11091109 if (item->sectionItem()) {
1110− QQmlContext *context = QQmlEngine::contextForObject(item->sectionItem())->parentContext();
1111− context->setContextProperty(QStringLiteral("delegateIndex"), m_firstVisibleIndex + i);
1110+ item->sectionItem()->setProperty("delegateIndex", m_firstVisibleIndex + i);
11121111 }
11131112 }
11141113
@@ -1270,8 +1269,7 @@ void ListViewWithPageHeader::layout()
12701269 } else {
12711270 // Update the top sticky section header
12721271 const QString section = m_delegateModel->stringValue(modelIndex, m_sectionProperty);
1273− QQmlContext *context = QQmlEngine::contextForObject(m_topSectionItem)->parentContext();
1274− context->setContextProperty(QStringLiteral("section"), section);
1272+ m_topSectionItem->setProperty("text", section);
12751273
12761274 QQuickItemPrivate::get(m_topSectionItem)->setCulled(false);
12771275 m_topSectionItem->setY(topSectionStickPos);
@@ -1283,19 +1281,18 @@ void ListViewWithPageHeader::layout()
12831281 break;
12841282 delegateIndex--;
12851283 }
1286− context->setContextProperty(QStringLiteral("delegateIndex"), delegateIndex);
1284+ m_topSectionItem->setProperty("delegateIndex", delegateIndex);
12871285 if (item->sectionItem()) {
12881286 QQuickItemPrivate::get(item->sectionItem())->setCulled(true);
12891287 }
12901288 }
12911289 }
12921290 }
1293− QQmlContext *context = QQmlEngine::contextForObject(item->m_item)->parentContext();
12941291 const qreal clipFrom = visibleFrom + (!item->sectionItem() && m_topSectionItem && !QQuickItemPrivate::get(m_topSectionItem)->culled ? m_topSectionItem->height() : 0);
12951292 if (!cull && pos < clipFrom) {
1296− context->setContextProperty(QStringLiteral("heightToClip"), clipFrom - pos);
1293+ item->m_item->setProperty("heightToClip", clipFrom - pos);
12971294 } else {
1298− context->setContextProperty(QStringLiteral("heightToClip"), QVariant::fromValue<int>(0));
1295+ item->m_item->setProperty("heightToClip", QVariant::fromValue<int>(0));
12991296 }
13001297// qDebug() << "ListViewWithPageHeader::layout" << item->m_item;
13011298 pos += item->height();
qml/Dash/DashCategoryBase.qml+3−11
@@ -24,17 +24,9 @@ Item {
2424 /* Relevant really only for ListViewWithPageHeader case: specify how many pixels we can overlap with the section header */
2525 readonly property int allowedOverlap: units.dp(1)
2626
27− property real __heightToClip: {
28− // Check this is in position where clipping is needed
29− if (typeof ListViewWithPageHeader !== 'undefined') {
30− if (typeof heightToClip !== 'undefined') {
31− if (heightToClip >= allowedOverlap) {
32− return heightToClip - allowedOverlap;
33− }
34− }
35− }
36− return 0;
37− }
27+ property real heightToClip: 0
28+ readonly property real __heightToClip: heightToClip >= allowedOverlap ? heightToClip - allowedOverlap : 0
29+
3830
3931 /*!
4032 \internal
qml/Dash/GenericScopeView.qml+2−2
@@ -604,10 +604,10 @@ FocusScope {
604604 sectionProperty: "name"
605605 sectionDelegate: ListItems.Header {
606606 objectName: "dashSectionHeader" + (delegate ? delegate.category : "")
607+ property int delegateIndex: -1
607608 readonly property var delegate: categoryView.item(delegateIndex)
608609 width: categoryView.width
609− height: section != "" ? units.gu(5) : 0
610− text: section
610+ height: text != "" ? units.gu(5) : 0
611611 color: scopeStyle ? scopeStyle.foreground : theme.palette.normal.baseText
612612 iconName: delegate && delegate.headerLink ? "go-next" : ""
613613 onClicked: {
tests/plugins/Dash/listviewwithpageheadersectiontest.cpp+2−2
@@ -116,12 +116,12 @@ private:
116116
117117 QString section(QQuickItem *item) const
118118 {
119− return item ? QQmlEngine::contextForObject(item)->parentContext()->contextProperty(QLatin1String("section")).toString() : QString();
119+ return item ? item->property("text").toString() : QString();
120120 }
121121
122122 int sectionDelegateIndex(QQuickItem *item) const
123123 {
124− return item ? QQmlEngine::contextForObject(item)->parentContext()->contextProperty(QLatin1String("delegateIndex")).toInt() : -1;
124+ return item ? item->property("delegateIndex").toInt() : -1;
125125 }
126126
127127private Q_SLOTS:
tests/plugins/Dash/listviewwithpageheadertestsection.qml+2−1
@@ -97,9 +97,10 @@ Rectangle {
9797 sectionProperty: "type"
9898 sectionDelegate: Component {
9999 Rectangle {
100+ property alias text: theText.text
100101 color: "green"
101102 height: 40
102− Text { text: section; font.pixelSize: 34 }
103+ Text { id: theText; font.pixelSize: 34 }
103104 anchors { left: parent.left; right: parent.right }
104105 }
105106 }
tests/plugins/Dash/tst_ListViewWithPageHeaderQML.qml+4−2
@@ -81,9 +81,10 @@ Rectangle {
8181 sectionDelegate: Component {
8282 id: sectionHeaderComponent
8383 Rectangle {
84+ property alias text: theText.text
8485 color: "green"
8586 height: listView.sectionHeaderHeight
86− Text { text: section; font.pixelSize: 34 }
87+ Text { id: theText; font.pixelSize: 34 }
8788 anchors { left: parent.left; right: parent.right }
8889 }
8990 }
@@ -92,9 +93,10 @@ Rectangle {
9293 Component {
9394 id: otherSectionHeaderComponent
9495 Rectangle {
96+ property alias text: theText.text
9597 color: "green"
9698 height: 50
97− Text { text: section; font.pixelSize: 34 }
99+ Text { id: theText; font.pixelSize: 34 }
98100 anchors { left: parent.left; right: parent.right }
99101 }
100102 }