Merge lp:~ken-vandine/dropping-letters/toolbar into lp:dropping-letters
- toolbar
- Merge into trunk
Proposed by
Ken VanDine
Status: | Merged |
---|---|
Approved by: | Alan Pope πΊπ§π± π¦ |
Approved revision: | 29 |
Merged at revision: | 24 |
Proposed branch: | lp:~ken-vandine/dropping-letters/toolbar |
Merge into: | lp:dropping-letters |
Diff against target: |
1291 lines (+608/-602) 5 files modified
debian/changelog (+11/-1) debian/control (+2/-2) debian/install (+2/-1) dropping-letters.qml (+592/-597) dropping-letters.qmlproject (+1/-1) |
To merge this branch: | bzr merge lp:~ken-vandine/dropping-letters/toolbar |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Alan Pope πΊπ§π± π¦ (community) | Approve | ||
Review via email: mp+162706@code.launchpad.net |
Commit message
* Use a toolbar for volume and new game instead of the small items on the
bottombar
* Add HUD support
Description of the change
* Use a toolbar for volume and new game instead of the small items on the
bottombar
* Add HUD support
To post a comment you must log in.
- 28. By Ken VanDine
-
Use a toolbar for volume and new game instead of the small items on the
bottombar - 29. By Ken VanDine
-
added New game to HUD
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'debian/changelog' |
2 | --- debian/changelog 2013-05-01 05:01:59 +0000 |
3 | +++ debian/changelog 2013-05-07 05:11:28 +0000 |
4 | @@ -1,4 +1,14 @@ |
5 | -dropping-letters (0.1) UNRELEASED; urgency=low |
6 | +dropping-letters (0.1.1) UNRELEASED; urgency=low |
7 | + |
8 | + * Use a toolbar for volume and new game instead of the small items on the |
9 | + bottombar |
10 | + * Add HUD support |
11 | + * debian/control |
12 | + - depend on qtdeclarative5-hud1.0 |
13 | + |
14 | + -- Ken VanDine <ken.vandine@canonical.com> Wed, 01 May 2013 18:00:42 -0700 |
15 | + |
16 | +dropping-letters (0.1) raring; urgency=low |
17 | |
18 | * Initial Release. |
19 | |
20 | |
21 | === modified file 'debian/control' |
22 | --- debian/control 2013-05-01 05:01:59 +0000 |
23 | +++ debian/control 2013-05-07 05:11:28 +0000 |
24 | @@ -5,11 +5,11 @@ |
25 | Build-Depends: debhelper (>= 9.0.0) |
26 | Standards-Version: 3.9.4 |
27 | Homepage: http://launchpad.net/dropping-letters |
28 | -Vcs-Bzr: https://code.launchpad.net/~sil/dropping-letters |
29 | +Vcs-Bzr: https://code.launchpad.net/~dropping-letters-devs/dropping-letters/trunk |
30 | |
31 | Package: dropping-letters |
32 | Architecture: all |
33 | -Depends: ${misc:Depends},qtdeclarative5-localstorage-plugin,qtdeclarative5-particles-plugin,qtdeclarative5-qtmultimedia-plugin,qtdeclarative5-qtquick2-plugin,qtdeclarative5-ubuntu-ui-toolkit-plugin|qt-components-ubuntu,qtdeclarative5-window-plugin,qtdeclarative5-xmllistmodel-plugin,qmlscene |
34 | +Depends: ${misc:Depends},qtdeclarative5-hud1.0,qtdeclarative5-localstorage-plugin,qtdeclarative5-particles-plugin,qtdeclarative5-qtmultimedia-plugin,qtdeclarative5-qtquick2-plugin,qtdeclarative5-ubuntu-ui-toolkit-plugin|qt-components-ubuntu,qtdeclarative5-window-plugin,qtdeclarative5-xmllistmodel-plugin,qmlscene |
35 | Description: Dropping Letters game |
36 | Build up words from falling letters to score |
37 | points. Don't let the letters build up to the |
38 | |
39 | === modified file 'debian/install' |
40 | --- debian/install 2013-05-01 05:01:59 +0000 |
41 | +++ debian/install 2013-05-07 05:11:28 +0000 |
42 | @@ -1,5 +1,6 @@ |
43 | -dropping-letters-ubuntu.qml /usr/share/dropping-letters |
44 | +dropping-letters.qml /usr/share/dropping-letters |
45 | volume-sprite.png /usr/share/dropping-letters |
46 | +new.png /usr/share/dropping-letters |
47 | test_load_binarydict.js /usr/share/dropping-letters |
48 | 80921__justinbw__buttonchime02up.ogg /usr/share/dropping-letters |
49 | audio-volume-high.svg /usr/share/dropping-letters |
50 | |
51 | === renamed file 'dropping-letters-ubuntu.qml' => 'dropping-letters.qml' |
52 | --- dropping-letters-ubuntu.qml 2013-05-01 06:10:15 +0000 |
53 | +++ dropping-letters.qml 2013-05-07 05:11:28 +0000 |
54 | @@ -5,6 +5,7 @@ |
55 | import QtQuick.LocalStorage 2.0 |
56 | import Ubuntu.Components 0.1 |
57 | import Ubuntu.Components.Popups 0.1 |
58 | +import Ubuntu.HUD 1.0 as HUD |
59 | |
60 | MainView { |
61 | id: mainView |
62 | @@ -12,617 +13,598 @@ |
63 | width: units.gu(45) // 48 * 7 + 2 * 7 + 2 |
64 | height: units.gu(65) // 48 * 10 + 2 * 10 + 50 |
65 | |
66 | - Flipable { |
67 | - id: flipable |
68 | - property bool flipped: false |
69 | - property variant db: null |
70 | - anchors.fill: parent |
71 | - |
72 | - transform: Rotation { |
73 | - id: rotation |
74 | - origin.x: flipable.width/2 |
75 | - origin.y: flipable.height/2 |
76 | - axis.x: 0; axis.y: 1; axis.z: 0 // set axis.y to 1 to rotate around y-axis |
77 | - angle: 0 // the default angle |
78 | - } |
79 | - property int minChromeHeight: 50 |
80 | - |
81 | - Component.onCompleted: { |
82 | - var db = LocalStorage.openDatabaseSync("dropping-letters", "1.0", "Dropping Letters", 1000); |
83 | - db.transaction(function(tx) { |
84 | - // Create the database if it doesn't already exist |
85 | - tx.executeSql('CREATE TABLE IF NOT EXISTS Scores(score INT, time TEXT)'); |
86 | - var res = tx.executeSql('SELECT score from Scores order by score DESC LIMIT 1'); |
87 | - if (res.rows.length === 0) { |
88 | - bestscore.updateScore(0); |
89 | - } else { |
90 | - bestscore.updateScore(res.rows.item(0).score); |
91 | - } |
92 | - }); |
93 | - } |
94 | - |
95 | - states: [ |
96 | - State { |
97 | - name: "back" |
98 | - PropertyChanges { target: rotation; angle: 180 } |
99 | - when: flipable.flipped |
100 | - }, |
101 | - State { |
102 | - name: "front" |
103 | - when: !flipable.flipped |
104 | - } |
105 | - ] |
106 | - |
107 | - transitions: [ |
108 | - Transition { |
109 | - NumberAnimation { target: rotation; property: "angle"; duration: 200 } |
110 | - } |
111 | - ] |
112 | - |
113 | - front: Rectangle { |
114 | - id: entry |
115 | - color: "#efefea" |
116 | - width: flipable.width // 48 * 7 + 2 * 7 + 2 |
117 | - height: flipable.height // 48 * 10 + 2 * 10 + 50 |
118 | - |
119 | - Column { |
120 | - id: logo |
121 | - anchors.centerIn: parent |
122 | - //spacing: units.dp(2) // 2 |
123 | - Repeater { |
124 | - id: titleRowRepeater |
125 | - model: ["DROP", "PING", "LETT", "ERS "] |
126 | - Row { |
127 | - id: titleRow |
128 | - //spacing: units.dp(2) // 2 |
129 | - property int lineIndex: index |
130 | - property string modelString: modelData |
131 | - Repeater { |
132 | - id: titleColRepeater |
133 | - model: modelData.split("") |
134 | - Rectangle { |
135 | - id: titleletter |
136 | - width: Math.max(flipable.width * 0.4, flipable.height * 0.4) / titleRowRepeater.count - titleRowRepeater.count * titleRow.spacing |
137 | - height: Math.max(flipable.width * 0.4, flipable.height * 0.4) / titleRowRepeater.count - titleRowRepeater.count * titleRow.spacing |
138 | - color: Qt.hsla(210/360, 0.84, 0.25 + ((4-parent.lineIndex) * 0.05) + ((4-index) * 0.05)); |
139 | - //radius: "medium" |
140 | - Label { |
141 | - text: modelData |
142 | - anchors.centerIn: parent |
143 | - fontSize: "x-large" |
144 | - font.bold: true |
145 | - color: "#ffffff" |
146 | - } |
147 | - states: [ |
148 | - State { name: "showing"; when: flipable.state == "front" |
149 | - PropertyChanges { target: titleletter; y: 0 } |
150 | - }, |
151 | - State { name: "notshowing"; when: flipable.state != "front" |
152 | - PropertyChanges { target: titleletter; y: -units.gu(300) } |
153 | - } |
154 | - ] |
155 | - Behavior on y { |
156 | - SequentialAnimation { |
157 | - PauseAnimation { |
158 | - duration: (35 * parent.modelString.length * (4-parent.lineIndex)) + ( |
159 | - 35 * index) } |
160 | - NumberAnimation { easing.type: Easing.OutQuart } |
161 | - } |
162 | - } |
163 | - } |
164 | - } |
165 | - } |
166 | - } |
167 | - } |
168 | - Label { |
169 | - id: playbutton |
170 | - text: "play" |
171 | - anchors.top: logo.bottom |
172 | - anchors.topMargin: units.gu(2) |
173 | - anchors.horizontalCenter: logo.horizontalCenter |
174 | - fontSize: "x-large" |
175 | - color: "#222222" |
176 | - } |
177 | - Label { |
178 | - id: bestscore |
179 | - property int bestsofar: 0 |
180 | - text: "..." |
181 | - anchors.top: playbutton.bottom |
182 | - anchors.topMargin: units.gu(2) |
183 | - anchors.horizontalCenter: logo.horizontalCenter |
184 | - fontSize: "large" |
185 | - color: "#222222" |
186 | - function updateScore(score) { |
187 | - if (score >= bestscore.bestsofar) { |
188 | - bestscore.text = "Best score: " + score; |
189 | - bestscore.bestsofar = score; |
190 | - } |
191 | - } |
192 | - } |
193 | - MouseArea { |
194 | - anchors.fill: parent |
195 | - enabled: !flipable.flipped |
196 | - onClicked: { |
197 | - lm.clear(); |
198 | - for (var i=0; i<7; i++) { |
199 | - lm.append({'letters': [] }); |
200 | - } |
201 | - accum.text = ""; |
202 | - droptimer.tickCount = 0; |
203 | - flipable.flipped = true |
204 | - } |
205 | - } |
206 | - |
207 | - Rectangle { |
208 | - id: helpbutton |
209 | - width: units.gu(5) |
210 | - height: units.gu(5) |
211 | - radius: units.gu(1) |
212 | - Label { |
213 | - text: "?" |
214 | - anchors.centerIn: parent |
215 | - } |
216 | - anchors.top: parent.top |
217 | - anchors.right: parent.right |
218 | - anchors.margins: units.gu(2) |
219 | - MouseArea { |
220 | - anchors.fill: parent |
221 | - onClicked: { |
222 | - PopupUtils.open(helppop, helpbutton) |
223 | - } |
224 | - } |
225 | - } |
226 | - Component { |
227 | - id: helppop |
228 | - Popover { |
229 | - id: helpsheet |
230 | - Rectangle { |
231 | - anchors.top: parent.top |
232 | - anchors.left: parent.left |
233 | - anchors.right: parent.right |
234 | - height: units.gu(15) |
235 | - border.color: "#ddd" |
236 | - radius: 2 |
237 | - Label { |
238 | - anchors.fill: parent |
239 | - anchors.margins: units.gu(1) |
240 | - text: "game by <a href='http://twitter.com/sil'>@sil</a><br>music: <a href='http://incompetech.com/music/royalty-free/index.html?isrc=USUAN1200076'>Easy Lemon</a> from Kevin McCloud (incompetech.com)<br>sounds: freesound from <a href='http://www.freesound.org/people/kantouth/sounds/106727/'>kantouth</a> / <a href='http://www.freesound.org/people/tictacshutup/sounds/407/'>tictacshutup</a> / <a href='http://www.freesound.org/people/dj-chronos/sounds/45137/'>dj-chronos</a> / <a href='http://www.freesound.org/people/justinbw/sounds/80921/'>justinbw</a>" |
241 | - wrapMode: Text.WordWrap |
242 | - textFormat: Text.StyledText |
243 | - onLinkActivated: Qt.openUrlExternally(link) |
244 | - } |
245 | - } |
246 | - } |
247 | - } |
248 | - |
249 | - } |
250 | - |
251 | - back: Rectangle { |
252 | - id: main |
253 | - color: "#58585A" |
254 | - width: flipable.width // 48 * 7 + 2 * 7 + 2 |
255 | - height: flipable.height // 48 * 10 + 2 * 10 + 50 |
256 | - property var selectedItems: [] |
257 | - /* |
258 | - obtained with: |
259 | - import re; fp=open('/usr/share/dict/words'); |
260 | - shorts=[re.sub('[^a-zA-Z]','',x.lower().strip()) for x in fp if len(x)<7]; |
261 | - from collections import Counter; c=Counter(''.join(shorts)); least=c.most_common()[-1][1]; |
262 | - print dict([(x.upper(),c[x]/least) for x in c]) |
263 | - */ |
264 | - property variant letterFreqs: { |
265 | - 'A': 66, 'C': 22, 'B': 19, 'E': 72, 'D': 28, 'G': 18, 'F': 12, 'I': 41, 'H': 20, |
266 | - 'K': 14, 'J': 4, 'M': 22, 'L': 40, 'O': 48, 'N': 35, 'Q': 1, 'P': 22, 'S': 75, |
267 | - 'R': 43, 'U': 26, 'T': 37, 'W': 13, 'V': 7, 'Y': 19, 'X': 3, 'Z': 4 |
268 | - } |
269 | - property variant letterScores: { |
270 | - "A":1,"B":3,"C":3,"D":2,"E":1,"F":4,"G":2,"H":4,"I":1,"J":8,"K":5,"L":1, |
271 | - "M":3,"N":1,"O":1,"P":3,"Q":10,"R":1,"S":1,"T":1,"U":1,"V":4,"W":4,"X":8, |
272 | - "Y":4,"Z":10 |
273 | - } |
274 | - property int score: 0 |
275 | - |
276 | - function getRandomWeightedLetter() { |
277 | - // could work out sumOfWeights once, but this is easier to understand |
278 | - var sumOfWeights = 0; |
279 | - for (var k in main.letterFreqs) { sumOfWeights += main.letterFreqs[k]; } |
280 | - var selection = Math.floor(Math.random() * sumOfWeights); |
281 | - for (var k in main.letterFreqs) { |
282 | - if (selection < main.letterFreqs[k]) return k; |
283 | - selection -= main.letterFreqs[k]; |
284 | - } |
285 | - } |
286 | - |
287 | - Audio { |
288 | - id: music |
289 | - source: "Easy_Lemon_60_second.ogg" |
290 | - autoPlay: true |
291 | - onStopped: music.play() |
292 | - muted: !volume.audible |
293 | - } |
294 | - |
295 | - Audio { |
296 | - id: click |
297 | - source: "407__tictacshutup__click-1-off-click.ogg" |
298 | - autoLoad: true |
299 | - muted: !volume.audible |
300 | - } |
301 | - |
302 | - Audio { |
303 | - id: success |
304 | - source: "80921__justinbw__buttonchime02up.ogg" |
305 | - autoLoad: true |
306 | - muted: !volume.audible |
307 | - } |
308 | - |
309 | - Audio { |
310 | - id: failure |
311 | - source: "106727__kantouth__cartoon-bing-low.ogg" |
312 | - autoLoad: true |
313 | - muted: !volume.audible |
314 | - } |
315 | - |
316 | - Audio { |
317 | - id: gameover |
318 | - source: "45137__dj-chronos__dark-church-bell.ogg" |
319 | - autoLoad: true |
320 | - onStopped: { |
321 | - flipable.flipped = false |
322 | - } |
323 | - muted: !volume.audible |
324 | - } |
325 | - |
326 | - Rectangle { |
327 | - id: bottombar |
328 | - anchors.bottom: main.bottom |
329 | - anchors.left: main.left |
330 | - anchors.right: main.right |
331 | - height: (main.height - (game.squaresize * 10 + 11)) / 2 |
332 | - z: 2 |
333 | - color: Qt.hsla(210/360, 0.84, 0.2) |
334 | - |
335 | - Rectangle { |
336 | - id: mainscore |
337 | - anchors.right: quitgame.left |
338 | - anchors.top: bottombar.top |
339 | - anchors.bottom: bottombar.bottom |
340 | - anchors.left: volume.right |
341 | - z: 2 |
342 | - color: Qt.rgba(0,0,0,0) |
343 | - Label { |
344 | - anchors.centerIn: parent |
345 | - fontSize: "x-large" |
346 | - text: "" + main.score |
347 | - color: "white" |
348 | - } |
349 | - } |
350 | - |
351 | - Rectangle { |
352 | - id: quitgame |
353 | - width: bottombar.height |
354 | - height: bottombar.height |
355 | - color: Qt.rgba(0,0,0,0) |
356 | - anchors.right: bottombar.right |
357 | - anchors.top: bottombar.top |
358 | - z: 3 |
359 | - |
360 | - Label { |
361 | - anchors.centerIn: parent |
362 | - text: "\u00d7" |
363 | - fontSize: "x-large" |
364 | - color: "white" |
365 | - MouseArea { |
366 | - anchors.fill: parent |
367 | - onClicked: { |
368 | - flipable.flipped = false; |
369 | - } |
370 | - } |
371 | - } |
372 | - } |
373 | - |
374 | - Rectangle { |
375 | - id: volume |
376 | - width: bottombar.height |
377 | - height: bottombar.height + 1 |
378 | - color: Qt.rgba(0,0,0,0) |
379 | - anchors.left: bottombar.left |
380 | - anchors.bottom: bottombar.bottom |
381 | - z: 3 |
382 | - clip: true |
383 | - property int frame: 0 |
384 | - property bool reverse: false |
385 | - property bool audible: true |
386 | - Image { |
387 | - id: image |
388 | - sourceSize.width: parent.height * 0.8 |
389 | - sourceSize.height: parent.height * 0.8 |
390 | - anchors.centerIn: parent |
391 | - source: volume.audible ? "audio-volume-high-symbolic.svg" : "audio-volume-muted-symbolic.svg"; |
392 | - } |
393 | - MouseArea { |
394 | - anchors.fill: parent |
395 | - onClicked: { |
396 | - volume.audible = !volume.audible |
397 | - } |
398 | - } |
399 | - } |
400 | - } |
401 | - |
402 | - Rectangle { |
403 | - id: topbar |
404 | - color: "blue" |
405 | - anchors.top: main.top |
406 | - anchors.left: main.left |
407 | - anchors.right: main.right |
408 | - height: (main.height - (game.squaresize * 10 + 11)) / 2 |
409 | - z: 2 |
410 | - |
411 | - Rectangle { |
412 | - anchors.fill: topbar |
413 | - z: 2 |
414 | - color: accum.text == "" ? "#efefea" : (accum.isValid ? Qt.hsla(124/360, 0.83, 0.45) : Qt.hsla(0, 0.83, 0.65)) |
415 | - id: suggestedWordContainer |
416 | - Label { |
417 | - id: accum |
418 | - anchors.centerIn: parent |
419 | - text: "" |
420 | - color: "white" |
421 | - fontSize: "x-large" |
422 | - font.bold: true |
423 | - property bool isValid: false |
424 | - function findBinaryWord( word ) { |
425 | - var bd = Wordlist.wordlist; |
426 | - var l = word.length; |
427 | - // Don't search if there's nothing to look through |
428 | - if ( !bd[l] ) { |
429 | - return false; |
430 | - } |
431 | - // Get the number of words in the dictionary bin |
432 | - var words = bd[l].length / l, |
433 | - // The low point from where we're starting the binary search |
434 | - low = 0, |
435 | - // The max high point |
436 | - high = words - 1, |
437 | - // And the precise middle of the search |
438 | - mid = Math.floor( words / 2 ); |
439 | - // We continue to look until we reach a final word |
440 | - while ( high >= low ) { |
441 | - // Grab the word at our current position |
442 | - var found = bd[l].substr( l * mid, l ); |
443 | - // If we've found the word, stop now |
444 | - if ( word === found ) { |
445 | - return true; |
446 | - } |
447 | - // Otherwise, compare |
448 | - // If we're too high, move lower |
449 | - if ( word < found ) { |
450 | - high = mid - 1; |
451 | - // If we're too low, go higher |
452 | - } else { |
453 | - low = mid + 1; |
454 | - } |
455 | - // And find the new search point |
456 | - mid = Math.floor( (low + high) / 2 ); |
457 | - } |
458 | - // Nothing was found |
459 | - return false; |
460 | - } |
461 | - onTextChanged: { |
462 | - accum.isValid = findBinaryWord(accum.text); |
463 | - } |
464 | - } |
465 | - function processSuggestedWord() { |
466 | - if (accum.isValid) { |
467 | - success.play(); |
468 | - var thisscore = 0, wordlength = accum.text.length; |
469 | - accum.text = ""; |
470 | - |
471 | - // tell the boxes to destroy themselves |
472 | - main.selectedItems.forEach(function(b) { |
473 | - thisscore += main.letterScores[b.containedLetter]; |
474 | - b.state = "dead"; |
475 | - }) |
476 | - main.selectedItems = []; |
477 | - main.score += thisscore * wordlength; |
478 | - scoredisplay.text = "" + (thisscore * wordlength); |
479 | - showscoredisplay.start(); |
480 | - } else { |
481 | - failure.play(); |
482 | - accum.text = ""; |
483 | - main.selectedItems.forEach(function(b) { b.selected = false; }) |
484 | - main.selectedItems = []; |
485 | - } |
486 | - } |
487 | - focus: true |
488 | - Keys.onReturnPressed: { |
489 | - suggestedWordContainer.processSuggestedWord(); |
490 | - } |
491 | - MouseArea { |
492 | - anchors.fill: parent |
493 | - onClicked: { suggestedWordContainer.processSuggestedWord(); } |
494 | - } |
495 | - } |
496 | - |
497 | - |
498 | - } |
499 | - |
500 | - Label { |
501 | - id: scoredisplay |
502 | - anchors.centerIn: parent |
503 | - z: 3 |
504 | - fontSize: "x-large" |
505 | - text: "200" |
506 | - color: "red" |
507 | - opacity: 0 |
508 | - } |
509 | - |
510 | - ParallelAnimation { |
511 | - id: showscoredisplay |
512 | - NumberAnimation { |
513 | - property: "scale" |
514 | - from: 0.1 |
515 | - to: 8.0 |
516 | - duration: 400 |
517 | - target: scoredisplay |
518 | - } |
519 | - SequentialAnimation { |
520 | - NumberAnimation { |
521 | - property: "opacity" |
522 | - from: 0 |
523 | - to: 1.0 |
524 | - duration: 20 |
525 | - target: scoredisplay |
526 | - } |
527 | - NumberAnimation { |
528 | - property: "opacity" |
529 | - from: 1.0 |
530 | - to: 0 |
531 | - duration: 380 |
532 | - target: scoredisplay |
533 | - } |
534 | - } |
535 | - } |
536 | - |
537 | - |
538 | - Timer { |
539 | - id: droptimer |
540 | - repeat: true |
541 | - running: flipable.flipped |
542 | - interval: 2000 |
543 | - property int tickCount: 0 |
544 | - triggeredOnStart: true |
545 | - onTriggered: { |
546 | - tickCount += 5 |
547 | - droptimer.interval = 2000 - tickCount |
548 | - var idx = Math.round(Math.random() * (lm.count - 1)); |
549 | - lm.get(idx).letters.append({ letter: main.getRandomWeightedLetter() }); |
550 | - if (lm.get(idx).letters.count >= 10) { |
551 | - droptimer.stop(); |
552 | - gameover.play(); |
553 | - var db = LocalStorage.openDatabaseSync("dropping-letters", "1.0", "Dropping Letters", 1000); |
554 | - db.transaction(function(tx) { |
555 | - tx.executeSql("insert into Scores values (?,?)", [main.score, 0]); |
556 | - bestscore.updateScore(main.score); |
557 | - }); |
558 | - } |
559 | - } |
560 | - } |
561 | - |
562 | - ListModel { |
563 | - id: lm |
564 | - } |
565 | - |
566 | - |
567 | - Rectangle { |
568 | - id: game |
569 | - property int squaresize: Math.min((flipable.width) / 7, (flipable.height - (flipable.minChromeHeight * 2)) / 10) |
570 | - anchors.top: topbar.bottom |
571 | - anchors.bottom: bottombar.top |
572 | - anchors.left: main.left |
573 | - anchors.right: main.right |
574 | - scale: -1 |
575 | + |
576 | + function resetGame () { |
577 | + lm.clear(); |
578 | + for (var i=0; i<7; i++) { |
579 | + lm.append({'letters': [] }); |
580 | + } |
581 | + accum.text = ""; |
582 | + droptimer.tickCount = 0; |
583 | + flipable.flipped = true; |
584 | + } |
585 | + |
586 | + Page { |
587 | + tools: ToolbarActions { |
588 | + Action { |
589 | + text: i18n.tr("Volume") |
590 | + iconSource: (volume.audible ? "audio-volume-high-symbolic.svg" : "audio-volume-muted-symbolic.svg") |
591 | + onTriggered: { |
592 | + volume.audible = !volume.audible; |
593 | + } |
594 | + } |
595 | + Action { |
596 | + text: i18n.tr("New game") |
597 | + iconSource: ("new.png") |
598 | + onTriggered: { |
599 | + resetGame(); |
600 | + } |
601 | + } |
602 | + } |
603 | + |
604 | + Item { |
605 | + id: volume |
606 | + property int frame: 0 |
607 | + property bool reverse: false |
608 | + property bool audible: true |
609 | + } |
610 | + |
611 | + Flipable { |
612 | + id: flipable |
613 | + property bool flipped: false |
614 | + property variant db: null |
615 | + anchors.fill: parent |
616 | + |
617 | + transform: Rotation { |
618 | + id: rotation |
619 | + origin.x: flipable.width/2 |
620 | + origin.y: flipable.height/2 |
621 | + axis.x: 0; axis.y: 1; axis.z: 0 // set axis.y to 1 to rotate around y-axis |
622 | + angle: 0 // the default angle |
623 | + } |
624 | + property int minChromeHeight: 50 |
625 | + |
626 | + Component.onCompleted: { |
627 | + var db = LocalStorage.openDatabaseSync("dropping-letters", "1.0", "Dropping Letters", 1000); |
628 | + db.transaction(function(tx) { |
629 | + // Create the database if it doesn't already exist |
630 | + tx.executeSql('CREATE TABLE IF NOT EXISTS Scores(score INT, time TEXT)'); |
631 | + var res = tx.executeSql('SELECT score from Scores order by score DESC LIMIT 1'); |
632 | + if (res.rows.length === 0) { |
633 | + bestscore.updateScore(0); |
634 | + } else { |
635 | + bestscore.updateScore(res.rows.item(0).score); |
636 | + } |
637 | + }); |
638 | + } |
639 | + |
640 | + states: [ |
641 | + State { |
642 | + name: "back" |
643 | + PropertyChanges { target: rotation; angle: 180 } |
644 | + when: flipable.flipped |
645 | + }, |
646 | + State { |
647 | + name: "front" |
648 | + when: !flipable.flipped |
649 | + } |
650 | + ] |
651 | + |
652 | + transitions: [ |
653 | + Transition { |
654 | + NumberAnimation { target: rotation; property: "angle"; duration: 200 } |
655 | + } |
656 | + ] |
657 | + |
658 | + front: Rectangle { |
659 | + id: entry |
660 | color: "#efefea" |
661 | - Row { |
662 | - anchors.horizontalCenter: game.horizontalCenter |
663 | - anchors.top: game.top |
664 | - anchors.topMargin: 1 |
665 | - //spacing: 1 |
666 | + width: flipable.width // 48 * 7 + 2 * 7 + 2 |
667 | + height: flipable.height // 48 * 10 + 2 * 10 + 50 |
668 | + |
669 | + Column { |
670 | + id: logo |
671 | + anchors.centerIn: parent |
672 | + //spacing: units.dp(2) // 2 |
673 | Repeater { |
674 | - model: lm |
675 | - Column { |
676 | - //spacing: 1 |
677 | - property int idx: index |
678 | - width: game.squaresize |
679 | - height: game.height |
680 | - add: Transition { |
681 | - NumberAnimation { properties: "y"; easing.type: Easing.OutBounce; duration: 1000 } |
682 | - } |
683 | - move: Transition { |
684 | - NumberAnimation { properties: "y"; easing.type: Easing.OutBounce } |
685 | - } |
686 | + id: titleRowRepeater |
687 | + model: ["DROP", "PING", "LETT", "ERS "] |
688 | + Row { |
689 | + id: titleRow |
690 | + //spacing: units.dp(2) // 2 |
691 | + property int lineIndex: index |
692 | + property string modelString: modelData |
693 | Repeater { |
694 | - model: letters |
695 | + id: titleColRepeater |
696 | + model: modelData.split("") |
697 | Rectangle { |
698 | - id: box |
699 | - property bool selected: false |
700 | - property int idx: index |
701 | - property string containedLetter: letter |
702 | - color: { |
703 | - if (lm.get(parent.idx).letters.count >= 10) { |
704 | - return "red"; |
705 | - } else if (!selected) { |
706 | - return Qt.hsla(210/360, 0.84, 0.25 + (idx * 0.05)); |
707 | - } else if (accum.isValid) { |
708 | - return Qt.hsla(124/360, 0.83, 0.45); // "#93cc98"; |
709 | - } else { |
710 | - return Qt.hsla(0, 0.83, 0.65); // "#cc9598" |
711 | - } |
712 | - } |
713 | + id: titleletter |
714 | + width: Math.max(flipable.width * 0.4, flipable.height * 0.4) / titleRowRepeater.count - titleRowRepeater.count * titleRow.spacing |
715 | + height: Math.max(flipable.width * 0.4, flipable.height * 0.4) / titleRowRepeater.count - titleRowRepeater.count * titleRow.spacing |
716 | + color: Qt.hsla(210/360, 0.84, 0.25 + ((4-parent.lineIndex) * 0.05) + ((4-index) * 0.05)); |
717 | //radius: "medium" |
718 | - scale: -1 |
719 | - width: game.squaresize |
720 | - height: game.squaresize |
721 | - y: game.height + game.squaresize |
722 | - z: 5 |
723 | Label { |
724 | + text: modelData |
725 | anchors.centerIn: parent |
726 | - text: letter |
727 | - fontSize: "large" |
728 | + fontSize: "x-large" |
729 | font.bold: true |
730 | color: "#ffffff" |
731 | } |
732 | - MouseArea { |
733 | - anchors.fill: parent |
734 | - onClicked: { |
735 | - if (!box.selected) { |
736 | - box.selected = true; |
737 | - accum.text += letter; |
738 | - click.play(); |
739 | - main.selectedItems[main.selectedItems.length] = box; |
740 | + states: [ |
741 | + State { name: "showing"; when: flipable.state == "front" |
742 | + PropertyChanges { target: titleletter; y: 0 } |
743 | + }, |
744 | + State { name: "notshowing"; when: flipable.state != "front" |
745 | + PropertyChanges { target: titleletter; y: -units.gu(300) } |
746 | + } |
747 | + ] |
748 | + Behavior on y { |
749 | + SequentialAnimation { |
750 | + PauseAnimation { |
751 | + duration: (35 * parent.modelString.length * (4-parent.lineIndex)) + ( |
752 | + 35 * index) } |
753 | + NumberAnimation { easing.type: Easing.OutQuart } |
754 | + } |
755 | + } |
756 | + } |
757 | + } |
758 | + } |
759 | + } |
760 | + } |
761 | + Label { |
762 | + id: playbutton |
763 | + text: i18n.tr("Play") |
764 | + anchors.top: logo.bottom |
765 | + anchors.topMargin: units.gu(2) |
766 | + anchors.horizontalCenter: logo.horizontalCenter |
767 | + fontSize: "x-large" |
768 | + color: "#222222" |
769 | + MouseArea { |
770 | + anchors.fill: parent |
771 | + enabled: !flipable.flipped |
772 | + onClicked: { |
773 | + resetGame(); |
774 | + } |
775 | + } |
776 | + } |
777 | + Label { |
778 | + id: bestscore |
779 | + property int bestsofar: 0 |
780 | + text: "..." |
781 | + anchors.top: playbutton.bottom |
782 | + anchors.topMargin: units.gu(2) |
783 | + anchors.horizontalCenter: logo.horizontalCenter |
784 | + fontSize: "large" |
785 | + color: "#222222" |
786 | + function updateScore(score) { |
787 | + if (score >= bestscore.bestsofar) { |
788 | + bestscore.text = "Best score: " + score; |
789 | + bestscore.bestsofar = score; |
790 | + } |
791 | + } |
792 | + } |
793 | + |
794 | + Rectangle { |
795 | + id: helpbutton |
796 | + width: units.gu(5) |
797 | + height: units.gu(5) |
798 | + radius: units.gu(1) |
799 | + Label { |
800 | + text: "?" |
801 | + anchors.centerIn: parent |
802 | + } |
803 | + anchors.top: parent.top |
804 | + anchors.right: parent.right |
805 | + anchors.margins: units.gu(2) |
806 | + MouseArea { |
807 | + anchors.fill: parent |
808 | + onClicked: { |
809 | + PopupUtils.open(helppop, helpbutton) |
810 | + } |
811 | + } |
812 | + } |
813 | + Component { |
814 | + id: helppop |
815 | + Popover { |
816 | + id: helpsheet |
817 | + Rectangle { |
818 | + anchors.top: parent.top |
819 | + anchors.left: parent.left |
820 | + anchors.right: parent.right |
821 | + height: units.gu(15) |
822 | + border.color: "#ddd" |
823 | + radius: 2 |
824 | + Label { |
825 | + anchors.fill: parent |
826 | + anchors.margins: units.gu(1) |
827 | + text: "game by <a href='http://twitter.com/sil'>@sil</a><br>music: <a href='http://incompetech.com/music/royalty-free/index.html?isrc=USUAN1200076'>Easy Lemon</a> from Kevin McCloud (incompetech.com)<br>sounds: freesound from <a href='http://www.freesound.org/people/kantouth/sounds/106727/'>kantouth</a> / <a href='http://www.freesound.org/people/tictacshutup/sounds/407/'>tictacshutup</a> / <a href='http://www.freesound.org/people/dj-chronos/sounds/45137/'>dj-chronos</a> / <a href='http://www.freesound.org/people/justinbw/sounds/80921/'>justinbw</a>" |
828 | + wrapMode: Text.WordWrap |
829 | + textFormat: Text.StyledText |
830 | + onLinkActivated: Qt.openUrlExternally(link) |
831 | + } |
832 | + } |
833 | + } |
834 | + } |
835 | + |
836 | + } |
837 | + |
838 | + back: Rectangle { |
839 | + id: main |
840 | + color: "#58585A" |
841 | + width: flipable.width // 48 * 7 + 2 * 7 + 2 |
842 | + height: flipable.height // 48 * 10 + 2 * 10 + 50 |
843 | + property var selectedItems: [] |
844 | + /* |
845 | + obtained with: |
846 | + import re; fp=open('/usr/share/dict/words'); |
847 | + shorts=[re.sub('[^a-zA-Z]','',x.lower().strip()) for x in fp if len(x)<7]; |
848 | + from collections import Counter; c=Counter(''.join(shorts)); least=c.most_common()[-1][1]; |
849 | + print dict([(x.upper(),c[x]/least) for x in c]) |
850 | + */ |
851 | + property variant letterFreqs: { |
852 | + 'A': 66, 'C': 22, 'B': 19, 'E': 72, 'D': 28, 'G': 18, 'F': 12, 'I': 41, 'H': 20, |
853 | + 'K': 14, 'J': 4, 'M': 22, 'L': 40, 'O': 48, 'N': 35, 'Q': 1, 'P': 22, 'S': 75, |
854 | + 'R': 43, 'U': 26, 'T': 37, 'W': 13, 'V': 7, 'Y': 19, 'X': 3, 'Z': 4 |
855 | + } |
856 | + property variant letterScores: { |
857 | + "A":1,"B":3,"C":3,"D":2,"E":1,"F":4,"G":2,"H":4,"I":1,"J":8,"K":5,"L":1, |
858 | + "M":3,"N":1,"O":1,"P":3,"Q":10,"R":1,"S":1,"T":1,"U":1,"V":4,"W":4,"X":8, |
859 | + "Y":4,"Z":10 |
860 | + } |
861 | + property int score: 0 |
862 | + |
863 | + function getRandomWeightedLetter() { |
864 | + // could work out sumOfWeights once, but this is easier to understand |
865 | + var sumOfWeights = 0; |
866 | + for (var k in main.letterFreqs) { sumOfWeights += main.letterFreqs[k]; } |
867 | + var selection = Math.floor(Math.random() * sumOfWeights); |
868 | + for (var k in main.letterFreqs) { |
869 | + if (selection < main.letterFreqs[k]) return k; |
870 | + selection -= main.letterFreqs[k]; |
871 | + } |
872 | + } |
873 | + |
874 | + Audio { |
875 | + id: music |
876 | + source: "Easy_Lemon_60_second.ogg" |
877 | + autoPlay: true |
878 | + onStopped: music.play() |
879 | + muted: !volume.audible |
880 | + } |
881 | + |
882 | + Audio { |
883 | + id: click |
884 | + source: "407__tictacshutup__click-1-off-click.ogg" |
885 | + autoLoad: true |
886 | + muted: !volume.audible |
887 | + } |
888 | + |
889 | + Audio { |
890 | + id: success |
891 | + source: "80921__justinbw__buttonchime02up.ogg" |
892 | + autoLoad: true |
893 | + muted: !volume.audible |
894 | + } |
895 | + |
896 | + Audio { |
897 | + id: failure |
898 | + source: "106727__kantouth__cartoon-bing-low.ogg" |
899 | + autoLoad: true |
900 | + muted: !volume.audible |
901 | + } |
902 | + |
903 | + Audio { |
904 | + id: gameover |
905 | + source: "45137__dj-chronos__dark-church-bell.ogg" |
906 | + autoLoad: true |
907 | + onStopped: { |
908 | + flipable.flipped = false |
909 | + } |
910 | + muted: !volume.audible |
911 | + } |
912 | + |
913 | + Rectangle { |
914 | + id: bottombar |
915 | + anchors.bottom: main.bottom |
916 | + anchors.left: main.left |
917 | + anchors.right: main.right |
918 | + height: (main.height - (game.squaresize * 10 + 11)) / 2 |
919 | + z: 2 |
920 | + color: Qt.hsla(210/360, 0.84, 0.2) |
921 | + |
922 | + Rectangle { |
923 | + id: mainscore |
924 | + anchors { |
925 | + centerIn: bottombar |
926 | + bottom: bottombar.bottom |
927 | + } |
928 | + z: 2 |
929 | + color: Qt.rgba(0,0,0,0) |
930 | + Label { |
931 | + anchors.centerIn: parent |
932 | + fontSize: "x-large" |
933 | + text: "" + main.score |
934 | + color: "white" |
935 | + } |
936 | + } |
937 | + } |
938 | + |
939 | + Rectangle { |
940 | + id: topbar |
941 | + color: "blue" |
942 | + anchors.top: main.top |
943 | + anchors.left: main.left |
944 | + anchors.right: main.right |
945 | + height: (main.height - (game.squaresize * 10 + 11)) / 2 |
946 | + z: 2 |
947 | + |
948 | + Rectangle { |
949 | + anchors.fill: topbar |
950 | + z: 2 |
951 | + color: accum.text == "" ? "#efefea" : (accum.isValid ? Qt.hsla(124/360, 0.83, 0.45) : Qt.hsla(0, 0.83, 0.65)) |
952 | + id: suggestedWordContainer |
953 | + Label { |
954 | + id: accum |
955 | + anchors.centerIn: parent |
956 | + text: "" |
957 | + color: "white" |
958 | + fontSize: "x-large" |
959 | + font.bold: true |
960 | + property bool isValid: false |
961 | + function findBinaryWord( word ) { |
962 | + var bd = Wordlist.wordlist; |
963 | + var l = word.length; |
964 | + // Don't search if there's nothing to look through |
965 | + if ( !bd[l] ) { |
966 | + return false; |
967 | + } |
968 | + // Get the number of words in the dictionary bin |
969 | + var words = bd[l].length / l, |
970 | + // The low point from where we're starting the binary search |
971 | + low = 0, |
972 | + // The max high point |
973 | + high = words - 1, |
974 | + // And the precise middle of the search |
975 | + mid = Math.floor( words / 2 ); |
976 | + // We continue to look until we reach a final word |
977 | + while ( high >= low ) { |
978 | + // Grab the word at our current position |
979 | + var found = bd[l].substr( l * mid, l ); |
980 | + // If we've found the word, stop now |
981 | + if ( word === found ) { |
982 | + return true; |
983 | + } |
984 | + // Otherwise, compare |
985 | + // If we're too high, move lower |
986 | + if ( word < found ) { |
987 | + high = mid - 1; |
988 | + // If we're too low, go higher |
989 | + } else { |
990 | + low = mid + 1; |
991 | + } |
992 | + // And find the new search point |
993 | + mid = Math.floor( (low + high) / 2 ); |
994 | + } |
995 | + // Nothing was found |
996 | + return false; |
997 | + } |
998 | + onTextChanged: { |
999 | + accum.isValid = findBinaryWord(accum.text); |
1000 | + } |
1001 | + } |
1002 | + function processSuggestedWord() { |
1003 | + if (accum.isValid) { |
1004 | + success.play(); |
1005 | + var thisscore = 0, wordlength = accum.text.length; |
1006 | + accum.text = ""; |
1007 | + |
1008 | + // tell the boxes to destroy themselves |
1009 | + main.selectedItems.forEach(function(b) { |
1010 | + thisscore += main.letterScores[b.containedLetter]; |
1011 | + b.state = "dead"; |
1012 | + }) |
1013 | + main.selectedItems = []; |
1014 | + main.score += thisscore * wordlength; |
1015 | + scoredisplay.text = "" + (thisscore * wordlength); |
1016 | + showscoredisplay.start(); |
1017 | + } else { |
1018 | + failure.play(); |
1019 | + accum.text = ""; |
1020 | + main.selectedItems.forEach(function(b) { b.selected = false; }) |
1021 | + main.selectedItems = []; |
1022 | + } |
1023 | + } |
1024 | + focus: true |
1025 | + Keys.onReturnPressed: { |
1026 | + suggestedWordContainer.processSuggestedWord(); |
1027 | + } |
1028 | + MouseArea { |
1029 | + anchors.fill: parent |
1030 | + onClicked: { suggestedWordContainer.processSuggestedWord(); } |
1031 | + } |
1032 | + } |
1033 | + |
1034 | + |
1035 | + } |
1036 | + |
1037 | + Label { |
1038 | + id: scoredisplay |
1039 | + anchors.centerIn: parent |
1040 | + z: 3 |
1041 | + fontSize: "x-large" |
1042 | + text: "200" |
1043 | + color: "red" |
1044 | + opacity: 0 |
1045 | + } |
1046 | + |
1047 | + ParallelAnimation { |
1048 | + id: showscoredisplay |
1049 | + NumberAnimation { |
1050 | + property: "scale" |
1051 | + from: 0.1 |
1052 | + to: 8.0 |
1053 | + duration: 400 |
1054 | + target: scoredisplay |
1055 | + } |
1056 | + SequentialAnimation { |
1057 | + NumberAnimation { |
1058 | + property: "opacity" |
1059 | + from: 0 |
1060 | + to: 1.0 |
1061 | + duration: 20 |
1062 | + target: scoredisplay |
1063 | + } |
1064 | + NumberAnimation { |
1065 | + property: "opacity" |
1066 | + from: 1.0 |
1067 | + to: 0 |
1068 | + duration: 380 |
1069 | + target: scoredisplay |
1070 | + } |
1071 | + } |
1072 | + } |
1073 | + |
1074 | + |
1075 | + Timer { |
1076 | + id: droptimer |
1077 | + repeat: true |
1078 | + running: flipable.flipped |
1079 | + interval: 2000 |
1080 | + property int tickCount: 0 |
1081 | + triggeredOnStart: true |
1082 | + onTriggered: { |
1083 | + tickCount += 5 |
1084 | + droptimer.interval = 2000 - tickCount |
1085 | + var idx = Math.round(Math.random() * (lm.count - 1)); |
1086 | + lm.get(idx).letters.append({ letter: main.getRandomWeightedLetter() }); |
1087 | + if (lm.get(idx).letters.count >= 10) { |
1088 | + droptimer.stop(); |
1089 | + gameover.play(); |
1090 | + var db = LocalStorage.openDatabaseSync("dropping-letters", "1.0", "Dropping Letters", 1000); |
1091 | + db.transaction(function(tx) { |
1092 | + tx.executeSql("insert into Scores values (?,?)", [main.score, 0]); |
1093 | + bestscore.updateScore(main.score); |
1094 | + }); |
1095 | + } |
1096 | + } |
1097 | + } |
1098 | + |
1099 | + ListModel { |
1100 | + id: lm |
1101 | + } |
1102 | + |
1103 | + |
1104 | + Rectangle { |
1105 | + id: game |
1106 | + property int squaresize: Math.min((flipable.width) / 7, (flipable.height - (flipable.minChromeHeight * 2)) / 10) |
1107 | + anchors.top: topbar.bottom |
1108 | + anchors.bottom: bottombar.top |
1109 | + anchors.left: main.left |
1110 | + anchors.right: main.right |
1111 | + scale: -1 |
1112 | + color: "#efefea" |
1113 | + Row { |
1114 | + anchors.horizontalCenter: game.horizontalCenter |
1115 | + anchors.top: game.top |
1116 | + anchors.topMargin: 1 |
1117 | + //spacing: 1 |
1118 | + Repeater { |
1119 | + model: lm |
1120 | + Column { |
1121 | + //spacing: 1 |
1122 | + property int idx: index |
1123 | + width: game.squaresize |
1124 | + height: game.height |
1125 | + add: Transition { |
1126 | + NumberAnimation { properties: "y"; easing.type: Easing.OutBounce; duration: 1000 } |
1127 | + } |
1128 | + move: Transition { |
1129 | + NumberAnimation { properties: "y"; easing.type: Easing.OutBounce } |
1130 | + } |
1131 | + Repeater { |
1132 | + model: letters |
1133 | + Rectangle { |
1134 | + id: box |
1135 | + property bool selected: false |
1136 | + property int idx: index |
1137 | + property string containedLetter: letter |
1138 | + color: { |
1139 | + if (lm.get(parent.idx).letters.count >= 10) { |
1140 | + return "red"; |
1141 | + } else if (!selected) { |
1142 | + return Qt.hsla(210/360, 0.84, 0.25 + (idx * 0.05)); |
1143 | + } else if (accum.isValid) { |
1144 | + return Qt.hsla(124/360, 0.83, 0.45); // "#93cc98"; |
1145 | } else { |
1146 | - if (box === main.selectedItems[main.selectedItems.length - 1]) { |
1147 | - main.selectedItems.pop(main.selectedItems.length - 1); |
1148 | - box.selected = false; |
1149 | - accum.text = accum.text.substr(0, accum.text.length - 1); |
1150 | + return Qt.hsla(0, 0.83, 0.65); // "#cc9598" |
1151 | + } |
1152 | + } |
1153 | + //radius: "medium" |
1154 | + scale: -1 |
1155 | + width: game.squaresize |
1156 | + height: game.squaresize |
1157 | + y: game.height + game.squaresize |
1158 | + z: 5 |
1159 | + Label { |
1160 | + anchors.centerIn: parent |
1161 | + text: letter |
1162 | + fontSize: "large" |
1163 | + font.bold: true |
1164 | + color: "#ffffff" |
1165 | + } |
1166 | + MouseArea { |
1167 | + anchors.fill: parent |
1168 | + onClicked: { |
1169 | + if (!box.selected) { |
1170 | + box.selected = true; |
1171 | + accum.text += letter; |
1172 | + click.play(); |
1173 | + main.selectedItems[main.selectedItems.length] = box; |
1174 | + } else { |
1175 | + if (box === main.selectedItems[main.selectedItems.length - 1]) { |
1176 | + main.selectedItems.pop(main.selectedItems.length - 1); |
1177 | + box.selected = false; |
1178 | + accum.text = accum.text.substr(0, accum.text.length - 1); |
1179 | + } |
1180 | } |
1181 | } |
1182 | } |
1183 | - } |
1184 | - Behavior on opacity { |
1185 | - SequentialAnimation { |
1186 | - ScriptAction { script: pulseEmitter.burst(1000); } |
1187 | - NumberAnimation { properties:"opacity"; duration: 500 } |
1188 | - ScriptAction { script: lm.get(box.parent.idx).letters.remove(box.idx); } |
1189 | - } |
1190 | - } |
1191 | - states: [ |
1192 | - State { name: "alive" }, |
1193 | - State { |
1194 | - name: "dead" |
1195 | - PropertyChanges { target: box; opacity: 0 } |
1196 | - } |
1197 | - ] |
1198 | - ParticleSystem { |
1199 | - id: particles |
1200 | - width: flipable.width / 2 |
1201 | - height: flipable.width / 2 |
1202 | - anchors.centerIn: parent |
1203 | - clip: false |
1204 | - ImageParticle { |
1205 | - source: "redStar.png" |
1206 | - alpha: 0 |
1207 | - colorVariation: 0.6 |
1208 | - } |
1209 | - Emitter { |
1210 | - id: pulseEmitter |
1211 | - x: parent.width/2 |
1212 | - y: parent.height/2 |
1213 | - emitRate: 2000 |
1214 | - lifeSpan: 500 |
1215 | - enabled: false |
1216 | - velocity: AngleDirection { magnitude: 256; angleVariation: 360; magnitudeVariation: 200; } |
1217 | - size: parent.width / 8 |
1218 | - sizeVariation: 8 |
1219 | + Behavior on opacity { |
1220 | + SequentialAnimation { |
1221 | + ScriptAction { script: pulseEmitter.burst(1000); } |
1222 | + NumberAnimation { properties:"opacity"; duration: 500 } |
1223 | + ScriptAction { script: lm.get(box.parent.idx).letters.remove(box.idx); } |
1224 | + } |
1225 | + } |
1226 | + states: [ |
1227 | + State { name: "alive" }, |
1228 | + State { |
1229 | + name: "dead" |
1230 | + PropertyChanges { target: box; opacity: 0 } |
1231 | + } |
1232 | + ] |
1233 | + ParticleSystem { |
1234 | + id: particles |
1235 | + width: flipable.width / 2 |
1236 | + height: flipable.width / 2 |
1237 | + anchors.centerIn: parent |
1238 | + clip: false |
1239 | + ImageParticle { |
1240 | + source: "redStar.png" |
1241 | + alpha: 0 |
1242 | + colorVariation: 0.6 |
1243 | + } |
1244 | + Emitter { |
1245 | + id: pulseEmitter |
1246 | + x: parent.width/2 |
1247 | + y: parent.height/2 |
1248 | + emitRate: 2000 |
1249 | + lifeSpan: 500 |
1250 | + enabled: false |
1251 | + velocity: AngleDirection { magnitude: 256; angleVariation: 360; magnitudeVariation: 200; } |
1252 | + size: parent.width / 8 |
1253 | + sizeVariation: 8 |
1254 | + } |
1255 | } |
1256 | } |
1257 | } |
1258 | @@ -633,4 +615,17 @@ |
1259 | } |
1260 | } |
1261 | } |
1262 | + HUD.HUD { |
1263 | + applicationIdentifier: "dropping-letters" |
1264 | + HUD.Context { |
1265 | + HUD.QuitAction { |
1266 | + onTriggered: Qt.quit() |
1267 | + } |
1268 | + HUD.Action { |
1269 | + label: i18n.tr("New game") |
1270 | + keywords: "Reset;Start;New" |
1271 | + onTriggered: resetGame() |
1272 | + } |
1273 | + } |
1274 | + } |
1275 | } |
1276 | |
1277 | === modified file 'dropping-letters.qmlproject' |
1278 | --- dropping-letters.qmlproject 2013-05-01 05:13:52 +0000 |
1279 | +++ dropping-letters.qmlproject 2013-05-07 05:11:28 +0000 |
1280 | @@ -3,7 +3,7 @@ |
1281 | import QmlProject 1.1 |
1282 | |
1283 | Project { |
1284 | - mainFile: "dropping-letters-ubuntu.qml" |
1285 | + mainFile: "dropping-letters.qml" |
1286 | |
1287 | /* Include .qml, .js, and image files from current directory and subdirectories */ |
1288 | QmlFiles { |
1289 | |
1290 | === added file 'new.png' |
1291 | Binary files new.png 1970-01-01 00:00:00 +0000 and new.png 2013-05-07 05:11:28 +0000 differ |
Looks good.