Fixed image preview
[harmattan/cameraplus] / qml / PostCapturePage.qml
1 // -*- qml -*-
2
3 /*!
4  * This file is part of CameraPlus.
5  *
6  * Copyright (C) 2012 Mohammed Sameer <msameer@foolab.org>
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
21  */
22
23 import QtQuick 1.1
24 import com.nokia.meego 1.1
25 import QtCamera 1.0
26 import CameraPlus 1.0
27
28 // TODO: losing resources while playback won't show an error
29 // TODO: mass storage mode interaction
30
31 CameraPage {
32         id: page
33
34         controlsVisible: false
35         policyMode: CameraResources.PostCapture
36         needsPipeline: false
37         standbyVisible: !Qt.application.active
38
39         property Item currentItem: null
40         property bool available: currentItem ? currentItem.itemData.available : false
41
42         Component.onCompleted: postCaptureModel.reload();
43
44         function launchGallery() {
45                 if (!gallery.launch()) {
46                         showError(qsTr("Failed to launch gallery"));
47                 }
48         }
49
50         function showInGallery() {
51                 if (!available) {
52                         return;
53                 }
54
55                 if (!gallery.show(currentItem.itemUrl)) {
56                         showError(qsTr("Failed to launch gallery"));
57                 }
58         }
59
60         Menu {
61                 id: menu
62                 MenuLayout {
63                         MenuItem {text: qsTr("Captures in gallery"); onClicked: launchGallery(); }
64                         MenuItem {text: qsTr("View in gallery"); enabled: available; onClicked: showInGallery(); }
65                 }
66         }
67
68         function deleteCurrentItem() {
69                 if (!available) {
70                         return;
71                 }
72
73                 deleteDialog.message = currentItem.itemData.fileName;
74                 deleteDialog.open();
75         }
76
77         QueryDialog {
78                 id: deleteDialog
79                 titleText: qsTr("Delete item?");
80                 acceptButtonText: qsTr("Yes");
81                 rejectButtonText: qsTr("No");
82                 onAccepted: {
83                         if (!remove.remove(currentItem.itemData.url)) {
84                                 showError(qsTr("Failed to delete item"));
85                         }
86                         else {
87                                 postCaptureModel.remove(currentItem.itemData);
88                         }
89                 }
90
91                 DeleteHelper {
92                         id: remove
93                 }
94         }
95
96         function shareCurrentItem() {
97                 if (!available) {
98                         return;
99                 }
100
101                 if (!share.share(currentItem.itemData.url)) {
102                                 showError(qsTr("Failed to launch share service"));
103                 }
104         }
105
106         function addOrRemoveFavorite() {
107                 if (!available) {
108                         return;
109                 }
110
111                 if (currentItem.itemData.favorite) {
112                         if (!trackerStore.removeFromFavorites(currentItem.itemData.url)) {
113                                 showError(qsTr("Failed to remove favorite"));
114                         }
115                         else {
116                                 currentItem.itemData.favorite = false;
117                         }
118                 }
119                 else {
120                         if (!trackerStore.addToFavorites(currentItem.itemData.url)) {
121                                 showError(qsTr("Failed to add favorite"));
122                         }
123                         else {
124                                 currentItem.itemData.favorite = true;
125                         }
126                 }
127         }
128
129         ShareHelper {
130                 id: share
131         }
132
133         GalleryHelper {
134                 id: gallery
135         }
136
137         Rectangle {
138                 color: "black"
139                 anchors.fill: parent
140         }
141
142         PathView {
143                 id: view
144                 anchors.fill: parent
145
146                 path: Path {
147                         startX: - view.width
148                         startY: view.height / 2
149                         PathLine { x: view.width * 2; y: view.height / 2 }
150                 }
151
152                 flickDeceleration: 999999 // Insanely high value to prevent panning multiple images
153                 preferredHighlightBegin: 0.5
154                 preferredHighlightEnd: 0.5
155                 highlightRangeMode: PathView.StrictlyEnforceRange
156                 pathItemCount: 3
157
158                 model: PostCaptureModel {
159                         id: postCaptureModel
160                         manufacturer: deviceInfo.manufacturer
161                         model: deviceInfo.model
162                         onError: {
163                                 console.log("Error populating model " + msg);
164                                 showError(qsTr("Failed to load captures"));
165                         }
166                 }
167
168                 Label {
169                         // TODO: Hide this when we have no items
170                         text: qsTr("No captures available");
171                         anchors.centerIn: parent
172                         font.pixelSize: 36
173                         visible: currentItem == null
174                 }
175
176                 delegate: PostCaptureItem {
177                         width: view.width - 10
178                         height: view.height
179                 }
180         }
181
182         CameraToolBar {
183                 id: toolBar
184                 expanded: true
185                 manualBack: true
186                 anchors.bottom: parent.bottom
187                 anchors.bottomMargin: show ? 20 : -1 * (height + 20)
188                 anchors.left: parent.left
189                 anchors.leftMargin: 20
190                 opacity: 0.8
191
192                 property bool show: true
193
194                 onClicked: pageStack.pop();
195
196                 Behavior on anchors.bottomMargin {
197                         PropertyAnimation { duration: 200; }
198                 }
199
200                 items: [
201                         ToolIcon { iconId: !available ? "icon-m-toolbar-favorite-mark-dimmed-white" : currentItem.itemData.favorite ? "icon-m-toolbar-favorite-mark-white" : "icon-m-toolbar-favorite-unmark-white"; onClicked: addOrRemoveFavorite(); },
202                         ToolIcon { iconId: available ? "icon-m-toolbar-share-white" : "icon-m-toolbar-share-dimmed-white"; onClicked: shareCurrentItem(); },
203                         ToolIcon { iconId: available ? "icon-m-toolbar-delete-white" : "icon-m-toolbar-delete-dimmed-white"; onClicked: deleteCurrentItem(); },
204                         ToolIcon { iconId: "icon-m-toolbar-view-menu-white"; onClicked: menu.open(); }
205                 ]
206         }
207
208         Rectangle {
209                 opacity: toolBar.opacity
210                 anchors.top: parent.top
211                 anchors.topMargin: toolBar.show ? 20 : -1 * (height + 20)
212                 anchors.left: parent.left
213                 anchors.leftMargin: 20
214                 anchors.right: parent.right
215                 anchors.rightMargin: 20
216                 visible: toolBar.visible
217                 height: toolBar.height
218                 color: toolBar.color
219                 border.color: toolBar.border.color
220                 radius: toolBar.radius
221
222                 Behavior on anchors.topMargin {
223                         PropertyAnimation { duration: 200; }
224                 }
225
226                 Label {
227                         text: currentItem ? currentItem.itemData.title : ""
228                         anchors.top: parent.top
229                         anchors.bottom: parent.bottom
230                         anchors.left: parent.left
231                         anchors.leftMargin: 20
232                         font.bold: true
233                         verticalAlignment: Text.AlignVCenter
234                 }
235
236                 Label {
237                         text: currentItem ? currentItem.itemData.created : ""
238                         font.bold: true
239                         anchors.top: parent.top
240                         anchors.bottom: parent.bottom
241                         anchors.right: parent.right
242                         anchors.rightMargin: 20
243                         verticalAlignment: Text.AlignVCenter
244                 }
245         }
246 }