Initial implementation of our own VideoPlayer declarative item
[harmattan/cameraplus] / declarative / camera.cpp
1 /*!
2  * This file is part of CameraPlus.
3  *
4  * Copyright (C) 2012-2013 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 "declarativeqtcameranotifications.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 #include "roi.h"
48
49 #include "videomute.h"
50 #include "videotorch.h"
51 #include "cameraconfig.h"
52
53 Camera::Camera(QDeclarativeItem *parent) :
54   QDeclarativeItem(parent),
55   m_cam(new QtCamera(this)),
56   m_dev(0),
57   m_vf(new QtCamGraphicsViewfinder(m_cam->config(), this)),
58   m_mode(Camera::UnknownMode),
59   m_notifications(new NotificationsContainer(this)),
60   m_zoom(0),
61   m_flash(0),
62   m_scene(0),
63   m_evComp(0),
64   m_whiteBalance(0),
65   m_colorTone(0),
66   m_iso(0),
67   m_exposure(0),
68   m_aperture(0),
69   m_noiseReduction(0),
70   m_flickerReduction(0),
71   m_focus(0),
72   m_autoFocus(0),
73   m_roi(0),
74   m_videoMute(0),
75   m_videoTorch(0),
76   m_config(new CameraConfig(this)) {
77
78   m_config->componentComplete();
79
80   QObject::connect(m_vf, SIGNAL(renderAreaChanged()), this, SIGNAL(renderAreaChanged()));
81   QObject::connect(m_vf, SIGNAL(videoResolutionChanged()), this, SIGNAL(videoResolutionChanged()));
82   QObject::connect(m_vf, SIGNAL(renderingEnabledChanged()), this, SIGNAL(renderingEnabledChanged()));
83 }
84
85 Camera::~Camera() {
86   if (m_dev) {
87     if (m_dev->activeMode()) {
88       m_dev->activeMode()->deactivate();
89     }
90
91     m_dev->stop(true);
92     m_dev->deleteLater();
93     m_dev = 0;
94   }
95
96   delete m_zoom;
97   delete m_flash;
98   delete m_scene;
99   delete m_evComp;
100   delete m_whiteBalance;
101   delete m_colorTone;
102   delete m_iso;
103   delete m_exposure;
104   delete m_aperture;
105   delete m_noiseReduction;
106   delete m_flickerReduction;
107   delete m_focus;
108   delete m_autoFocus;
109   delete m_roi;
110   delete m_videoMute;
111   delete m_videoTorch;
112 }
113
114 void Camera::componentComplete() {
115   QDeclarativeItem::componentComplete();
116
117   emit deviceCountChanged();
118 }
119
120 int Camera::deviceCount() const {
121   return m_cam ? m_cam->devices().size() : 0;
122 }
123
124 QString Camera::deviceName(int index) const {
125   return m_cam->devices().at(index).first;
126 }
127
128 QVariant Camera::deviceId(int index) const {
129   return m_cam->devices().at(index).second;
130 }
131
132 bool Camera::reset(const QVariant& deviceId, const CameraMode& mode) {
133   if (mode == Camera::UnknownMode) {
134     qmlInfo(this) << "Cannot set mode to unknown";
135     return false;
136   }
137
138   if (!isComponentComplete()) {
139     qmlInfo(this) << "Component is still not ready";
140     return false;
141   }
142
143   QVariant oldId = m_id;
144   Camera::CameraMode oldMode = m_mode;
145
146   if (setDeviceId(deviceId) && setMode(mode)) {
147     if (oldId != m_id) {
148       emit deviceIdChanged();
149       emit deviceChanged();
150
151       resetCapabilities();
152     }
153
154     if (oldMode != m_mode) {
155       emit modeChanged();
156     }
157
158     return true;
159   }
160
161   return false;
162 }
163
164 bool Camera::setDeviceId(const QVariant& deviceId) {
165   if (deviceId == m_id) {
166     return true;
167   }
168
169   if (m_dev && m_dev->stop(false)) {
170     delete m_dev;
171   }
172   else if (m_dev) {
173     qmlInfo(this) << "Failed to stop device";
174     return false;
175   }
176
177   m_dev = m_cam->device(deviceId, this);
178
179   m_id = deviceId;
180
181   m_vf->setDevice(m_dev);
182
183   QObject::connect(m_dev, SIGNAL(runningStateChanged(bool)),
184                       this, SIGNAL(runningStateChanged()));
185   QObject::connect(m_dev, SIGNAL(idleStateChanged(bool)), this, SIGNAL(idleStateChanged()));
186   QObject::connect(m_dev, SIGNAL(error(const QString&, int, const QString&)),
187                    this, SIGNAL(error(const QString&, int, const QString&)));
188
189   m_notifications->setDevice(m_dev);
190
191   return true;
192 }
193
194 QVariant Camera::deviceId() const {
195   return m_id;
196 }
197
198 void Camera::geometryChanged(const QRectF& newGeometry, const QRectF& oldGeometry) {
199   QDeclarativeItem::geometryChanged(newGeometry, oldGeometry);
200
201   // TODO: seems setting geometry breaks rendering somehow
202   //  m_vf->setGeometry(newGeometry);
203   m_vf->resize(newGeometry.size());
204 }
205
206 QtCamDevice *Camera::device() const {
207   return m_dev;
208 }
209
210 bool Camera::setMode(const Camera::CameraMode& mode) {
211   if (m_mode == mode) {
212     return true;
213   }
214
215   if (!m_dev) {
216     return false;
217   }
218
219   m_mode = mode;
220
221   if (m_dev->isRunning()) {
222     applyMode();
223   }
224
225   return true;
226 }
227
228 Camera::CameraMode Camera::mode() {
229   return m_mode;
230 }
231
232 bool Camera::start() {
233   if (!m_dev) {
234     return false;
235   }
236
237   if (!applyMode()) {
238     return false;
239   }
240
241   return m_dev->start();
242 }
243
244 bool Camera::stop(bool force) {
245   if (m_dev) {
246     return m_dev->stop(force);
247   }
248
249   return true;
250 }
251
252 bool Camera::isIdle() {
253   return m_dev ? m_dev->isIdle() : true;
254 }
255
256 bool Camera::isRunning() {
257   return m_dev ? m_dev->isRunning() : false;
258 }
259
260 bool Camera::applyMode() {
261   if (m_mode == Camera::UnknownMode) {
262     return false;
263   }
264
265   if (m_mode == Camera::VideoMode && m_dev->activeMode() != m_dev->videoMode()) {
266     m_dev->videoMode()->activate();
267   }
268   else if (m_mode == Camera::ImageMode && m_dev->activeMode() != m_dev->imageMode()) {
269     m_dev->imageMode()->activate();
270   }
271
272   return true;
273 }
274
275 QString Camera::imageSuffix() const {
276   return m_cam->config()->imageSuffix();
277 }
278
279 QString Camera::videoSuffix() const {
280   return m_cam->config()->videoSuffix();
281 }
282
283 DeclarativeQtCameraNotifications *Camera::notifications() const {
284   return m_notifications->notifications();
285 }
286
287 void Camera::setNotifications(DeclarativeQtCameraNotifications *notifications) {
288   if (m_notifications->setNotifications(notifications)) {
289
290     if (Sounds *s = dynamic_cast<Sounds *>(notifications)) {
291       s->setConfig(m_cam->config());
292       s->reload();
293     }
294
295     emit notificationsChanged();
296   }
297 }
298
299 QRectF Camera::renderArea() const {
300   return m_vf->renderArea();
301 }
302
303 QSizeF Camera::videoResolution() const {
304   return m_vf->videoResolution();
305 }
306
307 void Camera::resetCapabilities() {
308   QtCamDevice *dev = device();
309
310   delete m_zoom;
311   m_zoom = new Zoom(dev, this);
312   emit zoomChanged();
313
314   delete m_flash;
315   m_flash = new Flash(dev, this);
316   emit flashChanged();
317
318   delete m_scene;
319   m_scene = new Scene(dev, this);
320   emit sceneChanged();
321
322   delete m_evComp;
323   m_evComp = new EvComp(dev, this);
324   emit evCompChanged();
325
326   delete m_whiteBalance;
327   m_whiteBalance = new WhiteBalance(dev, this);
328   emit whiteBalanceChanged();
329
330   delete m_colorTone;
331   m_colorTone = new ColorTone(dev, this);
332   emit colorToneChanged();
333
334   delete m_iso;
335   m_iso = new Iso(dev, this);
336   emit isoChanged();
337
338   delete m_exposure;
339   m_exposure = new Exposure(dev, this);
340   emit exposureChanged();
341
342   delete m_aperture;
343   m_aperture = new Aperture(dev, this);
344   emit apertureChanged();
345
346   delete m_noiseReduction;
347   m_noiseReduction = new NoiseReduction(dev, this);
348   emit noiseReductionChanged();
349
350   delete m_flickerReduction;
351   m_flickerReduction = new FlickerReduction(dev, this);
352   emit flickerReductionChanged();
353
354   delete m_focus;
355   m_focus = new Focus(dev, this);
356   emit focusChanged();
357
358   delete m_autoFocus;
359   m_autoFocus = new AutoFocus(dev, this);
360   emit autoFocusChanged();
361
362   delete m_roi;
363   m_roi = new Roi(dev, this);
364   emit roiChanged();
365
366   delete m_videoMute;
367   m_videoMute = new VideoMute(dev, this);
368   emit videoMuteChanged();
369
370   delete m_videoTorch;
371   m_videoTorch = new VideoTorch(dev, this);
372   emit videoTorchChanged();
373 }
374
375 Zoom *Camera::zoom() const {
376   return m_zoom;
377 }
378
379 Flash *Camera::flash() const {
380   return m_flash;
381 }
382
383 Scene *Camera::scene() const {
384   return m_scene;
385 }
386
387 EvComp *Camera::evComp() const {
388   return m_evComp;
389 }
390
391 WhiteBalance *Camera::whiteBalance() const {
392   return m_whiteBalance;
393 }
394
395 ColorTone *Camera::colorTone() const {
396   return m_colorTone;
397 }
398
399 Iso *Camera::iso() const {
400   return m_iso;
401 }
402
403 Exposure *Camera::exposure() const {
404   return m_exposure;
405 }
406
407 Aperture *Camera::aperture() const {
408   return m_aperture;
409 }
410
411 NoiseReduction *Camera::noiseReduction() const {
412   return m_noiseReduction;
413 }
414
415 FlickerReduction *Camera::flickerReduction() const {
416   return m_flickerReduction;
417 }
418
419 Focus *Camera::focus() const {
420   return m_focus;
421 }
422
423 AutoFocus *Camera::autoFocus() const {
424   return m_autoFocus;
425 }
426
427 Roi *Camera::roi() const {
428   return m_roi;
429 }
430
431 VideoMute *Camera::videoMute() const {
432   return m_videoMute;
433 }
434
435 VideoTorch *Camera::videoTorch() const {
436   return m_videoTorch;
437 }
438
439 bool Camera::isRenderingEnabled() const {
440   return m_vf->isRenderingEnabled();
441 }
442
443 void Camera::setRenderingEnabled(bool enabled) {
444   m_vf->setRenderingEnabled(enabled);
445 }
446
447 CameraConfig *Camera::cameraConfig() const {
448   return m_config;
449 }