Parameters.cpp revision c9d7e4da3f963dadbea19e9b520fb7a7e28e614a
1/*
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 "Camera2-Parameters"
18#define ATRACE_TAG ATRACE_TAG_CAMERA
19//#define LOG_NDEBUG 0
20
21#include <utils/Log.h>
22#include <utils/Trace.h>
23
24#include <math.h>
25#include <stdlib.h>
26#include <cutils/properties.h>
27
28#include "Parameters.h"
29#include "system/camera.h"
30#include "camera/CameraParameters.h"
31
32namespace android {
33namespace camera2 {
34
35Parameters::Parameters(int cameraId,
36        int cameraFacing) :
37        cameraId(cameraId),
38        cameraFacing(cameraFacing),
39        info(NULL) {
40}
41
42Parameters::~Parameters() {
43}
44
45status_t Parameters::initialize(const CameraMetadata *info) {
46    status_t res;
47
48    if (info->entryCount() == 0) {
49        ALOGE("%s: No static information provided!", __FUNCTION__);
50        return BAD_VALUE;
51    }
52    Parameters::info = info;
53
54    res = buildFastInfo();
55    if (res != OK) return res;
56
57    CameraParameters params;
58
59    camera_metadata_ro_entry_t availableProcessedSizes =
60        staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES, 2);
61    if (!availableProcessedSizes.count) return NO_INIT;
62
63    // TODO: Pick more intelligently
64    previewWidth = availableProcessedSizes.data.i32[0];
65    previewHeight = availableProcessedSizes.data.i32[1];
66    videoWidth = previewWidth;
67    videoHeight = previewHeight;
68
69    params.setPreviewSize(previewWidth, previewHeight);
70    params.setVideoSize(videoWidth, videoHeight);
71    params.set(CameraParameters::KEY_PREFERRED_PREVIEW_SIZE_FOR_VIDEO,
72            String8::format("%dx%d",
73                    previewWidth, previewHeight));
74    {
75        String8 supportedPreviewSizes;
76        for (size_t i=0; i < availableProcessedSizes.count; i += 2) {
77            if (i != 0) supportedPreviewSizes += ",";
78            supportedPreviewSizes += String8::format("%dx%d",
79                    availableProcessedSizes.data.i32[i],
80                    availableProcessedSizes.data.i32[i+1]);
81        }
82        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_SIZES,
83                supportedPreviewSizes);
84        params.set(CameraParameters::KEY_SUPPORTED_VIDEO_SIZES,
85                supportedPreviewSizes);
86    }
87
88    camera_metadata_ro_entry_t availableFpsRanges =
89        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
90    if (!availableFpsRanges.count) return NO_INIT;
91
92    previewFpsRange[0] = availableFpsRanges.data.i32[0];
93    previewFpsRange[1] = availableFpsRanges.data.i32[1];
94
95    params.set(CameraParameters::KEY_PREVIEW_FPS_RANGE,
96            String8::format("%d,%d",
97                    previewFpsRange[0] * kFpsToApiScale,
98                    previewFpsRange[1] * kFpsToApiScale));
99
100    {
101        String8 supportedPreviewFpsRange;
102        for (size_t i=0; i < availableFpsRanges.count; i += 2) {
103            if (i != 0) supportedPreviewFpsRange += ",";
104            supportedPreviewFpsRange += String8::format("(%d,%d)",
105                    availableFpsRanges.data.i32[i] * kFpsToApiScale,
106                    availableFpsRanges.data.i32[i+1] * kFpsToApiScale);
107        }
108        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE,
109                supportedPreviewFpsRange);
110    }
111
112    previewFormat = HAL_PIXEL_FORMAT_YCrCb_420_SP;
113    params.set(CameraParameters::KEY_PREVIEW_FORMAT,
114            formatEnumToString(previewFormat)); // NV21
115
116    previewTransform = degToTransform(0,
117            cameraFacing == CAMERA_FACING_FRONT);
118
119    camera_metadata_ro_entry_t availableFormats =
120        staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
121
122    {
123        String8 supportedPreviewFormats;
124        bool addComma = false;
125        for (size_t i=0; i < availableFormats.count; i++) {
126            if (addComma) supportedPreviewFormats += ",";
127            addComma = true;
128            switch (availableFormats.data.i32[i]) {
129            case HAL_PIXEL_FORMAT_YCbCr_422_SP:
130                supportedPreviewFormats +=
131                    CameraParameters::PIXEL_FORMAT_YUV422SP;
132                break;
133            case HAL_PIXEL_FORMAT_YCrCb_420_SP:
134                supportedPreviewFormats +=
135                    CameraParameters::PIXEL_FORMAT_YUV420SP;
136                break;
137            case HAL_PIXEL_FORMAT_YCbCr_422_I:
138                supportedPreviewFormats +=
139                    CameraParameters::PIXEL_FORMAT_YUV422I;
140                break;
141            case HAL_PIXEL_FORMAT_YV12:
142                supportedPreviewFormats +=
143                    CameraParameters::PIXEL_FORMAT_YUV420P;
144                break;
145            case HAL_PIXEL_FORMAT_RGB_565:
146                supportedPreviewFormats +=
147                    CameraParameters::PIXEL_FORMAT_RGB565;
148                break;
149            case HAL_PIXEL_FORMAT_RGBA_8888:
150                supportedPreviewFormats +=
151                    CameraParameters::PIXEL_FORMAT_RGBA8888;
152                break;
153            // Not advertizing JPEG, RAW_SENSOR, etc, for preview formats
154            case HAL_PIXEL_FORMAT_RAW_SENSOR:
155            case HAL_PIXEL_FORMAT_BLOB:
156                addComma = false;
157                break;
158
159            default:
160                ALOGW("%s: Camera %d: Unknown preview format: %x",
161                        __FUNCTION__, cameraId, availableFormats.data.i32[i]);
162                addComma = false;
163                break;
164            }
165        }
166        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS,
167                supportedPreviewFormats);
168    }
169
170    // PREVIEW_FRAME_RATE / SUPPORTED_PREVIEW_FRAME_RATES are deprecated, but
171    // still have to do something sane for them
172
173    params.set(CameraParameters::KEY_PREVIEW_FRAME_RATE,
174            previewFpsRange[0] * kFpsToApiScale);
175
176    {
177        String8 supportedPreviewFrameRates;
178        for (size_t i=0; i < availableFpsRanges.count; i += 2) {
179            if (i != 0) supportedPreviewFrameRates += ",";
180            supportedPreviewFrameRates += String8::format("%d",
181                    availableFpsRanges.data.i32[i] * kFpsToApiScale);
182        }
183        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES,
184                supportedPreviewFrameRates);
185    }
186
187    camera_metadata_ro_entry_t availableJpegSizes =
188        staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES, 2);
189    if (!availableJpegSizes.count) return NO_INIT;
190
191    // TODO: Pick maximum
192    pictureWidth = availableJpegSizes.data.i32[0];
193    pictureHeight = availableJpegSizes.data.i32[1];
194
195    params.setPictureSize(pictureWidth,
196            pictureHeight);
197
198    {
199        String8 supportedPictureSizes;
200        for (size_t i=0; i < availableJpegSizes.count; i += 2) {
201            if (i != 0) supportedPictureSizes += ",";
202            supportedPictureSizes += String8::format("%dx%d",
203                    availableJpegSizes.data.i32[i],
204                    availableJpegSizes.data.i32[i+1]);
205        }
206        params.set(CameraParameters::KEY_SUPPORTED_PICTURE_SIZES,
207                supportedPictureSizes);
208    }
209
210    params.setPictureFormat(CameraParameters::PIXEL_FORMAT_JPEG);
211    params.set(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS,
212            CameraParameters::PIXEL_FORMAT_JPEG);
213
214    camera_metadata_ro_entry_t availableJpegThumbnailSizes =
215        staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES, 4);
216    if (!availableJpegThumbnailSizes.count) return NO_INIT;
217
218    // TODO: Pick default thumbnail size sensibly
219    jpegThumbSize[0] = availableJpegThumbnailSizes.data.i32[0];
220    jpegThumbSize[1] = availableJpegThumbnailSizes.data.i32[1];
221
222    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH,
223            jpegThumbSize[0]);
224    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT,
225            jpegThumbSize[1]);
226
227    {
228        String8 supportedJpegThumbSizes;
229        for (size_t i=0; i < availableJpegThumbnailSizes.count; i += 2) {
230            if (i != 0) supportedJpegThumbSizes += ",";
231            supportedJpegThumbSizes += String8::format("%dx%d",
232                    availableJpegThumbnailSizes.data.i32[i],
233                    availableJpegThumbnailSizes.data.i32[i+1]);
234        }
235        params.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES,
236                supportedJpegThumbSizes);
237    }
238
239    jpegThumbQuality = 90;
240    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY,
241            jpegThumbQuality);
242    jpegQuality = 90;
243    params.set(CameraParameters::KEY_JPEG_QUALITY,
244            jpegQuality);
245    jpegRotation = 0;
246    params.set(CameraParameters::KEY_ROTATION,
247            jpegRotation);
248
249    gpsEnabled = false;
250    gpsProcessingMethod = "unknown";
251    // GPS fields in CameraParameters are not set by implementation
252
253    wbMode = ANDROID_CONTROL_AWB_AUTO;
254    params.set(CameraParameters::KEY_WHITE_BALANCE,
255            CameraParameters::WHITE_BALANCE_AUTO);
256
257    camera_metadata_ro_entry_t availableWhiteBalanceModes =
258        staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
259    {
260        String8 supportedWhiteBalance;
261        bool addComma = false;
262        for (size_t i=0; i < availableWhiteBalanceModes.count; i++) {
263            if (addComma) supportedWhiteBalance += ",";
264            addComma = true;
265            switch (availableWhiteBalanceModes.data.u8[i]) {
266            case ANDROID_CONTROL_AWB_AUTO:
267                supportedWhiteBalance +=
268                    CameraParameters::WHITE_BALANCE_AUTO;
269                break;
270            case ANDROID_CONTROL_AWB_INCANDESCENT:
271                supportedWhiteBalance +=
272                    CameraParameters::WHITE_BALANCE_INCANDESCENT;
273                break;
274            case ANDROID_CONTROL_AWB_FLUORESCENT:
275                supportedWhiteBalance +=
276                    CameraParameters::WHITE_BALANCE_FLUORESCENT;
277                break;
278            case ANDROID_CONTROL_AWB_WARM_FLUORESCENT:
279                supportedWhiteBalance +=
280                    CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT;
281                break;
282            case ANDROID_CONTROL_AWB_DAYLIGHT:
283                supportedWhiteBalance +=
284                    CameraParameters::WHITE_BALANCE_DAYLIGHT;
285                break;
286            case ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT:
287                supportedWhiteBalance +=
288                    CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT;
289                break;
290            case ANDROID_CONTROL_AWB_TWILIGHT:
291                supportedWhiteBalance +=
292                    CameraParameters::WHITE_BALANCE_TWILIGHT;
293                break;
294            case ANDROID_CONTROL_AWB_SHADE:
295                supportedWhiteBalance +=
296                    CameraParameters::WHITE_BALANCE_SHADE;
297                break;
298            // Skipping values not mappable to v1 API
299            case ANDROID_CONTROL_AWB_OFF:
300                addComma = false;
301                break;
302            default:
303                ALOGW("%s: Camera %d: Unknown white balance value: %d",
304                        __FUNCTION__, cameraId,
305                        availableWhiteBalanceModes.data.u8[i]);
306                addComma = false;
307                break;
308            }
309        }
310        params.set(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE,
311                supportedWhiteBalance);
312    }
313
314    effectMode = ANDROID_CONTROL_EFFECT_OFF;
315    params.set(CameraParameters::KEY_EFFECT,
316            CameraParameters::EFFECT_NONE);
317
318    camera_metadata_ro_entry_t availableEffects =
319        staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
320    if (!availableEffects.count) return NO_INIT;
321    {
322        String8 supportedEffects;
323        bool addComma = false;
324        for (size_t i=0; i < availableEffects.count; i++) {
325            if (addComma) supportedEffects += ",";
326            addComma = true;
327            switch (availableEffects.data.u8[i]) {
328                case ANDROID_CONTROL_EFFECT_OFF:
329                    supportedEffects +=
330                        CameraParameters::EFFECT_NONE;
331                    break;
332                case ANDROID_CONTROL_EFFECT_MONO:
333                    supportedEffects +=
334                        CameraParameters::EFFECT_MONO;
335                    break;
336                case ANDROID_CONTROL_EFFECT_NEGATIVE:
337                    supportedEffects +=
338                        CameraParameters::EFFECT_NEGATIVE;
339                    break;
340                case ANDROID_CONTROL_EFFECT_SOLARIZE:
341                    supportedEffects +=
342                        CameraParameters::EFFECT_SOLARIZE;
343                    break;
344                case ANDROID_CONTROL_EFFECT_SEPIA:
345                    supportedEffects +=
346                        CameraParameters::EFFECT_SEPIA;
347                    break;
348                case ANDROID_CONTROL_EFFECT_POSTERIZE:
349                    supportedEffects +=
350                        CameraParameters::EFFECT_POSTERIZE;
351                    break;
352                case ANDROID_CONTROL_EFFECT_WHITEBOARD:
353                    supportedEffects +=
354                        CameraParameters::EFFECT_WHITEBOARD;
355                    break;
356                case ANDROID_CONTROL_EFFECT_BLACKBOARD:
357                    supportedEffects +=
358                        CameraParameters::EFFECT_BLACKBOARD;
359                    break;
360                case ANDROID_CONTROL_EFFECT_AQUA:
361                    supportedEffects +=
362                        CameraParameters::EFFECT_AQUA;
363                    break;
364                default:
365                    ALOGW("%s: Camera %d: Unknown effect value: %d",
366                        __FUNCTION__, cameraId, availableEffects.data.u8[i]);
367                    addComma = false;
368                    break;
369            }
370        }
371        params.set(CameraParameters::KEY_SUPPORTED_EFFECTS, supportedEffects);
372    }
373
374    antibandingMode = ANDROID_CONTROL_AE_ANTIBANDING_AUTO;
375    params.set(CameraParameters::KEY_ANTIBANDING,
376            CameraParameters::ANTIBANDING_AUTO);
377
378    camera_metadata_ro_entry_t availableAntibandingModes =
379        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
380    if (!availableAntibandingModes.count) return NO_INIT;
381    {
382        String8 supportedAntibanding;
383        bool addComma = false;
384        for (size_t i=0; i < availableAntibandingModes.count; i++) {
385            if (addComma) supportedAntibanding += ",";
386            addComma = true;
387            switch (availableAntibandingModes.data.u8[i]) {
388                case ANDROID_CONTROL_AE_ANTIBANDING_OFF:
389                    supportedAntibanding +=
390                        CameraParameters::ANTIBANDING_OFF;
391                    break;
392                case ANDROID_CONTROL_AE_ANTIBANDING_50HZ:
393                    supportedAntibanding +=
394                        CameraParameters::ANTIBANDING_50HZ;
395                    break;
396                case ANDROID_CONTROL_AE_ANTIBANDING_60HZ:
397                    supportedAntibanding +=
398                        CameraParameters::ANTIBANDING_60HZ;
399                    break;
400                case ANDROID_CONTROL_AE_ANTIBANDING_AUTO:
401                    supportedAntibanding +=
402                        CameraParameters::ANTIBANDING_AUTO;
403                    break;
404                default:
405                    ALOGW("%s: Camera %d: Unknown antibanding value: %d",
406                        __FUNCTION__, cameraId,
407                            availableAntibandingModes.data.u8[i]);
408                    addComma = false;
409                    break;
410            }
411        }
412        params.set(CameraParameters::KEY_SUPPORTED_ANTIBANDING,
413                supportedAntibanding);
414    }
415
416    sceneMode = ANDROID_CONTROL_OFF;
417    params.set(CameraParameters::KEY_SCENE_MODE,
418            CameraParameters::SCENE_MODE_AUTO);
419
420    camera_metadata_ro_entry_t availableSceneModes =
421        staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
422    if (!availableSceneModes.count) return NO_INIT;
423    {
424        String8 supportedSceneModes(CameraParameters::SCENE_MODE_AUTO);
425        bool addComma = true;
426        bool noSceneModes = false;
427        for (size_t i=0; i < availableSceneModes.count; i++) {
428            if (addComma) supportedSceneModes += ",";
429            addComma = true;
430            switch (availableSceneModes.data.u8[i]) {
431                case ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED:
432                    noSceneModes = true;
433                    break;
434                case ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY:
435                    // Not in old API
436                    addComma = false;
437                    break;
438                case ANDROID_CONTROL_SCENE_MODE_ACTION:
439                    supportedSceneModes +=
440                        CameraParameters::SCENE_MODE_ACTION;
441                    break;
442                case ANDROID_CONTROL_SCENE_MODE_PORTRAIT:
443                    supportedSceneModes +=
444                        CameraParameters::SCENE_MODE_PORTRAIT;
445                    break;
446                case ANDROID_CONTROL_SCENE_MODE_LANDSCAPE:
447                    supportedSceneModes +=
448                        CameraParameters::SCENE_MODE_LANDSCAPE;
449                    break;
450                case ANDROID_CONTROL_SCENE_MODE_NIGHT:
451                    supportedSceneModes +=
452                        CameraParameters::SCENE_MODE_NIGHT;
453                    break;
454                case ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT:
455                    supportedSceneModes +=
456                        CameraParameters::SCENE_MODE_NIGHT_PORTRAIT;
457                    break;
458                case ANDROID_CONTROL_SCENE_MODE_THEATRE:
459                    supportedSceneModes +=
460                        CameraParameters::SCENE_MODE_THEATRE;
461                    break;
462                case ANDROID_CONTROL_SCENE_MODE_BEACH:
463                    supportedSceneModes +=
464                        CameraParameters::SCENE_MODE_BEACH;
465                    break;
466                case ANDROID_CONTROL_SCENE_MODE_SNOW:
467                    supportedSceneModes +=
468                        CameraParameters::SCENE_MODE_SNOW;
469                    break;
470                case ANDROID_CONTROL_SCENE_MODE_SUNSET:
471                    supportedSceneModes +=
472                        CameraParameters::SCENE_MODE_SUNSET;
473                    break;
474                case ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO:
475                    supportedSceneModes +=
476                        CameraParameters::SCENE_MODE_STEADYPHOTO;
477                    break;
478                case ANDROID_CONTROL_SCENE_MODE_FIREWORKS:
479                    supportedSceneModes +=
480                        CameraParameters::SCENE_MODE_FIREWORKS;
481                    break;
482                case ANDROID_CONTROL_SCENE_MODE_SPORTS:
483                    supportedSceneModes +=
484                        CameraParameters::SCENE_MODE_SPORTS;
485                    break;
486                case ANDROID_CONTROL_SCENE_MODE_PARTY:
487                    supportedSceneModes +=
488                        CameraParameters::SCENE_MODE_PARTY;
489                    break;
490                case ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT:
491                    supportedSceneModes +=
492                        CameraParameters::SCENE_MODE_CANDLELIGHT;
493                    break;
494                case ANDROID_CONTROL_SCENE_MODE_BARCODE:
495                    supportedSceneModes +=
496                        CameraParameters::SCENE_MODE_BARCODE;
497                    break;
498                default:
499                    ALOGW("%s: Camera %d: Unknown scene mode value: %d",
500                        __FUNCTION__, cameraId,
501                            availableSceneModes.data.u8[i]);
502                    addComma = false;
503                    break;
504            }
505        }
506        if (!noSceneModes) {
507            params.set(CameraParameters::KEY_SUPPORTED_SCENE_MODES,
508                    supportedSceneModes);
509        }
510    }
511
512    camera_metadata_ro_entry_t flashAvailable =
513        staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
514    if (!flashAvailable.count) return NO_INIT;
515
516    camera_metadata_ro_entry_t availableAeModes =
517        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
518    if (!availableAeModes.count) return NO_INIT;
519
520    if (flashAvailable.data.u8[0]) {
521        flashMode = Parameters::FLASH_MODE_AUTO;
522        params.set(CameraParameters::KEY_FLASH_MODE,
523                CameraParameters::FLASH_MODE_AUTO);
524
525        String8 supportedFlashModes(CameraParameters::FLASH_MODE_OFF);
526        supportedFlashModes = supportedFlashModes +
527            "," + CameraParameters::FLASH_MODE_AUTO +
528            "," + CameraParameters::FLASH_MODE_ON +
529            "," + CameraParameters::FLASH_MODE_TORCH;
530        for (size_t i=0; i < availableAeModes.count; i++) {
531            if (availableAeModes.data.u8[i] ==
532                    ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE) {
533                supportedFlashModes = supportedFlashModes + "," +
534                    CameraParameters::FLASH_MODE_RED_EYE;
535                break;
536            }
537        }
538        params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
539                supportedFlashModes);
540    } else {
541        flashMode = Parameters::FLASH_MODE_OFF;
542        params.set(CameraParameters::KEY_FLASH_MODE,
543                CameraParameters::FLASH_MODE_OFF);
544        params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
545                CameraParameters::FLASH_MODE_OFF);
546    }
547
548    camera_metadata_ro_entry_t minFocusDistance =
549        staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE, 1, 1);
550    if (!minFocusDistance.count) return NO_INIT;
551
552    camera_metadata_ro_entry_t availableAfModes =
553        staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
554    if (!availableAfModes.count) return NO_INIT;
555
556    if (minFocusDistance.data.f[0] == 0) {
557        // Fixed-focus lens
558        focusMode = Parameters::FOCUS_MODE_FIXED;
559        params.set(CameraParameters::KEY_FOCUS_MODE,
560                CameraParameters::FOCUS_MODE_FIXED);
561        params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
562                CameraParameters::FOCUS_MODE_FIXED);
563    } else {
564        focusMode = Parameters::FOCUS_MODE_AUTO;
565        params.set(CameraParameters::KEY_FOCUS_MODE,
566                CameraParameters::FOCUS_MODE_AUTO);
567        String8 supportedFocusModes(CameraParameters::FOCUS_MODE_INFINITY);
568        bool addComma = true;
569
570        for (size_t i=0; i < availableAfModes.count; i++) {
571            if (addComma) supportedFocusModes += ",";
572            addComma = true;
573            switch (availableAfModes.data.u8[i]) {
574                case ANDROID_CONTROL_AF_AUTO:
575                    supportedFocusModes +=
576                        CameraParameters::FOCUS_MODE_AUTO;
577                    break;
578                case ANDROID_CONTROL_AF_MACRO:
579                    supportedFocusModes +=
580                        CameraParameters::FOCUS_MODE_MACRO;
581                    break;
582                case ANDROID_CONTROL_AF_CONTINUOUS_VIDEO:
583                    supportedFocusModes +=
584                        CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO;
585                    break;
586                case ANDROID_CONTROL_AF_CONTINUOUS_PICTURE:
587                    supportedFocusModes +=
588                        CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE;
589                    break;
590                case ANDROID_CONTROL_AF_EDOF:
591                    supportedFocusModes +=
592                        CameraParameters::FOCUS_MODE_EDOF;
593                    break;
594                // Not supported in old API
595                case ANDROID_CONTROL_AF_OFF:
596                    addComma = false;
597                    break;
598                default:
599                    ALOGW("%s: Camera %d: Unknown AF mode value: %d",
600                        __FUNCTION__, cameraId, availableAfModes.data.u8[i]);
601                    addComma = false;
602                    break;
603            }
604        }
605        params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
606                supportedFocusModes);
607    }
608
609    camera_metadata_ro_entry_t max3aRegions =
610        staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1);
611    if (!max3aRegions.count) return NO_INIT;
612
613    params.set(CameraParameters::KEY_MAX_NUM_FOCUS_AREAS,
614            max3aRegions.data.i32[0]);
615    params.set(CameraParameters::KEY_FOCUS_AREAS,
616            "(0,0,0,0,0)");
617    focusingAreas.clear();
618    focusingAreas.add(Parameters::Area(0,0,0,0,0));
619
620    camera_metadata_ro_entry_t availableFocalLengths =
621        staticInfo(ANDROID_LENS_AVAILABLE_FOCAL_LENGTHS);
622    if (!availableFocalLengths.count) return NO_INIT;
623
624    float minFocalLength = availableFocalLengths.data.f[0];
625    params.setFloat(CameraParameters::KEY_FOCAL_LENGTH, minFocalLength);
626
627    camera_metadata_ro_entry_t sensorSize =
628        staticInfo(ANDROID_SENSOR_PHYSICAL_SIZE, 2, 2);
629    if (!sensorSize.count) return NO_INIT;
630
631    // The fields of view here assume infinity focus, maximum wide angle
632    float horizFov = 180 / M_PI *
633            2 * atanf(sensorSize.data.f[0] / (2 * minFocalLength));
634    float vertFov  = 180 / M_PI *
635            2 * atanf(sensorSize.data.f[1] / (2 * minFocalLength));
636    params.setFloat(CameraParameters::KEY_HORIZONTAL_VIEW_ANGLE, horizFov);
637    params.setFloat(CameraParameters::KEY_VERTICAL_VIEW_ANGLE, vertFov);
638
639    exposureCompensation = 0;
640    params.set(CameraParameters::KEY_EXPOSURE_COMPENSATION,
641                exposureCompensation);
642
643    camera_metadata_ro_entry_t exposureCompensationRange =
644        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE, 2, 2);
645    if (!exposureCompensationRange.count) return NO_INIT;
646
647    params.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION,
648            exposureCompensationRange.data.i32[1]);
649    params.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION,
650            exposureCompensationRange.data.i32[0]);
651
652    camera_metadata_ro_entry_t exposureCompensationStep =
653        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_STEP, 1, 1);
654    if (!exposureCompensationStep.count) return NO_INIT;
655
656    params.setFloat(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP,
657            (float)exposureCompensationStep.data.r[0].numerator /
658            exposureCompensationStep.data.r[0].denominator);
659
660    autoExposureLock = false;
661    params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK,
662            CameraParameters::FALSE);
663    params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK_SUPPORTED,
664            CameraParameters::TRUE);
665
666    autoWhiteBalanceLock = false;
667    params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK,
668            CameraParameters::FALSE);
669    params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK_SUPPORTED,
670            CameraParameters::TRUE);
671
672    meteringAreas.add(Parameters::Area(0, 0, 0, 0, 0));
673    params.set(CameraParameters::KEY_MAX_NUM_METERING_AREAS,
674            max3aRegions.data.i32[0]);
675    params.set(CameraParameters::KEY_METERING_AREAS,
676            "(0,0,0,0,0)");
677
678    zoom = 0;
679    params.set(CameraParameters::KEY_ZOOM, zoom);
680    params.set(CameraParameters::KEY_MAX_ZOOM, NUM_ZOOM_STEPS - 1);
681
682    camera_metadata_ro_entry_t maxDigitalZoom =
683        staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM, /*minCount*/1, /*maxCount*/1);
684    if (!maxDigitalZoom.count) return NO_INIT;
685
686    {
687        String8 zoomRatios;
688        float zoom = 1.f;
689        float zoomIncrement = (maxDigitalZoom.data.f[0] - zoom) /
690                (NUM_ZOOM_STEPS-1);
691        bool addComma = false;
692        for (size_t i=0; i < NUM_ZOOM_STEPS; i++) {
693            if (addComma) zoomRatios += ",";
694            addComma = true;
695            zoomRatios += String8::format("%d", static_cast<int>(zoom * 100));
696            zoom += zoomIncrement;
697        }
698        params.set(CameraParameters::KEY_ZOOM_RATIOS, zoomRatios);
699    }
700
701    params.set(CameraParameters::KEY_ZOOM_SUPPORTED,
702            CameraParameters::TRUE);
703    params.set(CameraParameters::KEY_SMOOTH_ZOOM_SUPPORTED,
704            CameraParameters::TRUE);
705
706    params.set(CameraParameters::KEY_FOCUS_DISTANCES,
707            "Infinity,Infinity,Infinity");
708
709    params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_HW,
710            fastInfo.maxFaces);
711    params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_SW,
712            0);
713
714    params.set(CameraParameters::KEY_VIDEO_FRAME_FORMAT,
715            CameraParameters::PIXEL_FORMAT_ANDROID_OPAQUE);
716
717    params.set(CameraParameters::KEY_RECORDING_HINT,
718            CameraParameters::FALSE);
719
720    params.set(CameraParameters::KEY_VIDEO_SNAPSHOT_SUPPORTED,
721            CameraParameters::TRUE);
722
723    params.set(CameraParameters::KEY_VIDEO_STABILIZATION,
724            CameraParameters::FALSE);
725
726    camera_metadata_ro_entry_t availableVideoStabilizationModes =
727        staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
728    if (!availableVideoStabilizationModes.count) return NO_INIT;
729
730    if (availableVideoStabilizationModes.count > 1) {
731        params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
732                CameraParameters::TRUE);
733    } else {
734        params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
735                CameraParameters::FALSE);
736    }
737
738    // Set up initial state for non-Camera.Parameters state variables
739
740    storeMetadataInBuffers = true;
741    playShutterSound = true;
742    enableFaceDetect = false;
743
744    enableFocusMoveMessages = false;
745    afTriggerCounter = 1;
746    currentAfTriggerId = -1;
747
748    precaptureTriggerCounter = 1;
749
750    previewCallbackFlags = 0;
751
752    char value[PROPERTY_VALUE_MAX];
753    property_get("camera.disable_zsl_mode", value, "0");
754    if (!strcmp(value,"1")) {
755        ALOGI("Camera %d: Disabling ZSL mode", cameraId);
756        zslMode = false;
757    } else {
758        zslMode = true;
759    }
760
761    lightFx = LIGHTFX_NONE;
762
763    state = STOPPED;
764
765    paramsFlattened = params.flatten();
766
767    return OK;
768}
769
770status_t Parameters::buildFastInfo() {
771
772    camera_metadata_ro_entry_t activeArraySize =
773        staticInfo(ANDROID_SENSOR_ACTIVE_ARRAY_SIZE, 2, 2);
774    if (!activeArraySize.count) return NO_INIT;
775    int32_t arrayWidth = activeArraySize.data.i32[0];
776    int32_t arrayHeight = activeArraySize.data.i32[1];
777
778    camera_metadata_ro_entry_t availableFaceDetectModes =
779        staticInfo(ANDROID_STATS_AVAILABLE_FACE_DETECT_MODES);
780    if (!availableFaceDetectModes.count) return NO_INIT;
781
782    uint8_t bestFaceDetectMode =
783        ANDROID_STATS_FACE_DETECTION_OFF;
784    for (size_t i = 0 ; i < availableFaceDetectModes.count; i++) {
785        switch (availableFaceDetectModes.data.u8[i]) {
786            case ANDROID_STATS_FACE_DETECTION_OFF:
787                break;
788            case ANDROID_STATS_FACE_DETECTION_SIMPLE:
789                if (bestFaceDetectMode !=
790                        ANDROID_STATS_FACE_DETECTION_FULL) {
791                    bestFaceDetectMode =
792                        ANDROID_STATS_FACE_DETECTION_SIMPLE;
793                }
794                break;
795            case ANDROID_STATS_FACE_DETECTION_FULL:
796                bestFaceDetectMode =
797                    ANDROID_STATS_FACE_DETECTION_FULL;
798                break;
799            default:
800                ALOGE("%s: Camera %d: Unknown face detect mode %d:",
801                        __FUNCTION__, cameraId,
802                        availableFaceDetectModes.data.u8[i]);
803                return NO_INIT;
804        }
805    }
806
807    camera_metadata_ro_entry_t maxFacesDetected =
808        staticInfo(ANDROID_STATS_MAX_FACE_COUNT, 1, 1);
809    if (!maxFacesDetected.count) return NO_INIT;
810
811    int32_t maxFaces = maxFacesDetected.data.i32[0];
812
813    fastInfo.arrayWidth = arrayWidth;
814    fastInfo.arrayHeight = arrayHeight;
815    fastInfo.bestFaceDetectMode = bestFaceDetectMode;
816    fastInfo.maxFaces = maxFaces;
817    return OK;
818}
819
820camera_metadata_ro_entry_t Parameters::staticInfo(uint32_t tag,
821        size_t minCount, size_t maxCount) const {
822    status_t res;
823    camera_metadata_ro_entry_t entry = info->find(tag);
824
825    if (CC_UNLIKELY( entry.count == 0 )) {
826        const char* tagSection = get_camera_metadata_section_name(tag);
827        if (tagSection == NULL) tagSection = "<unknown>";
828        const char* tagName = get_camera_metadata_tag_name(tag);
829        if (tagName == NULL) tagName = "<unknown>";
830
831        ALOGE("Error finding static metadata entry '%s.%s' (%x)",
832                tagSection, tagName, tag);
833    } else if (CC_UNLIKELY(
834            (minCount != 0 && entry.count < minCount) ||
835            (maxCount != 0 && entry.count > maxCount) ) ) {
836        const char* tagSection = get_camera_metadata_section_name(tag);
837        if (tagSection == NULL) tagSection = "<unknown>";
838        const char* tagName = get_camera_metadata_tag_name(tag);
839        if (tagName == NULL) tagName = "<unknown>";
840        ALOGE("Malformed static metadata entry '%s.%s' (%x):"
841                "Expected between %d and %d values, but got %d values",
842                tagSection, tagName, tag, minCount, maxCount, entry.count);
843    }
844
845    return entry;
846}
847
848status_t Parameters::set(const String8& params) {
849    status_t res;
850
851    CameraParameters newParams(params);
852
853    // TODO: Currently ignoring any changes to supposedly read-only parameters
854    // such as supported preview sizes, etc. Should probably produce an error if
855    // they're changed.
856
857    /** Extract and verify new parameters */
858
859    size_t i;
860
861    Parameters validatedParams(*this);
862
863    // PREVIEW_SIZE
864    newParams.getPreviewSize(&validatedParams.previewWidth,
865            &validatedParams.previewHeight);
866
867    if (validatedParams.previewWidth != previewWidth ||
868            validatedParams.previewHeight != previewHeight) {
869        if (state >= PREVIEW) {
870            ALOGE("%s: Preview size cannot be updated when preview "
871                    "is active! (Currently %d x %d, requested %d x %d",
872                    __FUNCTION__,
873                    previewWidth, previewHeight,
874                    validatedParams.previewWidth, validatedParams.previewHeight);
875            return BAD_VALUE;
876        }
877        camera_metadata_ro_entry_t availablePreviewSizes =
878            staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
879        for (i = 0; i < availablePreviewSizes.count; i += 2 ) {
880            if ((availablePreviewSizes.data.i32[i] ==
881                    validatedParams.previewWidth) &&
882                (availablePreviewSizes.data.i32[i+1] ==
883                    validatedParams.previewHeight)) break;
884        }
885        if (i == availablePreviewSizes.count) {
886            ALOGE("%s: Requested preview size %d x %d is not supported",
887                    __FUNCTION__, validatedParams.previewWidth,
888                    validatedParams.previewHeight);
889            return BAD_VALUE;
890        }
891    }
892
893    // PREVIEW_FPS_RANGE
894    bool fpsRangeChanged = false;
895    newParams.getPreviewFpsRange(&validatedParams.previewFpsRange[0],
896            &validatedParams.previewFpsRange[1]);
897    validatedParams.previewFpsRange[0] /= kFpsToApiScale;
898    validatedParams.previewFpsRange[1] /= kFpsToApiScale;
899
900    if (validatedParams.previewFpsRange[0] != previewFpsRange[0] ||
901            validatedParams.previewFpsRange[1] != previewFpsRange[1]) {
902        fpsRangeChanged = true;
903        camera_metadata_ro_entry_t availablePreviewFpsRanges =
904            staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
905        for (i = 0; i < availablePreviewFpsRanges.count; i += 2) {
906            if ((availablePreviewFpsRanges.data.i32[i] ==
907                    validatedParams.previewFpsRange[0]) &&
908                (availablePreviewFpsRanges.data.i32[i+1] ==
909                    validatedParams.previewFpsRange[1]) ) {
910                break;
911            }
912        }
913        if (i == availablePreviewFpsRanges.count) {
914            ALOGE("%s: Requested preview FPS range %d - %d is not supported",
915                __FUNCTION__, validatedParams.previewFpsRange[0],
916                    validatedParams.previewFpsRange[1]);
917            return BAD_VALUE;
918        }
919        validatedParams.previewFps = validatedParams.previewFpsRange[0];
920    }
921
922    // PREVIEW_FORMAT
923    validatedParams.previewFormat =
924            formatStringToEnum(newParams.getPreviewFormat());
925    if (validatedParams.previewFormat != previewFormat) {
926        if (state >= PREVIEW) {
927            ALOGE("%s: Preview format cannot be updated when preview "
928                    "is active!", __FUNCTION__);
929            return BAD_VALUE;
930        }
931        camera_metadata_ro_entry_t availableFormats =
932            staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
933        for (i = 0; i < availableFormats.count; i++) {
934            if (availableFormats.data.i32[i] == validatedParams.previewFormat)
935                break;
936        }
937        if (i == availableFormats.count) {
938            ALOGE("%s: Requested preview format %s (0x%x) is not supported",
939                    __FUNCTION__, newParams.getPreviewFormat(),
940                    validatedParams.previewFormat);
941            return BAD_VALUE;
942        }
943    }
944
945    // PREVIEW_FRAME_RATE
946    // Deprecated, only use if the preview fps range is unchanged this time.
947    // The single-value FPS is the same as the minimum of the range.
948    if (!fpsRangeChanged) {
949        validatedParams.previewFps = newParams.getPreviewFrameRate() / kFpsToApiScale;
950        if (validatedParams.previewFps != previewFps) {
951            camera_metadata_ro_entry_t availableFrameRates =
952                staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES);
953            for (i = 0; i < availableFrameRates.count; i+=2) {
954                if (availableFrameRates.data.i32[i] ==
955                        validatedParams.previewFps) break;
956            }
957            if (i == availableFrameRates.count) {
958                ALOGE("%s: Requested preview frame rate %d is not supported",
959                        __FUNCTION__, validatedParams.previewFps);
960                return BAD_VALUE;
961            }
962            validatedParams.previewFpsRange[0] =
963                    availableFrameRates.data.i32[i];
964            validatedParams.previewFpsRange[1] =
965                    availableFrameRates.data.i32[i+1];
966        }
967    }
968
969    // PICTURE_SIZE
970    newParams.getPictureSize(&validatedParams.pictureWidth,
971            &validatedParams.pictureHeight);
972    if (validatedParams.pictureWidth == pictureWidth ||
973            validatedParams.pictureHeight == pictureHeight) {
974        camera_metadata_ro_entry_t availablePictureSizes =
975            staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES);
976        for (i = 0; i < availablePictureSizes.count; i+=2) {
977            if ((availablePictureSizes.data.i32[i] ==
978                    validatedParams.pictureWidth) &&
979                (availablePictureSizes.data.i32[i+1] ==
980                    validatedParams.pictureHeight)) break;
981        }
982        if (i == availablePictureSizes.count) {
983            ALOGE("%s: Requested picture size %d x %d is not supported",
984                    __FUNCTION__, validatedParams.pictureWidth,
985                    validatedParams.pictureHeight);
986            return BAD_VALUE;
987        }
988    }
989
990    // JPEG_THUMBNAIL_WIDTH/HEIGHT
991    validatedParams.jpegThumbSize[0] =
992            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH);
993    validatedParams.jpegThumbSize[1] =
994            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT);
995    if (validatedParams.jpegThumbSize[0] != jpegThumbSize[0] ||
996            validatedParams.jpegThumbSize[1] != jpegThumbSize[1]) {
997        camera_metadata_ro_entry_t availableJpegThumbSizes =
998            staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES);
999        for (i = 0; i < availableJpegThumbSizes.count; i+=2) {
1000            if ((availableJpegThumbSizes.data.i32[i] ==
1001                    validatedParams.jpegThumbSize[0]) &&
1002                (availableJpegThumbSizes.data.i32[i+1] ==
1003                    validatedParams.jpegThumbSize[1])) break;
1004        }
1005        if (i == availableJpegThumbSizes.count) {
1006            ALOGE("%s: Requested JPEG thumbnail size %d x %d is not supported",
1007                    __FUNCTION__, validatedParams.jpegThumbSize[0],
1008                    validatedParams.jpegThumbSize[1]);
1009            return BAD_VALUE;
1010        }
1011    }
1012
1013    // JPEG_THUMBNAIL_QUALITY
1014    validatedParams.jpegThumbQuality =
1015            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY);
1016    if (validatedParams.jpegThumbQuality < 0 ||
1017            validatedParams.jpegThumbQuality > 100) {
1018        ALOGE("%s: Requested JPEG thumbnail quality %d is not supported",
1019                __FUNCTION__, validatedParams.jpegThumbQuality);
1020        return BAD_VALUE;
1021    }
1022
1023    // JPEG_QUALITY
1024    validatedParams.jpegQuality =
1025            newParams.getInt(CameraParameters::KEY_JPEG_QUALITY);
1026    if (validatedParams.jpegQuality < 0 || validatedParams.jpegQuality > 100) {
1027        ALOGE("%s: Requested JPEG quality %d is not supported",
1028                __FUNCTION__, validatedParams.jpegQuality);
1029        return BAD_VALUE;
1030    }
1031
1032    // ROTATION
1033    validatedParams.jpegRotation =
1034            newParams.getInt(CameraParameters::KEY_ROTATION);
1035    if (validatedParams.jpegRotation != 0 &&
1036            validatedParams.jpegRotation != 90 &&
1037            validatedParams.jpegRotation != 180 &&
1038            validatedParams.jpegRotation != 270) {
1039        ALOGE("%s: Requested picture rotation angle %d is not supported",
1040                __FUNCTION__, validatedParams.jpegRotation);
1041        return BAD_VALUE;
1042    }
1043
1044    // GPS
1045
1046    const char *gpsLatStr =
1047            newParams.get(CameraParameters::KEY_GPS_LATITUDE);
1048    if (gpsLatStr != NULL) {
1049        const char *gpsLongStr =
1050                newParams.get(CameraParameters::KEY_GPS_LONGITUDE);
1051        const char *gpsAltitudeStr =
1052                newParams.get(CameraParameters::KEY_GPS_ALTITUDE);
1053        const char *gpsTimeStr =
1054                newParams.get(CameraParameters::KEY_GPS_TIMESTAMP);
1055        const char *gpsProcMethodStr =
1056                newParams.get(CameraParameters::KEY_GPS_PROCESSING_METHOD);
1057        if (gpsLongStr == NULL ||
1058                gpsAltitudeStr == NULL ||
1059                gpsTimeStr == NULL ||
1060                gpsProcMethodStr == NULL) {
1061            ALOGE("%s: Incomplete set of GPS parameters provided",
1062                    __FUNCTION__);
1063            return BAD_VALUE;
1064        }
1065        char *endPtr;
1066        errno = 0;
1067        validatedParams.gpsCoordinates[0] = strtod(gpsLatStr, &endPtr);
1068        if (errno || endPtr == gpsLatStr) {
1069            ALOGE("%s: Malformed GPS latitude: %s", __FUNCTION__, gpsLatStr);
1070            return BAD_VALUE;
1071        }
1072        errno = 0;
1073        validatedParams.gpsCoordinates[1] = strtod(gpsLongStr, &endPtr);
1074        if (errno || endPtr == gpsLongStr) {
1075            ALOGE("%s: Malformed GPS longitude: %s", __FUNCTION__, gpsLongStr);
1076            return BAD_VALUE;
1077        }
1078        errno = 0;
1079        validatedParams.gpsCoordinates[2] = strtod(gpsAltitudeStr, &endPtr);
1080        if (errno || endPtr == gpsAltitudeStr) {
1081            ALOGE("%s: Malformed GPS altitude: %s", __FUNCTION__,
1082                    gpsAltitudeStr);
1083            return BAD_VALUE;
1084        }
1085        errno = 0;
1086        validatedParams.gpsTimestamp = strtoll(gpsTimeStr, &endPtr, 10);
1087        if (errno || endPtr == gpsTimeStr) {
1088            ALOGE("%s: Malformed GPS timestamp: %s", __FUNCTION__, gpsTimeStr);
1089            return BAD_VALUE;
1090        }
1091        validatedParams.gpsProcessingMethod = gpsProcMethodStr;
1092
1093        validatedParams.gpsEnabled = true;
1094    } else {
1095        validatedParams.gpsEnabled = false;
1096    }
1097
1098    // WHITE_BALANCE
1099    validatedParams.wbMode = wbModeStringToEnum(
1100        newParams.get(CameraParameters::KEY_WHITE_BALANCE) );
1101    if (validatedParams.wbMode != wbMode) {
1102        camera_metadata_ro_entry_t availableWbModes =
1103            staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
1104        for (i = 0; i < availableWbModes.count; i++) {
1105            if (validatedParams.wbMode == availableWbModes.data.u8[i]) break;
1106        }
1107        if (i == availableWbModes.count) {
1108            ALOGE("%s: Requested white balance mode %s is not supported",
1109                    __FUNCTION__,
1110                    newParams.get(CameraParameters::KEY_WHITE_BALANCE));
1111            return BAD_VALUE;
1112        }
1113    }
1114
1115    // EFFECT
1116    validatedParams.effectMode = effectModeStringToEnum(
1117        newParams.get(CameraParameters::KEY_EFFECT) );
1118    if (validatedParams.effectMode != effectMode) {
1119        camera_metadata_ro_entry_t availableEffectModes =
1120            staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
1121        for (i = 0; i < availableEffectModes.count; i++) {
1122            if (validatedParams.effectMode == availableEffectModes.data.u8[i]) break;
1123        }
1124        if (i == availableEffectModes.count) {
1125            ALOGE("%s: Requested effect mode \"%s\" is not supported",
1126                    __FUNCTION__,
1127                    newParams.get(CameraParameters::KEY_EFFECT) );
1128            return BAD_VALUE;
1129        }
1130    }
1131
1132    // ANTIBANDING
1133    validatedParams.antibandingMode = abModeStringToEnum(
1134        newParams.get(CameraParameters::KEY_ANTIBANDING) );
1135    if (validatedParams.antibandingMode != antibandingMode) {
1136        camera_metadata_ro_entry_t availableAbModes =
1137            staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
1138        for (i = 0; i < availableAbModes.count; i++) {
1139            if (validatedParams.antibandingMode == availableAbModes.data.u8[i])
1140                break;
1141        }
1142        if (i == availableAbModes.count) {
1143            ALOGE("%s: Requested antibanding mode \"%s\" is not supported",
1144                    __FUNCTION__,
1145                    newParams.get(CameraParameters::KEY_ANTIBANDING));
1146            return BAD_VALUE;
1147        }
1148    }
1149
1150    // SCENE_MODE
1151    validatedParams.sceneMode = sceneModeStringToEnum(
1152        newParams.get(CameraParameters::KEY_SCENE_MODE) );
1153    if (validatedParams.sceneMode != sceneMode &&
1154            validatedParams.sceneMode !=
1155            ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED) {
1156        camera_metadata_ro_entry_t availableSceneModes =
1157            staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
1158        for (i = 0; i < availableSceneModes.count; i++) {
1159            if (validatedParams.sceneMode == availableSceneModes.data.u8[i])
1160                break;
1161        }
1162        if (i == availableSceneModes.count) {
1163            ALOGE("%s: Requested scene mode \"%s\" is not supported",
1164                    __FUNCTION__,
1165                    newParams.get(CameraParameters::KEY_SCENE_MODE));
1166            return BAD_VALUE;
1167        }
1168    }
1169
1170    // FLASH_MODE
1171    validatedParams.flashMode = flashModeStringToEnum(
1172        newParams.get(CameraParameters::KEY_FLASH_MODE) );
1173    if (validatedParams.flashMode != flashMode) {
1174        camera_metadata_ro_entry_t flashAvailable =
1175            staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
1176        if (!flashAvailable.data.u8[0] &&
1177                validatedParams.flashMode != Parameters::FLASH_MODE_OFF) {
1178            ALOGE("%s: Requested flash mode \"%s\" is not supported: "
1179                    "No flash on device", __FUNCTION__,
1180                    newParams.get(CameraParameters::KEY_FLASH_MODE));
1181            return BAD_VALUE;
1182        } else if (validatedParams.flashMode == Parameters::FLASH_MODE_RED_EYE) {
1183            camera_metadata_ro_entry_t availableAeModes =
1184                staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
1185            for (i = 0; i < availableAeModes.count; i++) {
1186                if (validatedParams.flashMode == availableAeModes.data.u8[i])
1187                    break;
1188            }
1189            if (i == availableAeModes.count) {
1190                ALOGE("%s: Requested flash mode \"%s\" is not supported",
1191                        __FUNCTION__,
1192                        newParams.get(CameraParameters::KEY_FLASH_MODE));
1193                return BAD_VALUE;
1194            }
1195        } else if (validatedParams.flashMode == -1) {
1196            ALOGE("%s: Requested flash mode \"%s\" is unknown",
1197                    __FUNCTION__,
1198                    newParams.get(CameraParameters::KEY_FLASH_MODE));
1199            return BAD_VALUE;
1200        }
1201    }
1202
1203    // FOCUS_MODE
1204    validatedParams.focusMode = focusModeStringToEnum(
1205        newParams.get(CameraParameters::KEY_FOCUS_MODE));
1206    if (validatedParams.focusMode != focusMode) {
1207        validatedParams.currentAfTriggerId = -1;
1208        if (validatedParams.focusMode != Parameters::FOCUS_MODE_FIXED) {
1209            camera_metadata_ro_entry_t minFocusDistance =
1210                staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE);
1211            if (minFocusDistance.data.f[0] == 0) {
1212                ALOGE("%s: Requested focus mode \"%s\" is not available: "
1213                        "fixed focus lens",
1214                        __FUNCTION__,
1215                        newParams.get(CameraParameters::KEY_FOCUS_MODE));
1216                return BAD_VALUE;
1217            } else if (validatedParams.focusMode !=
1218                    Parameters::FOCUS_MODE_INFINITY) {
1219                camera_metadata_ro_entry_t availableFocusModes =
1220                    staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
1221                for (i = 0; i < availableFocusModes.count; i++) {
1222                    if (validatedParams.focusMode ==
1223                            availableFocusModes.data.u8[i]) break;
1224                }
1225                if (i == availableFocusModes.count) {
1226                    ALOGE("%s: Requested focus mode \"%s\" is not supported",
1227                            __FUNCTION__,
1228                            newParams.get(CameraParameters::KEY_FOCUS_MODE));
1229                    return BAD_VALUE;
1230                }
1231            }
1232        }
1233    } else {
1234        validatedParams.currentAfTriggerId = currentAfTriggerId;
1235    }
1236
1237    // FOCUS_AREAS
1238    res = parseAreas(newParams.get(CameraParameters::KEY_FOCUS_AREAS),
1239            &validatedParams.focusingAreas);
1240    size_t max3aRegions =
1241        (size_t)staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1).data.i32[0];
1242    if (res == OK) res = validateAreas(validatedParams.focusingAreas,
1243            max3aRegions);
1244    if (res != OK) {
1245        ALOGE("%s: Requested focus areas are malformed: %s",
1246                __FUNCTION__, newParams.get(CameraParameters::KEY_FOCUS_AREAS));
1247        return BAD_VALUE;
1248    }
1249
1250    // EXPOSURE_COMPENSATION
1251    validatedParams.exposureCompensation =
1252        newParams.getInt(CameraParameters::KEY_EXPOSURE_COMPENSATION);
1253    camera_metadata_ro_entry_t exposureCompensationRange =
1254        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE);
1255    if ((validatedParams.exposureCompensation <
1256            exposureCompensationRange.data.i32[0]) ||
1257        (validatedParams.exposureCompensation >
1258            exposureCompensationRange.data.i32[1])) {
1259        ALOGE("%s: Requested exposure compensation index is out of bounds: %d",
1260                __FUNCTION__, validatedParams.exposureCompensation);
1261        return BAD_VALUE;
1262    }
1263
1264    // AUTO_EXPOSURE_LOCK (always supported)
1265    validatedParams.autoExposureLock = boolFromString(
1266        newParams.get(CameraParameters::KEY_AUTO_EXPOSURE_LOCK));
1267
1268    // AUTO_WHITEBALANCE_LOCK (always supported)
1269    validatedParams.autoWhiteBalanceLock = boolFromString(
1270        newParams.get(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK));
1271
1272    // METERING_AREAS
1273    res = parseAreas(newParams.get(CameraParameters::KEY_METERING_AREAS),
1274            &validatedParams.meteringAreas);
1275    if (res == OK) {
1276        res = validateAreas(validatedParams.meteringAreas, max3aRegions);
1277    }
1278    if (res != OK) {
1279        ALOGE("%s: Requested metering areas are malformed: %s",
1280                __FUNCTION__,
1281                newParams.get(CameraParameters::KEY_METERING_AREAS));
1282        return BAD_VALUE;
1283    }
1284
1285    // ZOOM
1286    validatedParams.zoom = newParams.getInt(CameraParameters::KEY_ZOOM);
1287    if (validatedParams.zoom < 0 || validatedParams.zoom > (int)NUM_ZOOM_STEPS) {
1288        ALOGE("%s: Requested zoom level %d is not supported",
1289                __FUNCTION__, validatedParams.zoom);
1290        return BAD_VALUE;
1291    }
1292
1293    // VIDEO_SIZE
1294    newParams.getVideoSize(&validatedParams.videoWidth,
1295            &validatedParams.videoHeight);
1296    if (validatedParams.videoWidth != videoWidth ||
1297            validatedParams.videoHeight != videoHeight) {
1298        if (state == RECORD) {
1299            ALOGE("%s: Video size cannot be updated when recording is active!",
1300                    __FUNCTION__);
1301            return BAD_VALUE;
1302        }
1303        camera_metadata_ro_entry_t availableVideoSizes =
1304            staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
1305        for (i = 0; i < availableVideoSizes.count; i += 2 ) {
1306            if ((availableVideoSizes.data.i32[i] ==
1307                    validatedParams.videoWidth) &&
1308                (availableVideoSizes.data.i32[i+1] ==
1309                    validatedParams.videoHeight)) break;
1310        }
1311        if (i == availableVideoSizes.count) {
1312            ALOGE("%s: Requested video size %d x %d is not supported",
1313                    __FUNCTION__, validatedParams.videoWidth,
1314                    validatedParams.videoHeight);
1315            return BAD_VALUE;
1316        }
1317    }
1318
1319    // RECORDING_HINT (always supported)
1320    validatedParams.recordingHint = boolFromString(
1321        newParams.get(CameraParameters::KEY_RECORDING_HINT) );
1322
1323    // VIDEO_STABILIZATION
1324    validatedParams.videoStabilization = boolFromString(
1325        newParams.get(CameraParameters::KEY_VIDEO_STABILIZATION) );
1326    camera_metadata_ro_entry_t availableVideoStabilizationModes =
1327        staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
1328    if (validatedParams.videoStabilization &&
1329            availableVideoStabilizationModes.count == 1) {
1330        ALOGE("%s: Video stabilization not supported", __FUNCTION__);
1331    }
1332
1333    // LIGHTFX
1334    validatedParams.lightFx = lightFxStringToEnum(
1335        newParams.get(CameraParameters::KEY_LIGHTFX));
1336
1337    /** Update internal parameters */
1338
1339    validatedParams.paramsFlattened = params;
1340    *this = validatedParams;
1341
1342    return OK;
1343}
1344
1345status_t Parameters::updateRequest(CameraMetadata *request) const {
1346    ATRACE_CALL();
1347    status_t res;
1348
1349    uint8_t metadataMode = ANDROID_REQUEST_METADATA_FULL;
1350    res = request->update(ANDROID_REQUEST_METADATA_MODE,
1351            &metadataMode, 1);
1352    if (res != OK) return res;
1353
1354    res = request->update(ANDROID_CONTROL_AE_TARGET_FPS_RANGE,
1355            previewFpsRange, 2);
1356    if (res != OK) return res;
1357
1358    res = request->update(ANDROID_CONTROL_AWB_MODE,
1359            &wbMode, 1);
1360    if (res != OK) return res;
1361
1362    uint8_t reqWbLock = autoWhiteBalanceLock ?
1363            ANDROID_CONTROL_AWB_LOCK_ON : ANDROID_CONTROL_AWB_LOCK_OFF;
1364    res = request->update(ANDROID_CONTROL_AWB_LOCK,
1365            &reqWbLock, 1);
1366
1367    res = request->update(ANDROID_CONTROL_EFFECT_MODE,
1368            &effectMode, 1);
1369    if (res != OK) return res;
1370    res = request->update(ANDROID_CONTROL_AE_ANTIBANDING_MODE,
1371            &antibandingMode, 1);
1372    if (res != OK) return res;
1373
1374    // android.hardware.Camera requires that when face detect is enabled, the
1375    // camera is in a face-priority mode. HAL2 splits this into separate parts
1376    // (face detection statistics and face priority scene mode). Map from other
1377    // to the other.
1378    uint8_t reqControlMode = ANDROID_CONTROL_AUTO;
1379    if (enableFaceDetect || sceneMode != ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED) {
1380        reqControlMode = ANDROID_CONTROL_USE_SCENE_MODE;
1381    }
1382    res = request->update(ANDROID_CONTROL_MODE,
1383            &reqControlMode, 1);
1384    if (res != OK) return res;
1385
1386    uint8_t reqSceneMode =
1387            (sceneMode !=
1388                    (uint8_t)ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED) ? sceneMode :
1389            enableFaceDetect ? (uint8_t)ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY :
1390            (uint8_t)ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED;
1391    res = request->update(ANDROID_CONTROL_SCENE_MODE,
1392            &reqSceneMode, 1);
1393    if (res != OK) return res;
1394
1395    uint8_t reqFlashMode = ANDROID_FLASH_OFF;
1396    uint8_t reqAeMode;
1397    switch (flashMode) {
1398        case Parameters::FLASH_MODE_OFF:
1399            reqAeMode = ANDROID_CONTROL_AE_ON; break;
1400        case Parameters::FLASH_MODE_AUTO:
1401            reqAeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH; break;
1402        case Parameters::FLASH_MODE_ON:
1403            reqAeMode = ANDROID_CONTROL_AE_ON_ALWAYS_FLASH; break;
1404        case Parameters::FLASH_MODE_TORCH:
1405            reqAeMode = ANDROID_CONTROL_AE_ON;
1406            reqFlashMode = ANDROID_FLASH_TORCH;
1407            break;
1408        case Parameters::FLASH_MODE_RED_EYE:
1409            reqAeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE; break;
1410        default:
1411            ALOGE("%s: Camera %d: Unknown flash mode %d", __FUNCTION__,
1412                    cameraId, flashMode);
1413            return BAD_VALUE;
1414    }
1415    res = request->update(ANDROID_FLASH_MODE,
1416            &reqFlashMode, 1);
1417    if (res != OK) return res;
1418    res = request->update(ANDROID_CONTROL_AE_MODE,
1419            &reqAeMode, 1);
1420    if (res != OK) return res;
1421
1422    uint8_t reqAeLock = autoExposureLock ?
1423            ANDROID_CONTROL_AE_LOCK_ON : ANDROID_CONTROL_AE_LOCK_OFF;
1424    res = request->update(ANDROID_CONTROL_AE_LOCK,
1425            &reqAeLock, 1);
1426
1427    float reqFocusDistance = 0; // infinity focus in diopters
1428    uint8_t reqFocusMode;
1429    switch (focusMode) {
1430        case Parameters::FOCUS_MODE_AUTO:
1431        case Parameters::FOCUS_MODE_MACRO:
1432        case Parameters::FOCUS_MODE_CONTINUOUS_VIDEO:
1433        case Parameters::FOCUS_MODE_CONTINUOUS_PICTURE:
1434        case Parameters::FOCUS_MODE_EDOF:
1435            reqFocusMode = focusMode;
1436            break;
1437        case Parameters::FOCUS_MODE_INFINITY:
1438        case Parameters::FOCUS_MODE_FIXED:
1439            reqFocusMode = ANDROID_CONTROL_AF_OFF;
1440            break;
1441        default:
1442            ALOGE("%s: Camera %d: Unknown focus mode %d", __FUNCTION__,
1443                    cameraId, focusMode);
1444            return BAD_VALUE;
1445    }
1446    res = request->update(ANDROID_LENS_FOCUS_DISTANCE,
1447            &reqFocusDistance, 1);
1448    if (res != OK) return res;
1449    res = request->update(ANDROID_CONTROL_AF_MODE,
1450            &reqFocusMode, 1);
1451    if (res != OK) return res;
1452
1453    size_t reqFocusingAreasSize = focusingAreas.size() * 5;
1454    int32_t *reqFocusingAreas = new int32_t[reqFocusingAreasSize];
1455    for (size_t i = 0; i < reqFocusingAreasSize; i += 5) {
1456        if (focusingAreas[i].weight != 0) {
1457            reqFocusingAreas[i + 0] =
1458                    normalizedXToArray(focusingAreas[i].left);
1459            reqFocusingAreas[i + 1] =
1460                    normalizedYToArray(focusingAreas[i].top);
1461            reqFocusingAreas[i + 2] =
1462                    normalizedXToArray(focusingAreas[i].right);
1463            reqFocusingAreas[i + 3] =
1464                    normalizedYToArray(focusingAreas[i].bottom);
1465        } else {
1466            reqFocusingAreas[i + 0] = 0;
1467            reqFocusingAreas[i + 1] = 0;
1468            reqFocusingAreas[i + 2] = 0;
1469            reqFocusingAreas[i + 3] = 0;
1470        }
1471        reqFocusingAreas[i + 4] = focusingAreas[i].weight;
1472    }
1473    res = request->update(ANDROID_CONTROL_AF_REGIONS,
1474            reqFocusingAreas, reqFocusingAreasSize);
1475    if (res != OK) return res;
1476    delete[] reqFocusingAreas;
1477
1478    res = request->update(ANDROID_CONTROL_AE_EXP_COMPENSATION,
1479            &exposureCompensation, 1);
1480    if (res != OK) return res;
1481
1482    size_t reqMeteringAreasSize = meteringAreas.size() * 5;
1483    int32_t *reqMeteringAreas = new int32_t[reqMeteringAreasSize];
1484    for (size_t i = 0; i < reqMeteringAreasSize; i += 5) {
1485        if (meteringAreas[i].weight != 0) {
1486            reqMeteringAreas[i + 0] =
1487                normalizedXToArray(meteringAreas[i].left);
1488            reqMeteringAreas[i + 1] =
1489                normalizedYToArray(meteringAreas[i].top);
1490            reqMeteringAreas[i + 2] =
1491                normalizedXToArray(meteringAreas[i].right);
1492            reqMeteringAreas[i + 3] =
1493                normalizedYToArray(meteringAreas[i].bottom);
1494        } else {
1495            reqMeteringAreas[i + 0] = 0;
1496            reqMeteringAreas[i + 1] = 0;
1497            reqMeteringAreas[i + 2] = 0;
1498            reqMeteringAreas[i + 3] = 0;
1499        }
1500        reqMeteringAreas[i + 4] = meteringAreas[i].weight;
1501    }
1502    res = request->update(ANDROID_CONTROL_AE_REGIONS,
1503            reqMeteringAreas, reqMeteringAreasSize);
1504    if (res != OK) return res;
1505
1506    res = request->update(ANDROID_CONTROL_AWB_REGIONS,
1507            reqMeteringAreas, reqMeteringAreasSize);
1508    if (res != OK) return res;
1509    delete[] reqMeteringAreas;
1510
1511    CropRegion crop = calculateCropRegion();
1512    int32_t reqCropRegion[3] = { crop.left, crop.top, crop.width };
1513    res = request->update(ANDROID_SCALER_CROP_REGION,
1514            reqCropRegion, 3);
1515    if (res != OK) return res;
1516
1517    uint8_t reqVstabMode = videoStabilization ?
1518            ANDROID_CONTROL_VIDEO_STABILIZATION_ON :
1519            ANDROID_CONTROL_VIDEO_STABILIZATION_OFF;
1520    res = request->update(ANDROID_CONTROL_VIDEO_STABILIZATION_MODE,
1521            &reqVstabMode, 1);
1522    if (res != OK) return res;
1523
1524    uint8_t reqFaceDetectMode = enableFaceDetect ?
1525            fastInfo.bestFaceDetectMode :
1526            (uint8_t)ANDROID_STATS_FACE_DETECTION_OFF;
1527    res = request->update(ANDROID_STATS_FACE_DETECT_MODE,
1528            &reqFaceDetectMode, 1);
1529    if (res != OK) return res;
1530
1531    return OK;
1532}
1533
1534const char* Parameters::getStateName(State state) {
1535#define CASE_ENUM_TO_CHAR(x) case x: return(#x); break;
1536    switch(state) {
1537        CASE_ENUM_TO_CHAR(DISCONNECTED)
1538        CASE_ENUM_TO_CHAR(STOPPED)
1539        CASE_ENUM_TO_CHAR(WAITING_FOR_PREVIEW_WINDOW)
1540        CASE_ENUM_TO_CHAR(PREVIEW)
1541        CASE_ENUM_TO_CHAR(RECORD)
1542        CASE_ENUM_TO_CHAR(STILL_CAPTURE)
1543        CASE_ENUM_TO_CHAR(VIDEO_SNAPSHOT)
1544        default:
1545            return "Unknown state!";
1546            break;
1547    }
1548#undef CASE_ENUM_TO_CHAR
1549}
1550
1551int Parameters::formatStringToEnum(const char *format) {
1552    return
1553        !format ?
1554            HAL_PIXEL_FORMAT_YCrCb_420_SP :
1555        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422SP) ?
1556            HAL_PIXEL_FORMAT_YCbCr_422_SP : // NV16
1557        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420SP) ?
1558            HAL_PIXEL_FORMAT_YCrCb_420_SP : // NV21
1559        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422I) ?
1560            HAL_PIXEL_FORMAT_YCbCr_422_I :  // YUY2
1561        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420P) ?
1562            HAL_PIXEL_FORMAT_YV12 :         // YV12
1563        !strcmp(format, CameraParameters::PIXEL_FORMAT_RGB565) ?
1564            HAL_PIXEL_FORMAT_RGB_565 :      // RGB565
1565        !strcmp(format, CameraParameters::PIXEL_FORMAT_RGBA8888) ?
1566            HAL_PIXEL_FORMAT_RGBA_8888 :    // RGB8888
1567        !strcmp(format, CameraParameters::PIXEL_FORMAT_BAYER_RGGB) ?
1568            HAL_PIXEL_FORMAT_RAW_SENSOR :   // Raw sensor data
1569        -1;
1570}
1571
1572const char* Parameters::formatEnumToString(int format) {
1573    const char *fmt;
1574    switch(format) {
1575        case HAL_PIXEL_FORMAT_YCbCr_422_SP: // NV16
1576            fmt = CameraParameters::PIXEL_FORMAT_YUV422SP;
1577            break;
1578        case HAL_PIXEL_FORMAT_YCrCb_420_SP: // NV21
1579            fmt = CameraParameters::PIXEL_FORMAT_YUV420SP;
1580            break;
1581        case HAL_PIXEL_FORMAT_YCbCr_422_I: // YUY2
1582            fmt = CameraParameters::PIXEL_FORMAT_YUV422I;
1583            break;
1584        case HAL_PIXEL_FORMAT_YV12:        // YV12
1585            fmt = CameraParameters::PIXEL_FORMAT_YUV420P;
1586            break;
1587        case HAL_PIXEL_FORMAT_RGB_565:     // RGB565
1588            fmt = CameraParameters::PIXEL_FORMAT_RGB565;
1589            break;
1590        case HAL_PIXEL_FORMAT_RGBA_8888:   // RGBA8888
1591            fmt = CameraParameters::PIXEL_FORMAT_RGBA8888;
1592            break;
1593        case HAL_PIXEL_FORMAT_RAW_SENSOR:
1594            ALOGW("Raw sensor preview format requested.");
1595            fmt = CameraParameters::PIXEL_FORMAT_BAYER_RGGB;
1596            break;
1597        default:
1598            ALOGE("%s: Unknown preview format: %x",
1599                    __FUNCTION__,  format);
1600            fmt = NULL;
1601            break;
1602    }
1603    return fmt;
1604}
1605
1606int Parameters::wbModeStringToEnum(const char *wbMode) {
1607    return
1608        !wbMode ?
1609            ANDROID_CONTROL_AWB_AUTO :
1610        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_AUTO) ?
1611            ANDROID_CONTROL_AWB_AUTO :
1612        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_INCANDESCENT) ?
1613            ANDROID_CONTROL_AWB_INCANDESCENT :
1614        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_FLUORESCENT) ?
1615            ANDROID_CONTROL_AWB_FLUORESCENT :
1616        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT) ?
1617            ANDROID_CONTROL_AWB_WARM_FLUORESCENT :
1618        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_DAYLIGHT) ?
1619            ANDROID_CONTROL_AWB_DAYLIGHT :
1620        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT) ?
1621            ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT :
1622        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_TWILIGHT) ?
1623            ANDROID_CONTROL_AWB_TWILIGHT :
1624        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_SHADE) ?
1625            ANDROID_CONTROL_AWB_SHADE :
1626        -1;
1627}
1628
1629int Parameters::effectModeStringToEnum(const char *effectMode) {
1630    return
1631        !effectMode ?
1632            ANDROID_CONTROL_EFFECT_OFF :
1633        !strcmp(effectMode, CameraParameters::EFFECT_NONE) ?
1634            ANDROID_CONTROL_EFFECT_OFF :
1635        !strcmp(effectMode, CameraParameters::EFFECT_MONO) ?
1636            ANDROID_CONTROL_EFFECT_MONO :
1637        !strcmp(effectMode, CameraParameters::EFFECT_NEGATIVE) ?
1638            ANDROID_CONTROL_EFFECT_NEGATIVE :
1639        !strcmp(effectMode, CameraParameters::EFFECT_SOLARIZE) ?
1640            ANDROID_CONTROL_EFFECT_SOLARIZE :
1641        !strcmp(effectMode, CameraParameters::EFFECT_SEPIA) ?
1642            ANDROID_CONTROL_EFFECT_SEPIA :
1643        !strcmp(effectMode, CameraParameters::EFFECT_POSTERIZE) ?
1644            ANDROID_CONTROL_EFFECT_POSTERIZE :
1645        !strcmp(effectMode, CameraParameters::EFFECT_WHITEBOARD) ?
1646            ANDROID_CONTROL_EFFECT_WHITEBOARD :
1647        !strcmp(effectMode, CameraParameters::EFFECT_BLACKBOARD) ?
1648            ANDROID_CONTROL_EFFECT_BLACKBOARD :
1649        !strcmp(effectMode, CameraParameters::EFFECT_AQUA) ?
1650            ANDROID_CONTROL_EFFECT_AQUA :
1651        -1;
1652}
1653
1654int Parameters::abModeStringToEnum(const char *abMode) {
1655    return
1656        !abMode ?
1657            ANDROID_CONTROL_AE_ANTIBANDING_AUTO :
1658        !strcmp(abMode, CameraParameters::ANTIBANDING_AUTO) ?
1659            ANDROID_CONTROL_AE_ANTIBANDING_AUTO :
1660        !strcmp(abMode, CameraParameters::ANTIBANDING_OFF) ?
1661            ANDROID_CONTROL_AE_ANTIBANDING_OFF :
1662        !strcmp(abMode, CameraParameters::ANTIBANDING_50HZ) ?
1663            ANDROID_CONTROL_AE_ANTIBANDING_50HZ :
1664        !strcmp(abMode, CameraParameters::ANTIBANDING_60HZ) ?
1665            ANDROID_CONTROL_AE_ANTIBANDING_60HZ :
1666        -1;
1667}
1668
1669int Parameters::sceneModeStringToEnum(const char *sceneMode) {
1670    return
1671        !sceneMode ?
1672            ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED :
1673        !strcmp(sceneMode, CameraParameters::SCENE_MODE_AUTO) ?
1674            ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED :
1675        !strcmp(sceneMode, CameraParameters::SCENE_MODE_ACTION) ?
1676            ANDROID_CONTROL_SCENE_MODE_ACTION :
1677        !strcmp(sceneMode, CameraParameters::SCENE_MODE_PORTRAIT) ?
1678            ANDROID_CONTROL_SCENE_MODE_PORTRAIT :
1679        !strcmp(sceneMode, CameraParameters::SCENE_MODE_LANDSCAPE) ?
1680            ANDROID_CONTROL_SCENE_MODE_LANDSCAPE :
1681        !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT) ?
1682            ANDROID_CONTROL_SCENE_MODE_NIGHT :
1683        !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT_PORTRAIT) ?
1684            ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT :
1685        !strcmp(sceneMode, CameraParameters::SCENE_MODE_THEATRE) ?
1686            ANDROID_CONTROL_SCENE_MODE_THEATRE :
1687        !strcmp(sceneMode, CameraParameters::SCENE_MODE_BEACH) ?
1688            ANDROID_CONTROL_SCENE_MODE_BEACH :
1689        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SNOW) ?
1690            ANDROID_CONTROL_SCENE_MODE_SNOW :
1691        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SUNSET) ?
1692            ANDROID_CONTROL_SCENE_MODE_SUNSET :
1693        !strcmp(sceneMode, CameraParameters::SCENE_MODE_STEADYPHOTO) ?
1694            ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO :
1695        !strcmp(sceneMode, CameraParameters::SCENE_MODE_FIREWORKS) ?
1696            ANDROID_CONTROL_SCENE_MODE_FIREWORKS :
1697        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SPORTS) ?
1698            ANDROID_CONTROL_SCENE_MODE_SPORTS :
1699        !strcmp(sceneMode, CameraParameters::SCENE_MODE_PARTY) ?
1700            ANDROID_CONTROL_SCENE_MODE_PARTY :
1701        !strcmp(sceneMode, CameraParameters::SCENE_MODE_CANDLELIGHT) ?
1702            ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT :
1703        !strcmp(sceneMode, CameraParameters::SCENE_MODE_BARCODE) ?
1704            ANDROID_CONTROL_SCENE_MODE_BARCODE:
1705        -1;
1706}
1707
1708Parameters::Parameters::flashMode_t Parameters::flashModeStringToEnum(
1709        const char *flashMode) {
1710    return
1711        !flashMode ?
1712            Parameters::FLASH_MODE_INVALID :
1713        !strcmp(flashMode, CameraParameters::FLASH_MODE_OFF) ?
1714            Parameters::FLASH_MODE_OFF :
1715        !strcmp(flashMode, CameraParameters::FLASH_MODE_AUTO) ?
1716            Parameters::FLASH_MODE_AUTO :
1717        !strcmp(flashMode, CameraParameters::FLASH_MODE_ON) ?
1718            Parameters::FLASH_MODE_ON :
1719        !strcmp(flashMode, CameraParameters::FLASH_MODE_RED_EYE) ?
1720            Parameters::FLASH_MODE_RED_EYE :
1721        !strcmp(flashMode, CameraParameters::FLASH_MODE_TORCH) ?
1722            Parameters::FLASH_MODE_TORCH :
1723        Parameters::FLASH_MODE_INVALID;
1724}
1725
1726Parameters::Parameters::focusMode_t Parameters::focusModeStringToEnum(
1727        const char *focusMode) {
1728    return
1729        !focusMode ?
1730            Parameters::FOCUS_MODE_INVALID :
1731        !strcmp(focusMode, CameraParameters::FOCUS_MODE_AUTO) ?
1732            Parameters::FOCUS_MODE_AUTO :
1733        !strcmp(focusMode, CameraParameters::FOCUS_MODE_INFINITY) ?
1734            Parameters::FOCUS_MODE_INFINITY :
1735        !strcmp(focusMode, CameraParameters::FOCUS_MODE_MACRO) ?
1736            Parameters::FOCUS_MODE_MACRO :
1737        !strcmp(focusMode, CameraParameters::FOCUS_MODE_FIXED) ?
1738            Parameters::FOCUS_MODE_FIXED :
1739        !strcmp(focusMode, CameraParameters::FOCUS_MODE_EDOF) ?
1740            Parameters::FOCUS_MODE_EDOF :
1741        !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO) ?
1742            Parameters::FOCUS_MODE_CONTINUOUS_VIDEO :
1743        !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE) ?
1744            Parameters::FOCUS_MODE_CONTINUOUS_PICTURE :
1745        Parameters::FOCUS_MODE_INVALID;
1746}
1747
1748Parameters::Parameters::lightFxMode_t Parameters::lightFxStringToEnum(
1749        const char *lightFxMode) {
1750    return
1751        !lightFxMode ?
1752            Parameters::LIGHTFX_NONE :
1753        !strcmp(lightFxMode, CameraParameters::LIGHTFX_LOWLIGHT) ?
1754            Parameters::LIGHTFX_LOWLIGHT :
1755        !strcmp(lightFxMode, CameraParameters::LIGHTFX_HDR) ?
1756            Parameters::LIGHTFX_HDR :
1757        Parameters::LIGHTFX_NONE;
1758}
1759
1760status_t Parameters::parseAreas(const char *areasCStr,
1761        Vector<Parameters::Area> *areas) {
1762    static const size_t NUM_FIELDS = 5;
1763    areas->clear();
1764    if (areasCStr == NULL) {
1765        // If no key exists, use default (0,0,0,0,0)
1766        areas->push();
1767        return OK;
1768    }
1769    String8 areasStr(areasCStr);
1770    ssize_t areaStart = areasStr.find("(", 0) + 1;
1771    while (areaStart != 0) {
1772        const char* area = areasStr.string() + areaStart;
1773        char *numEnd;
1774        int vals[NUM_FIELDS];
1775        for (size_t i = 0; i < NUM_FIELDS; i++) {
1776            errno = 0;
1777            vals[i] = strtol(area, &numEnd, 10);
1778            if (errno || numEnd == area) return BAD_VALUE;
1779            area = numEnd + 1;
1780        }
1781        areas->push(Parameters::Area(
1782            vals[0], vals[1], vals[2], vals[3], vals[4]) );
1783        areaStart = areasStr.find("(", areaStart) + 1;
1784    }
1785    return OK;
1786}
1787
1788status_t Parameters::validateAreas(const Vector<Parameters::Area> &areas,
1789                                      size_t maxRegions) {
1790    // Definition of valid area can be found in
1791    // include/camera/CameraParameters.h
1792    if (areas.size() == 0) return BAD_VALUE;
1793    if (areas.size() == 1) {
1794        if (areas[0].left == 0 &&
1795                areas[0].top == 0 &&
1796                areas[0].right == 0 &&
1797                areas[0].bottom == 0 &&
1798                areas[0].weight == 0) {
1799            // Single (0,0,0,0,0) entry is always valid (== driver decides)
1800            return OK;
1801        }
1802    }
1803    if (areas.size() > maxRegions) {
1804        ALOGE("%s: Too many areas requested: %d",
1805                __FUNCTION__, areas.size());
1806        return BAD_VALUE;
1807    }
1808
1809    for (Vector<Parameters::Area>::const_iterator a = areas.begin();
1810         a != areas.end(); a++) {
1811        if (a->weight < 1 || a->weight > 1000) return BAD_VALUE;
1812        if (a->left < -1000 || a->left > 1000) return BAD_VALUE;
1813        if (a->top < -1000 || a->top > 1000) return BAD_VALUE;
1814        if (a->right < -1000 || a->right > 1000) return BAD_VALUE;
1815        if (a->bottom < -1000 || a->bottom > 1000) return BAD_VALUE;
1816        if (a->left >= a->right) return BAD_VALUE;
1817        if (a->top >= a->bottom) return BAD_VALUE;
1818    }
1819    return OK;
1820}
1821
1822bool Parameters::boolFromString(const char *boolStr) {
1823    return !boolStr ? false :
1824        !strcmp(boolStr, CameraParameters::TRUE) ? true :
1825        false;
1826}
1827
1828int Parameters::degToTransform(int degrees, bool mirror) {
1829    if (!mirror) {
1830        if (degrees == 0) return 0;
1831        else if (degrees == 90) return HAL_TRANSFORM_ROT_90;
1832        else if (degrees == 180) return HAL_TRANSFORM_ROT_180;
1833        else if (degrees == 270) return HAL_TRANSFORM_ROT_270;
1834    } else {  // Do mirror (horizontal flip)
1835        if (degrees == 0) {           // FLIP_H and ROT_0
1836            return HAL_TRANSFORM_FLIP_H;
1837        } else if (degrees == 90) {   // FLIP_H and ROT_90
1838            return HAL_TRANSFORM_FLIP_H | HAL_TRANSFORM_ROT_90;
1839        } else if (degrees == 180) {  // FLIP_H and ROT_180
1840            return HAL_TRANSFORM_FLIP_V;
1841        } else if (degrees == 270) {  // FLIP_H and ROT_270
1842            return HAL_TRANSFORM_FLIP_V | HAL_TRANSFORM_ROT_90;
1843        }
1844    }
1845    ALOGE("%s: Bad input: %d", __FUNCTION__, degrees);
1846    return -1;
1847}
1848
1849int Parameters::arrayXToNormalized(int width) const {
1850    return width * 2000 / (fastInfo.arrayWidth - 1) - 1000;
1851}
1852
1853int Parameters::arrayYToNormalized(int height) const {
1854    return height * 2000 / (fastInfo.arrayHeight - 1) - 1000;
1855}
1856
1857int Parameters::normalizedXToArray(int x) const {
1858    return (x + 1000) * (fastInfo.arrayWidth - 1) / 2000;
1859}
1860
1861int Parameters::normalizedYToArray(int y) const {
1862    return (y + 1000) * (fastInfo.arrayHeight - 1) / 2000;
1863}
1864
1865Parameters::CropRegion Parameters::calculateCropRegion(void) const {
1866
1867    float zoomLeft, zoomTop, zoomWidth, zoomHeight;
1868
1869    // Need to convert zoom index into a crop rectangle. The rectangle is
1870    // chosen to maximize its area on the sensor
1871
1872    camera_metadata_ro_entry_t maxDigitalZoom =
1873            staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM);
1874    // For each zoom step by how many pixels more do we change the zoom
1875    float zoomIncrement = (maxDigitalZoom.data.f[0] - 1) /
1876            (NUM_ZOOM_STEPS-1);
1877    // The desired activeAreaWidth/cropAreaWidth ratio (or height if h>w)
1878    // via interpolating zoom step into a zoom ratio
1879    float zoomRatio = 1 + zoomIncrement * zoom;
1880    ALOG_ASSERT( (zoomRatio >= 1.f && zoomRatio <= maxDigitalZoom.data.f[0]),
1881        "Zoom ratio calculated out of bounds. Expected 1 - %f, actual: %f",
1882        maxDigitalZoom.data.f[0], zoomRatio);
1883
1884    ALOGV("Zoom maxDigital=%f, increment=%f, ratio=%f, previewWidth=%d, "
1885          "previewHeight=%d, activeWidth=%d, activeHeight=%d",
1886          maxDigitalZoom.data.f[0], zoomIncrement, zoomRatio, previewWidth,
1887          previewHeight, fastInfo.arrayWidth, fastInfo.arrayHeight);
1888
1889    /*
1890     * Assumption: On the HAL side each stream buffer calculates its crop
1891     * rectangle as follows:
1892     *   cropRect = (zoomLeft, zoomRight,
1893     *               zoomWidth, zoomHeight * zoomWidth / outputWidth);
1894     *
1895     * Note that if zoomWidth > bufferWidth, the new cropHeight > zoomHeight
1896     *      (we can then get into trouble if the cropHeight > arrayHeight).
1897     * By selecting the zoomRatio based on the smallest outputRatio, we
1898     * guarantee this will never happen.
1899     */
1900
1901    // Enumerate all possible output sizes, select the one with the smallest
1902    // aspect ratio
1903    float minOutputWidth, minOutputHeight, minOutputRatio;
1904    {
1905        float outputSizes[][2] = {
1906            { previewWidth,     previewHeight },
1907            { videoWidth,       videoHeight },
1908            /* don't include jpeg thumbnail size - it's valid for
1909               it to be set to (0,0), meaning 'no thumbnail' */
1910        //  { jpegThumbSize[0], jpegThumbSize[1] },
1911            { pictureWidth,     pictureHeight },
1912        };
1913
1914        minOutputWidth = outputSizes[0][0];
1915        minOutputHeight = outputSizes[0][1];
1916        minOutputRatio = minOutputWidth / minOutputHeight;
1917        for (unsigned int i = 0;
1918             i < sizeof(outputSizes) / sizeof(outputSizes[0]);
1919             ++i) {
1920
1921            float outputWidth = outputSizes[i][0];
1922            float outputHeight = outputSizes[i][1];
1923            float outputRatio = outputWidth / outputHeight;
1924
1925            if (minOutputRatio > outputRatio) {
1926                minOutputRatio = outputRatio;
1927                minOutputWidth = outputWidth;
1928                minOutputHeight = outputHeight;
1929            }
1930
1931            // and then use this output ratio instead of preview output ratio
1932            ALOGV("Enumerating output ratio %f = %f / %f, min is %f",
1933                  outputRatio, outputWidth, outputHeight, minOutputRatio);
1934        }
1935    }
1936
1937    /* Ensure that the width/height never go out of bounds
1938     * by scaling across a diffent dimension if an out-of-bounds
1939     * possibility exists.
1940     *
1941     * e.g. if the previewratio < arrayratio and e.g. zoomratio = 1.0, then by
1942     * calculating the zoomWidth from zoomHeight we'll actually get a
1943     * zoomheight > arrayheight
1944     */
1945    float arrayRatio = 1.f * fastInfo.arrayWidth / fastInfo.arrayHeight;
1946    if (minOutputRatio >= arrayRatio) {
1947        // Adjust the height based on the width
1948        zoomWidth =  fastInfo.arrayWidth / zoomRatio;
1949        zoomHeight = zoomWidth *
1950                minOutputHeight / minOutputWidth;
1951
1952    } else {
1953        // Adjust the width based on the height
1954        zoomHeight = fastInfo.arrayHeight / zoomRatio;
1955        zoomWidth = zoomHeight *
1956                minOutputWidth / minOutputHeight;
1957    }
1958    // centering the zoom area within the active area
1959    zoomLeft = (fastInfo.arrayWidth - zoomWidth) / 2;
1960    zoomTop = (fastInfo.arrayHeight - zoomHeight) / 2;
1961
1962    ALOGV("Crop region calculated (x=%d,y=%d,w=%f,h=%f) for zoom=%d",
1963        (int32_t)zoomLeft, (int32_t)zoomTop, zoomWidth, zoomHeight, this->zoom);
1964
1965
1966    CropRegion crop = { zoomLeft, zoomTop, zoomWidth, zoomHeight };
1967    return crop;
1968}
1969
1970}; // namespace camera2
1971}; // namespace android
1972