2 * Copyright (C) 2013 Canonical Ltd
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 * Authored by: Thomas Voß <thomas.voss@canonical.com>
17 * Ricardo Salveti de Araujo <ricardo.salveti@canonical.com>
20 #include <hybris/internal/camera_control.h>
21 #include <hybris/camera/camera_compatibility_layer.h>
22 #include <hybris/camera/camera_compatibility_layer_capabilities.h>
23 #include <hybris/camera/camera_compatibility_layer_configuration_translator.h>
25 #include <hybris/internal/surface_flinger_compatibility_layer_internal.h>
27 #include <binder/ProcessState.h>
28 #include <camera/Camera.h>
29 #include <camera/CameraParameters.h>
30 #include <gui/SurfaceTexture.h>
31 #include <ui/GraphicBuffer.h>
34 #define LOG_TAG "CameraCompatibilityLayer"
35 #include <utils/KeyedVector.h>
36 #include <utils/Log.h>
38 #define REPORT_FUNCTION() ALOGV("%s \n", __PRETTY_FUNCTION__)
40 // From android::SurfaceTexture::FrameAvailableListener
41 void CameraControl::onFrameAvailable()
45 listener
->on_preview_texture_needs_update_cb(listener
->context
);
48 // From android::CameraListener
49 void CameraControl::notify(int32_t msg_type
, int32_t ext1
, int32_t ext2
)
52 printf("\text1: %d, ext2: %d \n", ext1
, ext2
);
58 case CAMERA_MSG_ERROR
:
59 if (listener
->on_msg_error_cb
)
60 listener
->on_msg_error_cb(listener
->context
);
62 case CAMERA_MSG_SHUTTER
:
63 if (listener
->on_msg_shutter_cb
)
64 listener
->on_msg_shutter_cb(listener
->context
);
67 if (listener
->on_msg_zoom_cb
)
68 listener
->on_msg_zoom_cb(listener
->context
, ext1
);
70 case CAMERA_MSG_FOCUS
:
71 if (listener
->on_msg_focus_cb
)
72 listener
->on_msg_focus_cb(listener
->context
);
79 void CameraControl::postData(
81 const android::sp
<android::IMemory
>& data
,
82 camera_frame_metadata_t
* metadata
)
90 case CAMERA_MSG_RAW_IMAGE
:
91 if (listener
->on_data_raw_image_cb
)
92 listener
->on_data_raw_image_cb(data
->pointer(), data
->size(), listener
->context
);
94 case CAMERA_MSG_COMPRESSED_IMAGE
:
95 if (listener
->on_data_compressed_image_cb
)
96 listener
->on_data_compressed_image_cb(data
->pointer(), data
->size(), listener
->context
);
103 void CameraControl::postDataTimestamp(
106 const android::sp
<android::IMemory
>& data
)
116 NativeBufferAlloc::NativeBufferAlloc() {
119 NativeBufferAlloc::~NativeBufferAlloc() {
122 sp
<GraphicBuffer
> NativeBufferAlloc::createGraphicBuffer(uint32_t w
, uint32_t h
,
123 PixelFormat format
, uint32_t usage
, status_t
* error
) {
124 sp
<GraphicBuffer
> graphicBuffer(new GraphicBuffer(w
, h
, format
, usage
));
125 status_t err
= graphicBuffer
->initCheck();
127 if (err
!= 0 || graphicBuffer
->handle
== 0) {
128 if (err
== NO_MEMORY
) {
129 GraphicBuffer::dumpAllocationsToSystemLog();
131 ALOGI("GraphicBufferAlloc::createGraphicBuffer(w=%d, h=%d) "
132 "failed (%s), handle=%p",
133 w
, h
, strerror(-err
), graphicBuffer
->handle
);
136 return graphicBuffer
;
143 android::sp
<CameraControl
> camera_control_instance
;
147 int android_camera_get_number_of_devices()
150 return android::Camera::getNumberOfCameras();
153 CameraControl
* android_camera_connect_to(CameraType camera_type
, CameraControlListener
* listener
)
158 int32_t camera_count
= camera_id
= android::Camera::getNumberOfCameras();
160 for (camera_id
= 0; camera_id
< camera_count
; camera_id
++) {
161 android::CameraInfo ci
;
162 android::Camera::getCameraInfo(camera_id
, &ci
);
164 if (ci
.facing
== camera_type
)
168 if (camera_id
== camera_count
)
171 CameraControl
* cc
= new CameraControl();
172 cc
->listener
= listener
;
173 cc
->camera
= android::Camera::connect(camera_id
);
175 if (cc
->camera
== NULL
)
178 cc
->camera_parameters
= android::CameraParameters(cc
->camera
->getParameters());
180 camera_control_instance
= cc
;
181 cc
->camera
->setListener(camera_control_instance
);
184 // TODO: Move this to a more generic component
185 android::ProcessState::self()->startThreadPool();
190 void android_camera_disconnect(CameraControl
* control
)
195 android::Mutex::Autolock
al(control
->guard
);
197 if (control
->preview_texture
!= NULL
)
198 control
->preview_texture
->abandon();
200 control
->camera
->disconnect();
201 control
->camera
->unlock();
204 int android_camera_lock(CameraControl
* control
)
206 android::Mutex::Autolock
al(control
->guard
);
207 return control
->camera
->lock();
210 int android_camera_unlock(CameraControl
* control
)
212 android::Mutex::Autolock
al(control
->guard
);
213 return control
->camera
->unlock();
216 void android_camera_delete(CameraControl
* control
)
221 void android_camera_dump_parameters(CameraControl
* control
)
226 printf("%s \n", control
->camera
->getParameters().string());
229 void android_camera_set_flash_mode(CameraControl
* control
, FlashMode mode
)
234 android::Mutex::Autolock
al(control
->guard
);
235 control
->camera_parameters
.set(
236 android::CameraParameters::KEY_FLASH_MODE
,
238 control
->camera
->setParameters(control
->camera_parameters
.flatten());
241 void android_camera_get_flash_mode(CameraControl
* control
, FlashMode
* mode
)
246 android::Mutex::Autolock
al(control
->guard
);
247 static const char* flash_mode
= control
->camera_parameters
.get(
248 android::CameraParameters::KEY_FLASH_MODE
);
250 *mode
= flash_modes_lut
.valueFor(android::String8(flash_mode
));
252 *mode
= FLASH_MODE_OFF
;
255 void android_camera_set_white_balance_mode(CameraControl
* control
, WhiteBalanceMode mode
)
260 android::Mutex::Autolock
al(control
->guard
);
262 control
->camera_parameters
.set(
263 android::CameraParameters::KEY_WHITE_BALANCE
,
264 white_balance_modes
[mode
]);
265 control
->camera
->setParameters(control
->camera_parameters
.flatten());
268 void android_camera_get_white_balance_mode(CameraControl
* control
, WhiteBalanceMode
* mode
)
273 android::Mutex::Autolock
al(control
->guard
);
275 *mode
= white_balance_modes_lut
.valueFor(
277 control
->camera_parameters
.get(
278 android::CameraParameters::KEY_WHITE_BALANCE
)));
281 void android_camera_set_scene_mode(CameraControl
* control
, SceneMode mode
)
286 android::Mutex::Autolock
al(control
->guard
);
288 control
->camera_parameters
.set(
289 android::CameraParameters::KEY_SCENE_MODE
,
291 control
->camera
->setParameters(control
->camera_parameters
.flatten());
294 void android_camera_get_scene_mode(CameraControl
* control
, SceneMode
* mode
)
299 android::Mutex::Autolock
al(control
->guard
);
301 *mode
= scene_modes_lut
.valueFor(
303 control
->camera_parameters
.get(
304 android::CameraParameters::KEY_SCENE_MODE
)));
307 void android_camera_set_auto_focus_mode(CameraControl
* control
, AutoFocusMode mode
)
312 android::Mutex::Autolock
al(control
->guard
);
314 control
->camera_parameters
.set(
315 android::CameraParameters::KEY_FOCUS_MODE
,
316 auto_focus_modes
[mode
]);
317 control
->camera
->setParameters(control
->camera_parameters
.flatten());
320 void android_camera_get_auto_focus_mode(CameraControl
* control
, AutoFocusMode
* mode
)
325 android::Mutex::Autolock
al(control
->guard
);
327 *mode
= auto_focus_modes_lut
.valueFor(
329 control
->camera_parameters
.get(
330 android::CameraParameters::KEY_FOCUS_MODE
)));
334 void android_camera_set_effect_mode(CameraControl
* control
, EffectMode mode
)
339 android::Mutex::Autolock
al(control
->guard
);
341 control
->camera_parameters
.set(
342 android::CameraParameters::KEY_EFFECT
,
344 control
->camera
->setParameters(control
->camera_parameters
.flatten());
347 void android_camera_get_effect_mode(CameraControl
* control
, EffectMode
* mode
)
352 android::Mutex::Autolock
al(control
->guard
);
354 *mode
= effect_modes_lut
.valueFor(
356 control
->camera_parameters
.get(
357 android::CameraParameters::KEY_EFFECT
)));
360 void android_camera_get_preview_fps_range(CameraControl
* control
, int* min
, int* max
)
365 android::Mutex::Autolock
al(control
->guard
);
367 control
->camera_parameters
.getPreviewFpsRange(min
, max
);
370 void android_camera_set_preview_fps(CameraControl
* control
, int fps
)
375 android::Mutex::Autolock
al(control
->guard
);
376 control
->camera_parameters
.setPreviewFrameRate(fps
);
377 control
->camera
->setParameters(control
->camera_parameters
.flatten());
380 void android_camera_get_preview_fps(CameraControl
* control
, int* fps
)
385 android::Mutex::Autolock
al(control
->guard
);
386 *fps
= control
->camera_parameters
.getPreviewFrameRate();
389 void android_camera_enumerate_supported_preview_sizes(CameraControl
* control
, size_callback cb
, void* ctx
)
394 android::Mutex::Autolock
al(control
->guard
);
395 android::Vector
<android::Size
> sizes
;
396 control
->camera_parameters
.getSupportedPreviewSizes(sizes
);
398 for (unsigned int i
= 0; i
< sizes
.size(); i
++) {
399 cb(ctx
, sizes
[i
].width
, sizes
[i
].height
);
403 void android_camera_enumerate_supported_picture_sizes(CameraControl
* control
, size_callback cb
, void* ctx
)
408 android::Mutex::Autolock
al(control
->guard
);
409 android::Vector
<android::Size
> sizes
;
410 control
->camera_parameters
.getSupportedPictureSizes(sizes
);
412 for (unsigned int i
= 0; i
< sizes
.size(); i
++) {
413 cb(ctx
, sizes
[i
].width
, sizes
[i
].height
);
417 void android_camera_get_preview_size(CameraControl
* control
, int* width
, int* height
)
422 android::Mutex::Autolock
al(control
->guard
);
424 control
->camera_parameters
.getPreviewSize(width
, height
);
427 void android_camera_set_preview_size(CameraControl
* control
, int width
, int height
)
432 android::Mutex::Autolock
al(control
->guard
);
434 control
->camera_parameters
.setPreviewSize(width
, height
);
435 control
->camera
->setParameters(control
->camera_parameters
.flatten());
438 void android_camera_get_picture_size(CameraControl
* control
, int* width
, int* height
)
443 android::Mutex::Autolock
al(control
->guard
);
445 control
->camera_parameters
.getPictureSize(width
, height
);
448 void android_camera_set_picture_size(CameraControl
* control
, int width
, int height
)
453 android::Mutex::Autolock
al(control
->guard
);
455 control
->camera_parameters
.setPictureSize(width
, height
);
456 control
->camera
->setParameters(control
->camera_parameters
.flatten());
459 void android_camera_get_current_zoom(CameraControl
* control
, int* zoom
)
464 android::Mutex::Autolock
al(control
->guard
);
466 *zoom
= control
->camera_parameters
.getInt(android::CameraParameters::KEY_ZOOM
);
469 void android_camera_get_max_zoom(CameraControl
* control
, int* zoom
)
474 android::Mutex::Autolock
al(control
->guard
);
476 *zoom
= control
->camera_parameters
.getInt(android::CameraParameters::KEY_MAX_ZOOM
);
479 void android_camera_set_display_orientation(CameraControl
* control
, int32_t clockwise_rotation_degree
)
484 android::Mutex::Autolock
al(control
->guard
);
485 static const int32_t ignored_parameter
= 0;
486 control
->camera
->sendCommand(CAMERA_CMD_SET_DISPLAY_ORIENTATION
, clockwise_rotation_degree
, ignored_parameter
);
489 void android_camera_get_preview_texture_transformation(CameraControl
* control
, float m
[16])
494 if (control
->preview_texture
== NULL
)
497 control
->preview_texture
->getTransformMatrix(m
);
500 void android_camera_update_preview_texture(CameraControl
* control
)
505 control
->preview_texture
->updateTexImage();
508 void android_camera_set_preview_texture(CameraControl
* control
, int texture_id
)
513 static const bool allow_synchronous_mode
= false;
515 android::sp
<android::NativeBufferAlloc
> native_alloc(
516 new android::NativeBufferAlloc()
519 android::sp
<android::BufferQueue
> buffer_queue(
520 new android::BufferQueue(false, NULL
, native_alloc
)
523 if (control
->preview_texture
== NULL
) {
524 control
->preview_texture
= android::sp
<android::SurfaceTexture
>(
525 new android::SurfaceTexture(
527 allow_synchronous_mode
,
528 GL_TEXTURE_EXTERNAL_OES
,
533 control
->preview_texture
->setFrameAvailableListener(
534 android::sp
<android::SurfaceTexture::FrameAvailableListener
>(control
));
535 control
->camera
->setPreviewTexture(control
->preview_texture
->getBufferQueue());
538 void android_camera_set_preview_surface(CameraControl
* control
, SfSurface
* surface
)
544 android::Mutex::Autolock
al(control
->guard
);
545 control
->camera
->setPreviewDisplay(surface
->surface
);
548 void android_camera_start_preview(CameraControl
* control
)
553 android::Mutex::Autolock
al(control
->guard
);
554 control
->camera
->startPreview();
557 void android_camera_stop_preview(CameraControl
* control
)
562 android::Mutex::Autolock
al(control
->guard
);
563 control
->camera
->stopPreview();
566 void android_camera_start_autofocus(CameraControl
* control
)
571 android::Mutex::Autolock
al(control
->guard
);
572 control
->camera
->autoFocus();
575 void android_camera_stop_autofocus(CameraControl
* control
)
580 android::Mutex::Autolock
al(control
->guard
);
581 control
->camera
->cancelAutoFocus();
584 void android_camera_start_zoom(CameraControl
* control
, int32_t zoom
)
589 static const int ignored_argument
= 0;
591 android::Mutex::Autolock
al(control
->guard
);
592 control
->camera
->sendCommand(CAMERA_CMD_START_SMOOTH_ZOOM
,
597 // Adjust the zoom level immediately as opposed to smoothly zoomin gin.
598 void android_camera_set_zoom(CameraControl
* control
, int32_t zoom
)
603 android::Mutex::Autolock
al(control
->guard
);
605 control
->camera_parameters
.set(
606 android::CameraParameters::KEY_ZOOM
,
609 control
->camera
->setParameters(control
->camera_parameters
.flatten());
612 void android_camera_stop_zoom(CameraControl
* control
)
617 static const int ignored_argument
= 0;
619 android::Mutex::Autolock
al(control
->guard
);
620 control
->camera
->sendCommand(CAMERA_CMD_STOP_SMOOTH_ZOOM
,
625 void android_camera_take_snapshot(CameraControl
* control
)
629 android::Mutex::Autolock
al(control
->guard
);
630 control
->camera
->takePicture(CAMERA_MSG_SHUTTER
| CAMERA_MSG_COMPRESSED_IMAGE
);
633 void android_camera_set_preview_format(CameraControl
* control
, CameraPixelFormat pf
)
638 android::Mutex::Autolock
al(control
->guard
);
640 control
->camera_parameters
.set(
641 android::CameraParameters::KEY_PREVIEW_FORMAT
,
642 camera_pixel_formats
[pf
]);
644 control
->camera
->setParameters(control
->camera_parameters
.flatten());
647 void android_camera_get_preview_format(CameraControl
* control
, CameraPixelFormat
* pf
)
652 android::Mutex::Autolock
al(control
->guard
);
654 *pf
= pixel_formats_lut
.valueFor(
656 control
->camera_parameters
.get(
657 android::CameraParameters::KEY_PREVIEW_FORMAT
)));
660 void android_camera_set_focus_region(
661 CameraControl
* control
,
667 android::Mutex::Autolock
al(control
->guard
);
668 static const char* focus_region_pattern
= "(%d,%d,%d,%d,%d)";
669 static char focus_region
[256];
670 snprintf(focus_region
,
671 sizeof(focus_region
),
672 focus_region_pattern
,
679 control
->camera_parameters
.set(
680 android::CameraParameters::KEY_FOCUS_AREAS
,
683 control
->camera
->setParameters(control
->camera_parameters
.flatten());
686 void android_camera_reset_focus_region(CameraControl
* control
)
688 static FocusRegion region
= { 0, 0, 0, 0, 0 };
690 android_camera_set_focus_region(control
, ®ion
);
693 void android_camera_set_rotation(CameraControl
* control
, int rotation
)
698 android::Mutex::Autolock
al(control
->guard
);
699 control
->camera_parameters
.set(
700 android::CameraParameters::KEY_ROTATION
,
702 control
->camera
->setParameters(control
->camera_parameters
.flatten());
705 void android_camera_enumerate_supported_video_sizes(CameraControl
* control
, size_callback cb
, void* ctx
)
711 android::Mutex::Autolock
al(control
->guard
);
712 android::Vector
<android::Size
> sizes
;
713 control
->camera_parameters
.getSupportedVideoSizes(sizes
);
715 for (unsigned int i
= 0; i
< sizes
.size(); i
++) {
716 cb(ctx
, sizes
[i
].width
, sizes
[i
].height
);
720 void android_camera_get_video_size(CameraControl
* control
, int* width
, int* height
)
725 android::Mutex::Autolock
al(control
->guard
);
727 control
->camera_parameters
.getVideoSize(width
, height
);
730 void android_camera_set_video_size(CameraControl
* control
, int width
, int height
)
735 android::Mutex::Autolock
al(control
->guard
);
737 control
->camera_parameters
.setVideoSize(width
, height
);
738 control
->camera
->setParameters(control
->camera_parameters
.flatten());