Declarative Camera should deactivete active mode when destroyed before stopping the...
[harmattan/cameraplus] / declarative / camera.cpp
1 /*!
2  * This file is part of CameraPlus.
3  *
4  * Copyright (C) 2012 Mohammed Sameer <msameer@foolab.org>
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
19  */
20
21 #include "camera.h"
22 #include "qtcamera.h"
23 #include "qtcamdevice.h"
24 #include "qtcammode.h"
25 #include "qtcamimagemode.h"
26 #include "qtcamvideomode.h"
27 #include "qtcamgraphicsviewfinder.h"
28 #include "qtcamconfig.h"
29 #include "notifications.h"
30 #include "notificationscontainer.h"
31 #include "sounds.h"
32 #include <QDeclarativeInfo>
33
34 #include "zoom.h"
35 #include "flash.h"
36 #include "scene.h"
37 #include "evcomp.h"
38 #include "whitebalance.h"
39 #include "colortone.h"
40 #include "iso.h"
41 #include "exposure.h"
42 #include "aperture.h"
43 #include "noisereduction.h"
44 #include "flickerreduction.h"
45 #include "focus.h"
46 #include "autofocus.h"
47
48 #include "videomute.h"
49 #include "videotorch.h"
50
51 Camera::Camera(QDeclarativeItem *parent) :
52   QDeclarativeItem(parent),
53   m_cam(new QtCamera(this)),
54   m_dev(0),
55   m_vf(new QtCamGraphicsViewfinder(m_cam->config(), this)),
56   m_mode(Camera::UnknownMode),
57   m_notifications(new NotificationsContainer(this)),
58   m_zoom(0),
59   m_flash(0),
60   m_scene(0),
61   m_evComp(0),
62   m_whiteBalance(0),
63   m_colorTone(0),
64   m_iso(0),
65   m_exposure(0),
66   m_aperture(0),
67   m_noiseReduction(0),
68   m_flickerReduction(0),
69   m_focus(0),
70   m_autoFocus(0),
71   m_videoMute(0),
72   m_videoTorch(0) {
73
74   QObject::connect(m_vf, SIGNAL(renderAreaChanged()), this, SIGNAL(renderAreaChanged()));
75   QObject::connect(m_vf, SIGNAL(videoResolutionChanged()), this, SIGNAL(videoResolutionChanged()));
76   QObject::connect(m_vf, SIGNAL(renderingEnabledChanged()), this, SIGNAL(renderingEnabledChanged()));
77 }
78
79 Camera::~Camera() {
80   if (m_dev) {
81     if (m_dev->activeMode()) {
82       m_dev->activeMode()->deactivate();
83     }
84
85     m_dev->stop(true);
86     m_dev->deleteLater();
87     m_dev = 0;
88   }
89
90   delete m_zoom;
91   delete m_flash;
92   delete m_scene;
93   delete m_evComp;
94   delete m_whiteBalance;
95   delete m_colorTone;
96   delete m_iso;
97   delete m_exposure;
98   delete m_aperture;
99   delete m_noiseReduction;
100   delete m_flickerReduction;
101   delete m_focus;
102   delete m_autoFocus;
103   delete m_videoMute;
104   delete m_videoTorch;
105   // TODO: cleanup
106 }
107
108 void Camera::componentComplete() {
109   QDeclarativeItem::componentComplete();
110
111   emit deviceCountChanged();
112 }
113
114 int Camera::deviceCount() const {
115   return m_cam ? m_cam->devices().size() : 0;
116 }
117
118 QString Camera::deviceName(int index) const {
119   return m_cam->devices().at(index).first;
120 }
121
122 QVariant Camera::deviceId(int index) const {
123   return m_cam->devices().at(index).second;
124 }
125
126 bool Camera::reset(const QVariant& deviceId, const CameraMode& mode) {
127   if (mode == Camera::UnknownMode) {
128     qmlInfo(this) << "Cannot set mode to unknown";
129     return false;
130   }
131
132   if (!isComponentComplete()) {
133     qmlInfo(this) << "Component is still not ready";
134     return false;
135   }
136
137   QVariant oldId = m_id;
138   Camera::CameraMode oldMode = m_mode;
139
140   if (setDeviceId(deviceId) && setMode(mode)) {
141     if (oldId != m_id) {
142       emit deviceIdChanged();
143       emit deviceChanged();
144
145       resetCapabilities();
146     }
147
148     if (oldMode != m_mode) {
149       emit modeChanged();
150     }
151
152     return true;
153   }
154
155   return false;
156 }
157
158 bool Camera::setDeviceId(const QVariant& deviceId) {
159   if (deviceId == m_id) {
160     return true;
161   }
162
163   if (m_dev && m_dev->stop(false)) {
164     delete m_dev;
165   }
166   else if (m_dev) {
167     qmlInfo(this) << "Failed to stop device";
168     return false;
169   }
170
171   m_dev = m_cam->device(deviceId, this);
172
173   m_id = deviceId;
174
175   m_vf->setDevice(m_dev);
176
177   QObject::connect(m_dev, SIGNAL(runningStateChanged(bool)),
178                       this, SIGNAL(runningStateChanged()));
179   QObject::connect(m_dev, SIGNAL(idleStateChanged(bool)), this, SIGNAL(idleStateChanged()));
180   QObject::connect(m_dev, SIGNAL(error(const QString&, int, const QString&)),
181                    this, SIGNAL(error(const QString&, int, const QString&)));
182
183   m_notifications->setDevice(m_dev);
184
185   return true;
186 }
187
188 QVariant Camera::deviceId() const {
189   return m_id;
190 }
191
192 void Camera::geometryChanged(const QRectF& newGeometry, const QRectF& oldGeometry) {
193   QDeclarativeItem::geometryChanged(newGeometry, oldGeometry);
194
195   m_vf->setGeometry(newGeometry);
196 }
197
198 QtCamDevice *Camera::device() const {
199   return m_dev;
200 }
201
202 bool Camera::setMode(const Camera::CameraMode& mode) {
203   if (m_mode == mode) {
204     return true;
205   }
206
207   if (!m_dev) {
208     return false;
209   }
210
211   m_mode = mode;
212
213   if (m_dev->isRunning()) {
214     applyMode();
215   }
216
217   return true;
218 }
219
220 Camera::CameraMode Camera::mode() {
221   return m_mode;
222 }
223
224 bool Camera::start() {
225   if (!m_dev) {
226     return false;
227   }
228
229   if (!applyMode()) {
230     return false;
231   }
232
233   return m_dev->start();
234 }
235
236 bool Camera::stop(bool force) {
237   if (m_dev) {
238     return m_dev->stop(force);
239   }
240
241   return true;
242 }
243
244 bool Camera::isIdle() {
245   return m_dev ? m_dev->isIdle() : true;
246 }
247
248 bool Camera::isRunning() {
249   return m_dev ? m_dev->isRunning() : false;
250 }
251
252 bool Camera::applyMode() {
253   if (m_mode == Camera::UnknownMode) {
254     return false;
255   }
256
257   if (m_mode == Camera::VideoMode && m_dev->activeMode() != m_dev->videoMode()) {
258     m_dev->videoMode()->activate();
259   }
260   else if (m_mode == Camera::ImageMode && m_dev->activeMode() != m_dev->imageMode()) {
261     m_dev->imageMode()->activate();
262   }
263
264   return true;
265 }
266
267 QString Camera::imageSuffix() const {
268   return m_cam->config()->imageSuffix();
269 }
270
271 QString Camera::videoSuffix() const {
272   return m_cam->config()->videoSuffix();
273 }
274
275 Notifications *Camera::notifications() const {
276   return m_notifications->notifications();
277 }
278
279 void Camera::setNotifications(Notifications *notifications) {
280   if (m_notifications->setNotifications(notifications)) {
281
282     if (Sounds *s = dynamic_cast<Sounds *>(notifications)) {
283       s->setConfig(m_cam->config());
284       s->reload();
285     }
286
287     emit notificationsChanged();
288   }
289 }
290
291 QRectF Camera::renderArea() const {
292   return m_vf->renderArea();
293 }
294
295 QSizeF Camera::videoResolution() const {
296   return m_vf->videoResolution();
297 }
298
299 void Camera::resetCapabilities() {
300   QtCamDevice *dev = device();
301
302   delete m_zoom;
303   m_zoom = new Zoom(dev, this);
304   emit zoomChanged();
305
306   delete m_flash;
307   m_flash = new Flash(dev, this);
308   emit flashChanged();
309
310   delete m_scene;
311   m_scene = new Scene(dev, this);
312   emit sceneChanged();
313
314   delete m_evComp;
315   m_evComp = new EvComp(dev, this);
316   emit evCompChanged();
317
318   delete m_whiteBalance;
319   m_whiteBalance = new WhiteBalance(dev, this);
320   emit whiteBalanceChanged();
321
322   delete m_colorTone;
323   m_colorTone = new ColorTone(dev, this);
324   emit colorToneChanged();
325
326   delete m_iso;
327   m_iso = new Iso(dev, this);
328   emit isoChanged();
329
330   delete m_exposure;
331   m_exposure = new Exposure(dev, this);
332   emit exposureChanged();
333
334   delete m_aperture;
335   m_aperture = new Aperture(dev, this);
336   emit apertureChanged();
337
338   delete m_noiseReduction;
339   m_noiseReduction = new NoiseReduction(dev, this);
340   emit noiseReductionChanged();
341
342   delete m_flickerReduction;
343   m_flickerReduction = new FlickerReduction(dev, this);
344   emit flickerReductionChanged();
345
346   delete m_focus;
347   m_focus = new Focus(dev, this);
348   emit focusChanged();
349
350   delete m_autoFocus;
351   m_autoFocus = new AutoFocus(dev, this);
352   emit autoFocusChanged();
353
354   delete m_videoMute;
355   m_videoMute = new VideoMute(dev, this);
356   emit videoMuteChanged();
357
358   delete m_videoTorch;
359   m_videoTorch = new VideoTorch(dev, this);
360   emit videoTorchChanged();
361 }
362
363 Zoom *Camera::zoom() const {
364   return m_zoom;
365 }
366
367 Flash *Camera::flash() const {
368   return m_flash;
369 }
370
371 Scene *Camera::scene() const {
372   return m_scene;
373 }
374
375 EvComp *Camera::evComp() const {
376   return m_evComp;
377 }
378
379 WhiteBalance *Camera::whiteBalance() const {
380   return m_whiteBalance;
381 }
382
383 ColorTone *Camera::colorTone() const {
384   return m_colorTone;
385 }
386
387 Iso *Camera::iso() const {
388   return m_iso;
389 }
390
391 Exposure *Camera::exposure() const {
392   return m_exposure;
393 }
394
395 Aperture *Camera::aperture() const {
396   return m_aperture;
397 }
398
399 NoiseReduction *Camera::noiseReduction() const {
400   return m_noiseReduction;
401 }
402
403 FlickerReduction *Camera::flickerReduction() const {
404   return m_flickerReduction;
405 }
406
407 Focus *Camera::focus() const {
408   return m_focus;
409 }
410
411 AutoFocus *Camera::autoFocus() const {
412   return m_autoFocus;
413 }
414
415 VideoMute *Camera::videoMute() const {
416   return m_videoMute;
417 }
418
419 VideoTorch *Camera::videoTorch() const {
420   return m_videoTorch;
421 }
422
423 bool Camera::isRenderingEnabled() const {
424   return m_vf->isRenderingEnabled();
425 }
426
427 void Camera::setRenderingEnabled(bool enabled) {
428   m_vf->setRenderingEnabled(enabled);
429 }