~dpm/ubuntu-rssreader-app/enable-translations

« back to all changes in this revision

Viewing changes to OrganicGrid.qml

  • Committer: Tarmac
  • Author(s): Roman Shchekin
  • Date: 2013-09-20 18:08:13 UTC
  • mfrom: (68.1.2 grid-optimization)
  • Revision ID: tarmac-20130920180813-8s4hjzig4kwki1x4
My speedups. I've got between 150 and 500 % performance improvement depending on amount of articles in Tab.

Approved by Ubuntu Phone Apps Jenkins Bot.

Show diffs side-by-side

added added

removed removed

Lines of Context:
9
9
 
10
10
    anchors.fill: parent
11
11
 
12
 
    property variant rectangleList: []
 
12
    property var rectangleList: []
13
13
    property int tag_id
14
14
    property bool isAll: false
15
 
    property variant feedArray: []
 
15
    property var feedArray: []
 
16
 
 
17
    Component.onCompleted: {
 
18
        prepareComponents()
 
19
    }
 
20
 
 
21
    property var delegateComponents: []
 
22
 
 
23
    function prepareComponents() {
 
24
        var componentsPath = "article_items/" + "Article"
 
25
        var alignNames = ["TextA", "TextB", "OneImgA", "FullImg"]
 
26
        for (var i = 0; i < alignNames.length; i++) {
 
27
            var componentName = componentsPath + alignNames[i] + ".qml";
 
28
            delegateComponents[i] = Qt.createComponent(componentName);
 
29
        }
 
30
    }
16
31
 
17
32
    /*!
18
33
      * \brief check collision of two article items
20
35
      */
21
36
    function checkCollision(rect1, rect2) {
22
37
        return (rect1.y  <= rect2.y + rect2.height) &&
23
 
                 (rect2.y <= rect2.y + rect1.height) &&
 
38
                 (rect2.y <= rect1.y + rect1.height) &&
24
39
                 (rect1.x <= rect2.x + rect2.width) &&
25
40
                 (rect2.x <= rect1.x + rect1.width)
26
41
    }
60
75
      * Reloads the organic view. See inline comments for details.
61
76
      */
62
77
    function reload() {
 
78
        console.time("reload_grid")
63
79
        clear()
64
80
        // Decide if we should load all articles in our database or a subset.
65
81
        if (!isAll)
74
90
        }
75
91
        else if (tag_id == -2) {
76
92
            var favArticles = DB.loadFavouriteArticles()
77
 
            for (var i=0; i < favArticles.rows.length; i++)
 
93
            for (var i = 0; i < favArticles.rows.length; i++)
78
94
            {
79
95
                addArticleToModel(favArticles.rows[i])
80
96
            }
81
97
        }
82
98
        else {
83
99
            var feedArticles = DB.loadArticles({"isAll": true});
84
 
            for (var i=0; i < feedArticles.rows.length; i++)
 
100
            for (var i = 0; i < feedArticles.rows.length; i++)
85
101
            {
86
102
                addArticleToModel(feedArticles.rows[i])
87
103
            }
91
107
        var xEdge = 0;
92
108
        var lastColumnX = 0;
93
109
        var y = randomMargin();
 
110
 
94
111
        // A hard-coded sequence that gives an organic look, but is not
95
112
        // completely random
96
113
        var sequence = [0,1,0,1,2,1,0,0,2,1,0,1,0,0];
97
 
        // TODO: Remove hard limit on 300 items
 
114
        // var componentsPath = "article_items/" + "Article"
 
115
 
98
116
        for(var i = 0; i < articleModel.count; i++) {
99
117
            var article = articleModel.get(i);
100
118
//            var imageArray = ImageSeparator.separate(article.content)
104
122
 
105
123
            // Pick the type of size we will use for this item from the sequence
106
124
            var sizeType = sequence[i % sequence.length];
107
 
            var alignType = parseInt(Math.random() * 2)
 
125
            var alignType = Math.round(Math.random())
108
126
//            if(hasImage) {
109
127
//                alignType = parseInt(Math.random() * 4);
110
128
//            } else {
111
129
//                alignType = parseInt(Math.random() * 2);
112
130
//            }
113
131
 
114
 
            var alignName
 
132
            //var alignName
 
133
            var alignIndex
115
134
 
116
 
            // Name of the QML file to be used
117
 
            var componentName
118
 
            var noImageName = ""
119
135
            if(!hasImage) {
120
136
                switch(alignType) {
121
137
                case 0:
122
 
                    alignName = "TextA"
 
138
                    //alignName = "TextA"
 
139
                    alignIndex = 0
123
140
                    break;
124
141
                case 1:
125
 
                    alignName = "TextB"
 
142
                    //alignName = "TextB"
 
143
                    alignIndex = 1
126
144
                    break;
127
145
                }
128
 
                noImageName += "NoImage";
 
146
                //noImageName += "NoImage";
129
147
                sizeType = 0;
130
148
            }
131
149
            else {
132
150
                switch(alignType) {
133
151
                case 0:
134
 
                    alignName = "OneImgA"
 
152
                    //alignName = "OneImgA"
 
153
                    alignIndex = 2
135
154
                    break;
136
155
                case 1:
137
 
                    alignName = "FullImg"
 
156
                    //alignName = "FullImg"
 
157
                    alignIndex = 3
138
158
                    break;
139
159
                }
140
160
            }
141
 
            componentName = "article_items/" + "Article" + alignName + ".qml";
142
161
 
143
 
            // create component for an article
144
 
            var component = Qt.createComponent(componentName);
145
 
            if(component.status !== Component.Ready) {
146
 
                console.log("Error loading component:", component.errorString());
147
 
                continue; // Skip if we for some reason could not create this component
148
 
            }
 
162
            var component = delegateComponents[alignIndex] //Qt.createComponent(componentName);
149
163
 
150
164
            var properties = {
151
165
                "rss_item": article,
173
187
            articleItem.y = y
174
188
 
175
189
            // Check for collisions with all other items
176
 
            // TODO: See if this may be limited to only the previous two colums
177
 
            for(var j = 0; j < rectangleList.length; j++) {
 
190
            // mrqtros: Now we are look only at 0xA last items.
 
191
            //for(var j = 0; j < rectangleList.length; j++) { // mrqtros
 
192
            for(var j = Math.max(0, rectangleList.length - 0xA); j < rectangleList.length; j++) {
178
193
                var rect2 = rectangleList[j]
179
194
                if(checkCollision(articleItem, rect2)) {
180
195
                    articleItem.x = rect2.x + rect2.width + randomMargin();
184
199
            // Did we move the x-edge value further to the right than before?
185
200
            lastColumnX = Math.max(articleItem.x, lastColumnX);
186
201
 
187
 
            // Push this item to all lists and all that stuff
188
 
            var list = rectangleList
189
 
            list.push(articleItem)
190
 
            rectangleList = list
 
202
            rectangleList.push(articleItem)
191
203
 
192
204
            // Increment y for the next item
193
205
            y += articleItem.height + randomMargin();
194
206
        }
 
207
 
195
208
        organicFlickable.scrollToStart()
 
209
        console.timeEnd("reload_grid")
196
210
    }
197
211
 
198
212
    /*!