diff --git a/examples/TODO b/examples/TODO new file mode 100644 index 000000000..d6a69fec9 --- /dev/null +++ b/examples/TODO @@ -0,0 +1,8 @@ +Still to be ported + + +Applets: +* nowplaying +* pairsgame +* samegame + diff --git a/examples/applets/nowplaying/contents/qml/main.qml b/examples/applets/nowplaying/contents/qml/main.qml new file mode 100644 index 000000000..39938ddfb --- /dev/null +++ b/examples/applets/nowplaying/contents/qml/main.qml @@ -0,0 +1,135 @@ +/* + * Copyright 2010 Marco Martin + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Library General Public License as + * published by the Free Software Foundation; either version 2, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details + * + * You should have received a copy of the GNU Library General Public + * License along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +import Qt 4.7 +import org.kde.plasma.graphicswidgets 0.1 as PlasmaWidgets +import org.kde.plasma.core 0.1 as PlasmaCore +import org.kde.plasma.graphicslayouts 4.7 as GraphicsLayouts + + +QGraphicsWidget { + id: page; + preferredSize: "200x200" + minimumSize: "200x20" + property string activeSource: '' + + Item { + id:main + + PlasmaCore.DataSource { + id: dataSource + dataEngine: "nowplaying" + connectedSources: ['players'] + interval: 500 + + onNewData: { + if (sourceName == 'players') { + print("going to connect to " + data['players'][0]) + activeSource = data['players'][0] + connectedSources = ['players', activeSource] + } + } + + onDataChanged: { + if (!activeSource) { + return; + } + + if (data[activeSource].State == "playing") { + playPause.setIcon("media-playback-pause") + } else { + playPause.setIcon("media-playback-start") + } + + progress.value = 100*data[activeSource].Position/data[activeSource].Length + } + } + + PlasmaCore.Theme { + id: theme + } + } + + Component.onCompleted: + { + dataSource.serviceForSource(activeSource).associateWidget(stop, "stop"); + dataSource.serviceForSource(activeSource).associateWidget(progress, "progress"); + } + + layout: GraphicsLayouts.QGraphicsLinearLayout { + + PlasmaWidgets.IconWidget { + id: playPause + property string state: "stop" + + onClicked: { + var operation; + if (dataSource.data[activeSource].State == "playing") { + operation = "pause" + } else { + operation = "play" + } + var data = dataSource.serviceForSource(activeSource).operationDescription(operation); + print(dataSource.serviceForSource(activeSource).name); + + for ( var i in data ) { + print(i + ' -> ' + data[i] ); + } + + dataSource.serviceForSource(activeSource).startOperationCall(dataSource.serviceForSource(activeSource).operationDescription(operation)); + print("stopping"); + } + } + + PlasmaWidgets.IconWidget { + id: stop + Component.onCompleted: { + setIcon("media-playback-stop"); + } + onClicked: { + var data = dataSource.serviceForSource(activeSource).operationDescription("stop"); + print(dataSource.serviceForSource(activeSource).name); + + for ( var i in data ) { + print(i + ' -> ' + data[i] ); + } + + dataSource.serviceForSource(activeSource).startOperationCall(dataSource.serviceForSource(activeSource).operationDescription("stop")); + print("stopping"); + } + } + + PlasmaWidgets.Slider { + id: progress + orientation: Qt.Horizontal + + onSliderMoved: { + var operation = dataSource.serviceForSource(activeSource).operationDescription("seek"); + operation.seconds = Math.round(dataSource.data[activeSource].Length*(value/100)); + + for ( var i in operation ) { + print(i + ' -> ' + operation[i] ); + } + + dataSource.serviceForSource(activeSource).startOperationCall(operation); + print("set progress to " + progress); + } + } + } +} diff --git a/examples/applets/nowplaying/metadata.desktop b/examples/applets/nowplaying/metadata.desktop new file mode 100644 index 000000000..900f4dcdd --- /dev/null +++ b/examples/applets/nowplaying/metadata.desktop @@ -0,0 +1,32 @@ +[Desktop Entry] +Name=Now playing (QML) +Name[ja]=今聴いているもの (QML) +Name[km]=ឥឡូវ​កំពុង​ចាក់ (QML) +Name[nds]=Lopen Stück (QML) +Name[pt]=Agora a tocar (QML) +Name[pt_BR]=Reproduzindo agora (QML) +Name[sv]=Spelar nu (QML) +Name[uk]=Зараз відтворюється (QML) +Name[x-test]=xxNow playing (QML)xx +Comment=A proof of concept media player controller qml +Comment[km]=ការ​បញ្ជាក់​​ឧបករណ៍​ត្រួតពិនិត្យ​កម្មវិធី​ចាក់​មេឌៀ​គោល qml +Comment[pt]=Uma prova de conceito de um controlador multimédia em QML +Comment[pt_BR]=Uma prova de conceito de um controlador multimídia em QML +Comment[sv]=Ett koncept för ett kontrollverktyg för mediaspelare i QML +Comment[uk]=Тестова програма для спостереження за відтворенням мультимедійних даних, написана мовою qml +Comment[x-test]=xxA proof of concept media player controller qmlxx +Encoding=UTF-8 +Icon=applications-multimedia +ServiceTypes=Plasma/Applet +Type=Service +X-KDE-PluginInfo-Author=Marco Martin +X-KDE-PluginInfo-Category=Examples +X-KDE-PluginInfo-Depends= +X-KDE-PluginInfo-Email=notmart@gmail.com +X-KDE-PluginInfo-EnabledByDefault=true +X-KDE-PluginInfo-License=GPL +X-KDE-PluginInfo-Name=org.kde.nowplaying-qml +X-KDE-PluginInfo-Version=1.0 +X-KDE-PluginInfo-Website=http://plasma.kde.org/ +X-Plasma-API=declarativeappletscript +X-Plasma-MainScript=qml/main.qml diff --git a/examples/applets/pairsgame/contents/ui/Card.qml b/examples/applets/pairsgame/contents/ui/Card.qml new file mode 100644 index 000000000..c2db4cf2b --- /dev/null +++ b/examples/applets/pairsgame/contents/ui/Card.qml @@ -0,0 +1,138 @@ +/*************************************************************************** + * Copyright 2010 by Davide Bettio * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . * + ***************************************************************************/ + +import QtQuick 1.0 + +Flipable { + id: card; + property string cardPicture: "card.svgz"; + property bool showPicture: false; + property bool matched: false; + state: "normal" + width: cardBack.width + height: cardBack.height + + Behavior on opacity { + NumberAnimation { + target: card + property: "opacity" + duration: 300 + } + } + + front: Image { + id: cardBack + anchors.centerIn: parent + source: "card.svgz"; + } + back: Image { + anchors.centerIn: parent + source: cardPicture; + } + + transform: Rotation { + id: rotation + origin.x: card.width/2 + origin.y: card.height/2 + axis.x: 0; axis.y: 1; axis.z: 0 + angle: 0 + Behavior on angle { + NumberAnimation { + target: rotation + property: "angle" + duration: 300 + } + } + } + + SequentialAnimation { + id: checkAnimation + NumberAnimation { + target: rotation + property: "angle" + duration: 300 + from: 0 + to: 180 + } + PauseAnimation { + duration: 300 + } + NumberAnimation { + target: rotation + property: "angle" + duration: 300 + from: 180 + to: 0 + } + } + + MouseArea { + id: mouseArea; + anchors.fill: parent; + onClicked: { + if (!pairsCanvas.currentCard){ + pairsCanvas.currentCard = card; + card.state = "checking" + } else if (pairsCanvas.currentCard != card) { + if (pairsCanvas.currentCard.cardPicture == card.cardPicture){ + card.state = pairsCanvas.currentCard.state = "matched" + pairsCanvas.matchesCountdown--; + } else { + card.state = pairsCanvas.currentCard.state = "normal" + checkAnimation.running = true + } + pairsCanvas.currentCard = null; + } + } + } + + states: [ + State { + name: "normal"; + PropertyChanges { + target: card; + showPicture: false + } + PropertyChanges { + target: rotation; + angle: 0 + } + }, + State { + name: "checking"; + PropertyChanges { + target: rotation; + angle: 180 + } + }, + State { + name: "matched"; + PropertyChanges { + target: card; + opacity: 0.3 + enabled: false + showPicture: true + } + PropertyChanges { + target: rotation; + angle: 180 + } + } + ] +} diff --git a/examples/applets/pairsgame/contents/ui/GameTimer.qml b/examples/applets/pairsgame/contents/ui/GameTimer.qml new file mode 100644 index 000000000..385d59601 --- /dev/null +++ b/examples/applets/pairsgame/contents/ui/GameTimer.qml @@ -0,0 +1,49 @@ +/*************************************************************************** + * Copyright 2010 by Marco Martin * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . * + ***************************************************************************/ + +import QtQuick 1.0 + +Rectangle { + id:main + property int time: 0 + property bool running: true + + color: Qt.rgba(1,1,1,0.7) + radius: 10 + smooth: true + + width: childrenRect.width + 20 + height: childrenRect.height + 20 + Text { + anchors.horizontalCenter: parent.horizontalCenter + x: 10 + y: 10 + text: ""+Math.floor((time/60)/10)+Math.floor((time/60))+":"+Math.floor((time%60)/10)+(time%60)%10 + font.pointSize: 22 + } + + Timer { + interval: 1000 + running: main.running + repeat: true + onTriggered: { + time++ + } + } +} diff --git a/examples/applets/pairsgame/contents/ui/WinMessage.qml b/examples/applets/pairsgame/contents/ui/WinMessage.qml new file mode 100644 index 000000000..b94445cc1 --- /dev/null +++ b/examples/applets/pairsgame/contents/ui/WinMessage.qml @@ -0,0 +1,49 @@ +/*************************************************************************** + * Copyright 2010 by Marco Martin * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . * + ***************************************************************************/ + +import QtQuick 1.0 + +Rectangle { + id:main + property int time: 0 + property bool running: true + + color: Qt.rgba(1,1,1,0.7) + radius: 10 + smooth: true + + width: childrenRect.width + 20 + height: childrenRect.height + 20 + Text { + x: 10 + y: 10 + text: "WIN!!!" + font.pointSize: 52 + } + + Behavior on y { + NumberAnimation { + target: main + property: "y" + duration: 1000 + easing.type: "OutBounce" + + } + } +} diff --git a/examples/applets/pairsgame/contents/ui/application-exit.png b/examples/applets/pairsgame/contents/ui/application-exit.png new file mode 100644 index 000000000..32be6b3f1 Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/application-exit.png differ diff --git a/examples/applets/pairsgame/contents/ui/background.jpg b/examples/applets/pairsgame/contents/ui/background.jpg new file mode 100644 index 000000000..9a327ee7b Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/background.jpg differ diff --git a/examples/applets/pairsgame/contents/ui/bug-card.png b/examples/applets/pairsgame/contents/ui/bug-card.png new file mode 100644 index 000000000..f749ee23b Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/bug-card.png differ diff --git a/examples/applets/pairsgame/contents/ui/card.svgz b/examples/applets/pairsgame/contents/ui/card.svgz new file mode 100644 index 000000000..993b7655a Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/card.svgz differ diff --git a/examples/applets/pairsgame/contents/ui/cards-reset.png b/examples/applets/pairsgame/contents/ui/cards-reset.png new file mode 100644 index 000000000..d84366b2c Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/cards-reset.png differ diff --git a/examples/applets/pairsgame/contents/ui/clock-card.png b/examples/applets/pairsgame/contents/ui/clock-card.png new file mode 100644 index 000000000..360ca80e0 Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/clock-card.png differ diff --git a/examples/applets/pairsgame/contents/ui/gamelogic.js b/examples/applets/pairsgame/contents/ui/gamelogic.js new file mode 100644 index 000000000..712af4af0 --- /dev/null +++ b/examples/applets/pairsgame/contents/ui/gamelogic.js @@ -0,0 +1,50 @@ +/*************************************************************************** + * Copyright 2010 by Davide Bettio * + * Copyright 2010 by Marco Martin * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . * + ***************************************************************************/ + + +var rows = 3 +var columns = 4 +var maxVal = rows*columns +var elementsGrid = new Array(rows) +for (var i=0; i < rows; ++i) { + elementsGrid[i] = new Array(columns) +} + +function init() +{ + gameTimer.running = true + gameTimer.time = 0 + winMessage.y = -winMessage.height + matchesCountdown = rows*columns / 2; + var pairs = new Array("bug", "bug", "clock", "clock", "kde", "kde", "konqueror", "konqueror", "magicwand", "magicwand", "plasma", "plasma") + elements.clear(); + var remaining = maxVal + for (var i=0; i < maxVal; ++i) { + var randVal = Math.round((Math.random()*remaining-1)) + + var element = pairs.splice(randVal, 1) + + --remaining + elements.append({"card": String(element)}) + + elementsGrid[Math.floor(i/columns)][columns%i] = element + } +} + diff --git a/examples/applets/pairsgame/contents/ui/kde-card.png b/examples/applets/pairsgame/contents/ui/kde-card.png new file mode 100644 index 000000000..2311fc3b4 Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/kde-card.png differ diff --git a/examples/applets/pairsgame/contents/ui/konqueror-card.png b/examples/applets/pairsgame/contents/ui/konqueror-card.png new file mode 100644 index 000000000..4612299c5 Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/konqueror-card.png differ diff --git a/examples/applets/pairsgame/contents/ui/magicwand-card.png b/examples/applets/pairsgame/contents/ui/magicwand-card.png new file mode 100644 index 000000000..ba5300bfb Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/magicwand-card.png differ diff --git a/examples/applets/pairsgame/contents/ui/main.qml b/examples/applets/pairsgame/contents/ui/main.qml new file mode 100644 index 000000000..4e73517de --- /dev/null +++ b/examples/applets/pairsgame/contents/ui/main.qml @@ -0,0 +1,82 @@ +/*************************************************************************** + * Copyright 2010 by Davide Bettio * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA . * + ***************************************************************************/ + +import QtQuick 1.0 +import "gamelogic.js" as GameLogic + + +Image { + id: pairsCanvas; + width: 800; + height: 480; + source: "background.jpg" + property Item currentCard; + property int matchesCountdown; + + onMatchesCountdownChanged: { + if (matchesCountdown == 0) { + gameTimer.running = false + winMessage.y = pairsCanvas.height/2 - winMessage.height/2 + } + } + + + Column { + Image { + source: "cards-reset.png" + + MouseArea { + anchors.fill: parent; + onClicked: GameLogic.init(); + } + } + GameTimer { + id: gameTimer + width: parent.width + } + } + + ListModel { + id: elements + Component.onCompleted: { + GameLogic.init() + } + } + + Grid { + id: mainGrid + anchors.fill: parent + rows: GameLogic.rows + columns: GameLogic.columns + spacing: 5 + Repeater { + id: repeater + model: elements + delegate: Card { + cardPicture: card+"-card.png" + } + } + } + + WinMessage { + id: winMessage + anchors.horizontalCenter: mainGrid.horizontalCenter + y: -height + } +} diff --git a/examples/applets/pairsgame/contents/ui/plasma-card.png b/examples/applets/pairsgame/contents/ui/plasma-card.png new file mode 100644 index 000000000..4e54c9037 Binary files /dev/null and b/examples/applets/pairsgame/contents/ui/plasma-card.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/.directory b/examples/applets/samegame/contents/qml/SamegameCore/.directory new file mode 100644 index 000000000..74d4d9cc5 --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/.directory @@ -0,0 +1,2 @@ +[Dolphin] +Timestamp=2010,8,30,14,12,1 diff --git a/examples/applets/samegame/contents/qml/SamegameCore/BoomBlock.qml b/examples/applets/samegame/contents/qml/SamegameCore/BoomBlock.qml new file mode 100644 index 000000000..43050af25 --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/BoomBlock.qml @@ -0,0 +1,109 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the QtDeclarative module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** No Commercial Usage +** This file contains pre-release code and may not be distributed. +** You may use this file in accordance with the terms and conditions +** contained in the Technology Preview License Agreement accompanying +** this package. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** If you have questions regarding the use of this file, please contact +** Nokia at qt-info@nokia.com. +** +** +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import Qt 4.7 +import Qt.labs.particles 1.0 + +Item { + id: block + property bool dying: false + property bool spawned: false + property int type: 0 + + Behavior on x { + enabled: spawned; + SpringAnimation{ spring: 2; damping: 0.2 } + } + Behavior on y { + SpringAnimation{ spring: 2; damping: 0.2 } + } + + Image { + id: img + source: { + if(type == 0){ + "pics/redStone.png"; + } else if(type == 1) { + "pics/blueStone.png"; + } else { + "pics/greenStone.png"; + } + } + opacity: 0 + Behavior on opacity { NumberAnimation { duration: 200 } } + anchors.fill: parent + } + + Particles { + id: particles + + width: 1; height: 1 + anchors.centerIn: parent + + emissionRate: 0 + lifeSpan: 700; lifeSpanDeviation: 600 + angle: 0; angleDeviation: 360; + velocity: 100; velocityDeviation: 30 + source: { + if(type == 0){ + "pics/redStar.png"; + } else if (type == 1) { + "pics/blueStar.png"; + } else { + "pics/greenStar.png"; + } + } + } + + states: [ + State { + name: "AliveState"; when: spawned == true && dying == false + PropertyChanges { target: img; opacity: 1 } + }, + + State { + name: "DeathState"; when: dying == true + StateChangeScript { script: particles.burst(50); } + PropertyChanges { target: img; opacity: 0 } + StateChangeScript { script: block.destroy(1000); } + } + ] +} diff --git a/examples/applets/samegame/contents/qml/SamegameCore/Button.qml b/examples/applets/samegame/contents/qml/SamegameCore/Button.qml new file mode 100644 index 000000000..d5979b26d --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/Button.qml @@ -0,0 +1,75 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the QtDeclarative module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** No Commercial Usage +** This file contains pre-release code and may not be distributed. +** You may use this file in accordance with the terms and conditions +** contained in the Technology Preview License Agreement accompanying +** this package. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** If you have questions regarding the use of this file, please contact +** Nokia at qt-info@nokia.com. +** +** +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import Qt 4.7 + +Rectangle { + id: container + + property string text: "Button" + + signal clicked + + width: buttonLabel.width + 20; height: buttonLabel.height + 6 + smooth: true + border { width: 1; color: Qt.darker(activePalette.button) } + radius: 8 + color: activePalette.button + + gradient: Gradient { + GradientStop { + position: 0.0 + color: { + if (mouseArea.pressed) + return activePalette.dark + else + return activePalette.light + } + } + GradientStop { position: 1.0; color: activePalette.button } + } + + MouseArea { id: mouseArea; anchors.fill: parent; onClicked: container.clicked() } + + Text { + id: buttonLabel; text: container.text; anchors.centerIn: container; color: activePalette.buttonText + } +} diff --git a/examples/applets/samegame/contents/qml/SamegameCore/Dialog.qml b/examples/applets/samegame/contents/qml/SamegameCore/Dialog.qml new file mode 100644 index 000000000..7e64bd63d --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/Dialog.qml @@ -0,0 +1,77 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the QtDeclarative module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** No Commercial Usage +** This file contains pre-release code and may not be distributed. +** You may use this file in accordance with the terms and conditions +** contained in the Technology Preview License Agreement accompanying +** this package. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** If you have questions regarding the use of this file, please contact +** Nokia at qt-info@nokia.com. +** +** +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import Qt 4.7 + +Rectangle { + id: page + + property Item text: dialogText + + signal closed + signal opened + function forceClose() { + if(page.opacity == 0) + return; //already closed + page.closed(); + page.opacity = 0; + } + + function show(txt) { + page.opened(); + dialogText.text = txt; + page.opacity = 1; + } + + width: dialogText.width + 20; height: dialogText.height + 20 + color: "white" + border.width: 1 + opacity: 0 + visible: opacity > 0 + Behavior on opacity { + NumberAnimation { duration: 1000 } + } + + Text { id: dialogText; anchors.centerIn: parent; text: "Hello World!" } + + MouseArea { anchors.fill: parent; onClicked: forceClose(); } +} + diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/background.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/background.png new file mode 100644 index 000000000..3734a2774 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/background.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStar.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStar.png new file mode 100644 index 000000000..ff9588f80 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStar.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStone.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStone.png new file mode 100644 index 000000000..20e43c75b Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/blueStone.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStar.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStar.png new file mode 100644 index 000000000..cd0685471 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStar.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStone.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStone.png new file mode 100644 index 000000000..b568a1900 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/greenStone.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/redStar.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/redStar.png new file mode 100644 index 000000000..0a4dffe58 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/redStar.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/redStone.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/redStone.png new file mode 100644 index 000000000..36b09a268 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/redStone.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/star.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/star.png new file mode 100644 index 000000000..defbde53c Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/star.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/pics/yellowStone.png b/examples/applets/samegame/contents/qml/SamegameCore/pics/yellowStone.png new file mode 100644 index 000000000..b1ce76212 Binary files /dev/null and b/examples/applets/samegame/contents/qml/SamegameCore/pics/yellowStone.png differ diff --git a/examples/applets/samegame/contents/qml/SamegameCore/qmldir b/examples/applets/samegame/contents/qml/SamegameCore/qmldir new file mode 100644 index 000000000..e17b1f5d2 --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/qmldir @@ -0,0 +1,3 @@ +BoomBlock BoomBlock.qml +Button Button.qml +Dialog Dialog.qml diff --git a/examples/applets/samegame/contents/qml/SamegameCore/samegame.js b/examples/applets/samegame/contents/qml/SamegameCore/samegame.js new file mode 100755 index 000000000..aa1b35981 --- /dev/null +++ b/examples/applets/samegame/contents/qml/SamegameCore/samegame.js @@ -0,0 +1,237 @@ +/* This script file handles the game logic */ + +var maxColumn = 10; +var maxRow = 15; +var maxIndex = maxColumn*maxRow; +var board = new Array(maxIndex); +var blockSrc = "SamegameCore/BoomBlock.qml"; +var scoresURL = ""; +var gameDuration; +var component = Qt.createComponent(blockSrc); + +//Index function used instead of a 2D array +function index(column,row) { + return column + (row * maxColumn); +} + +function timeStr(msecs) { + var secs = Math.floor(msecs/1000); + var m = Math.floor(secs/60); + var ret = "" + m + "m " + (secs%60) + "s"; + return ret; +} + +function startNewGame() +{ + //Delete blocks from previous game + for(var i = 0; i= maxColumn || column < 0 || row >= maxRow || row < 0) + return; + if(board[index(column, row)] == null) + return; + //If it's a valid block, remove it and all connected (does nothing if it's not connected) + floodFill(column,row, -1); + if(fillFound <= 0) + return; + gameCanvas.score += (fillFound - 1) * (fillFound - 1); + shuffleDown(); + victoryCheck(); +} + +function floodFill(column,row,type) +{ + if(board[index(column, row)] == null) + return; + var first = false; + if(type == -1){ + first = true; + type = board[index(column,row)].type; + + //Flood fill initialization + fillFound = 0; + floodBoard = new Array(maxIndex); + } + if(column >= maxColumn || column < 0 || row >= maxRow || row < 0) + return; + if(floodBoard[index(column, row)] == 1 || (!first && type != board[index(column,row)].type)) + return; + floodBoard[index(column, row)] = 1; + floodFill(column+1,row,type); + floodFill(column-1,row,type); + floodFill(column,row+1,type); + floodFill(column,row-1,type); + if(first==true && fillFound == 0) + return;//Can't remove single blocks + board[index(column,row)].dying = true; + board[index(column,row)] = null; + fillFound += 1; +} + +function shuffleDown() +{ + //Fall down + for(var column=0; column=0; row--){ + if(board[index(column,row)] == null){ + fallDist += 1; + }else{ + if(fallDist > 0){ + var obj = board[index(column,row)]; + obj.y = (row+fallDist) * gameCanvas.blockSize; + board[index(column,row+fallDist)] = obj; + board[index(column,row)] = null; + } + } + } + } + //Fall to the left + fallDist = 0; + for(column=0; column 0){ + for(row=0; row=0; column--) + if(board[index(column, maxRow - 1)] != null) + deservesBonus = false; + if(deservesBonus) + gameCanvas.score += 500; + //Checks for game over + if(deservesBonus || !(floodMoveCheck(0,maxRow-1, -1))){ + gameDuration = new Date() - gameDuration; + nameInputDialog.show("You won! Please enter your name: "); + nameInputDialog.initialWidth = nameInputDialog.text.width + 20; + nameInputDialog.width = nameInputDialog.initialWidth; + nameInputDialog.text.opacity = 0;//Just a spacer + } +} + +//only floods up and right, to see if it can find adjacent same-typed blocks +function floodMoveCheck(column, row, type) +{ + if(column >= maxColumn || column < 0 || row >= maxRow || row < 0) + return false; + if(board[index(column, row)] == null) + return false; + var myType = board[index(column, row)].type; + if(type == myType) + return true; + return floodMoveCheck(column + 1, row, myType) || + floodMoveCheck(column, row - 1, board[index(column,row)].type); +} + +function createBlock(column,row){ + // Note that we don't wait for the component to become ready. This will + // only work if the block QML is a local file. Otherwise the component will + // not be ready immediately. There is a statusChanged signal on the + // component you could use if you want to wait to load remote files. + if(component.status == Component.Ready){ + var dynamicObject = component.createObject(gameCanvas); + if(dynamicObject == null){ + console.log("error creating block"); + console.log(component.errorString()); + return false; + } + dynamicObject.type = Math.floor(Math.random() * 3); + dynamicObject.x = column*gameCanvas.blockSize; + dynamicObject.y = row*gameCanvas.blockSize; + dynamicObject.width = gameCanvas.blockSize; + dynamicObject.height = gameCanvas.blockSize; + dynamicObject.spawned = true; + board[index(column,row)] = dynamicObject; + }else{ + console.log("error loading block component"); + console.log(component.errorString()); + return false; + } + return true; +} + +function saveHighScore(name) { + if(scoresURL!="") + sendHighScore(name); + //OfflineStorage + var db = openDatabaseSync("SameGameScores", "1.0", "Local SameGame High Scores",100); + var dataStr = "INSERT INTO Scores VALUES(?, ?, ?, ?)"; + var data = [name, gameCanvas.score, maxColumn+"x"+maxRow ,Math.floor(gameDuration/1000)]; + db.transaction( + function(tx) { + tx.executeSql('CREATE TABLE IF NOT EXISTS Scores(name TEXT, score NUMBER, gridSize TEXT, time NUMBER)'); + tx.executeSql(dataStr, data); + + //Only show results for the current grid size + var rs = tx.executeSql('SELECT * FROM Scores WHERE gridSize = "'+maxColumn+"x"+maxRow+'" ORDER BY score desc LIMIT 10'); + var r = "\nHIGH SCORES for this grid size\n\n" + for(var i = 0; i < rs.rows.length; i++){ + r += (i+1)+". " + rs.rows.item(i).name +' got ' + + rs.rows.item(i).score + ' points in ' + + rs.rows.item(i).time + ' seconds.\n'; + } + dialog.show(r); + } + ); +} + +function sendHighScore(name) { + var postman = new XMLHttpRequest() + var postData = "name="+name+"&score="+gameCanvas.score + +"&gridSize="+maxColumn+"x"+maxRow +"&time="+Math.floor(gameDuration/1000); + postman.open("POST", scoresURL, true); + postman.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); + postman.onreadystatechange = function() { + if (postman.readyState == postman.DONE) { + dialog.show("Your score has been uploaded."); + } + } + postman.send(postData); +} diff --git a/examples/applets/samegame/contents/qml/highscores/README b/examples/applets/samegame/contents/qml/highscores/README new file mode 100644 index 000000000..eaa00fae3 --- /dev/null +++ b/examples/applets/samegame/contents/qml/highscores/README @@ -0,0 +1 @@ +The SameGame example can interface with a simple PHP script to store XML high score data on a remote server. We do not have a publically accessible server available for this use, but if you have access to a PHP capable webserver you can copy the files (score_data.xml, score.php, score_style.xsl) to it and alter the highscore_server variable at the top of the samegame.js file to point to it. diff --git a/examples/applets/samegame/contents/qml/highscores/score_data.xml b/examples/applets/samegame/contents/qml/highscores/score_data.xml new file mode 100755 index 000000000..c3fd90d9c --- /dev/null +++ b/examples/applets/samegame/contents/qml/highscores/score_data.xml @@ -0,0 +1,2 @@ +1000000Alan the Tester0x00 +6213Alan12x1751 diff --git a/examples/applets/samegame/contents/qml/highscores/score_style.xsl b/examples/applets/samegame/contents/qml/highscores/score_style.xsl new file mode 100755 index 000000000..670354c96 --- /dev/null +++ b/examples/applets/samegame/contents/qml/highscores/score_style.xsl @@ -0,0 +1,28 @@ + + + + + SameGame High Scores + +

SameGame High Scores

+ + + + + + + + + + + + + + + + +
NameScoreGrid SizeTime, s
+ + +
+
diff --git a/examples/applets/samegame/contents/qml/highscores/scores.php b/examples/applets/samegame/contents/qml/highscores/scores.php new file mode 100755 index 000000000..3cceb2d73 --- /dev/null +++ b/examples/applets/samegame/contents/qml/highscores/scores.php @@ -0,0 +1,34 @@ +"; + echo "SameGame High Scores"; + if($score > 0){#Sending in a new high score + $name = $_POST["name"]; + $grid = $_POST["gridSize"]; + $time = $_POST["time"]; + if($name == "") + $name = "Anonymous"; + //if($grid != "10x10"){ + //Need a standard, so as to reject others? + //} + $file = fopen("score_data.xml", "a"); #It's XML. Happy? + $ret = fwrite($file, "". $score . "" + . $name . "" . $grid . "" + . $time . "\n"); + echo "Your score has been recorded. Thanks for playing!"; + if($ret == False) + echo "
There was an error though, so don't expect to see that score again."; + }else{#Read high score list + #Now uses XSLT to display. So just print the file. With XML cruft added. + #Note that firefox at least won't apply the XSLT on a php file. So redirecting + $file = fopen("scores.xml", "w"); + $ret = fwrite($file, '' . "\n" + . '' . "\n" + . "\n" . file_get_contents("score_data.xml") . "\n"); + if($ret == False) + echo "There was an internal error. Sorry."; + else + echo ''; + } + echo ""; +?> diff --git a/examples/applets/samegame/contents/qml/samegame.qml b/examples/applets/samegame/contents/qml/samegame.qml new file mode 100644 index 000000000..bf2e70648 --- /dev/null +++ b/examples/applets/samegame/contents/qml/samegame.qml @@ -0,0 +1,162 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the QtDeclarative module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** No Commercial Usage +** This file contains pre-release code and may not be distributed. +** You may use this file in accordance with the terms and conditions +** contained in the Technology Preview License Agreement accompanying +** this package. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** If you have questions regarding the use of this file, please contact +** Nokia at qt-info@nokia.com. +** +** +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import Qt 4.7 +import "SamegameCore" +import "SamegameCore/samegame.js" as Logic + +Rectangle { + id: screen + width: 490; height: 720 + property bool inAnotherDemo: false //Samegame often is just plonked straight into other demos + clip:true + + SystemPalette { id: activePalette } + + Item { + width: parent.width + anchors { top: parent.top; left:parent.left; right: parent.right; bottom: toolBar.top } + + Image { + id: background + anchors.fill: parent + source: "SamegameCore/pics/background.png" + fillMode: Image.Scale + } + + Item { + id: gameCanvas + property int score: 0 + property int blockSize: 40 + + z: 20; anchors.centerIn: parent + width: parent.width - (parent.width % blockSize); + height: parent.height - (parent.height % blockSize); + + MouseArea { + anchors.fill: parent; onClicked: Logic.handleClick(mouse.x,mouse.y); + } + } + } + + Dialog { id: dialog; anchors.centerIn: parent; z: 21 } + + Dialog { + id: nameInputDialog + + property int initialWidth: 0 + + anchors.centerIn: parent + z: 22; + + Behavior on width { + NumberAnimation {} + enabled: nameInputDialog.initialWidth != 0 + } + + onOpened: nameInputText.focus = true; + onClosed: { + nameInputText.focus = false; + if (nameInputText.text != "") + Logic.saveHighScore(nameInputText.text); + } + Text { + id: dialogText + anchors { left: nameInputDialog.left; leftMargin: 20; verticalCenter: parent.verticalCenter } + text: "You won! Please enter your name: " + } + MouseArea { + anchors.fill: parent + onClicked: { + if (nameInputText.text == "") + nameInputText.openSoftwareInputPanel(); + else + nameInputDialog.forceClose(); + } + } + + TextInput { + id: nameInputText + anchors { verticalCenter: parent.verticalCenter; left: dialogText.right } + focus: false + autoScroll: false + maximumLength: 24 + onTextChanged: { + var newWidth = nameInputText.width + dialogText.width + 40; + if ( (newWidth > nameInputDialog.width && newWidth < screen.width) + || (nameInputDialog.width > nameInputDialog.initialWidth) ) + nameInputDialog.width = newWidth; + } + onAccepted: { + nameInputDialog.forceClose(); + } + } + } + + Rectangle { + id: toolBar + width: parent.width; height: 32 + color: activePalette.window + anchors.bottom: screen.bottom + + Button { + id: newGameButton + anchors { left: parent.left; leftMargin: 3; verticalCenter: parent.verticalCenter } + text: "New Game" + onClicked: Logic.startNewGame() + } + + Button { + visible: !inAnotherDemo + text: "Quit" + anchors { left: newGameButton.right; leftMargin: 3; verticalCenter: parent.verticalCenter } + onClicked: Qt.quit(); + } + + Text { + id: score + anchors { right: parent.right; rightMargin: 3; verticalCenter: parent.verticalCenter } + text: "Score: " + gameCanvas.score + font.bold: true + color: activePalette.windowText + } + } +} diff --git a/examples/applets/samegame/metadata.desktop b/examples/applets/samegame/metadata.desktop new file mode 100644 index 000000000..609b2986d --- /dev/null +++ b/examples/applets/samegame/metadata.desktop @@ -0,0 +1,31 @@ +[Desktop Entry] +Encoding=UTF-8 +Name=Same game (QML) +Name[km]=ល្បែង​ Same (QML) +Name[pt]=Jogo Same (QML) +Name[pt_BR]=Jogo Same (QML) +Name[sv]=Same game (QML) +Name[uk]=Та сама гра (QML) +Name[x-test]=xxSame game (QML)xx +Comment=The Same game QML Qt demo converted as plasmoid +Comment[km]=ល្បែង Same QML Qt បាន​បម្លែង​ជា plasmoid +Comment[pt]=O jogo Same do Qt, em QML, convertido para um plasmóide +Comment[pt_BR]=O jogo Same do Qt em QML, convertido para um plasmoide +Comment[sv]=Same game QML Qt-demonstrationen konverterad till en Plasmoid +Comment[uk]=Плазмоїд-демонстрація тієї самої гри на основі QML +Comment[x-test]=xxThe Same game QML Qt demo converted as plasmoidxx + +Type=Service +ServiceTypes=Plasma/Applet +Icon=applications-games +X-Plasma-API=declarativeappletscript +X-Plasma-MainScript=qml/samegame.qml +X-KDE-PluginInfo-Author=Marco Martin +X-KDE-PluginInfo-Email=notmart@gmail.com +X-KDE-PluginInfo-Name=org.kde.samegame-qml +X-KDE-PluginInfo-Version=1.0 +X-KDE-PluginInfo-Website=http://plasma.kde.org/ +X-KDE-PluginInfo-Category=Examples +X-KDE-PluginInfo-Depends= +X-KDE-PluginInfo-License=GPL +X-KDE-PluginInfo-EnabledByDefault=true