Merge lp:~martin-borho/ubuntu-weather-app/conditional-weather into lp:ubuntu-weather-app/obsolete.trunk
- conditional-weather
- Merge into trunk
Proposed by
David Planella
Status: | Merged | ||||
---|---|---|---|---|---|
Approved by: | David Planella | ||||
Approved revision: | 203 | ||||
Merged at revision: | 202 | ||||
Proposed branch: | lp:~martin-borho/ubuntu-weather-app/conditional-weather | ||||
Merge into: | lp:ubuntu-weather-app/obsolete.trunk | ||||
Diff against target: |
896 lines (+482/-247) 9 files modified
components/AddLocationSheet.qml (+0/-1) components/CurrentWeather.qml (+66/-233) components/CurrentWeatherDetail.qml (+122/-0) components/CurrentWeatherFront.qml (+76/-0) components/LocationTab.qml (+97/-3) components/ScrollingArea.qml (+112/-0) components/WeatherApi.js (+8/-8) key.js (+0/-1) tests/autopilot/ubuntu_weather_app/tests/test_settings.py (+1/-1) |
||||
To merge this branch: | bzr merge lp:~martin-borho/ubuntu-weather-app/conditional-weather | ||||
Related bugs: |
|
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Ubuntu Phone Apps Jenkins Bot | continuous-integration | Approve | |
David Planella | Approve | ||
Review via email: mp+207152@code.launchpad.net |
Commit message
Initial tablet design of the Weather app.
Description of the change
Initial tablet design of the Weather app.
I'm proposing the branch on behalf of Martin (the original author) to advance work in terms of landing this for the MWC release today.
To post a comment you must log in.
Revision history for this message
Ubuntu Phone Apps Jenkins Bot (ubuntu-phone-apps-jenkins-bot) wrote : | # |
review:
Needs Fixing
(continuous-integration)
Revision history for this message
David Planella (dpm) wrote : | # |
Looks awesome to me!
review:
Approve
Revision history for this message
Ubuntu Phone Apps Jenkins Bot (ubuntu-phone-apps-jenkins-bot) : | # |
review:
Approve
(continuous-integration)
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'components/AddLocationSheet.qml' |
2 | --- components/AddLocationSheet.qml 2014-02-08 13:25:26 +0000 |
3 | +++ components/AddLocationSheet.qml 2014-02-19 12:16:52 +0000 |
4 | @@ -37,7 +37,6 @@ |
5 | Cities.preList.forEach(function(loc) { |
6 | citiesModel.append(loc) |
7 | }) |
8 | - Theme.palette.normal.backgroundText = "#656565" //color: Theme.palette.normal.baseText |
9 | } |
10 | |
11 | Connections { |
12 | |
13 | === modified file 'components/CurrentWeather.qml' |
14 | --- components/CurrentWeather.qml 2014-02-15 14:31:10 +0000 |
15 | +++ components/CurrentWeather.qml 2014-02-19 12:16:52 +0000 |
16 | @@ -18,6 +18,7 @@ |
17 | */ |
18 | import QtQuick 2.0 |
19 | import Ubuntu.Components 0.1 |
20 | +import Ubuntu.Layouts 0.1 |
21 | import "./" as Components |
22 | |
23 | Rectangle { |
24 | @@ -43,7 +44,7 @@ |
25 | property string speedScale: (mainView.settings["wind_units"] === "mph") ? "mph" : "km/h" |
26 | property string precipScale: (mainView.settings["precip_units"] === "in") ? "in" : "mm" |
27 | |
28 | - property NumberAnimation appearAnimation: currentConditionIcon.appearAnimation |
29 | + property NumberAnimation appearAnimation: frontrect.conditionIcon.appearAnimation |
30 | |
31 | width: parent.width |
32 | anchors.fill: parent |
33 | @@ -77,7 +78,42 @@ |
34 | onToggle: {flipable.flipped = !flipable.flipped} |
35 | } |
36 | |
37 | - Flipable { |
38 | + Layouts { |
39 | + objectName: "WeatherLayout" |
40 | + id: layoutsCurrent |
41 | + anchors.fill: parent |
42 | + layouts: [ |
43 | + ConditionalLayout { |
44 | + name: "WeatherItem" |
45 | + when: layouts.width > units.gu(80) |
46 | + Rectangle { |
47 | + color: "transparent" |
48 | + anchors.fill: parent |
49 | + CurrentWeatherFront { |
50 | + id: frontrect |
51 | + shapeSize: units.gu(18) |
52 | + anchors { |
53 | + horizontalCenter: parent.horizontalCenter |
54 | + verticalCenter: parent.verticalCenter |
55 | + verticalCenterOffset: -(parent.height*0.1); |
56 | + } |
57 | + } |
58 | + CurrentWeatherDetail { |
59 | + id: backrect |
60 | + height: parent.height/2 |
61 | + shapeSize: units.gu(14) |
62 | + gridColumns: 4 |
63 | + anchors { |
64 | + horizontalCenter: parent.horizontalCenter |
65 | + verticalCenter: parent.verticalCenter |
66 | + verticalCenterOffset: (parent.height*0.2); |
67 | + } |
68 | + } |
69 | + Components.ScrollingArea {} |
70 | + } |
71 | + } |
72 | + ] |
73 | + Flipable { |
74 | id: flipable |
75 | height: parent.height |
76 | width:parent.width |
77 | @@ -85,231 +121,28 @@ |
78 | anchors.verticalCenterOffset: -units.gu(3) |
79 | property bool flipped: false |
80 | |
81 | - MouseArea { |
82 | - id: flippedarea |
83 | - property bool wasHourlyScrolled: false |
84 | - property int startY: 0 |
85 | - property double startTime: 0 |
86 | - property int sectionHeight: flippedarea.height/hourly.count |
87 | - property int lastIndex: -1 |
88 | - anchors.fill: parent |
89 | - anchors.top: parent.top |
90 | - anchors.topMargin: units.gu(3.5) |
91 | - onClicked: { |
92 | - mouse.accepted = true; |
93 | - if(!wasHourlyScrolled) { |
94 | - var movement = Math.round(startY-mouse.y); |
95 | - if(movement < 10 && movement > -10) { |
96 | - // flip to detail data |
97 | - flipable.flipped = !flipable.flipped; |
98 | - } else { |
99 | - // switch to next/prevoius day |
100 | - if(movement >= 10) { |
101 | - dailyForecastList.incrementCurrentIndex(); |
102 | - } else if(movement <= -10) { |
103 | - dailyForecastList.decrementCurrentIndex(); |
104 | - } |
105 | - dailyForecastList.positionViewAtIndex(dailyForecastList.currentIndex,ListView.SnapPosition); |
106 | - flipable.flipped = false; |
107 | - } |
108 | - } |
109 | - } |
110 | - onPressed: { |
111 | - wasHourlyScrolled = false; |
112 | - startY = mouse.y; |
113 | - startTime = new Date().getTime() |
114 | - } |
115 | - onPositionChanged: { |
116 | - mouse.accepted = true; |
117 | - var distance = (parent.height - mouse.y), |
118 | - now = new Date().getTime(), |
119 | - speed = distance/(now-startTime); |
120 | - if(speed < 2.3 && !flipable.flipped) { |
121 | - // slow scrolling detected |
122 | - var movement = Math.round(distance/sectionHeight); |
123 | - if(movement > 0) { |
124 | - var hourIndex = movement-1, |
125 | - currentHour = currentWeather.hourly.get(hourIndex); |
126 | - if( currentHour !== undefined && (lastIndex < 0 || lastIndex !== hourIndex)) { |
127 | - wasHourlyScrolled = true; |
128 | - currentConditionIcon.condition = currentWeather.hourly.get(hourIndex).icon; |
129 | - var temp = currentWeather.hourly.get(hourIndex)[mainView.settings["units"]].temp; |
130 | - currentConditionTempContent.currentTemp = temp; |
131 | - adjustBackground(Math.round(temp)); |
132 | - var dateData = currentWeather.hourly.get(hourIndex).date; |
133 | - var dateTime = new Date(dateData.year, dateData.month, dateData.date, dateData.hours, dateData.minutes) |
134 | - // TRANSLATORS: this is a date to which a time of the day will be appended |
135 | - var dateTimeString = Qt.formatDateTime(dateTime, i18n.tr('dddd, dd MMMM')) + ' - ' + Qt.formatTime(dateTime); |
136 | - dateComponent.dateString = dateTimeString; |
137 | - dateComponent.renderText(); |
138 | - hourlyScrollEffect.start(); |
139 | - lastIndex = hourIndex; |
140 | - } |
141 | - } |
142 | - } |
143 | - } |
144 | - onReleased: { |
145 | - if(wasHourlyScrolled) { |
146 | - // reset temp and date to current day |
147 | - var currentDayData = dayForecastModel.get(dailyForecastList.currentIndex); |
148 | - currentConditionIcon.condition = currentDayData.condIcon; |
149 | - currentConditionIcon.appearAnimation.start(); |
150 | - currentConditionTempContent.currentTemp = currentDayData.temp; |
151 | - adjustBackground(Math.round(currentDayData.temp)); |
152 | - dateComponent.dateString = currentDayData.date; |
153 | - dateComponent.renderText(); |
154 | - lastIndex = -1; |
155 | - } |
156 | - } |
157 | - } |
158 | - |
159 | - back: |
160 | - Rectangle { |
161 | - id: backrect |
162 | - anchors.fill: parent |
163 | - color: "transparent" |
164 | - |
165 | - Column { |
166 | - id: leftColumn |
167 | - anchors { |
168 | - horizontalCenter: parent.horizontalCenter |
169 | - horizontalCenterOffset: units.gu(-8) |
170 | - verticalCenter: parent.verticalCenter |
171 | - } |
172 | - spacing: units.gu(1) |
173 | - |
174 | - UbuntuShape { |
175 | - color: "#10000000" |
176 | - radius: "medium" |
177 | - |
178 | - width: units.gu(15) |
179 | - height: units.gu(15) |
180 | - |
181 | - Components.WeatherDetailComponent { |
182 | - value: currentWeather.humidity |
183 | - measure: i18n.tr("Humidity") |
184 | - unit: i18n.tr('%') |
185 | - anchors.fill: parent |
186 | - } |
187 | - } |
188 | - |
189 | - UbuntuShape { |
190 | - color: "#10000000" |
191 | - radius: "medium" |
192 | - |
193 | - width: units.gu(15) |
194 | - height: units.gu(15) |
195 | - |
196 | - Components.WeatherDetailComponent { |
197 | - objectName: "WindSpeedValue" |
198 | - value: currentWeather.windSpeed |
199 | - measure: i18n.tr("Wind speed") |
200 | - unit: currentWeather.speedScale + " " + currentWeather.windDir |
201 | - anchors.fill: parent |
202 | - } |
203 | - } |
204 | - } |
205 | - |
206 | - Column { |
207 | - id: rightColumn |
208 | - anchors { |
209 | - horizontalCenter: parent.horizontalCenter |
210 | - horizontalCenterOffset: units.gu(8) |
211 | - verticalCenter: parent.verticalCenter |
212 | - } |
213 | - spacing: units.gu(1) |
214 | - |
215 | - UbuntuShape { |
216 | - color: "#10000000" |
217 | - radius: "medium" |
218 | - |
219 | - width: units.gu(15) |
220 | - height: units.gu(15) |
221 | - |
222 | - Components.WeatherDetailComponent { |
223 | - value: (currentWeather.propPrecip !== "") ? currentWeather.propPrecip: currentWeather.pressure |
224 | - measure: (currentWeather.propPrecip !== "") ? getProcipLabel(): i18n.tr("Pressure") |
225 | - unit: (currentWeather.propPrecip !== "") ? i18n.tr("Percent") : i18n.tr("mbar") |
226 | - anchors.fill: parent |
227 | - } |
228 | - } |
229 | - |
230 | - UbuntuShape { |
231 | - color: "#10000000" |
232 | - radius: "medium" |
233 | - |
234 | - width: units.gu(15) |
235 | - height: units.gu(15) |
236 | - |
237 | - Components.WeatherDetailComponent { |
238 | - objectName: "PrecipitationValue" |
239 | - value: (currentWeather.uvIndex !== "") ? currentWeather.uvIndex : currentWeather.precipitation |
240 | - measure: (currentWeather.uvIndex !== "") ? i18n.tr("UV index"): i18n.tr("Precipitation") |
241 | - unit: (currentWeather.uvIndex !== "") ? getUvLabel() : i18n.tr("Percent"); |
242 | - anchors.fill: parent |
243 | - } |
244 | - } |
245 | - } |
246 | - } |
247 | - |
248 | - front: |
249 | - Rectangle { |
250 | - id: frontrect |
251 | - color: "transparent" |
252 | - anchors.fill: parent |
253 | - |
254 | - UbuntuShape { |
255 | - id: currentCondition |
256 | - color: "#10000000" |
257 | - radius: "medium" |
258 | - |
259 | - width: units.gu(15) |
260 | - height: units.gu(15) |
261 | - anchors { |
262 | - horizontalCenter: parent.horizontalCenter |
263 | - horizontalCenterOffset: units.gu(-8) |
264 | - verticalCenter: parent.verticalCenter |
265 | - } |
266 | - |
267 | - Components.WeatherConditionIconComponent { |
268 | - id: currentConditionIcon |
269 | - anchors.centerIn: parent |
270 | - anchors.margins: units.gu(1) |
271 | - condition: currentWeather.icon |
272 | - } |
273 | - } |
274 | - |
275 | - UbuntuShape { |
276 | - id: currentConditionTemp |
277 | - color: "#10000000" |
278 | - radius: "medium" |
279 | - width: units.gu(15) |
280 | - height: units.gu(15) |
281 | - anchors { |
282 | - horizontalCenter: parent.horizontalCenter |
283 | - horizontalCenterOffset: units.gu(8) |
284 | - verticalCenter: parent.verticalCenter |
285 | - } |
286 | - |
287 | - Components.WeatherTemperatureComponent { |
288 | - id: currentConditionTempContent |
289 | - currentTemp: currentWeather.currentTemp |
290 | - tempScale: currentWeather.tempScale |
291 | - minTemp: currentWeather.minTemp |
292 | - maxTemp: currentWeather.maxTemp |
293 | - anchors.fill: parent |
294 | - } |
295 | - } |
296 | - } |
297 | + Components.ScrollingArea {} |
298 | + |
299 | + back: CurrentWeatherDetail { |
300 | + id: backrect |
301 | + Layouts.item: "back" |
302 | + anchors.fill: parent |
303 | + } |
304 | + |
305 | + front: CurrentWeatherFront { |
306 | + id: frontrect |
307 | + anchors.fill: parent |
308 | + Layouts.item: "front" |
309 | + } |
310 | |
311 | states:[ |
312 | State { |
313 | name: "back" |
314 | - when: flipable.flipped |
315 | + when: flipable.flipped && layouts.width < units.gu(80) |
316 | }, |
317 | State { |
318 | name: "front" |
319 | - when: !flipable.flipped |
320 | + when: !flipable.flipped && layouts.width < units.gu(80) |
321 | } |
322 | ] |
323 | |
324 | @@ -318,10 +151,10 @@ |
325 | to:"back" |
326 | SequentialAnimation{ |
327 | ParallelAnimation { |
328 | - NumberAnimation { target: currentCondition; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: units.gu(8); easing: UbuntuAnimation.StandardEasing } |
329 | - NumberAnimation { target: currentConditionTemp; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: units.gu(-8); easing: UbuntuAnimation.StandardEasing } |
330 | - NumberAnimation {target: currentConditionIcon; property: "opacity"; to:0; duration: UbuntuAnimation.SlowDuration} |
331 | - NumberAnimation {target: currentConditionTempContent; property: "opacity"; to:0; duration: UbuntuAnimation.SlowDuration} |
332 | + NumberAnimation { target: frontrect.condition; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: units.gu(8); easing: UbuntuAnimation.StandardEasing } |
333 | + NumberAnimation { target: frontrect.conditionTemp; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: units.gu(-8); easing: UbuntuAnimation.StandardEasing } |
334 | + NumberAnimation {target: frontrect.conditionIcon; property: "opacity"; to:0; duration: UbuntuAnimation.SlowDuration} |
335 | + NumberAnimation {target: frontrect.conditionTempContent; property: "opacity"; to:0; duration: UbuntuAnimation.SlowDuration} |
336 | } |
337 | ParallelAnimation { |
338 | NumberAnimation {target: backrect; property: "opacity"; to:1; duration: UbuntuAnimation.SlowDuration} |
339 | @@ -339,10 +172,10 @@ |
340 | }else{ |
341 | backrect.opacity = 0; |
342 | frontrect.opacity = 1; |
343 | - currentConditionIcon.opacity = 1; |
344 | - currentConditionTempContent.opacity = 1; |
345 | - currentCondition.anchors.verticalCenterOffset = 0; |
346 | - currentConditionTemp.anchors.verticalCenterOffset = 0; |
347 | + frontrect.conditionIcon.opacity = 1; |
348 | + frontrect.conditionTempContent.opacity = 1; |
349 | + frontrect.condition.anchors.verticalCenterOffset = 0; |
350 | + frontrect.conditionTemp.anchors.verticalCenterOffset = 0; |
351 | } |
352 | } |
353 | } |
354 | @@ -357,12 +190,12 @@ |
355 | NumberAnimation {target: backrect; property: "opacity"; to:0; duration: UbuntuAnimation.SlowDuration} |
356 | } |
357 | ParallelAnimation{ |
358 | - NumberAnimation {target: currentConditionIcon; property: "opacity"; to:1; duration: UbuntuAnimation.SlowDuration} |
359 | - NumberAnimation {target: currentConditionTempContent; property: "opacity"; to:1; duration: UbuntuAnimation.SlowDuration} |
360 | - NumberAnimation { target: currentCondition; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: 0; easing: UbuntuAnimation.StandardEasingReverse } |
361 | - NumberAnimation { target: currentConditionTemp; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: 0; easing: UbuntuAnimation.StandardEasingReverse } |
362 | + NumberAnimation {target: frontrect.conditionIcon; property: "opacity"; to:1; duration: UbuntuAnimation.SlowDuration} |
363 | + NumberAnimation {target: frontrect.conditionTempContent; property: "opacity"; to:1; duration: UbuntuAnimation.SlowDuration} |
364 | + NumberAnimation { target: frontrect.condition; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: 0; easing: UbuntuAnimation.StandardEasingReverse } |
365 | + NumberAnimation { target: frontrect.conditionTemp; property: "anchors.verticalCenterOffset"; duration: UbuntuAnimation.SlowDuration; to: 0; easing: UbuntuAnimation.StandardEasingReverse } |
366 | } |
367 | } |
368 | } |
369 | } |
370 | - |
371 | +} |
372 | |
373 | === added file 'components/CurrentWeatherDetail.qml' |
374 | --- components/CurrentWeatherDetail.qml 1970-01-01 00:00:00 +0000 |
375 | +++ components/CurrentWeatherDetail.qml 2014-02-19 12:16:52 +0000 |
376 | @@ -0,0 +1,122 @@ |
377 | +/* |
378 | + * Copyright (C) 2013 Canonical Ltd |
379 | + * |
380 | + * This program is free software: you can redistribute it and/or modify |
381 | + * it under the terms of the GNU General Public License version 3 as |
382 | + * published by the Free Software Foundation. |
383 | + * |
384 | + * This program is distributed in the hope that it will be useful, |
385 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
386 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
387 | + * GNU General Public License for more details. |
388 | + * |
389 | + * You should have received a copy of the GNU General Public License |
390 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
391 | + * |
392 | + * Authored by: Raúl Yeguas <neokore@gmail.com> |
393 | + * Martin Borho <martin@borho.net> |
394 | + */ |
395 | +import QtQuick 2.0 |
396 | +import Ubuntu.Components 0.1 |
397 | +import Ubuntu.Layouts 0.1 |
398 | +import "./" as Components |
399 | + |
400 | +Rectangle { |
401 | + id: backrect |
402 | + color: "transparent" |
403 | + property int shapeSize: units.gu(15) |
404 | + property int gridColumns: 2 |
405 | + |
406 | + function getProcipLabel() { |
407 | + // show the right Label, depending on precipitation type |
408 | + return (currentWeather.precipType === "snow") ? i18n.tr("Chance of Snow") : i18n.tr("Chance of Rain") |
409 | + } |
410 | + |
411 | + function getUvLabel() { |
412 | + var label = "", |
413 | + uvInt = parseInt(currentWeather.uvIndex); |
414 | + if(uvInt <= 2) { |
415 | + label = i18n.tr("Low"); |
416 | + } else if(uvInt <= 5) { |
417 | + label = i18n.tr("Moderate"); |
418 | + } else if(uvInt <= 8) { |
419 | + label = i18n.tr("High"); |
420 | + } else if(uvInt <= 10) { |
421 | + label = i18n.tr("Very high"); |
422 | + } else { |
423 | + label = i18n.tr("Extreme"); |
424 | + } |
425 | + return label; |
426 | + } |
427 | + |
428 | + Grid { |
429 | + columns: gridColumns |
430 | + spacing: units.gu(1) |
431 | + anchors { |
432 | + horizontalCenter: parent.horizontalCenter |
433 | + verticalCenter: parent.verticalCenter |
434 | + } |
435 | + |
436 | + UbuntuShape { |
437 | + color: "#10000000" |
438 | + radius: "medium" |
439 | + |
440 | + width: shapeSize |
441 | + height: shapeSize |
442 | + |
443 | + Components.WeatherDetailComponent { |
444 | + value: currentWeather.humidity |
445 | + measure: i18n.tr("Humidity") |
446 | + unit: i18n.tr('%') |
447 | + anchors.fill: parent |
448 | + } |
449 | + } |
450 | + |
451 | + UbuntuShape { |
452 | + color: "#10000000" |
453 | + radius: "medium" |
454 | + |
455 | + width: shapeSize |
456 | + height: shapeSize |
457 | + |
458 | + Components.WeatherDetailComponent { |
459 | + objectName: "WindSpeedValue" |
460 | + value: currentWeather.windSpeed |
461 | + measure: i18n.tr("Wind speed") |
462 | + unit: currentWeather.speedScale + " " + currentWeather.windDir |
463 | + anchors.fill: parent |
464 | + } |
465 | + } |
466 | + |
467 | + UbuntuShape { |
468 | + color: "#10000000" |
469 | + radius: "medium" |
470 | + |
471 | + width: shapeSize |
472 | + height: shapeSize |
473 | + |
474 | + Components.WeatherDetailComponent { |
475 | + value: (currentWeather.propPrecip !== "") ? currentWeather.propPrecip: currentWeather.pressure |
476 | + measure: (currentWeather.propPrecip !== "") ? getProcipLabel(): i18n.tr("Pressure") |
477 | + unit: (currentWeather.propPrecip !== "") ? i18n.tr("Percent") : i18n.tr("mbar") |
478 | + anchors.fill: parent |
479 | + } |
480 | + } |
481 | + |
482 | + UbuntuShape { |
483 | + color: "#10000000" |
484 | + radius: "medium" |
485 | + |
486 | + width: shapeSize |
487 | + height: shapeSize |
488 | + |
489 | + Components.WeatherDetailComponent { |
490 | + objectName: "PrecipitationValue" |
491 | + value: (currentWeather.uvIndex !== "") ? currentWeather.uvIndex : currentWeather.precipitation |
492 | + measure: (currentWeather.uvIndex !== "") ? i18n.tr("UV index"): i18n.tr("Precipitation") |
493 | + unit: (currentWeather.uvIndex !== "") ? getUvLabel() : currentWeather.precipScale; |
494 | + anchors.fill: parent |
495 | + } |
496 | + } |
497 | + } |
498 | +} |
499 | |
500 | === added file 'components/CurrentWeatherFront.qml' |
501 | --- components/CurrentWeatherFront.qml 1970-01-01 00:00:00 +0000 |
502 | +++ components/CurrentWeatherFront.qml 2014-02-19 12:16:52 +0000 |
503 | @@ -0,0 +1,76 @@ |
504 | +/* |
505 | + * Copyright (C) 2013 Canonical Ltd |
506 | + * |
507 | + * This program is free software: you can redistribute it and/or modify |
508 | + * it under the terms of the GNU General Public License version 3 as |
509 | + * published by the Free Software Foundation. |
510 | + * |
511 | + * This program is distributed in the hope that it will be useful, |
512 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
513 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
514 | + * GNU General Public License for more details. |
515 | + * |
516 | + * You should have received a copy of the GNU General Public License |
517 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
518 | + * |
519 | + * Authored by: Raúl Yeguas <neokore@gmail.com> |
520 | + * Martin Borho <martin@borho.net> |
521 | + */ |
522 | +import QtQuick 2.0 |
523 | +import Ubuntu.Components 0.1 |
524 | +import Ubuntu.Layouts 0.1 |
525 | +import "./" as Components |
526 | + |
527 | +Rectangle { |
528 | + id: frontrect |
529 | + color: "transparent" |
530 | + |
531 | + property alias condition: currentCondition |
532 | + property alias conditionIcon: currentConditionIcon |
533 | + property alias conditionTempContent: currentConditionTempContent |
534 | + property alias conditionTemp: currentConditionTemp |
535 | + property int shapeSize: units.gu(15) |
536 | + |
537 | + UbuntuShape { |
538 | + id: currentCondition |
539 | + color: "#10000000" |
540 | + radius: "medium" |
541 | + |
542 | + width: shapeSize |
543 | + height: shapeSize |
544 | + anchors { |
545 | + horizontalCenter: parent.horizontalCenter |
546 | + horizontalCenterOffset: -(shapeSize*0.53)//units.gu(-8) |
547 | + verticalCenter: parent.verticalCenter |
548 | + } |
549 | + |
550 | + Components.WeatherConditionIconComponent { |
551 | + id: currentConditionIcon |
552 | + anchors.centerIn: parent |
553 | + anchors.margins: units.gu(1) |
554 | + condition: currentWeather.icon |
555 | + } |
556 | + } |
557 | + |
558 | + UbuntuShape { |
559 | + id: currentConditionTemp |
560 | + color: "#10000000" |
561 | + radius: "medium" |
562 | + width: shapeSize |
563 | + height: shapeSize |
564 | + anchors { |
565 | + horizontalCenter: parent.horizontalCenter |
566 | + horizontalCenterOffset: shapeSize*0.53//units.gu(8) |
567 | + verticalCenter: parent.verticalCenter |
568 | + } |
569 | + |
570 | + Components.WeatherTemperatureComponent { |
571 | + id: currentConditionTempContent |
572 | + currentTemp: Math.round(currentWeather.currentTemp) |
573 | + tempScale: currentWeather.tempScale |
574 | + minTemp: Math.round(currentWeather.minTemp) |
575 | + maxTemp: Math.round(currentWeather.maxTemp) |
576 | + anchors.fill: parent |
577 | + } |
578 | + } |
579 | +} |
580 | |
581 | === modified file 'components/LocationTab.qml' |
582 | --- components/LocationTab.qml 2014-02-15 14:31:10 +0000 |
583 | +++ components/LocationTab.qml 2014-02-19 12:16:52 +0000 |
584 | @@ -19,6 +19,8 @@ |
585 | import QtQuick 2.0 |
586 | import Ubuntu.Components.Popups 0.1 |
587 | import Ubuntu.Components 0.1 |
588 | +import Ubuntu.Components.ListItems 0.1 as ListItem |
589 | +import Ubuntu.Layouts 0.1 |
590 | import QtFeedback 5.0 |
591 | |
592 | Tab { |
593 | @@ -128,13 +130,103 @@ |
594 | id: dayForecastModel |
595 | } |
596 | |
597 | + Layouts { |
598 | + objectName: "WeatherLayout" |
599 | + id: layouts |
600 | + anchors.fill: parent |
601 | + layouts: [ |
602 | + ConditionalLayout { |
603 | + name: "WeatherData" |
604 | + when: layouts.width > units.gu(80) |
605 | + Rectangle { |
606 | + anchors.fill: parent |
607 | + color: "transparent" |
608 | + ItemLayout { |
609 | + item: "ForecastList" |
610 | + width: parent.width*0.625 |
611 | + height:parent.height |
612 | + } |
613 | + ItemLayout { |
614 | + item: "TabFooter" |
615 | + width: mainView.width*0.625 |
616 | + height: units.gu(8) |
617 | + anchors.bottom: parent.bottom |
618 | + clip: true |
619 | + } |
620 | + Rectangle { |
621 | + width: parent.width*0.375 |
622 | + height:parent.height |
623 | + anchors.right: parent.right |
624 | + anchors.top: parent.top |
625 | + color: "black" |
626 | + opacity: 0.3 |
627 | + } |
628 | + Rectangle { |
629 | + id: sideLabel |
630 | + anchors.top: parent.top |
631 | + anchors.right: parent.right |
632 | + width: parent.width*0.375 |
633 | + height: units.gu(6) |
634 | + color: "transparent" |
635 | + Label { |
636 | + text: i18n.tr("Forecast") |
637 | + fontSize: "large" |
638 | + anchors.left:parent.left |
639 | + anchors.leftMargin: units.gu(3) |
640 | + anchors.verticalCenter: parent.verticalCenter |
641 | + } |
642 | + } |
643 | + ListView { |
644 | + id: locationDailySide |
645 | + width: (parent.width*0.375)-units.gu(1) |
646 | + height: parent.height-sideLabel.height-units.gu(9) |
647 | + anchors.right: parent.right |
648 | + anchors.top: sideLabel.bottom |
649 | + model:dayForecastModel |
650 | + clip: true |
651 | + // TODO doubled code, to refactor |
652 | + property var conditionIcon: { |
653 | + "clear_day": "02", |
654 | + "clear_night": "12", |
655 | + "few_clouds_day": "05", |
656 | + "few_clouds_night": "04", |
657 | + "scattered_clouds_day": "05", |
658 | + "scattered_clouds_night": "04", |
659 | + "broken_clouds_day": "03", |
660 | + "broken_clouds_night": "03", |
661 | + "mostly_cloudy": "03", |
662 | + "shower_rain_day": "09", |
663 | + "shower_rain_night": "09", |
664 | + "rain_day": "09", |
665 | + "rain_night": "09", |
666 | + "thunderstorm_day": "13", |
667 | + "thunderstorm_night": "13", |
668 | + "snow_day": "14", |
669 | + "snow_night": "14", |
670 | + "chance_snow_day": "11", |
671 | + "chances_now_night": "11", |
672 | + "snow_shower": "11", |
673 | + "mist_day": "06", |
674 | + "mist_night": "06" |
675 | + } |
676 | + delegate: ListItem.Subtitled { |
677 | + subText: "H:"+Math.round(temp)+" L:"+Math.round(tempMin) |
678 | + text: date |
679 | + //selected: (dailyForecastList.currentIndex == index) |
680 | + iconSource: "../resources/images/"+locationDailySide.conditionIcon[dayForecastModel.get(index).condIcon]+".png" |
681 | + onClicked: { dailyForecastList.currentIndex = index } |
682 | + } |
683 | + } |
684 | + } |
685 | + } |
686 | + ] |
687 | ListView { |
688 | id: dailyForecastList |
689 | objectName: "DailyForecastList" |
690 | width: parent.width |
691 | height:parent.height |
692 | model:dayForecastModel |
693 | - |
694 | + Layouts.item: "ForecastList" |
695 | onCurrentIndexChanged: { |
696 | if(visible) { |
697 | var data = dayForecastModel.get(currentIndex) |
698 | @@ -195,11 +287,13 @@ |
699 | } |
700 | LastUpdatedComponent{ |
701 | id: lastUpdatedComponent |
702 | - anchors.bottom: (tabFooter.visible) ? tabFooter.top : parent.bottom |
703 | + anchors.bottom: parent.bottom |
704 | + anchors.bottomMargin: (tabFooter.visible) ? units.gu(8) : 0 |
705 | } |
706 | TabFooter { |
707 | id:tabFooter |
708 | objectName: "TabFooter" |
709 | + Layouts.item: "TabFooter" |
710 | visible: !dataProviderLogo.visible |
711 | } |
712 | Image { |
713 | @@ -236,7 +330,7 @@ |
714 | } |
715 | } |
716 | } |
717 | - |
718 | + } |
719 | |
720 | tools: ToolbarItems { |
721 | id: pageTools |
722 | |
723 | === added file 'components/ScrollingArea.qml' |
724 | --- components/ScrollingArea.qml 1970-01-01 00:00:00 +0000 |
725 | +++ components/ScrollingArea.qml 2014-02-19 12:16:52 +0000 |
726 | @@ -0,0 +1,112 @@ |
727 | +import QtQuick 2.0 |
728 | + |
729 | +MouseArea { |
730 | + id: flippedarea |
731 | + property bool wasHourlyScrolled: false |
732 | + property int startY: 0 |
733 | + property double startTime: 0 |
734 | + property int sectionHeight: flippedarea.height/hourly.count |
735 | + property int lastIndex: -1 |
736 | + anchors.fill: parent |
737 | + anchors.top: parent.top |
738 | + anchors.topMargin: units.gu(3.5) |
739 | + onClicked: { |
740 | + mouse.accepted = true; |
741 | + if(!wasHourlyScrolled) { |
742 | + var movement = Math.round(startY-mouse.y); |
743 | + if(movement < 10 && movement > -10) { |
744 | + // flip to detail data |
745 | + flipable.flipped = !flipable.flipped; |
746 | + } else { |
747 | + // switch to next/prevoius day |
748 | + if(movement >= 10) { |
749 | + dailyForecastList.incrementCurrentIndex(); |
750 | + } else if(movement <= -10) { |
751 | + dailyForecastList.decrementCurrentIndex(); |
752 | + } |
753 | + dailyForecastList.positionViewAtIndex(dailyForecastList.currentIndex,ListView.SnapPosition); |
754 | + flipable.flipped = false; |
755 | + } |
756 | + } |
757 | + } |
758 | + onPressed: { |
759 | + wasHourlyScrolled = false; |
760 | + startY = mouse.y; |
761 | + startTime = new Date().getTime() |
762 | + } |
763 | + onPositionChanged: { |
764 | + mouse.accepted = true; |
765 | + var distance = (parent.height - mouse.y), |
766 | + now = new Date().getTime(), |
767 | + speed = distance/(now-startTime); |
768 | + if(speed < 2.3 && !flipable.flipped) { |
769 | + // slow scrolling detected |
770 | + var movement = Math.round(distance/sectionHeight); |
771 | + if(movement > 0) { |
772 | + var hourIndex = movement-1, |
773 | + currentHour = currentWeather.hourly.get(hourIndex); |
774 | + if( currentHour !== undefined && (lastIndex < 0 || lastIndex !== hourIndex)) { |
775 | + wasHourlyScrolled = true; |
776 | + frontrect.conditionIcon.condition = currentHour.icon; |
777 | + var temp = currentHour[mainView.settings["units"]].temp; |
778 | + frontrect.conditionTempContent.currentTemp = temp; |
779 | + adjustBackground(Math.round(temp)); |
780 | + // adjust detail data |
781 | + currentWeather.humidity = currentHour.humidity |
782 | + currentWeather.windSpeed = currentHour[mainView.settings["units"]].windSpeed |
783 | + currentWeather.windDir = currentHour.windDir |
784 | + if(currentHour.propPrecip !== undefined && currentHour.propPrecip !== "") { |
785 | + currentWeather.propPrecip = currentHour.propPrecip; |
786 | + } else { |
787 | + currentWeather.pressure = currentHour.pressure |
788 | + } |
789 | + if(currentHour.uvIndex !== undefined && currentHour.uvIndex !== "") { |
790 | + currentWeather.uvIndex = currentHour.uvIndex; |
791 | + } else { |
792 | + var precip_units = (mainView.settings.precip_units === 'in') ? 'imperial' : 'metric'; |
793 | + currentWeather.precipitation = +(currentHour[precip_units].rain || currentHour[precip_units].snow || 0).toFixed(2) |
794 | + } |
795 | + // adjust date data |
796 | + var dateData = currentHour.date; |
797 | + var dateTime = new Date(dateData.year, dateData.month, dateData.date, dateData.hours, dateData.minutes) |
798 | + // TRANSLATORS: this is a date to which a time of the day will be appended |
799 | + var dateTimeString = Qt.formatDateTime(dateTime, i18n.tr('dddd, dd MMMM')) + ' - ' + Qt.formatTime(dateTime); |
800 | + dateComponent.dateString = dateTimeString; |
801 | + dateComponent.renderText(); |
802 | + // |
803 | + hourlyScrollEffect.start(); |
804 | + lastIndex = hourIndex; |
805 | + } |
806 | + } |
807 | + } |
808 | + } |
809 | + onReleased: { |
810 | + if(wasHourlyScrolled) { |
811 | + // reset temp and date to current day |
812 | + var currentDayData = dayForecastModel.get(dailyForecastList.currentIndex); |
813 | + frontrect.conditionIcon.condition = currentDayData.condIcon; |
814 | + frontrect.conditionIcon.appearAnimation.start(); |
815 | + frontrect.conditionTempContent.currentTemp = currentDayData.temp; |
816 | + // set back detail data |
817 | + currentWeather.humidity = currentDayData.humid |
818 | + currentWeather.windSpeed = currentDayData.wind_speed |
819 | + currentWeather.windDir = currentDayData.wind_dir |
820 | + if(currentDayData.prop_precip !== undefined && currentDayData.prop_precip !== "") { |
821 | + currentWeather.propPrecip = currentDayData.prop_precip; |
822 | + } else { |
823 | + currentWeather.pressure = currentDayData.press |
824 | + } |
825 | + if(currentDayData.uv !== undefined && currentDayData.uv !== "") { |
826 | + currentWeather.uvIndex = currentDayData.uv; |
827 | + } else { |
828 | + var precip_units = (mainView.settings.precip_units === 'in') ? 'imperial' : 'metric'; |
829 | + currentWeather.precipitation = currentDayData.precip |
830 | + } |
831 | + // set back date data |
832 | + adjustBackground(Math.round(currentDayData.temp)); |
833 | + dateComponent.dateString = currentDayData.date; |
834 | + dateComponent.renderText(); |
835 | + lastIndex = -1; |
836 | + } |
837 | + } |
838 | +} |
839 | |
840 | === modified file 'components/WeatherApi.js' |
841 | --- components/WeatherApi.js 2014-02-11 18:00:07 +0000 |
842 | +++ components/WeatherApi.js 2014-02-19 12:16:52 +0000 |
843 | @@ -214,20 +214,20 @@ |
844 | date: date, |
845 | metric: { |
846 | temp:data.main.temp, |
847 | - windSpeed: calcKmh(data.main.speed), |
848 | - rain: data.main.rain || 0, |
849 | - snow: data.main.snow || 0 |
850 | + windSpeed: calcKmh(data.wind.speed), |
851 | + rain: data.main.rain || ((data.rain) ? data.rain["3h"] : false ) || 0, |
852 | + snow: data.main.snow || ((data.snow) ? data.snow["3h"] : false ) || 0 |
853 | }, |
854 | imperial: { |
855 | temp: calcFahrenheit(data.main.temp), |
856 | - windSpeed: calcMph(data.main.speed), |
857 | - rain: calcInch(data.main.rain || 0), |
858 | - snow: calcInch(data.main.snow || 0) |
859 | + windSpeed: calcMph(data.wind.speed), |
860 | + rain: calcInch(data.main.rain || ((data.rain) ? data.rain["3h"] : false ) || 0), |
861 | + snow: calcInch(data.main.snow || ((data.snow) ? data.snow["3h"] : false ) ||0) |
862 | }, |
863 | humidity: data.main.humidity, |
864 | pressure: data.main.pressure, |
865 | - windDeg: data.main.deg, |
866 | - windDir: calcWindDir(data.main.deg), |
867 | + windDeg: data.wind.deg, |
868 | + windDir: calcWindDir(data.wind.deg), |
869 | icon: _icon_map[data.weather[0].icon], |
870 | condition: data.weather[0] |
871 | }; |
872 | |
873 | === added file 'key.js' |
874 | --- key.js 1970-01-01 00:00:00 +0000 |
875 | +++ key.js 2014-02-19 12:16:52 +0000 |
876 | @@ -0,0 +1,1 @@ |
877 | +var twcKey = ""; |
878 | |
879 | === removed file 'key.js' |
880 | --- key.js 2014-02-15 14:51:47 +0000 |
881 | +++ key.js 1970-01-01 00:00:00 +0000 |
882 | @@ -1,1 +0,0 @@ |
883 | -var twcKey = ""; |
884 | |
885 | === modified file 'tests/autopilot/ubuntu_weather_app/tests/test_settings.py' |
886 | --- tests/autopilot/ubuntu_weather_app/tests/test_settings.py 2014-01-24 13:58:48 +0000 |
887 | +++ tests/autopilot/ubuntu_weather_app/tests/test_settings.py 2014-02-19 12:16:52 +0000 |
888 | @@ -58,7 +58,7 @@ |
889 | 'QQuickText', objectName='CurrentTempText') |
890 | if units == "imperial": |
891 | self.assertThat(today_temp_scale.text, Eventually(Equals(u'°F'))) |
892 | - self.assertThat(today_temp.text, Eventually(Equals(u'26'))) |
893 | + self.assertThat(today_temp.text, Eventually(Equals(u'27'))) |
894 | self.assertThat(tomorrow_temp.text, Eventually(Equals(u'23'))) |
895 | else: |
896 | self.assertThat(today_temp_scale.text, Eventually(Equals(u'°C'))) |
FAILED: Continuous integration, rev:203 /code.launchpad .net/~martin- borho/ubuntu- weather- app/conditional -weather/ +merge/ 207152/ +edit-commit- message
No commit message was specified in the merge proposal. Click on the following link and set the commit message (if you want a jenkins rebuild you need to trigger it yourself):
https:/
http:// 91.189. 93.70:8080/ job/ubuntu- weather- app-ci/ 143/ 91.189. 93.70:8080/ job/ubuntu- weather- app-raring- amd64-ci/ 141 91.189. 93.70:8080/ job/ubuntu- weather- app-saucy- amd64-ci/ 141 91.189. 93.70:8080/ job/ubuntu- weather- app-trusty- amd64-ci/ 55
Executed test runs:
SUCCESS: http://
SUCCESS: http://
SUCCESS: http://
Click here to trigger a rebuild: 91.189. 93.70:8080/ job/ubuntu- weather- app-ci/ 143/rebuild
http://