blob: c90f81a76f08cf1e7be28124c04c73867a985978 [file] [log] [blame]
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07001/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
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
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
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.
15 */
16
17#define LOG_TAG "Camera2Client"
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070018#define ATRACE_TAG ATRACE_TAG_CAMERA
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070019//#define LOG_NDEBUG 0
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070020
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070021#include <utils/Log.h>
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070022#include <utils/Trace.h>
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070023
24#include <cutils/properties.h>
25#include <gui/SurfaceTextureClient.h>
26#include <gui/Surface.h>
27
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070028#include <math.h>
29
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070030#include "Camera2Client.h"
31
32namespace android {
33
34#define ALOG1(...) ALOGD_IF(gLogLevel >= 1, __VA_ARGS__);
35#define ALOG2(...) ALOGD_IF(gLogLevel >= 2, __VA_ARGS__);
36
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070037static int getCallingPid() {
38 return IPCThreadState::self()->getCallingPid();
39}
40
41static int getCallingUid() {
42 return IPCThreadState::self()->getCallingUid();
43}
44
45// Interface used by CameraService
46
47Camera2Client::Camera2Client(const sp<CameraService>& cameraService,
48 const sp<ICameraClient>& cameraClient,
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070049 int cameraId,
50 int cameraFacing,
51 int clientPid):
52 Client(cameraService, cameraClient,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070053 cameraId, cameraFacing, clientPid),
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -070054 mState(NOT_INITIALIZED),
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -070055 mPreviewStreamId(NO_STREAM),
56 mPreviewRequest(NULL),
57 mCaptureStreamId(NO_STREAM),
58 mCaptureRequest(NULL)
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070059{
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070060 ATRACE_CALL();
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070061
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070062 mDevice = new Camera2Device(cameraId);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070063}
64
65status_t Camera2Client::initialize(camera_module_t *module)
66{
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070067 ATRACE_CALL();
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070068 status_t res;
69
70 res = mDevice->initialize(module);
71 if (res != OK) {
72 ALOGE("%s: Camera %d: unable to initialize device: %s (%d)",
73 __FUNCTION__, mCameraId, strerror(-res), res);
74 return NO_INIT;
75 }
76
77 res = buildDefaultParameters();
78 if (res != OK) {
79 ALOGE("%s: Camera %d: unable to build defaults: %s (%d)",
80 __FUNCTION__, mCameraId, strerror(-res), res);
81 return NO_INIT;
82 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -070083
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070084 if (gLogLevel >= 1) {
85 ALOGD("%s: Default parameters converted from camera %d:", __FUNCTION__,
86 mCameraId);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -070087 ALOGD("%s", mParamsFlattened.string());
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070088 }
89
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -070090 mState = STOPPED;
91
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070092 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -070093}
94
95Camera2Client::~Camera2Client() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -070096 ATRACE_CALL();
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -070097 ALOGV("%s: Camera %d: Shutting down", __FUNCTION__, mCameraId);
98
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -070099 mDestructionStarted = true;
100
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -0700101 disconnect();
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -0700102
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700103}
104
105status_t Camera2Client::dump(int fd, const Vector<String16>& args) {
Eino-Ville Talvala611f6192012-05-31 12:28:23 -0700106 String8 result;
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700107 result.appendFormat("Client2[%d] (%p) PID: %d, dump:\n",
Eino-Ville Talvala611f6192012-05-31 12:28:23 -0700108 mCameraId,
109 getCameraClient()->asBinder().get(),
110 mClientPid);
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700111 result.append(" State: ");
112#define CASE_APPEND_ENUM(x) case x: result.append(#x "\n"); break;
113
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700114 result.append(getStateName(mState));
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700115
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700116 result.append("\n Current parameters:\n");
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700117 result.appendFormat(" Preview size: %d x %d\n",
118 mParameters.previewWidth, mParameters.previewHeight);
119 result.appendFormat(" Preview FPS range: %d - %d\n",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700120 mParameters.previewFpsRange[0], mParameters.previewFpsRange[1]);
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700121 result.appendFormat(" Preview HAL pixel format: 0x%x\n",
122 mParameters.previewFormat);
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700123 result.appendFormat(" Preview transform: %x\n",
124 mParameters.previewTransform);
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700125 result.appendFormat(" Picture size: %d x %d\n",
126 mParameters.pictureWidth, mParameters.pictureHeight);
127 result.appendFormat(" Jpeg thumbnail size: %d x %d\n",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700128 mParameters.jpegThumbSize[0], mParameters.jpegThumbSize[1]);
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700129 result.appendFormat(" Jpeg quality: %d, thumbnail quality: %d\n",
130 mParameters.jpegQuality, mParameters.jpegThumbQuality);
131 result.appendFormat(" Jpeg rotation: %d\n", mParameters.jpegRotation);
132 result.appendFormat(" GPS tags %s\n",
133 mParameters.gpsEnabled ? "enabled" : "disabled");
134 if (mParameters.gpsEnabled) {
135 result.appendFormat(" GPS lat x long x alt: %f x %f x %f\n",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700136 mParameters.gpsCoordinates[0], mParameters.gpsCoordinates[1],
137 mParameters.gpsCoordinates[2]);
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700138 result.appendFormat(" GPS timestamp: %lld\n",
139 mParameters.gpsTimestamp);
140 result.appendFormat(" GPS processing method: %s\n",
141 mParameters.gpsProcessingMethod.string());
142 }
143
144 result.append(" White balance mode: ");
145 switch (mParameters.wbMode) {
146 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_AUTO)
147 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_INCANDESCENT)
148 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_FLUORESCENT)
149 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_WARM_FLUORESCENT)
150 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_DAYLIGHT)
151 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT)
152 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_TWILIGHT)
153 CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_SHADE)
154 default: result.append("UNKNOWN\n");
155 }
156
157 result.append(" Effect mode: ");
158 switch (mParameters.effectMode) {
159 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_OFF)
160 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_MONO)
161 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_NEGATIVE)
162 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_SOLARIZE)
163 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_SEPIA)
164 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_POSTERIZE)
165 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_WHITEBOARD)
166 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_BLACKBOARD)
167 CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_AQUA)
168 default: result.append("UNKNOWN\n");
169 }
170
171 result.append(" Antibanding mode: ");
172 switch (mParameters.antibandingMode) {
173 CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_AUTO)
174 CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_OFF)
175 CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_50HZ)
176 CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_60HZ)
177 default: result.append("UNKNOWN\n");
178 }
179
180 result.append(" Scene mode: ");
181 switch (mParameters.sceneMode) {
182 case ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED:
183 result.append("AUTO\n"); break;
184 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_ACTION)
185 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_PORTRAIT)
186 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_LANDSCAPE)
187 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_NIGHT)
188 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT)
189 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_THEATRE)
190 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_BEACH)
191 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SNOW)
192 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SUNSET)
193 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO)
194 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_FIREWORKS)
195 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SPORTS)
196 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_PARTY)
197 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT)
198 CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_BARCODE)
199 default: result.append("UNKNOWN\n");
200 }
201
202 result.append(" Flash mode: ");
203 switch (mParameters.flashMode) {
204 CASE_APPEND_ENUM(Parameters::FLASH_MODE_OFF)
205 CASE_APPEND_ENUM(Parameters::FLASH_MODE_AUTO)
206 CASE_APPEND_ENUM(Parameters::FLASH_MODE_ON)
207 CASE_APPEND_ENUM(Parameters::FLASH_MODE_TORCH)
208 CASE_APPEND_ENUM(Parameters::FLASH_MODE_RED_EYE)
209 CASE_APPEND_ENUM(Parameters::FLASH_MODE_INVALID)
210 default: result.append("UNKNOWN\n");
211 }
212
213 result.append(" Focus mode: ");
214 switch (mParameters.focusMode) {
215 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_AUTO)
216 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_MACRO)
217 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_CONTINUOUS_VIDEO)
218 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_CONTINUOUS_PICTURE)
219 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_EDOF)
220 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_INFINITY)
221 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_FIXED)
222 CASE_APPEND_ENUM(Parameters::FOCUS_MODE_INVALID)
223 default: result.append("UNKNOWN\n");
224 }
225
226 result.append(" Focusing areas:\n");
227 for (size_t i = 0; i < mParameters.focusingAreas.size(); i++) {
228 result.appendFormat(" [ (%d, %d, %d, %d), weight %d ]\n",
229 mParameters.focusingAreas[i].left,
230 mParameters.focusingAreas[i].top,
231 mParameters.focusingAreas[i].right,
232 mParameters.focusingAreas[i].bottom,
233 mParameters.focusingAreas[i].weight);
234 }
235
236 result.appendFormat(" Exposure compensation index: %d\n",
237 mParameters.exposureCompensation);
238
239 result.appendFormat(" AE lock %s, AWB lock %s\n",
240 mParameters.autoExposureLock ? "enabled" : "disabled",
241 mParameters.autoWhiteBalanceLock ? "enabled" : "disabled" );
242
243 result.appendFormat(" Metering areas:\n");
244 for (size_t i = 0; i < mParameters.meteringAreas.size(); i++) {
245 result.appendFormat(" [ (%d, %d, %d, %d), weight %d ]\n",
246 mParameters.meteringAreas[i].left,
247 mParameters.meteringAreas[i].top,
248 mParameters.meteringAreas[i].right,
249 mParameters.meteringAreas[i].bottom,
250 mParameters.meteringAreas[i].weight);
251 }
252
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700253 result.appendFormat(" Zoom index: %d\n", mParameters.zoom);
254 result.appendFormat(" Video size: %d x %d\n", mParameters.videoWidth,
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700255 mParameters.videoHeight);
256
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700257 result.appendFormat(" Recording hint is %s\n",
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700258 mParameters.recordingHint ? "set" : "not set");
259
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700260 result.appendFormat(" Video stabilization is %s\n",
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700261 mParameters.videoStabilization ? "enabled" : "disabled");
262
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700263 result.append(" Current streams:\n");
264 result.appendFormat(" Preview stream ID: %d\n", mPreviewStreamId);
265 result.appendFormat(" Capture stream ID: %d\n", mCaptureStreamId);
266
267 result.append(" Current requests:\n");
268 if (mPreviewRequest != NULL) {
269 result.append(" Preview request:\n");
270 write(fd, result.string(), result.size());
271 dump_camera_metadata(mPreviewRequest, fd, 2);
272 } else {
273 result.append(" Preview request: undefined\n");
274 write(fd, result.string(), result.size());
275 }
276
277 if (mCaptureRequest != NULL) {
278 result = " Capture request:\n";
279 write(fd, result.string(), result.size());
280 dump_camera_metadata(mCaptureRequest, fd, 2);
281 } else {
282 result = " Capture request: undefined\n";
283 write(fd, result.string(), result.size());
284 }
285
286 result = " Device dump:\n";
Eino-Ville Talvala611f6192012-05-31 12:28:23 -0700287 write(fd, result.string(), result.size());
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700288
Eino-Ville Talvala3297daa2012-06-14 10:49:45 -0700289 status_t res = mDevice->dump(fd, args);
290 if (res != OK) {
291 result = String8::format(" Error dumping device: %s (%d)",
292 strerror(-res), res);
293 write(fd, result.string(), result.size());
294 }
Eino-Ville Talvala7f610842012-06-07 10:20:51 -0700295
296#undef CASE_APPEND_ENUM
Eino-Ville Talvala611f6192012-05-31 12:28:23 -0700297 return NO_ERROR;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700298}
299
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700300const char* Camera2Client::getStateName(State state) {
301#define CASE_ENUM_TO_CHAR(x) case x: return(#x); break;
302 switch(state) {
303 CASE_ENUM_TO_CHAR(NOT_INITIALIZED)
304 CASE_ENUM_TO_CHAR(STOPPED)
305 CASE_ENUM_TO_CHAR(WAITING_FOR_PREVIEW_WINDOW)
306 CASE_ENUM_TO_CHAR(PREVIEW)
307 CASE_ENUM_TO_CHAR(RECORD)
308 CASE_ENUM_TO_CHAR(STILL_CAPTURE)
309 CASE_ENUM_TO_CHAR(VIDEO_SNAPSHOT)
310 default:
311 return "Unknown state!";
312 break;
313 }
314#undef CASE_ENUM_TO_CHAR
315}
316
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700317// ICamera interface
318
319void Camera2Client::disconnect() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700320 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700321 Mutex::Autolock icl(mICameraLock);
322
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -0700323 if (mDevice == 0) return;
324
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700325 stopPreviewLocked();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700326
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700327 mDevice->waitUntilDrained();
328
329 if (mPreviewStreamId != NO_STREAM) {
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700330 mDevice->deleteStream(mPreviewStreamId);
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700331 mPreviewStreamId = NO_STREAM;
332 }
333
334 if (mCaptureStreamId != NO_STREAM) {
335 mDevice->deleteStream(mCaptureStreamId);
336 mCaptureStreamId = NO_STREAM;
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700337 }
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -0700338
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700339 CameraService::Client::disconnect();
340}
341
342status_t Camera2Client::connect(const sp<ICameraClient>& client) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700343 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700344 Mutex::Autolock icl(mICameraLock);
345
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700346 return BAD_VALUE;
347}
348
349status_t Camera2Client::lock() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700350 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700351 Mutex::Autolock icl(mICameraLock);
352
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700353 return BAD_VALUE;
354}
355
356status_t Camera2Client::unlock() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700357 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700358 Mutex::Autolock icl(mICameraLock);
359
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700360 return BAD_VALUE;
361}
362
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700363status_t Camera2Client::setPreviewDisplay(
364 const sp<Surface>& surface) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700365 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700366 Mutex::Autolock icl(mICameraLock);
367
368 if (mState >= PREVIEW) return INVALID_OPERATION;
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700369
370 sp<IBinder> binder;
371 sp<ANativeWindow> window;
372 if (surface != 0) {
373 binder = surface->asBinder();
374 window = surface;
375 }
376
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700377 return setPreviewWindowLocked(binder,window);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700378}
379
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700380status_t Camera2Client::setPreviewTexture(
381 const sp<ISurfaceTexture>& surfaceTexture) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700382 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700383 Mutex::Autolock icl(mICameraLock);
384
385 if (mState >= PREVIEW) return INVALID_OPERATION;
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700386
387 sp<IBinder> binder;
388 sp<ANativeWindow> window;
389 if (surfaceTexture != 0) {
390 binder = surfaceTexture->asBinder();
391 window = new SurfaceTextureClient(surfaceTexture);
392 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700393 return setPreviewWindowLocked(binder, window);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700394}
395
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700396status_t Camera2Client::setPreviewWindowLocked(const sp<IBinder>& binder,
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700397 sp<ANativeWindow> window) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700398 ATRACE_CALL();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700399 status_t res;
400
401 if (binder == mPreviewSurface) {
402 return NO_ERROR;
403 }
404
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700405 if (mPreviewStreamId != NO_STREAM) {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700406 res = mDevice->waitUntilDrained();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700407 if (res != OK) {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700408 ALOGE("%s: Error waiting for preview to drain: %s (%d)",
409 __FUNCTION__, strerror(-res), res);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700410 return res;
411 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700412 res = mDevice->deleteStream(mPreviewStreamId);
413 if (res != OK) {
414 ALOGE("%s: Unable to delete old preview stream: %s (%d)",
415 __FUNCTION__, strerror(-res), res);
416 return res;
417 }
418 mPreviewStreamId = NO_STREAM;
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700419 }
420
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -0700421 mPreviewSurface = binder;
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700422 mPreviewWindow = window;
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -0700423
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700424 if (mState == WAITING_FOR_PREVIEW_WINDOW) {
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700425 return startPreviewLocked();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700426 }
427
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700428 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700429}
430
431void Camera2Client::setPreviewCallbackFlag(int flag) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700432 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700433 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700434}
435
436status_t Camera2Client::startPreview() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700437 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700438 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700439 return startPreviewLocked();
440}
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700441
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700442status_t Camera2Client::startPreviewLocked() {
443 ATRACE_CALL();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700444 status_t res;
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700445 if (mState >= PREVIEW) {
446 ALOGE("%s: Can't start preview in state %s",
447 __FUNCTION__, getStateName(mState));
448 return INVALID_OPERATION;
449 }
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700450
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700451 if (mPreviewWindow == 0) {
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700452 mState = WAITING_FOR_PREVIEW_WINDOW;
453 return OK;
454 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700455 mState = STOPPED;
456
457 res = updatePreviewStream();
458 if (res != OK) {
459 ALOGE("%s: Camera %d: Unable to update preview stream: %s (%d)",
460 __FUNCTION__, mCameraId, strerror(-res), res);
461 return res;
462 }
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700463
464 if (mPreviewRequest == NULL) {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700465 res = updatePreviewRequest();
466 if (res != OK) {
467 ALOGE("%s: Camera %d: Unable to create preview request: %s (%d)",
468 __FUNCTION__, mCameraId, strerror(-res), res);
469 return res;
470 }
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700471 }
472
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700473 res = updateEntry(mPreviewRequest,
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700474 ANDROID_REQUEST_OUTPUT_STREAMS,
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700475 &mPreviewStreamId, 1);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700476 if (res != OK) {
477 ALOGE("%s: Camera %d: Unable to set up preview request: %s (%d)",
478 __FUNCTION__, mCameraId, strerror(-res), res);
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700479 return res;
480 }
481 res = sort_camera_metadata(mPreviewRequest);
482 if (res != OK) {
483 ALOGE("%s: Camera %d: Error sorting preview request: %s (%d)",
484 __FUNCTION__, mCameraId, strerror(-res), res);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700485 return res;
486 }
487
488 res = mDevice->setStreamingRequest(mPreviewRequest);
489 if (res != OK) {
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -0700490 ALOGE("%s: Camera %d: Unable to set preview request to start preview: "
491 "%s (%d)",
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700492 __FUNCTION__, mCameraId, strerror(-res), res);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700493 return res;
494 }
495 mState = PREVIEW;
496
497 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700498}
499
500void Camera2Client::stopPreview() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700501 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700502 Mutex::Autolock icl(mICameraLock);
503 stopPreviewLocked();
504}
505
506void Camera2Client::stopPreviewLocked() {
507 ATRACE_CALL();
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700508 switch (mState) {
509 case NOT_INITIALIZED:
510 ALOGE("%s: Camera %d: Call before initialized",
511 __FUNCTION__, mCameraId);
512 break;
513 case STOPPED:
514 break;
515 case STILL_CAPTURE:
516 ALOGE("%s: Camera %d: Cannot stop preview during still capture.",
517 __FUNCTION__, mCameraId);
518 break;
519 case RECORD:
520 // TODO: Handle record stop here
521 case PREVIEW:
522 mDevice->setStreamingRequest(NULL);
523 case WAITING_FOR_PREVIEW_WINDOW:
524 mState = STOPPED;
525 break;
526 default:
527 ALOGE("%s: Camera %d: Unknown state %d", __FUNCTION__, mCameraId,
528 mState);
529 }
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700530}
531
532bool Camera2Client::previewEnabled() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700533 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700534 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700535 return mState == PREVIEW;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700536}
537
538status_t Camera2Client::storeMetaDataInBuffers(bool enabled) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700539 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700540 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700541 return BAD_VALUE;
542}
543
544status_t Camera2Client::startRecording() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700545 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700546 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700547 return BAD_VALUE;
548}
549
550void Camera2Client::stopRecording() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700551 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700552 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700553}
554
555bool Camera2Client::recordingEnabled() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700556 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700557 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700558 return BAD_VALUE;
559}
560
561void Camera2Client::releaseRecordingFrame(const sp<IMemory>& mem) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700562 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700563 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700564}
565
566status_t Camera2Client::autoFocus() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700567 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700568 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700569 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700570}
571
572status_t Camera2Client::cancelAutoFocus() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700573 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700574 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -0700575 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700576}
577
578status_t Camera2Client::takePicture(int msgType) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700579 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700580 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700581 status_t res;
582
583 switch (mState) {
584 case NOT_INITIALIZED:
585 case STOPPED:
586 case WAITING_FOR_PREVIEW_WINDOW:
587 ALOGE("%s: Camera %d: Cannot take picture without preview enabled",
588 __FUNCTION__, mCameraId);
589 return INVALID_OPERATION;
590 case PREVIEW:
591 case RECORD:
592 // Good to go for takePicture
593 break;
594 case STILL_CAPTURE:
595 case VIDEO_SNAPSHOT:
596 ALOGE("%s: Camera %d: Already taking a picture",
597 __FUNCTION__, mCameraId);
598 return INVALID_OPERATION;
599 }
600
601 Mutex::Autolock pl(mParamsLock);
602
603 res = updateCaptureStream();
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700604 if (res != OK) {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700605 ALOGE("%s: Camera %d: Can't set up still image stream: %s (%d)",
606 __FUNCTION__, mCameraId, strerror(-res), res);
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700607 return res;
608 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700609
610 if (mCaptureRequest == NULL) {
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700611 res = updateCaptureRequest();
612 if (res != OK) {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700613 ALOGE("%s: Camera %d: Can't create still image capture request: "
614 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
Eino-Ville Talvala4ecfec32012-06-12 17:13:48 -0700615 return res;
616 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700617 }
618
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700619 // TODO: For video snapshot, will need 3 streams here
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700620 camera_metadata_entry_t outputStreams;
621 uint8_t streamIds[2] = { mPreviewStreamId, mCaptureStreamId };
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700622 res = updateEntry(mCaptureRequest, ANDROID_REQUEST_OUTPUT_STREAMS,
623 &streamIds, 2);
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700624 if (res != OK) {
625 ALOGE("%s: Camera %d: Unable to set up still image capture request: "
626 "%s (%d)",
627 __FUNCTION__, mCameraId, strerror(-res), res);
628 return res;
629 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -0700630 res = sort_camera_metadata(mCaptureRequest);
631 if (res != OK) {
632 ALOGE("%s: Camera %d: Unable to sort capture request: %s (%d)",
633 __FUNCTION__, mCameraId, strerror(-res), res);
634 return res;
635 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -0700636
637 camera_metadata_t *captureCopy = clone_camera_metadata(mCaptureRequest);
638 if (captureCopy == NULL) {
639 ALOGE("%s: Camera %d: Unable to copy capture request for HAL device",
640 __FUNCTION__, mCameraId);
641 return NO_MEMORY;
642 }
643
644 if (mState == PREVIEW) {
645 res = mDevice->setStreamingRequest(NULL);
646 if (res != OK) {
647 ALOGE("%s: Camera %d: Unable to stop preview for still capture: "
648 "%s (%d)",
649 __FUNCTION__, mCameraId, strerror(-res), res);
650 return res;
651 }
652 }
653
654 res = mDevice->capture(captureCopy);
655 if (res != OK) {
656 ALOGE("%s: Camera %d: Unable to submit still image capture request: "
657 "%s (%d)",
658 __FUNCTION__, mCameraId, strerror(-res), res);
659 return res;
660 }
661
662 switch (mState) {
663 case PREVIEW:
664 mState = STILL_CAPTURE;
665 break;
666 case RECORD:
667 mState = VIDEO_SNAPSHOT;
668 break;
669 default:
670 ALOGE("%s: Camera %d: Unknown state for still capture!",
671 __FUNCTION__, mCameraId);
672 return INVALID_OPERATION;
673 }
674
675 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -0700676}
677
678status_t Camera2Client::setParameters(const String8& params) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -0700679 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -0700680 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700681 Mutex::Autolock pl(mParamsLock);
682 status_t res;
683
684 CameraParameters newParams(params);
685
686 // TODO: Currently ignoring any changes to supposedly read-only
687 // parameters such as supported preview sizes, etc. Should probably
688 // produce an error if they're changed.
689
690 /** Extract and verify new parameters */
691
692 size_t i;
693
694 // PREVIEW_SIZE
695 int previewWidth, previewHeight;
696 newParams.getPreviewSize(&previewWidth, &previewHeight);
697
698 if (previewWidth != mParameters.previewWidth ||
699 previewHeight != mParameters.previewHeight) {
700 if (mState >= PREVIEW) {
701 ALOGE("%s: Preview size cannot be updated when preview "
702 "is active!", __FUNCTION__);
703 return BAD_VALUE;
704 }
705 camera_metadata_entry_t availablePreviewSizes =
706 staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
707 for (i = 0; i < availablePreviewSizes.count; i += 2 ) {
708 if (availablePreviewSizes.data.i32[i] == previewWidth &&
709 availablePreviewSizes.data.i32[i+1] == previewHeight) break;
710 }
711 if (i == availablePreviewSizes.count) {
712 ALOGE("%s: Requested preview size %d x %d is not supported",
713 __FUNCTION__, previewWidth, previewHeight);
714 return BAD_VALUE;
715 }
716 }
717
718 // PREVIEW_FPS_RANGE
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700719 int previewFpsRange[2];
720 int previewFps = 0;
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700721 bool fpsRangeChanged = false;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700722 newParams.getPreviewFpsRange(&previewFpsRange[0], &previewFpsRange[1]);
723 if (previewFpsRange[0] != mParameters.previewFpsRange[0] ||
724 previewFpsRange[1] != mParameters.previewFpsRange[1]) {
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700725 fpsRangeChanged = true;
726 camera_metadata_entry_t availablePreviewFpsRanges =
727 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
728 for (i = 0; i < availablePreviewFpsRanges.count; i += 2) {
729 if ((availablePreviewFpsRanges.data.i32[i] ==
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700730 previewFpsRange[0]) &&
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700731 (availablePreviewFpsRanges.data.i32[i+1] ==
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700732 previewFpsRange[1]) ) {
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700733 break;
734 }
735 }
736 if (i == availablePreviewFpsRanges.count) {
737 ALOGE("%s: Requested preview FPS range %d - %d is not supported",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700738 __FUNCTION__, previewFpsRange[0], previewFpsRange[1]);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700739 return BAD_VALUE;
740 }
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700741 previewFps = previewFpsRange[0];
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700742 }
743
744 // PREVIEW_FORMAT
745 int previewFormat = formatStringToEnum(newParams.getPreviewFormat());
746 if (previewFormat != mParameters.previewFormat) {
747 if (mState >= PREVIEW) {
748 ALOGE("%s: Preview format cannot be updated when preview "
749 "is active!", __FUNCTION__);
750 return BAD_VALUE;
751 }
752 camera_metadata_entry_t availableFormats =
753 staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
754 for (i = 0; i < availableFormats.count; i++) {
755 if (availableFormats.data.i32[i] == previewFormat) break;
756 }
757 if (i == availableFormats.count) {
758 ALOGE("%s: Requested preview format %s (0x%x) is not supported",
759 __FUNCTION__, newParams.getPreviewFormat(), previewFormat);
760 return BAD_VALUE;
761 }
762 }
763
764 // PREVIEW_FRAME_RATE
765 // Deprecated, only use if the preview fps range is unchanged this time.
766 // The single-value FPS is the same as the minimum of the range.
767 if (!fpsRangeChanged) {
768 previewFps = newParams.getPreviewFrameRate();
769 if (previewFps != mParameters.previewFps) {
770 camera_metadata_entry_t availableFrameRates =
771 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES);
772 for (i = 0; i < availableFrameRates.count; i+=2) {
773 if (availableFrameRates.data.i32[i] == previewFps) break;
774 }
775 if (i == availableFrameRates.count) {
776 ALOGE("%s: Requested preview frame rate %d is not supported",
777 __FUNCTION__, previewFps);
778 return BAD_VALUE;
779 }
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700780 previewFpsRange[0] = availableFrameRates.data.i32[i];
781 previewFpsRange[1] = availableFrameRates.data.i32[i+1];
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700782 }
783 }
784
785 // PICTURE_SIZE
786 int pictureWidth, pictureHeight;
787 newParams.getPictureSize(&pictureWidth, &pictureHeight);
788 if (pictureWidth == mParameters.pictureWidth ||
789 pictureHeight == mParameters.pictureHeight) {
790 camera_metadata_entry_t availablePictureSizes =
791 staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES);
792 for (i = 0; i < availablePictureSizes.count; i+=2) {
793 if (availablePictureSizes.data.i32[i] == pictureWidth &&
794 availablePictureSizes.data.i32[i+1] == pictureHeight) break;
795 }
796 if (i == availablePictureSizes.count) {
797 ALOGE("%s: Requested picture size %d x %d is not supported",
798 __FUNCTION__, pictureWidth, pictureHeight);
799 return BAD_VALUE;
800 }
801 }
802
803 // JPEG_THUMBNAIL_WIDTH/HEIGHT
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700804 int jpegThumbSize[2];
805 jpegThumbSize[0] =
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700806 newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH);
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700807 jpegThumbSize[1] =
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700808 newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT);
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700809 if (jpegThumbSize[0] != mParameters.jpegThumbSize[0] ||
810 jpegThumbSize[1] != mParameters.jpegThumbSize[1]) {
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700811 camera_metadata_entry_t availableJpegThumbSizes =
812 staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES);
813 for (i = 0; i < availableJpegThumbSizes.count; i+=2) {
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700814 if (availableJpegThumbSizes.data.i32[i] == jpegThumbSize[0] &&
815 availableJpegThumbSizes.data.i32[i+1] == jpegThumbSize[1]) {
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700816 break;
817 }
818 }
819 if (i == availableJpegThumbSizes.count) {
820 ALOGE("%s: Requested JPEG thumbnail size %d x %d is not supported",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700821 __FUNCTION__, jpegThumbSize[0], jpegThumbSize[1]);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700822 return BAD_VALUE;
823 }
824 }
825
826 // JPEG_THUMBNAIL_QUALITY
827 int jpegThumbQuality =
828 newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY);
829 if (jpegThumbQuality < 0 || jpegThumbQuality > 100) {
830 ALOGE("%s: Requested JPEG thumbnail quality %d is not supported",
831 __FUNCTION__, jpegThumbQuality);
832 return BAD_VALUE;
833 }
834
835 // JPEG_QUALITY
836 int jpegQuality =
837 newParams.getInt(CameraParameters::KEY_JPEG_QUALITY);
838 if (jpegQuality < 0 || jpegQuality > 100) {
839 ALOGE("%s: Requested JPEG quality %d is not supported",
840 __FUNCTION__, jpegQuality);
841 return BAD_VALUE;
842 }
843
844 // ROTATION
845 int jpegRotation =
846 newParams.getInt(CameraParameters::KEY_ROTATION);
847 if (jpegRotation != 0 &&
848 jpegRotation != 90 &&
849 jpegRotation != 180 &&
850 jpegRotation != 270) {
851 ALOGE("%s: Requested picture rotation angle %d is not supported",
852 __FUNCTION__, jpegRotation);
853 return BAD_VALUE;
854 }
855
856 // GPS
857 bool gpsEnabled = false;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700858 double gpsCoordinates[3] = {0,0,0};
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700859 int64_t gpsTimestamp = 0;
860 String8 gpsProcessingMethod;
861 const char *gpsLatStr =
862 newParams.get(CameraParameters::KEY_GPS_LATITUDE);
863 if (gpsLatStr != NULL) {
864 const char *gpsLongStr =
865 newParams.get(CameraParameters::KEY_GPS_LONGITUDE);
866 const char *gpsAltitudeStr =
867 newParams.get(CameraParameters::KEY_GPS_ALTITUDE);
868 const char *gpsTimeStr =
869 newParams.get(CameraParameters::KEY_GPS_TIMESTAMP);
870 const char *gpsProcMethodStr =
871 newParams.get(CameraParameters::KEY_GPS_PROCESSING_METHOD);
872 if (gpsLongStr == NULL ||
873 gpsAltitudeStr == NULL ||
874 gpsTimeStr == NULL ||
875 gpsProcMethodStr == NULL) {
876 ALOGE("%s: Incomplete set of GPS parameters provided",
877 __FUNCTION__);
878 return BAD_VALUE;
879 }
880 char *endPtr;
881 errno = 0;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700882 gpsCoordinates[0] = strtod(gpsLatStr, &endPtr);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700883 if (errno || endPtr == gpsLatStr) {
884 ALOGE("%s: Malformed GPS latitude: %s", __FUNCTION__, gpsLatStr);
885 return BAD_VALUE;
886 }
887 errno = 0;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700888 gpsCoordinates[1] = strtod(gpsLongStr, &endPtr);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700889 if (errno || endPtr == gpsLongStr) {
890 ALOGE("%s: Malformed GPS longitude: %s", __FUNCTION__, gpsLongStr);
891 return BAD_VALUE;
892 }
893 errno = 0;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -0700894 gpsCoordinates[2] = strtod(gpsAltitudeStr, &endPtr);
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -0700895 if (errno || endPtr == gpsAltitudeStr) {
896 ALOGE("%s: Malformed GPS altitude: %s", __FUNCTION__,
897 gpsAltitudeStr);
898 return BAD_VALUE;
899 }
900 errno = 0;
901 gpsTimestamp = strtoll(gpsTimeStr, &endPtr, 10);
902 if (errno || endPtr == gpsTimeStr) {
903 ALOGE("%s: Malformed GPS timestamp: %s", __FUNCTION__, gpsTimeStr);
904 return BAD_VALUE;
905 }
906 gpsProcessingMethod = gpsProcMethodStr;
907
908 gpsEnabled = true;
909 }
910
911 // WHITE_BALANCE
912 int wbMode = wbModeStringToEnum(
913 newParams.get(CameraParameters::KEY_WHITE_BALANCE) );
914 if (wbMode != mParameters.wbMode) {
915 camera_metadata_entry_t availableWbModes =
916 staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
917 for (i = 0; i < availableWbModes.count; i++) {
918 if (wbMode == availableWbModes.data.u8[i]) break;
919 }
920 if (i == availableWbModes.count) {
921 ALOGE("%s: Requested white balance mode %s is not supported",
922 __FUNCTION__,
923 newParams.get(CameraParameters::KEY_WHITE_BALANCE));
924 return BAD_VALUE;
925 }
926 }
927
928 // EFFECT
929 int effectMode = effectModeStringToEnum(
930 newParams.get(CameraParameters::KEY_EFFECT) );
931 if (effectMode != mParameters.effectMode) {
932 camera_metadata_entry_t availableEffectModes =
933 staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
934 for (i = 0; i < availableEffectModes.count; i++) {
935 if (effectMode == availableEffectModes.data.u8[i]) break;
936 }
937 if (i == availableEffectModes.count) {
938 ALOGE("%s: Requested effect mode \"%s\" is not supported",
939 __FUNCTION__,
940 newParams.get(CameraParameters::KEY_EFFECT) );
941 return BAD_VALUE;
942 }
943 }
944
945 // ANTIBANDING
946 int antibandingMode = abModeStringToEnum(
947 newParams.get(CameraParameters::KEY_ANTIBANDING) );
948 if (antibandingMode != mParameters.antibandingMode) {
949 camera_metadata_entry_t availableAbModes =
950 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
951 for (i = 0; i < availableAbModes.count; i++) {
952 if (antibandingMode == availableAbModes.data.u8[i]) break;
953 }
954 if (i == availableAbModes.count) {
955 ALOGE("%s: Requested antibanding mode \"%s\" is not supported",
956 __FUNCTION__,
957 newParams.get(CameraParameters::KEY_ANTIBANDING));
958 return BAD_VALUE;
959 }
960 }
961
962 // SCENE_MODE
963 int sceneMode = sceneModeStringToEnum(
964 newParams.get(CameraParameters::KEY_SCENE_MODE) );
965 if (sceneMode != mParameters.sceneMode) {
966 camera_metadata_entry_t availableSceneModes =
967 staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
968 for (i = 0; i < availableSceneModes.count; i++) {
969 if (sceneMode == availableSceneModes.data.u8[i]) break;
970 }
971 if (i == availableSceneModes.count) {
972 ALOGE("%s: Requested scene mode \"%s\" is not supported",
973 __FUNCTION__,
974 newParams.get(CameraParameters::KEY_SCENE_MODE));
975 return BAD_VALUE;
976 }
977 }
978
979 // FLASH_MODE
980 Parameters::flashMode_t flashMode = flashModeStringToEnum(
981 newParams.get(CameraParameters::KEY_FLASH_MODE) );
982 if (flashMode != mParameters.flashMode) {
983 camera_metadata_entry_t flashAvailable =
984 staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
985 if (!flashAvailable.data.u8[0] &&
986 flashMode != Parameters::FLASH_MODE_OFF) {
987 ALOGE("%s: Requested flash mode \"%s\" is not supported: "
988 "No flash on device", __FUNCTION__,
989 newParams.get(CameraParameters::KEY_FLASH_MODE));
990 return BAD_VALUE;
991 } else if (flashMode == Parameters::FLASH_MODE_RED_EYE) {
992 camera_metadata_entry_t availableAeModes =
993 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
994 for (i = 0; i < availableAeModes.count; i++) {
995 if (flashMode == availableAeModes.data.u8[i]) break;
996 }
997 if (i == availableAeModes.count) {
998 ALOGE("%s: Requested flash mode \"%s\" is not supported",
999 __FUNCTION__,
1000 newParams.get(CameraParameters::KEY_FLASH_MODE));
1001 return BAD_VALUE;
1002 }
1003 } else if (flashMode == -1) {
1004 ALOGE("%s: Requested flash mode \"%s\" is unknown",
1005 __FUNCTION__,
1006 newParams.get(CameraParameters::KEY_FLASH_MODE));
1007 return BAD_VALUE;
1008 }
1009 }
1010
1011 // FOCUS_MODE
1012 Parameters::focusMode_t focusMode = focusModeStringToEnum(
1013 newParams.get(CameraParameters::KEY_FOCUS_MODE));
1014 if (focusMode != mParameters.focusMode) {
1015 if (focusMode != Parameters::FOCUS_MODE_FIXED) {
1016 camera_metadata_entry_t minFocusDistance =
1017 staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE);
1018 if (minFocusDistance.data.f[0] == 0) {
1019 ALOGE("%s: Requested focus mode \"%s\" is not available: "
1020 "fixed focus lens",
1021 __FUNCTION__,
1022 newParams.get(CameraParameters::KEY_FOCUS_MODE));
1023 return BAD_VALUE;
1024 } else if (focusMode != Parameters::FOCUS_MODE_INFINITY) {
1025 camera_metadata_entry_t availableFocusModes =
1026 staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
1027 for (i = 0; i < availableFocusModes.count; i++) {
1028 if (focusMode == availableFocusModes.data.u8[i]) break;
1029 }
1030 if (i == availableFocusModes.count) {
1031 ALOGE("%s: Requested focus mode \"%s\" is not supported",
1032 __FUNCTION__,
1033 newParams.get(CameraParameters::KEY_FOCUS_MODE));
1034 return BAD_VALUE;
1035 }
1036 }
1037 }
1038 }
1039
1040 // FOCUS_AREAS
1041 Vector<Parameters::Area> focusingAreas;
1042 res = parseAreas(newParams.get(CameraParameters::KEY_FOCUS_AREAS),
1043 &focusingAreas);
1044 size_t max3aRegions =
1045 (size_t)staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1).data.i32[0];
1046 if (res == OK) res = validateAreas(focusingAreas, max3aRegions);
1047 if (res != OK) {
1048 ALOGE("%s: Requested focus areas are malformed: %s",
1049 __FUNCTION__, newParams.get(CameraParameters::KEY_FOCUS_AREAS));
1050 return BAD_VALUE;
1051 }
1052
1053 // EXPOSURE_COMPENSATION
1054 int exposureCompensation =
1055 newParams.getInt(CameraParameters::KEY_EXPOSURE_COMPENSATION);
1056 camera_metadata_entry_t exposureCompensationRange =
1057 staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE);
1058 if (exposureCompensation < exposureCompensationRange.data.i32[0] ||
1059 exposureCompensation > exposureCompensationRange.data.i32[1]) {
1060 ALOGE("%s: Requested exposure compensation index is out of bounds: %d",
1061 __FUNCTION__, exposureCompensation);
1062 return BAD_VALUE;
1063 }
1064
1065 // AUTO_EXPOSURE_LOCK (always supported)
1066 bool autoExposureLock = boolFromString(
1067 newParams.get(CameraParameters::KEY_AUTO_EXPOSURE_LOCK));
1068
1069 // AUTO_WHITEBALANCE_LOCK (always supported)
1070 bool autoWhiteBalanceLock = boolFromString(
1071 newParams.get(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK));
1072
1073 // METERING_AREAS
1074 Vector<Parameters::Area> meteringAreas;
1075 res = parseAreas(newParams.get(CameraParameters::KEY_METERING_AREAS),
1076 &meteringAreas);
1077 if (res == OK) res = validateAreas(focusingAreas, max3aRegions);
1078 if (res != OK) {
1079 ALOGE("%s: Requested metering areas are malformed: %s",
1080 __FUNCTION__,
1081 newParams.get(CameraParameters::KEY_METERING_AREAS));
1082 return BAD_VALUE;
1083 }
1084
1085 // ZOOM
1086 int zoom = newParams.getInt(CameraParameters::KEY_ZOOM);
1087 if (zoom < 0 || zoom > (int)NUM_ZOOM_STEPS) {
1088 ALOGE("%s: Requested zoom level %d is not supported",
1089 __FUNCTION__, zoom);
1090 return BAD_VALUE;
1091 }
1092
1093 // VIDEO_SIZE
1094 int videoWidth, videoHeight;
1095 newParams.getVideoSize(&videoWidth, &videoHeight);
1096 if (videoWidth != mParameters.videoWidth ||
1097 videoHeight != mParameters.videoHeight) {
1098 if (mState == RECORD) {
1099 ALOGE("%s: Video size cannot be updated when recording is active!",
1100 __FUNCTION__);
1101 return BAD_VALUE;
1102 }
1103 camera_metadata_entry_t availableVideoSizes =
1104 staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
1105 for (i = 0; i < availableVideoSizes.count; i += 2 ) {
1106 if (availableVideoSizes.data.i32[i] == videoWidth &&
1107 availableVideoSizes.data.i32[i+1] == videoHeight) break;
1108 }
1109 if (i == availableVideoSizes.count) {
1110 ALOGE("%s: Requested video size %d x %d is not supported",
1111 __FUNCTION__, videoWidth, videoHeight);
1112 return BAD_VALUE;
1113 }
1114 }
1115
1116 // RECORDING_HINT (always supported)
1117 bool recordingHint = boolFromString(
1118 newParams.get(CameraParameters::KEY_RECORDING_HINT) );
1119
1120 // VIDEO_STABILIZATION
1121 bool videoStabilization = boolFromString(
1122 newParams.get(CameraParameters::KEY_VIDEO_STABILIZATION) );
1123 camera_metadata_entry_t availableVideoStabilizationModes =
1124 staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
1125 if (videoStabilization && availableVideoStabilizationModes.count == 1) {
1126 ALOGE("%s: Video stabilization not supported", __FUNCTION__);
1127 }
1128
1129 /** Update internal parameters */
1130 mParameters.previewWidth = previewWidth;
1131 mParameters.previewHeight = previewHeight;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001132 mParameters.previewFpsRange[0] = previewFpsRange[0];
1133 mParameters.previewFpsRange[1] = previewFpsRange[1];
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07001134 mParameters.previewFps = previewFps;
1135 mParameters.previewFormat = previewFormat;
1136
1137 mParameters.pictureWidth = pictureWidth;
1138 mParameters.pictureHeight = pictureHeight;
1139
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001140 mParameters.jpegThumbSize[0] = jpegThumbSize[0];
1141 mParameters.jpegThumbSize[1] = jpegThumbSize[1];
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07001142 mParameters.jpegQuality = jpegQuality;
1143 mParameters.jpegThumbQuality = jpegThumbQuality;
1144
1145 mParameters.gpsEnabled = gpsEnabled;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001146 mParameters.gpsCoordinates[0] = gpsCoordinates[0];
1147 mParameters.gpsCoordinates[1] = gpsCoordinates[1];
1148 mParameters.gpsCoordinates[2] = gpsCoordinates[2];
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07001149 mParameters.gpsTimestamp = gpsTimestamp;
1150 mParameters.gpsProcessingMethod = gpsProcessingMethod;
1151
1152 mParameters.wbMode = wbMode;
1153 mParameters.effectMode = effectMode;
1154 mParameters.antibandingMode = antibandingMode;
1155 mParameters.sceneMode = sceneMode;
1156
1157 mParameters.flashMode = flashMode;
1158 mParameters.focusMode = focusMode;
1159
1160 mParameters.focusingAreas = focusingAreas;
1161 mParameters.exposureCompensation = exposureCompensation;
1162 mParameters.autoExposureLock = autoExposureLock;
1163 mParameters.autoWhiteBalanceLock = autoWhiteBalanceLock;
1164 mParameters.meteringAreas = meteringAreas;
1165 mParameters.zoom = zoom;
1166
1167 mParameters.videoWidth = videoWidth;
1168 mParameters.videoHeight = videoHeight;
1169
1170 mParameters.recordingHint = recordingHint;
1171 mParameters.videoStabilization = videoStabilization;
1172
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07001173 res = updatePreviewRequest();
1174 if (res != OK) {
1175 ALOGE("%s: Camera %d: Unable to update preview request: %s (%d)",
1176 __FUNCTION__, mCameraId, strerror(-res), res);
1177 return res;
1178 }
1179 res = updateCaptureRequest();
1180 if (res != OK) {
1181 ALOGE("%s: Camera %d: Unable to update capture request: %s (%d)",
1182 __FUNCTION__, mCameraId, strerror(-res), res);
1183 return res;
1184 }
1185
1186 if (mState == PREVIEW) {
1187 res = mDevice->setStreamingRequest(mPreviewRequest);
1188 if (res != OK) {
1189 ALOGE("%s: Camera %d: Error streaming new preview request: %s (%d)",
1190 __FUNCTION__, mCameraId, strerror(-res), res);
1191 return res;
1192 }
1193 }
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07001194
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07001195 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07001196}
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001197
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07001198String8 Camera2Client::getParameters() const {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -07001199 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -07001200 Mutex::Autolock icl(mICameraLock);
1201
1202 Mutex::Autolock pl(mParamsLock);
1203
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001204 // TODO: Deal with focus distances
1205 return mParamsFlattened;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07001206}
1207
1208status_t Camera2Client::sendCommand(int32_t cmd, int32_t arg1, int32_t arg2) {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -07001209 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -07001210 Mutex::Autolock icl(mICameraLock);
Eino-Ville Talvalac94cd192012-06-15 12:47:42 -07001211
1212 ALOGV("%s: Camera %d: Command %d (%d, %d)", __FUNCTION__, mCameraId,
1213 cmd, arg1, arg2);
1214
1215 if (cmd == CAMERA_CMD_SET_DISPLAY_ORIENTATION) {
1216 int transform = degToTransform(arg1,
1217 mCameraFacing == CAMERA_FACING_FRONT);
1218 if (transform == -1) {
1219 ALOGE("%s: Camera %d: Error setting %d as display orientation value",
1220 __FUNCTION__, mCameraId, arg1);
1221 return BAD_VALUE;
1222 }
1223 if (transform != mParameters.previewTransform &&
1224 mPreviewStreamId != NO_STREAM) {
1225 mDevice->setStreamTransform(mPreviewStreamId, transform);
1226 }
1227 mParameters.previewTransform = transform;
1228 return OK;
1229 }
1230
1231 ALOGE("%s: Camera %d: Unimplemented command %d (%d, %d)", __FUNCTION__,
1232 mCameraId, cmd, arg1, arg2);
1233
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07001234 return OK;
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07001235}
1236
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001237/** Device-related methods */
1238
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07001239void Camera2Client::onCaptureAvailable() {
1240 ATRACE_CALL();
1241 status_t res;
1242 sp<ICameraClient> currentClient;
1243 CpuConsumer::LockedBuffer imgBuffer;
1244 {
1245 Mutex::Autolock icl(mICameraLock);
1246
1247 // TODO: Signal errors here upstream
1248 if (mState != STILL_CAPTURE && mState != VIDEO_SNAPSHOT) {
1249 ALOGE("%s: Camera %d: Still image produced unexpectedly!",
1250 __FUNCTION__, mCameraId);
1251 return;
1252 }
1253
1254 res = mCaptureConsumer->lockNextBuffer(&imgBuffer);
1255 if (res != OK) {
1256 ALOGE("%s: Camera %d: Error receiving still image buffer: %s (%d)",
1257 __FUNCTION__, mCameraId, strerror(-res), res);
1258 return;
1259 }
1260
1261 if (imgBuffer.format != HAL_PIXEL_FORMAT_BLOB) {
1262 ALOGE("%s: Camera %d: Unexpected format for still image: "
1263 "%x, expected %x", __FUNCTION__, mCameraId,
1264 imgBuffer.format,
1265 HAL_PIXEL_FORMAT_BLOB);
1266 mCaptureConsumer->unlockBuffer(imgBuffer);
1267 return;
1268 }
1269
1270 // TODO: Optimize this to avoid memcopy
1271 void* captureMemory = mCaptureHeap->getBase();
1272 size_t size = mCaptureHeap->getSize();
1273 memcpy(captureMemory, imgBuffer.data, size);
1274
1275 mCaptureConsumer->unlockBuffer(imgBuffer);
1276
1277 currentClient = mCameraClient;
1278 switch (mState) {
1279 case STILL_CAPTURE:
1280 mState = STOPPED;
1281 break;
1282 case VIDEO_SNAPSHOT:
1283 mState = RECORD;
1284 break;
1285 default:
1286 ALOGE("%s: Camera %d: Unexpected state %d", __FUNCTION__,
1287 mCameraId, mState);
1288 break;
1289 }
1290 }
1291 // Call outside mICameraLock to allow re-entrancy from notification
1292 if (currentClient != 0) {
1293 currentClient->dataCallback(CAMERA_MSG_COMPRESSED_IMAGE,
1294 mCaptureMemory, NULL);
1295 }
1296}
1297
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001298camera_metadata_entry_t Camera2Client::staticInfo(uint32_t tag,
1299 size_t minCount, size_t maxCount) {
1300 status_t res;
1301 camera_metadata_entry_t entry;
1302 res = find_camera_metadata_entry(mDevice->info(),
1303 tag,
1304 &entry);
1305 if (CC_UNLIKELY( res != OK )) {
1306 const char* tagSection = get_camera_metadata_section_name(tag);
1307 if (tagSection == NULL) tagSection = "<unknown>";
1308 const char* tagName = get_camera_metadata_tag_name(tag);
1309 if (tagName == NULL) tagName = "<unknown>";
1310
1311 ALOGE("Error finding static metadata entry '%s.%s' (%x): %s (%d)",
1312 tagSection, tagName, tag, strerror(-res), res);
1313 entry.count = 0;
1314 entry.data.u8 = NULL;
1315 } else if (CC_UNLIKELY(
1316 (minCount != 0 && entry.count < minCount) ||
1317 (maxCount != 0 && entry.count > maxCount) ) ) {
1318 const char* tagSection = get_camera_metadata_section_name(tag);
1319 if (tagSection == NULL) tagSection = "<unknown>";
1320 const char* tagName = get_camera_metadata_tag_name(tag);
1321 if (tagName == NULL) tagName = "<unknown>";
1322 ALOGE("Malformed static metadata entry '%s.%s' (%x):"
1323 "Expected between %d and %d values, but got %d values",
1324 tagSection, tagName, tag, minCount, maxCount, entry.count);
1325 entry.count = 0;
1326 entry.data.u8 = NULL;
1327 }
1328
1329 return entry;
1330}
1331
1332/** Utility methods */
1333
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001334
1335status_t Camera2Client::buildDefaultParameters() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -07001336 ATRACE_CALL();
Eino-Ville Talvalaac45eb32012-06-07 10:24:51 -07001337 Mutex::Autolock pl(mParamsLock);
1338
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001339 status_t res;
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001340 CameraParameters params;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001341
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001342 camera_metadata_entry_t availableProcessedSizes =
1343 staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES, 2);
1344 if (!availableProcessedSizes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001345
1346 // TODO: Pick more intelligently
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001347 mParameters.previewWidth = availableProcessedSizes.data.i32[0];
1348 mParameters.previewHeight = availableProcessedSizes.data.i32[1];
1349 mParameters.videoWidth = mParameters.previewWidth;
1350 mParameters.videoHeight = mParameters.previewHeight;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001351
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001352 params.setPreviewSize(mParameters.previewWidth, mParameters.previewHeight);
1353 params.setVideoSize(mParameters.videoWidth, mParameters.videoHeight);
1354 params.set(CameraParameters::KEY_PREFERRED_PREVIEW_SIZE_FOR_VIDEO,
1355 String8::format("%dx%d",
1356 mParameters.previewWidth, mParameters.previewHeight));
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001357 {
1358 String8 supportedPreviewSizes;
1359 for (size_t i=0; i < availableProcessedSizes.count; i += 2) {
1360 if (i != 0) supportedPreviewSizes += ",";
1361 supportedPreviewSizes += String8::format("%dx%d",
1362 availableProcessedSizes.data.i32[i],
1363 availableProcessedSizes.data.i32[i+1]);
1364 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001365 params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_SIZES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001366 supportedPreviewSizes);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001367 params.set(CameraParameters::KEY_SUPPORTED_VIDEO_SIZES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001368 supportedPreviewSizes);
1369 }
1370
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001371 camera_metadata_entry_t availableFpsRanges =
1372 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
1373 if (!availableFpsRanges.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001374
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001375 mParameters.previewFpsRange[0] = availableFpsRanges.data.i32[0];
1376 mParameters.previewFpsRange[1] = availableFpsRanges.data.i32[1];
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001377
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001378 params.set(CameraParameters::KEY_PREVIEW_FPS_RANGE,
1379 String8::format("%d,%d",
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001380 mParameters.previewFpsRange[0],
1381 mParameters.previewFpsRange[1]));
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001382
1383 {
1384 String8 supportedPreviewFpsRange;
1385 for (size_t i=0; i < availableFpsRanges.count; i += 2) {
1386 if (i != 0) supportedPreviewFpsRange += ",";
1387 supportedPreviewFpsRange += String8::format("(%d,%d)",
1388 availableFpsRanges.data.i32[i],
1389 availableFpsRanges.data.i32[i+1]);
1390 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001391 params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001392 supportedPreviewFpsRange);
1393 }
1394
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001395 mParameters.previewFormat = HAL_PIXEL_FORMAT_YCrCb_420_SP;
1396 params.set(CameraParameters::KEY_PREVIEW_FORMAT,
1397 formatEnumToString(mParameters.previewFormat)); // NV21
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001398
Eino-Ville Talvalac94cd192012-06-15 12:47:42 -07001399 mParameters.previewTransform = degToTransform(0,
1400 mCameraFacing == CAMERA_FACING_FRONT);
1401
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001402 camera_metadata_entry_t availableFormats =
1403 staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
1404
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001405 {
1406 String8 supportedPreviewFormats;
1407 bool addComma = false;
1408 for (size_t i=0; i < availableFormats.count; i++) {
1409 if (addComma) supportedPreviewFormats += ",";
1410 addComma = true;
1411 switch (availableFormats.data.i32[i]) {
1412 case HAL_PIXEL_FORMAT_YCbCr_422_SP:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001413 supportedPreviewFormats +=
1414 CameraParameters::PIXEL_FORMAT_YUV422SP;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001415 break;
1416 case HAL_PIXEL_FORMAT_YCrCb_420_SP:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001417 supportedPreviewFormats +=
1418 CameraParameters::PIXEL_FORMAT_YUV420SP;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001419 break;
1420 case HAL_PIXEL_FORMAT_YCbCr_422_I:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001421 supportedPreviewFormats +=
1422 CameraParameters::PIXEL_FORMAT_YUV422I;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001423 break;
1424 case HAL_PIXEL_FORMAT_YV12:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001425 supportedPreviewFormats +=
1426 CameraParameters::PIXEL_FORMAT_YUV420P;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001427 break;
1428 case HAL_PIXEL_FORMAT_RGB_565:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001429 supportedPreviewFormats +=
1430 CameraParameters::PIXEL_FORMAT_RGB565;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001431 break;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001432 case HAL_PIXEL_FORMAT_RGBA_8888:
1433 supportedPreviewFormats +=
1434 CameraParameters::PIXEL_FORMAT_RGBA8888;
1435 break;
1436 // Not advertizing JPEG, RAW_SENSOR, etc, for preview formats
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001437 case HAL_PIXEL_FORMAT_RAW_SENSOR:
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001438 case HAL_PIXEL_FORMAT_BLOB:
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001439 addComma = false;
1440 break;
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001441
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001442 default:
1443 ALOGW("%s: Camera %d: Unknown preview format: %x",
1444 __FUNCTION__, mCameraId, availableFormats.data.i32[i]);
1445 addComma = false;
1446 break;
1447 }
1448 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001449 params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001450 supportedPreviewFormats);
1451 }
1452
1453 // PREVIEW_FRAME_RATE / SUPPORTED_PREVIEW_FRAME_RATES are deprecated, but
1454 // still have to do something sane for them
1455
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001456 params.set(CameraParameters::KEY_PREVIEW_FRAME_RATE,
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001457 mParameters.previewFpsRange[0]);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001458
1459 {
1460 String8 supportedPreviewFrameRates;
1461 for (size_t i=0; i < availableFpsRanges.count; i += 2) {
1462 if (i != 0) supportedPreviewFrameRates += ",";
1463 supportedPreviewFrameRates += String8::format("%d",
1464 availableFpsRanges.data.i32[i]);
1465 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001466 params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001467 supportedPreviewFrameRates);
1468 }
1469
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001470 camera_metadata_entry_t availableJpegSizes =
1471 staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES, 2);
1472 if (!availableJpegSizes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001473
1474 // TODO: Pick maximum
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001475 mParameters.pictureWidth = availableJpegSizes.data.i32[0];
1476 mParameters.pictureHeight = availableJpegSizes.data.i32[1];
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001477
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001478 params.setPictureSize(mParameters.pictureWidth,
1479 mParameters.pictureHeight);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001480
1481 {
1482 String8 supportedPictureSizes;
1483 for (size_t i=0; i < availableJpegSizes.count; i += 2) {
1484 if (i != 0) supportedPictureSizes += ",";
1485 supportedPictureSizes += String8::format("%dx%d",
1486 availableJpegSizes.data.i32[i],
1487 availableJpegSizes.data.i32[i+1]);
1488 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001489 params.set(CameraParameters::KEY_SUPPORTED_PICTURE_SIZES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001490 supportedPictureSizes);
1491 }
1492
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001493 params.setPictureFormat(CameraParameters::PIXEL_FORMAT_JPEG);
1494 params.set(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS,
1495 CameraParameters::PIXEL_FORMAT_JPEG);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001496
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001497 camera_metadata_entry_t availableJpegThumbnailSizes =
1498 staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES, 2);
1499 if (!availableJpegThumbnailSizes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001500
1501 // TODO: Pick default thumbnail size sensibly
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001502 mParameters.jpegThumbSize[0] = availableJpegThumbnailSizes.data.i32[0];
1503 mParameters.jpegThumbSize[1] = availableJpegThumbnailSizes.data.i32[1];
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001504
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001505 params.set(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH,
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001506 mParameters.jpegThumbSize[0]);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001507 params.set(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT,
Eino-Ville Talvala11b7cde2012-06-15 12:37:35 -07001508 mParameters.jpegThumbSize[1]);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001509
1510 {
1511 String8 supportedJpegThumbSizes;
1512 for (size_t i=0; i < availableJpegThumbnailSizes.count; i += 2) {
1513 if (i != 0) supportedJpegThumbSizes += ",";
1514 supportedJpegThumbSizes += String8::format("%dx%d",
1515 availableJpegThumbnailSizes.data.i32[i],
1516 availableJpegThumbnailSizes.data.i32[i+1]);
1517 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001518 params.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001519 supportedJpegThumbSizes);
1520 }
1521
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001522 mParameters.jpegThumbQuality = 90;
1523 params.set(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY,
1524 mParameters.jpegThumbQuality);
1525 mParameters.jpegQuality = 90;
1526 params.set(CameraParameters::KEY_JPEG_QUALITY,
1527 mParameters.jpegQuality);
1528 mParameters.jpegRotation = 0;
1529 params.set(CameraParameters::KEY_ROTATION,
1530 mParameters.jpegRotation);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001531
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001532 mParameters.gpsEnabled = false;
1533 mParameters.gpsProcessingMethod = "unknown";
1534 // GPS fields in CameraParameters are not set by implementation
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001535
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001536 mParameters.wbMode = ANDROID_CONTROL_AWB_AUTO;
1537 params.set(CameraParameters::KEY_WHITE_BALANCE,
1538 CameraParameters::WHITE_BALANCE_AUTO);
1539
1540 camera_metadata_entry_t availableWhiteBalanceModes =
1541 staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001542 {
1543 String8 supportedWhiteBalance;
1544 bool addComma = false;
1545 for (size_t i=0; i < availableWhiteBalanceModes.count; i++) {
1546 if (addComma) supportedWhiteBalance += ",";
1547 addComma = true;
1548 switch (availableWhiteBalanceModes.data.u8[i]) {
1549 case ANDROID_CONTROL_AWB_AUTO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001550 supportedWhiteBalance +=
1551 CameraParameters::WHITE_BALANCE_AUTO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001552 break;
1553 case ANDROID_CONTROL_AWB_INCANDESCENT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001554 supportedWhiteBalance +=
1555 CameraParameters::WHITE_BALANCE_INCANDESCENT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001556 break;
1557 case ANDROID_CONTROL_AWB_FLUORESCENT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001558 supportedWhiteBalance +=
1559 CameraParameters::WHITE_BALANCE_FLUORESCENT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001560 break;
1561 case ANDROID_CONTROL_AWB_WARM_FLUORESCENT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001562 supportedWhiteBalance +=
1563 CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001564 break;
1565 case ANDROID_CONTROL_AWB_DAYLIGHT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001566 supportedWhiteBalance +=
1567 CameraParameters::WHITE_BALANCE_DAYLIGHT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001568 break;
1569 case ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001570 supportedWhiteBalance +=
1571 CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001572 break;
1573 case ANDROID_CONTROL_AWB_TWILIGHT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001574 supportedWhiteBalance +=
1575 CameraParameters::WHITE_BALANCE_TWILIGHT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001576 break;
1577 case ANDROID_CONTROL_AWB_SHADE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001578 supportedWhiteBalance +=
1579 CameraParameters::WHITE_BALANCE_SHADE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001580 break;
1581 // Skipping values not mappable to v1 API
1582 case ANDROID_CONTROL_AWB_OFF:
1583 addComma = false;
1584 break;
1585 default:
1586 ALOGW("%s: Camera %d: Unknown white balance value: %d",
1587 __FUNCTION__, mCameraId,
1588 availableWhiteBalanceModes.data.u8[i]);
1589 addComma = false;
1590 break;
1591 }
1592 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001593 params.set(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001594 supportedWhiteBalance);
1595 }
1596
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001597 mParameters.effectMode = ANDROID_CONTROL_EFFECT_OFF;
1598 params.set(CameraParameters::KEY_EFFECT,
1599 CameraParameters::EFFECT_NONE);
1600
1601 camera_metadata_entry_t availableEffects =
1602 staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
1603 if (!availableEffects.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001604 {
1605 String8 supportedEffects;
1606 bool addComma = false;
1607 for (size_t i=0; i < availableEffects.count; i++) {
1608 if (addComma) supportedEffects += ",";
1609 addComma = true;
1610 switch (availableEffects.data.u8[i]) {
1611 case ANDROID_CONTROL_EFFECT_OFF:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001612 supportedEffects +=
1613 CameraParameters::EFFECT_NONE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001614 break;
1615 case ANDROID_CONTROL_EFFECT_MONO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001616 supportedEffects +=
1617 CameraParameters::EFFECT_MONO;
1618 break;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001619 case ANDROID_CONTROL_EFFECT_NEGATIVE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001620 supportedEffects +=
1621 CameraParameters::EFFECT_NEGATIVE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001622 break;
1623 case ANDROID_CONTROL_EFFECT_SOLARIZE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001624 supportedEffects +=
1625 CameraParameters::EFFECT_SOLARIZE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001626 break;
1627 case ANDROID_CONTROL_EFFECT_SEPIA:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001628 supportedEffects +=
1629 CameraParameters::EFFECT_SEPIA;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001630 break;
1631 case ANDROID_CONTROL_EFFECT_POSTERIZE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001632 supportedEffects +=
1633 CameraParameters::EFFECT_POSTERIZE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001634 break;
1635 case ANDROID_CONTROL_EFFECT_WHITEBOARD:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001636 supportedEffects +=
1637 CameraParameters::EFFECT_WHITEBOARD;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001638 break;
1639 case ANDROID_CONTROL_EFFECT_BLACKBOARD:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001640 supportedEffects +=
1641 CameraParameters::EFFECT_BLACKBOARD;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001642 break;
1643 case ANDROID_CONTROL_EFFECT_AQUA:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001644 supportedEffects +=
1645 CameraParameters::EFFECT_AQUA;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001646 break;
1647 default:
1648 ALOGW("%s: Camera %d: Unknown effect value: %d",
1649 __FUNCTION__, mCameraId, availableEffects.data.u8[i]);
1650 addComma = false;
1651 break;
1652 }
1653 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001654 params.set(CameraParameters::KEY_SUPPORTED_EFFECTS, supportedEffects);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001655 }
1656
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001657 mParameters.antibandingMode = ANDROID_CONTROL_AE_ANTIBANDING_AUTO;
1658 params.set(CameraParameters::KEY_ANTIBANDING,
1659 CameraParameters::ANTIBANDING_AUTO);
1660
1661 camera_metadata_entry_t availableAntibandingModes =
1662 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
1663 if (!availableAntibandingModes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001664 {
1665 String8 supportedAntibanding;
1666 bool addComma = false;
1667 for (size_t i=0; i < availableAntibandingModes.count; i++) {
1668 if (addComma) supportedAntibanding += ",";
1669 addComma = true;
1670 switch (availableAntibandingModes.data.u8[i]) {
1671 case ANDROID_CONTROL_AE_ANTIBANDING_OFF:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001672 supportedAntibanding +=
1673 CameraParameters::ANTIBANDING_OFF;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001674 break;
1675 case ANDROID_CONTROL_AE_ANTIBANDING_50HZ:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001676 supportedAntibanding +=
1677 CameraParameters::ANTIBANDING_50HZ;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001678 break;
1679 case ANDROID_CONTROL_AE_ANTIBANDING_60HZ:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001680 supportedAntibanding +=
1681 CameraParameters::ANTIBANDING_60HZ;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001682 break;
1683 case ANDROID_CONTROL_AE_ANTIBANDING_AUTO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001684 supportedAntibanding +=
1685 CameraParameters::ANTIBANDING_AUTO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001686 break;
1687 default:
1688 ALOGW("%s: Camera %d: Unknown antibanding value: %d",
1689 __FUNCTION__, mCameraId,
1690 availableAntibandingModes.data.u8[i]);
1691 addComma = false;
1692 break;
1693 }
1694 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001695 params.set(CameraParameters::KEY_SUPPORTED_ANTIBANDING,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001696 supportedAntibanding);
1697 }
1698
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001699 mParameters.sceneMode = ANDROID_CONTROL_OFF;
1700 params.set(CameraParameters::KEY_SCENE_MODE,
1701 CameraParameters::SCENE_MODE_AUTO);
1702
1703 camera_metadata_entry_t availableSceneModes =
1704 staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
1705 if (!availableSceneModes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001706 {
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001707 String8 supportedSceneModes(CameraParameters::SCENE_MODE_AUTO);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001708 bool addComma = true;
1709 bool noSceneModes = false;
1710 for (size_t i=0; i < availableSceneModes.count; i++) {
1711 if (addComma) supportedSceneModes += ",";
1712 addComma = true;
1713 switch (availableSceneModes.data.u8[i]) {
1714 case ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED:
1715 noSceneModes = true;
1716 break;
1717 case ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY:
1718 // Not in old API
1719 addComma = false;
1720 break;
1721 case ANDROID_CONTROL_SCENE_MODE_ACTION:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001722 supportedSceneModes +=
1723 CameraParameters::SCENE_MODE_ACTION;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001724 break;
1725 case ANDROID_CONTROL_SCENE_MODE_PORTRAIT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001726 supportedSceneModes +=
1727 CameraParameters::SCENE_MODE_PORTRAIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001728 break;
1729 case ANDROID_CONTROL_SCENE_MODE_LANDSCAPE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001730 supportedSceneModes +=
1731 CameraParameters::SCENE_MODE_LANDSCAPE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001732 break;
1733 case ANDROID_CONTROL_SCENE_MODE_NIGHT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001734 supportedSceneModes +=
1735 CameraParameters::SCENE_MODE_NIGHT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001736 break;
1737 case ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001738 supportedSceneModes +=
1739 CameraParameters::SCENE_MODE_NIGHT_PORTRAIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001740 break;
1741 case ANDROID_CONTROL_SCENE_MODE_THEATRE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001742 supportedSceneModes +=
1743 CameraParameters::SCENE_MODE_THEATRE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001744 break;
1745 case ANDROID_CONTROL_SCENE_MODE_BEACH:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001746 supportedSceneModes +=
1747 CameraParameters::SCENE_MODE_BEACH;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001748 break;
1749 case ANDROID_CONTROL_SCENE_MODE_SNOW:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001750 supportedSceneModes +=
1751 CameraParameters::SCENE_MODE_SNOW;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001752 break;
1753 case ANDROID_CONTROL_SCENE_MODE_SUNSET:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001754 supportedSceneModes +=
1755 CameraParameters::SCENE_MODE_SUNSET;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001756 break;
1757 case ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001758 supportedSceneModes +=
1759 CameraParameters::SCENE_MODE_STEADYPHOTO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001760 break;
1761 case ANDROID_CONTROL_SCENE_MODE_FIREWORKS:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001762 supportedSceneModes +=
1763 CameraParameters::SCENE_MODE_FIREWORKS;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001764 break;
1765 case ANDROID_CONTROL_SCENE_MODE_SPORTS:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001766 supportedSceneModes +=
1767 CameraParameters::SCENE_MODE_SPORTS;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001768 break;
1769 case ANDROID_CONTROL_SCENE_MODE_PARTY:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001770 supportedSceneModes +=
1771 CameraParameters::SCENE_MODE_PARTY;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001772 break;
1773 case ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001774 supportedSceneModes +=
1775 CameraParameters::SCENE_MODE_CANDLELIGHT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001776 break;
1777 case ANDROID_CONTROL_SCENE_MODE_BARCODE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001778 supportedSceneModes +=
1779 CameraParameters::SCENE_MODE_BARCODE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001780 break;
1781 default:
1782 ALOGW("%s: Camera %d: Unknown scene mode value: %d",
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001783 __FUNCTION__, mCameraId,
1784 availableSceneModes.data.u8[i]);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001785 addComma = false;
1786 break;
1787 }
1788 }
1789 if (!noSceneModes) {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001790 params.set(CameraParameters::KEY_SUPPORTED_SCENE_MODES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001791 supportedSceneModes);
1792 }
1793 }
1794
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001795 camera_metadata_entry_t flashAvailable =
1796 staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
1797 if (!flashAvailable.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001798
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001799 camera_metadata_entry_t availableAeModes =
1800 staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
1801 if (!availableAeModes.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001802
1803 if (flashAvailable.data.u8[0]) {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001804 mParameters.flashMode = Parameters::FLASH_MODE_AUTO;
1805 params.set(CameraParameters::KEY_FLASH_MODE,
1806 CameraParameters::FLASH_MODE_AUTO);
1807
1808 String8 supportedFlashModes(CameraParameters::FLASH_MODE_OFF);
1809 supportedFlashModes = supportedFlashModes +
1810 "," + CameraParameters::FLASH_MODE_AUTO +
1811 "," + CameraParameters::FLASH_MODE_ON +
1812 "," + CameraParameters::FLASH_MODE_TORCH;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001813 for (size_t i=0; i < availableAeModes.count; i++) {
1814 if (availableAeModes.data.u8[i] ==
1815 ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE) {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001816 supportedFlashModes = supportedFlashModes + "," +
1817 CameraParameters::FLASH_MODE_RED_EYE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001818 break;
1819 }
1820 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001821 params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001822 supportedFlashModes);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001823 } else {
1824 mParameters.flashMode = Parameters::FLASH_MODE_OFF;
1825 params.set(CameraParameters::KEY_FLASH_MODE,
1826 CameraParameters::FLASH_MODE_OFF);
1827 params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
1828 CameraParameters::FLASH_MODE_OFF);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001829 }
1830
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001831 camera_metadata_entry_t minFocusDistance =
1832 staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE, 1, 1);
1833 if (!minFocusDistance.count) return NO_INIT;
1834
1835 camera_metadata_entry_t availableAfModes =
1836 staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
1837 if (!availableAfModes.count) return NO_INIT;
1838
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001839 if (minFocusDistance.data.f[0] == 0) {
1840 // Fixed-focus lens
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001841 mParameters.focusMode = Parameters::FOCUS_MODE_FIXED;
1842 params.set(CameraParameters::KEY_FOCUS_MODE,
1843 CameraParameters::FOCUS_MODE_FIXED);
1844 params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
1845 CameraParameters::FOCUS_MODE_FIXED);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001846 } else {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001847 mParameters.focusMode = Parameters::FOCUS_MODE_AUTO;
1848 params.set(CameraParameters::KEY_FOCUS_MODE,
1849 CameraParameters::FOCUS_MODE_AUTO);
1850 String8 supportedFocusModes(CameraParameters::FOCUS_MODE_FIXED);
1851 supportedFocusModes = supportedFocusModes + "," +
1852 CameraParameters::FOCUS_MODE_INFINITY;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001853 bool addComma = true;
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001854
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001855 for (size_t i=0; i < availableAfModes.count; i++) {
1856 if (addComma) supportedFocusModes += ",";
1857 addComma = true;
1858 switch (availableAfModes.data.u8[i]) {
1859 case ANDROID_CONTROL_AF_AUTO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001860 supportedFocusModes +=
1861 CameraParameters::FOCUS_MODE_AUTO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001862 break;
1863 case ANDROID_CONTROL_AF_MACRO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001864 supportedFocusModes +=
1865 CameraParameters::FOCUS_MODE_MACRO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001866 break;
1867 case ANDROID_CONTROL_AF_CONTINUOUS_VIDEO:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001868 supportedFocusModes +=
1869 CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001870 break;
1871 case ANDROID_CONTROL_AF_CONTINUOUS_PICTURE:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001872 supportedFocusModes +=
1873 CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001874 break;
1875 case ANDROID_CONTROL_AF_EDOF:
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001876 supportedFocusModes +=
1877 CameraParameters::FOCUS_MODE_EDOF;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001878 break;
Eino-Ville Talvalabd47b7b2012-06-07 10:34:20 -07001879 // Not supported in old API
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001880 case ANDROID_CONTROL_AF_OFF:
1881 addComma = false;
1882 break;
1883 default:
1884 ALOGW("%s: Camera %d: Unknown AF mode value: %d",
1885 __FUNCTION__, mCameraId, availableAfModes.data.u8[i]);
1886 addComma = false;
1887 break;
1888 }
1889 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001890 params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001891 supportedFocusModes);
1892 }
1893
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001894 camera_metadata_entry_t max3aRegions =
1895 staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1);
1896 if (!max3aRegions.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001897
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001898 params.set(CameraParameters::KEY_MAX_NUM_FOCUS_AREAS,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001899 max3aRegions.data.i32[0]);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001900 params.set(CameraParameters::KEY_FOCUS_AREAS,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001901 "(0,0,0,0,0)");
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001902 mParameters.focusingAreas.clear();
1903 mParameters.focusingAreas.add(Parameters::Area(0,0,0,0,0));
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001904
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001905 camera_metadata_entry_t availableFocalLengths =
1906 staticInfo(ANDROID_LENS_AVAILABLE_FOCAL_LENGTHS);
1907 if (!availableFocalLengths.count) return NO_INIT;
1908
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001909 float minFocalLength = availableFocalLengths.data.f[0];
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001910 params.setFloat(CameraParameters::KEY_FOCAL_LENGTH, minFocalLength);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001911
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001912 camera_metadata_entry_t sensorSize =
1913 staticInfo(ANDROID_SENSOR_PHYSICAL_SIZE, 2, 2);
1914 if (!sensorSize.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001915
1916 // The fields of view here assume infinity focus, maximum wide angle
1917 float horizFov = 180 / M_PI *
1918 2 * atanf(sensorSize.data.f[0] / (2 * minFocalLength));
1919 float vertFov = 180 / M_PI *
1920 2 * atanf(sensorSize.data.f[1] / (2 * minFocalLength));
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001921 params.setFloat(CameraParameters::KEY_HORIZONTAL_VIEW_ANGLE, horizFov);
1922 params.setFloat(CameraParameters::KEY_VERTICAL_VIEW_ANGLE, vertFov);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001923
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001924 mParameters.exposureCompensation = 0;
1925 params.set(CameraParameters::KEY_EXPOSURE_COMPENSATION,
1926 mParameters.exposureCompensation);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001927
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001928 camera_metadata_entry_t exposureCompensationRange =
1929 staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE, 2, 2);
1930 if (!exposureCompensationRange.count) return NO_INIT;
1931
1932 params.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001933 exposureCompensationRange.data.i32[1]);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001934 params.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001935 exposureCompensationRange.data.i32[0]);
1936
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001937 camera_metadata_entry_t exposureCompensationStep =
1938 staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_STEP, 1, 1);
1939 if (!exposureCompensationStep.count) return NO_INIT;
1940
1941 params.setFloat(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001942 exposureCompensationStep.data.r[0].numerator /
1943 exposureCompensationStep.data.r[0].denominator);
1944
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001945 mParameters.autoExposureLock = false;
1946 params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK,
1947 CameraParameters::FALSE);
1948 params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK_SUPPORTED,
1949 CameraParameters::TRUE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001950
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001951 mParameters.autoWhiteBalanceLock = false;
1952 params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK,
1953 CameraParameters::FALSE);
1954 params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK_SUPPORTED,
1955 CameraParameters::TRUE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001956
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001957 mParameters.meteringAreas.add(Parameters::Area(0, 0, 0, 0, 0));
1958 params.set(CameraParameters::KEY_MAX_NUM_METERING_AREAS,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001959 max3aRegions.data.i32[0]);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001960 params.set(CameraParameters::KEY_METERING_AREAS,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001961 "(0,0,0,0,0)");
1962
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001963 mParameters.zoom = 0;
1964 params.set(CameraParameters::KEY_ZOOM, mParameters.zoom);
1965 params.set(CameraParameters::KEY_MAX_ZOOM, NUM_ZOOM_STEPS - 1);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001966
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001967 camera_metadata_entry_t maxDigitalZoom =
1968 staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM, 1, 1);
1969 if (!maxDigitalZoom.count) return NO_INIT;
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001970
1971 {
1972 String8 zoomRatios;
1973 float zoom = 1.f;
1974 float zoomIncrement = (maxDigitalZoom.data.f[0] - zoom) /
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07001975 (NUM_ZOOM_STEPS-1);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001976 bool addComma = false;
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07001977 for (size_t i=0; i < NUM_ZOOM_STEPS; i++) {
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001978 if (addComma) zoomRatios += ",";
1979 addComma = true;
1980 zoomRatios += String8::format("%d", static_cast<int>(zoom * 100));
1981 zoom += zoomIncrement;
1982 }
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001983 params.set(CameraParameters::KEY_ZOOM_RATIOS, zoomRatios);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001984 }
1985
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001986 params.set(CameraParameters::KEY_ZOOM_SUPPORTED,
1987 CameraParameters::TRUE);
1988 params.set(CameraParameters::KEY_SMOOTH_ZOOM_SUPPORTED,
1989 CameraParameters::TRUE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001990
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001991 params.set(CameraParameters::KEY_FOCUS_DISTANCES,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001992 "Infinity,Infinity,Infinity");
1993
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001994 camera_metadata_entry_t maxFacesDetected =
1995 staticInfo(ANDROID_STATS_MAX_FACE_COUNT, 1, 1);
1996 params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_HW,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001997 maxFacesDetected.data.i32[0]);
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07001998 params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_SW,
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07001999 0);
2000
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002001 params.set(CameraParameters::KEY_VIDEO_FRAME_FORMAT,
2002 formatEnumToString(HAL_PIXEL_FORMAT_YCrCb_420_SP));
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002003
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002004 params.set(CameraParameters::KEY_RECORDING_HINT,
2005 CameraParameters::FALSE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002006
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002007 params.set(CameraParameters::KEY_VIDEO_SNAPSHOT_SUPPORTED,
2008 CameraParameters::TRUE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002009
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002010 params.set(CameraParameters::KEY_VIDEO_STABILIZATION,
2011 CameraParameters::FALSE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002012
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002013 camera_metadata_entry_t availableVideoStabilizationModes =
2014 staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
2015 if (!availableVideoStabilizationModes.count) return NO_INIT;
2016
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002017 if (availableVideoStabilizationModes.count > 1) {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002018 params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
2019 CameraParameters::TRUE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002020 } else {
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002021 params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
2022 CameraParameters::FALSE);
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002023 }
2024
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002025 mParamsFlattened = params.flatten();
2026
Eino-Ville Talvalaf69c70d2012-05-20 15:59:14 -07002027 return OK;
2028}
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07002029
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002030status_t Camera2Client::updatePreviewStream() {
2031 ATRACE_CALL();
2032 status_t res;
2033 if (mPreviewStreamId != NO_STREAM) {
2034 // Check if stream parameters have to change
2035 uint32_t currentWidth, currentHeight;
2036 res = mDevice->getStreamInfo(mPreviewStreamId,
2037 &currentWidth, &currentHeight, 0);
2038 if (res != OK) {
2039 ALOGE("%s: Camera %d: Error querying preview stream info: "
2040 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2041 return res;
2042 }
2043 if (currentWidth != (uint32_t)mParameters.previewWidth ||
2044 currentHeight != (uint32_t)mParameters.previewHeight) {
2045 res = mDevice->waitUntilDrained();
2046 if (res != OK) {
2047 ALOGE("%s: Camera %d: Error waiting for preview to drain: "
2048 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2049 return res;
2050 }
2051 res = mDevice->deleteStream(mPreviewStreamId);
2052 if (res != OK) {
2053 ALOGE("%s: Camera %d: Unable to delete old output stream "
2054 "for preview: %s (%d)", __FUNCTION__, mCameraId,
2055 strerror(-res), res);
2056 return res;
2057 }
2058 mPreviewStreamId = NO_STREAM;
2059 }
2060 }
2061
2062 if (mPreviewStreamId == NO_STREAM) {
2063 res = mDevice->createStream(mPreviewWindow,
2064 mParameters.previewWidth, mParameters.previewHeight,
2065 CAMERA2_HAL_PIXEL_FORMAT_OPAQUE, 0,
2066 &mPreviewStreamId);
2067 if (res != OK) {
2068 ALOGE("%s: Camera %d: Unable to create preview stream: %s (%d)",
2069 __FUNCTION__, mCameraId, strerror(-res), res);
2070 return res;
2071 }
2072 }
2073
Eino-Ville Talvalac94cd192012-06-15 12:47:42 -07002074 res = mDevice->setStreamTransform(mPreviewStreamId,
2075 mParameters.previewTransform);
2076 if (res != OK) {
2077 ALOGE("%s: Camera %d: Unable to set preview stream transform: "
2078 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2079 return res;
2080 }
2081
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002082 return OK;
2083}
2084
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07002085status_t Camera2Client::updatePreviewRequest() {
Eino-Ville Talvalaa1890972012-05-31 11:18:52 -07002086 ATRACE_CALL();
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07002087 status_t res;
2088 if (mPreviewRequest == NULL) {
2089 res = mDevice->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
2090 &mPreviewRequest);
2091 if (res != OK) {
2092 ALOGE("%s: Camera %d: Unable to create default preview request: "
2093 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2094 return res;
2095 }
2096 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002097
2098 res = updateRequestCommon(mPreviewRequest);
2099 if (res != OK) {
2100 ALOGE("%s: Camera %d: Unable to update common entries of preview "
2101 "request: %s (%d)", __FUNCTION__, mCameraId,
2102 strerror(-res), res);
2103 return res;
2104 }
2105
Eino-Ville Talvala6db981c2012-05-21 18:54:30 -07002106 return OK;
2107}
2108
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002109status_t Camera2Client::updateCaptureStream() {
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002110 ATRACE_CALL();
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002111 status_t res;
2112 // Find out buffer size for JPEG
2113 camera_metadata_entry_t maxJpegSize =
2114 staticInfo(ANDROID_JPEG_MAX_SIZE);
2115 if (maxJpegSize.count == 0) {
2116 ALOGE("%s: Camera %d: Can't find ANDROID_JPEG_MAX_SIZE!",
2117 __FUNCTION__, mCameraId);
2118 return INVALID_OPERATION;
2119 }
2120
2121 if (mCaptureConsumer == 0) {
2122 // Create CPU buffer queue endpoint
2123 mCaptureConsumer = new CpuConsumer(1);
2124 mCaptureConsumer->setFrameAvailableListener(new CaptureWaiter(this));
2125 mCaptureConsumer->setName(String8("Camera2Client::CaptureConsumer"));
2126 mCaptureWindow = new SurfaceTextureClient(
2127 mCaptureConsumer->getProducerInterface());
2128 // Create memory for API consumption
2129 mCaptureHeap = new MemoryHeapBase(maxJpegSize.data.i32[0], 0,
2130 "Camera2Client::CaptureHeap");
2131 if (mCaptureHeap->getSize() == 0) {
2132 ALOGE("%s: Camera %d: Unable to allocate memory for capture",
2133 __FUNCTION__, mCameraId);
2134 return NO_MEMORY;
2135 }
2136 mCaptureMemory = new MemoryBase(mCaptureHeap,
2137 0, maxJpegSize.data.i32[0]);
2138 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002139
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002140 if (mCaptureStreamId != NO_STREAM) {
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002141 // Check if stream parameters have to change
2142 uint32_t currentWidth, currentHeight;
2143 res = mDevice->getStreamInfo(mCaptureStreamId,
2144 &currentWidth, &currentHeight, 0);
2145 if (res != OK) {
2146 ALOGE("%s: Camera %d: Error querying capture output stream info: "
2147 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2148 return res;
2149 }
2150 if (currentWidth != (uint32_t)mParameters.pictureWidth ||
2151 currentHeight != (uint32_t)mParameters.pictureHeight) {
2152 res = mDevice->deleteStream(mCaptureStreamId);
2153 if (res != OK) {
2154 ALOGE("%s: Camera %d: Unable to delete old output stream "
2155 "for capture: %s (%d)", __FUNCTION__, mCameraId,
2156 strerror(-res), res);
2157 return res;
2158 }
2159 mCaptureStreamId = NO_STREAM;
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002160 }
2161 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002162
2163 if (mCaptureStreamId == NO_STREAM) {
2164 // Create stream for HAL production
2165 res = mDevice->createStream(mCaptureWindow,
2166 mParameters.pictureWidth, mParameters.pictureHeight,
2167 HAL_PIXEL_FORMAT_BLOB, maxJpegSize.data.i32[0],
2168 &mCaptureStreamId);
2169 if (res != OK) {
2170 ALOGE("%s: Camera %d: Can't create output stream for capture: "
2171 "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2172 return res;
2173 }
2174
2175 }
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002176 return OK;
2177}
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002178
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002179status_t Camera2Client::updateCaptureRequest() {
2180 ATRACE_CALL();
2181 status_t res;
2182 if (mCaptureRequest == NULL) {
2183 res = mDevice->createDefaultRequest(CAMERA2_TEMPLATE_STILL_CAPTURE,
2184 &mCaptureRequest);
2185 if (res != OK) {
2186 ALOGE("%s: Camera %d: Unable to create default still image request:"
2187 " %s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2188 return res;
2189 }
2190 }
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002191
2192 res = updateRequestCommon(mCaptureRequest);
2193 if (res != OK) {
2194 ALOGE("%s: Camera %d: Unable to update common entries of capture "
2195 "request: %s (%d)", __FUNCTION__, mCameraId,
2196 strerror(-res), res);
2197 return res;
2198 }
2199
2200 res = updateEntry(mCaptureRequest,
2201 ANDROID_JPEG_THUMBNAIL_SIZE,
2202 mParameters.jpegThumbSize, 2);
2203 if (res != OK) return res;
2204 res = updateEntry(mCaptureRequest,
2205 ANDROID_JPEG_THUMBNAIL_QUALITY,
2206 &mParameters.jpegThumbQuality, 1);
2207 if (res != OK) return res;
2208 res = updateEntry(mCaptureRequest,
2209 ANDROID_JPEG_QUALITY,
2210 &mParameters.jpegQuality, 1);
2211 if (res != OK) return res;
2212 res = updateEntry(mCaptureRequest,
2213 ANDROID_JPEG_ORIENTATION,
2214 &mParameters.jpegRotation, 1);
2215 if (res != OK) return res;
2216
2217 if (mParameters.gpsEnabled) {
2218 res = updateEntry(mCaptureRequest,
2219 ANDROID_JPEG_GPS_COORDINATES,
2220 mParameters.gpsCoordinates, 3);
2221 if (res != OK) return res;
2222 res = updateEntry(mCaptureRequest,
2223 ANDROID_JPEG_GPS_TIMESTAMP,
2224 &mParameters.gpsTimestamp, 1);
2225 if (res != OK) return res;
2226 res = updateEntry(mCaptureRequest,
2227 ANDROID_JPEG_GPS_PROCESSING_METHOD,
2228 mParameters.gpsProcessingMethod.string(),
2229 mParameters.gpsProcessingMethod.size());
2230 if (res != OK) return res;
2231 } else {
2232 res = deleteEntry(mCaptureRequest,
2233 ANDROID_JPEG_GPS_COORDINATES);
2234 if (res != OK) return res;
2235 res = deleteEntry(mCaptureRequest,
2236 ANDROID_JPEG_GPS_TIMESTAMP);
2237 if (res != OK) return res;
2238 res = deleteEntry(mCaptureRequest,
2239 ANDROID_JPEG_GPS_PROCESSING_METHOD);
2240 if (res != OK) return res;
2241 }
2242
Eino-Ville Talvalad4bcfde2012-06-07 17:12:38 -07002243 return OK;
2244}
2245
Eino-Ville Talvalabe0573b2012-06-15 12:42:30 -07002246status_t Camera2Client::updateRequestCommon(camera_metadata_t *request) {
2247 ATRACE_CALL();
2248 status_t res;
2249 res = updateEntry(request,
2250 ANDROID_CONTROL_AE_TARGET_FPS_RANGE, mParameters.previewFpsRange, 2);
2251 if (res != OK) return res;
2252
2253 uint8_t wbMode = mParameters.autoWhiteBalanceLock ?
2254 ANDROID_CONTROL_AWB_LOCKED : mParameters.wbMode;
2255 res = updateEntry(request,
2256 ANDROID_CONTROL_AWB_MODE, &wbMode, 1);
2257 if (res != OK) return res;
2258 res = updateEntry(request,
2259 ANDROID_CONTROL_EFFECT_MODE, &mParameters.effectMode, 1);
2260 if (res != OK) return res;
2261 res = updateEntry(request,
2262 ANDROID_CONTROL_AE_ANTIBANDING_MODE,
2263 &mParameters.antibandingMode, 1);
2264 if (res != OK) return res;
2265
2266 uint8_t controlMode =
2267 (mParameters.sceneMode == ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED) ?
2268 ANDROID_CONTROL_AUTO : ANDROID_CONTROL_USE_SCENE_MODE;
2269 res = updateEntry(request,
2270 ANDROID_CONTROL_MODE, &controlMode, 1);
2271 if (res != OK) return res;
2272 if (controlMode == ANDROID_CONTROL_USE_SCENE_MODE) {
2273 res = updateEntry(request,
2274 ANDROID_CONTROL_SCENE_MODE,
2275 &mParameters.sceneMode, 1);
2276 if (res != OK) return res;
2277 }
2278
2279 uint8_t flashMode = ANDROID_FLASH_OFF;
2280 uint8_t aeMode;
2281 switch (mParameters.flashMode) {
2282 case Parameters::FLASH_MODE_OFF:
2283 aeMode = ANDROID_CONTROL_AE_ON; break;
2284 case Parameters::FLASH_MODE_AUTO:
2285 aeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH; break;
2286 case Parameters::FLASH_MODE_ON:
2287 aeMode = ANDROID_CONTROL_AE_ON_ALWAYS_FLASH; break;
2288 case Parameters::FLASH_MODE_TORCH:
2289 aeMode = ANDROID_CONTROL_AE_ON;
2290 flashMode = ANDROID_FLASH_TORCH;
2291 break;
2292 case Parameters::FLASH_MODE_RED_EYE:
2293 aeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE; break;
2294 default:
2295 ALOGE("%s: Camera %d: Unknown flash mode %d", __FUNCTION__,
2296 mCameraId, mParameters.flashMode);
2297 return BAD_VALUE;
2298 }
2299 if (mParameters.autoExposureLock) aeMode = ANDROID_CONTROL_AE_LOCKED;
2300
2301 res = updateEntry(request,
2302 ANDROID_FLASH_MODE, &flashMode, 1);
2303 if (res != OK) return res;
2304 res = updateEntry(request,
2305 ANDROID_CONTROL_AE_MODE, &aeMode, 1);
2306 if (res != OK) return res;
2307
2308 float focusDistance = 0; // infinity focus in diopters
2309 uint8_t focusMode;
2310 switch (mParameters.focusMode) {
2311 case Parameters::FOCUS_MODE_AUTO:
2312 case Parameters::FOCUS_MODE_MACRO:
2313 case Parameters::FOCUS_MODE_CONTINUOUS_VIDEO:
2314 case Parameters::FOCUS_MODE_CONTINUOUS_PICTURE:
2315 case Parameters::FOCUS_MODE_EDOF:
2316 focusMode = mParameters.focusMode;
2317 break;
2318 case Parameters::FOCUS_MODE_INFINITY:
2319 case Parameters::FOCUS_MODE_FIXED:
2320 focusMode = ANDROID_CONTROL_AF_OFF;
2321 break;
2322 default:
2323 ALOGE("%s: Camera %d: Unknown focus mode %d", __FUNCTION__,
2324 mCameraId, mParameters.focusMode);
2325 return BAD_VALUE;
2326 }
2327 res = updateEntry(request,
2328 ANDROID_LENS_FOCUS_DISTANCE, &focusDistance, 1);
2329 if (res != OK) return res;
2330 res = updateEntry(request,
2331 ANDROID_CONTROL_AF_MODE, &focusMode, 1);
2332 if (res != OK) return res;
2333
2334 size_t focusingAreasSize = mParameters.focusingAreas.size() * 5;
2335 int32_t *focusingAreas = new int32_t[focusingAreasSize];
2336 for (size_t i = 0; i < focusingAreasSize; i += 5) {
2337 focusingAreas[i + 0] = mParameters.focusingAreas[i].left;
2338 focusingAreas[i + 1] = mParameters.focusingAreas[i].top;
2339 focusingAreas[i + 2] = mParameters.focusingAreas[i].right;
2340 focusingAreas[i + 3] = mParameters.focusingAreas[i].bottom;
2341 focusingAreas[i + 4] = mParameters.focusingAreas[i].weight;
2342 }
2343 res = updateEntry(request,
2344 ANDROID_CONTROL_AF_REGIONS, focusingAreas,focusingAreasSize);
2345 if (res != OK) return res;
2346 delete[] focusingAreas;
2347
2348 res = updateEntry(request,
2349 ANDROID_CONTROL_AE_EXP_COMPENSATION,
2350 &mParameters.exposureCompensation, 1);
2351 if (res != OK) return res;
2352
2353 size_t meteringAreasSize = mParameters.meteringAreas.size() * 5;
2354 int32_t *meteringAreas = new int32_t[meteringAreasSize];
2355 for (size_t i = 0; i < meteringAreasSize; i += 5) {
2356 meteringAreas[i + 0] = mParameters.meteringAreas[i].left;
2357 meteringAreas[i + 1] = mParameters.meteringAreas[i].top;
2358 meteringAreas[i + 2] = mParameters.meteringAreas[i].right;
2359 meteringAreas[i + 3] = mParameters.meteringAreas[i].bottom;
2360 meteringAreas[i + 4] = mParameters.meteringAreas[i].weight;
2361 }
2362 res = updateEntry(request,
2363 ANDROID_CONTROL_AE_REGIONS, meteringAreas, meteringAreasSize);
2364 if (res != OK) return res;
2365
2366 res = updateEntry(request,
2367 ANDROID_CONTROL_AWB_REGIONS, meteringAreas, meteringAreasSize);
2368 if (res != OK) return res;
2369 delete[] meteringAreas;
2370
2371 // Need to convert zoom index into a crop rectangle. The rectangle is
2372 // chosen to maximize its area on the sensor
2373
2374 camera_metadata_entry_t maxDigitalZoom =
2375 staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM);
2376 float zoomIncrement = (maxDigitalZoom.data.f[0] - 1) /
2377 (NUM_ZOOM_STEPS-1);
2378 float zoomRatio = 1 + zoomIncrement * mParameters.zoom;
2379
2380 camera_metadata_entry_t activePixelArraySize =
2381 staticInfo(ANDROID_SENSOR_ACTIVE_ARRAY_SIZE, 2, 2);
2382 int32_t arrayWidth = activePixelArraySize.data.i32[0];
2383 int32_t arrayHeight = activePixelArraySize.data.i32[1];
2384 float zoomLeft, zoomTop, zoomWidth, zoomHeight;
2385 if (mParameters.previewWidth >= mParameters.previewHeight) {
2386 zoomWidth = arrayWidth / zoomRatio;
2387 zoomHeight = zoomWidth *
2388 mParameters.previewHeight / mParameters.previewWidth;
2389 } else {
2390 zoomHeight = arrayHeight / zoomRatio;
2391 zoomWidth = zoomHeight *
2392 mParameters.previewWidth / mParameters.previewHeight;
2393 }
2394 zoomLeft = (arrayWidth - zoomWidth) / 2;
2395 zoomTop = (arrayHeight - zoomHeight) / 2;
2396
2397 int32_t cropRegion[3] = { zoomLeft, zoomTop, zoomWidth };
2398 res = updateEntry(request,
2399 ANDROID_SCALER_CROP_REGION, cropRegion, 3);
2400 if (res != OK) return res;
2401
2402 // TODO: Decide how to map recordingHint, or whether just to ignore it
2403
2404 uint8_t vstabMode = mParameters.videoStabilization ?
2405 ANDROID_CONTROL_VIDEO_STABILIZATION_ON :
2406 ANDROID_CONTROL_VIDEO_STABILIZATION_OFF;
2407 res = updateEntry(request,
2408 ANDROID_CONTROL_VIDEO_STABILIZATION_MODE,
2409 &vstabMode, 1);
2410 if (res != OK) return res;
2411
2412 return OK;
2413}
2414
2415status_t Camera2Client::updateEntry(camera_metadata_t *buffer,
2416 uint32_t tag, const void *data, size_t data_count) {
2417 camera_metadata_entry_t entry;
2418 status_t res;
2419 res = find_camera_metadata_entry(buffer, tag, &entry);
2420 if (res == NAME_NOT_FOUND) {
2421 res = add_camera_metadata_entry(buffer,
2422 tag, data, data_count);
2423 } else if (res == OK) {
2424 res = update_camera_metadata_entry(buffer,
2425 entry.index, data, data_count, NULL);
2426 }
2427
2428 if (res != OK) {
2429 ALOGE("%s: Unable to update metadata entry %s.%s (%x): %s (%d)",
2430 __FUNCTION__, get_camera_metadata_section_name(tag),
2431 get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2432 }
2433 return res;
2434}
2435
2436status_t Camera2Client::deleteEntry(camera_metadata_t *buffer, uint32_t tag) {
2437 camera_metadata_entry_t entry;
2438 status_t res;
2439 res = find_camera_metadata_entry(buffer, tag, &entry);
2440 if (res == NAME_NOT_FOUND) {
2441 return OK;
2442 } else if (res != OK) {
2443 ALOGE("%s: Error looking for entry %s.%s (%x): %s %d",
2444 __FUNCTION__,
2445 get_camera_metadata_section_name(tag),
2446 get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2447 return res;
2448 }
2449 res = delete_camera_metadata_entry(buffer, entry.index);
2450 if (res != OK) {
2451 ALOGE("%s: Error deleting entry %s.%s (%x): %s %d",
2452 __FUNCTION__,
2453 get_camera_metadata_section_name(tag),
2454 get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2455 }
2456 return res;
2457}
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07002458int Camera2Client::formatStringToEnum(const char *format) {
2459 return
2460 !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422SP) ?
2461 HAL_PIXEL_FORMAT_YCbCr_422_SP : // NV16
2462 !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420SP) ?
2463 HAL_PIXEL_FORMAT_YCrCb_420_SP : // NV21
2464 !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422I) ?
2465 HAL_PIXEL_FORMAT_YCbCr_422_I : // YUY2
2466 !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420P) ?
2467 HAL_PIXEL_FORMAT_YV12 : // YV12
2468 !strcmp(format, CameraParameters::PIXEL_FORMAT_RGB565) ?
2469 HAL_PIXEL_FORMAT_RGB_565 : // RGB565
2470 !strcmp(format, CameraParameters::PIXEL_FORMAT_RGBA8888) ?
2471 HAL_PIXEL_FORMAT_RGBA_8888 : // RGB8888
2472 !strcmp(format, CameraParameters::PIXEL_FORMAT_BAYER_RGGB) ?
2473 HAL_PIXEL_FORMAT_RAW_SENSOR : // Raw sensor data
2474 -1;
2475}
2476
Eino-Ville Talvala3cca1362012-06-07 10:07:18 -07002477const char* Camera2Client::formatEnumToString(int format) {
2478 const char *fmt;
2479 switch(format) {
2480 case HAL_PIXEL_FORMAT_YCbCr_422_SP: // NV16
2481 fmt = CameraParameters::PIXEL_FORMAT_YUV422SP;
2482 break;
2483 case HAL_PIXEL_FORMAT_YCrCb_420_SP: // NV21
2484 fmt = CameraParameters::PIXEL_FORMAT_YUV420SP;
2485 break;
2486 case HAL_PIXEL_FORMAT_YCbCr_422_I: // YUY2
2487 fmt = CameraParameters::PIXEL_FORMAT_YUV422I;
2488 break;
2489 case HAL_PIXEL_FORMAT_YV12: // YV12
2490 fmt = CameraParameters::PIXEL_FORMAT_YUV420P;
2491 break;
2492 case HAL_PIXEL_FORMAT_RGB_565: // RGB565
2493 fmt = CameraParameters::PIXEL_FORMAT_RGB565;
2494 break;
2495 case HAL_PIXEL_FORMAT_RGBA_8888: // RGBA8888
2496 fmt = CameraParameters::PIXEL_FORMAT_RGBA8888;
2497 break;
2498 case HAL_PIXEL_FORMAT_RAW_SENSOR:
2499 ALOGW("Raw sensor preview format requested.");
2500 fmt = CameraParameters::PIXEL_FORMAT_BAYER_RGGB;
2501 break;
2502 default:
2503 ALOGE("%s: Unknown preview format: %x",
2504 __FUNCTION__, format);
2505 fmt = NULL;
2506 break;
2507 }
2508 return fmt;
2509}
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07002510
2511int Camera2Client::wbModeStringToEnum(const char *wbMode) {
2512 return
2513 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_AUTO) ?
2514 ANDROID_CONTROL_AWB_AUTO :
2515 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_INCANDESCENT) ?
2516 ANDROID_CONTROL_AWB_INCANDESCENT :
2517 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_FLUORESCENT) ?
2518 ANDROID_CONTROL_AWB_FLUORESCENT :
2519 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT) ?
2520 ANDROID_CONTROL_AWB_WARM_FLUORESCENT :
2521 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_DAYLIGHT) ?
2522 ANDROID_CONTROL_AWB_DAYLIGHT :
2523 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT) ?
2524 ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT :
2525 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_TWILIGHT) ?
2526 ANDROID_CONTROL_AWB_TWILIGHT :
2527 !strcmp(wbMode, CameraParameters::WHITE_BALANCE_SHADE) ?
2528 ANDROID_CONTROL_AWB_SHADE :
2529 -1;
2530}
2531
2532int Camera2Client::effectModeStringToEnum(const char *effectMode) {
2533 return
2534 !strcmp(effectMode, CameraParameters::EFFECT_NONE) ?
2535 ANDROID_CONTROL_EFFECT_OFF :
2536 !strcmp(effectMode, CameraParameters::EFFECT_MONO) ?
2537 ANDROID_CONTROL_EFFECT_MONO :
2538 !strcmp(effectMode, CameraParameters::EFFECT_NEGATIVE) ?
2539 ANDROID_CONTROL_EFFECT_NEGATIVE :
2540 !strcmp(effectMode, CameraParameters::EFFECT_SOLARIZE) ?
2541 ANDROID_CONTROL_EFFECT_SOLARIZE :
2542 !strcmp(effectMode, CameraParameters::EFFECT_SEPIA) ?
2543 ANDROID_CONTROL_EFFECT_SEPIA :
2544 !strcmp(effectMode, CameraParameters::EFFECT_POSTERIZE) ?
2545 ANDROID_CONTROL_EFFECT_POSTERIZE :
2546 !strcmp(effectMode, CameraParameters::EFFECT_WHITEBOARD) ?
2547 ANDROID_CONTROL_EFFECT_WHITEBOARD :
2548 !strcmp(effectMode, CameraParameters::EFFECT_BLACKBOARD) ?
2549 ANDROID_CONTROL_EFFECT_BLACKBOARD :
2550 !strcmp(effectMode, CameraParameters::EFFECT_AQUA) ?
2551 ANDROID_CONTROL_EFFECT_AQUA :
2552 -1;
2553}
2554
2555int Camera2Client::abModeStringToEnum(const char *abMode) {
2556 return
2557 !strcmp(abMode, CameraParameters::ANTIBANDING_AUTO) ?
2558 ANDROID_CONTROL_AE_ANTIBANDING_AUTO :
2559 !strcmp(abMode, CameraParameters::ANTIBANDING_OFF) ?
2560 ANDROID_CONTROL_AE_ANTIBANDING_OFF :
2561 !strcmp(abMode, CameraParameters::ANTIBANDING_50HZ) ?
2562 ANDROID_CONTROL_AE_ANTIBANDING_50HZ :
2563 !strcmp(abMode, CameraParameters::ANTIBANDING_60HZ) ?
2564 ANDROID_CONTROL_AE_ANTIBANDING_60HZ :
2565 -1;
2566}
2567
2568int Camera2Client::sceneModeStringToEnum(const char *sceneMode) {
2569 return
2570 !strcmp(sceneMode, CameraParameters::SCENE_MODE_AUTO) ?
2571 ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED :
2572 !strcmp(sceneMode, CameraParameters::SCENE_MODE_ACTION) ?
2573 ANDROID_CONTROL_SCENE_MODE_ACTION :
2574 !strcmp(sceneMode, CameraParameters::SCENE_MODE_PORTRAIT) ?
2575 ANDROID_CONTROL_SCENE_MODE_PORTRAIT :
2576 !strcmp(sceneMode, CameraParameters::SCENE_MODE_LANDSCAPE) ?
2577 ANDROID_CONTROL_SCENE_MODE_LANDSCAPE :
2578 !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT) ?
2579 ANDROID_CONTROL_SCENE_MODE_NIGHT :
2580 !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT_PORTRAIT) ?
2581 ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT :
2582 !strcmp(sceneMode, CameraParameters::SCENE_MODE_THEATRE) ?
2583 ANDROID_CONTROL_SCENE_MODE_THEATRE :
2584 !strcmp(sceneMode, CameraParameters::SCENE_MODE_BEACH) ?
2585 ANDROID_CONTROL_SCENE_MODE_BEACH :
2586 !strcmp(sceneMode, CameraParameters::SCENE_MODE_SNOW) ?
2587 ANDROID_CONTROL_SCENE_MODE_SNOW :
2588 !strcmp(sceneMode, CameraParameters::SCENE_MODE_SUNSET) ?
2589 ANDROID_CONTROL_SCENE_MODE_SUNSET :
2590 !strcmp(sceneMode, CameraParameters::SCENE_MODE_STEADYPHOTO) ?
2591 ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO :
2592 !strcmp(sceneMode, CameraParameters::SCENE_MODE_FIREWORKS) ?
2593 ANDROID_CONTROL_SCENE_MODE_FIREWORKS :
2594 !strcmp(sceneMode, CameraParameters::SCENE_MODE_SPORTS) ?
2595 ANDROID_CONTROL_SCENE_MODE_SPORTS :
2596 !strcmp(sceneMode, CameraParameters::SCENE_MODE_PARTY) ?
2597 ANDROID_CONTROL_SCENE_MODE_PARTY :
2598 !strcmp(sceneMode, CameraParameters::SCENE_MODE_CANDLELIGHT) ?
2599 ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT :
2600 !strcmp(sceneMode, CameraParameters::SCENE_MODE_BARCODE) ?
2601 ANDROID_CONTROL_SCENE_MODE_BARCODE:
2602 -1;
2603}
2604
2605Camera2Client::Parameters::flashMode_t Camera2Client::flashModeStringToEnum(
2606 const char *flashMode) {
2607 return
2608 !strcmp(flashMode, CameraParameters::FLASH_MODE_OFF) ?
2609 Parameters::FLASH_MODE_OFF :
2610 !strcmp(flashMode, CameraParameters::FLASH_MODE_AUTO) ?
2611 Parameters::FLASH_MODE_AUTO :
2612 !strcmp(flashMode, CameraParameters::FLASH_MODE_ON) ?
2613 Parameters::FLASH_MODE_ON :
2614 !strcmp(flashMode, CameraParameters::FLASH_MODE_RED_EYE) ?
2615 Parameters::FLASH_MODE_RED_EYE :
2616 !strcmp(flashMode, CameraParameters::FLASH_MODE_TORCH) ?
2617 Parameters::FLASH_MODE_TORCH :
2618 Parameters::FLASH_MODE_INVALID;
2619}
2620
2621Camera2Client::Parameters::focusMode_t Camera2Client::focusModeStringToEnum(
2622 const char *focusMode) {
2623 return
2624 !strcmp(focusMode, CameraParameters::FOCUS_MODE_AUTO) ?
2625 Parameters::FOCUS_MODE_AUTO :
2626 !strcmp(focusMode, CameraParameters::FOCUS_MODE_INFINITY) ?
2627 Parameters::FOCUS_MODE_INFINITY :
2628 !strcmp(focusMode, CameraParameters::FOCUS_MODE_MACRO) ?
2629 Parameters::FOCUS_MODE_MACRO :
2630 !strcmp(focusMode, CameraParameters::FOCUS_MODE_FIXED) ?
2631 Parameters::FOCUS_MODE_FIXED :
2632 !strcmp(focusMode, CameraParameters::FOCUS_MODE_EDOF) ?
2633 Parameters::FOCUS_MODE_EDOF :
2634 !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO) ?
2635 Parameters::FOCUS_MODE_CONTINUOUS_VIDEO :
2636 !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE) ?
2637 Parameters::FOCUS_MODE_CONTINUOUS_PICTURE :
2638 Parameters::FOCUS_MODE_INVALID;
2639}
2640
2641status_t Camera2Client::parseAreas(const char *areasCStr,
2642 Vector<Parameters::Area> *areas) {
2643 static const size_t NUM_FIELDS = 5;
2644 areas->clear();
2645 if (areasCStr == NULL) {
2646 // If no key exists, use default (0,0,0,0,0)
2647 areas->push();
2648 return OK;
2649 }
2650 String8 areasStr(areasCStr);
2651 ssize_t areaStart = areasStr.find("(", 0) + 1;
2652 while (areaStart != 0) {
2653 const char* area = areasStr.string() + areaStart;
2654 char *numEnd;
2655 int vals[NUM_FIELDS];
2656 for (size_t i = 0; i < NUM_FIELDS; i++) {
2657 errno = 0;
2658 vals[i] = strtol(area, &numEnd, 10);
2659 if (errno || numEnd == area) return BAD_VALUE;
2660 area = numEnd + 1;
2661 }
2662 areas->push(Parameters::Area(
2663 vals[0], vals[1], vals[2], vals[3], vals[4]) );
2664 areaStart = areasStr.find("(", areaStart) + 1;
2665 }
2666 return OK;
2667}
2668
2669status_t Camera2Client::validateAreas(const Vector<Parameters::Area> &areas,
2670 size_t maxRegions) {
2671 // Definition of valid area can be found in
2672 // include/camera/CameraParameters.h
2673 if (areas.size() == 0) return BAD_VALUE;
2674 if (areas.size() == 1) {
2675 if (areas[0].left == 0 &&
2676 areas[0].top == 0 &&
2677 areas[0].right == 0 &&
2678 areas[0].bottom == 0 &&
2679 areas[0].weight == 0) {
2680 // Single (0,0,0,0,0) entry is always valid (== driver decides)
2681 return OK;
2682 }
2683 }
2684 if (areas.size() > maxRegions) {
2685 ALOGE("%s: Too many areas requested: %d",
2686 __FUNCTION__, areas.size());
2687 return BAD_VALUE;
2688 }
2689
2690 for (Vector<Parameters::Area>::const_iterator a = areas.begin();
2691 a != areas.end(); a++) {
2692 if (a->weight < 1 || a->weight > 1000) return BAD_VALUE;
2693 if (a->left < -1000 || a->left > 1000) return BAD_VALUE;
2694 if (a->top < -1000 || a->top > 1000) return BAD_VALUE;
2695 if (a->right < -1000 || a->right > 1000) return BAD_VALUE;
2696 if (a->bottom < -1000 || a->bottom > 1000) return BAD_VALUE;
2697 if (a->left >= a->right) return BAD_VALUE;
2698 if (a->top >= a->bottom) return BAD_VALUE;
2699 }
2700 return OK;
2701}
2702
2703bool Camera2Client::boolFromString(const char *boolStr) {
2704 return !boolStr ? false :
2705 !strcmp(boolStr, CameraParameters::TRUE) ? true :
2706 false;
2707}
2708
Eino-Ville Talvalac94cd192012-06-15 12:47:42 -07002709int Camera2Client::degToTransform(int degrees, bool mirror) {
2710 if (!mirror) {
2711 if (degrees == 0) return 0;
2712 else if (degrees == 90) return HAL_TRANSFORM_ROT_90;
2713 else if (degrees == 180) return HAL_TRANSFORM_ROT_180;
2714 else if (degrees == 270) return HAL_TRANSFORM_ROT_270;
2715 } else { // Do mirror (horizontal flip)
2716 if (degrees == 0) { // FLIP_H and ROT_0
2717 return HAL_TRANSFORM_FLIP_H;
2718 } else if (degrees == 90) { // FLIP_H and ROT_90
2719 return HAL_TRANSFORM_FLIP_H | HAL_TRANSFORM_ROT_90;
2720 } else if (degrees == 180) { // FLIP_H and ROT_180
2721 return HAL_TRANSFORM_FLIP_V;
2722 } else if (degrees == 270) { // FLIP_H and ROT_270
2723 return HAL_TRANSFORM_FLIP_V | HAL_TRANSFORM_ROT_90;
2724 }
2725 }
2726 ALOGE("%s: Bad input: %d", __FUNCTION__, degrees);
2727 return -1;
2728}
Eino-Ville Talvala6861a4e2012-06-07 10:32:12 -07002729
Eino-Ville Talvala61ab9f92012-05-17 10:30:54 -07002730} // namespace android