From c52b876faea09e94b69fee865e249cb3a2b0bfb1 Mon Sep 17 00:00:00 2001 From: Eino-Ville Talvala Date: Wed, 5 Aug 2015 15:43:30 -0700 Subject: Camera/gralloc: Add basic capability handling, support DEPTH Also fix bug with AE not correctly overriding sensor values when ON but still INACTIVE. - Add Y16 support to gralloc (treat exactly as RAW16) - Add Y16 output support to camera - Adds depth static and dynamic fields to camera: - poseRotation - poseTranslation - intrinsicCalibration - radialDistortion - availableDepthStreamConfigurations - availableDepthMinFrameDurations - availableDepthStallDurations - depthIsExclusive Bug: 20537722 Change-Id: If64bb2a698a8a49777f848cfc6401d8fba299541 --- camera/EmulatedFakeCamera3.cpp | 1241 ++++++++++++++++++++++--------------- camera/fake-pipeline2/Base.h | 1 + camera/fake-pipeline2/Sensor.cpp | 90 ++- camera/fake-pipeline2/Sensor.h | 3 + opengl/system/gralloc/gralloc.cpp | 3 +- 5 files changed, 824 insertions(+), 514 deletions(-) diff --git a/camera/EmulatedFakeCamera3.cpp b/camera/EmulatedFakeCamera3.cpp index fe5e26b..f59c774 100644 --- a/camera/EmulatedFakeCamera3.cpp +++ b/camera/EmulatedFakeCamera3.cpp @@ -38,6 +38,8 @@ #include "fake-pipeline2/JpegCompressor.h" #include +#include + #if defined(LOG_NNDEBUG) && LOG_NNDEBUG == 0 #define ALOGVV ALOGV #else @@ -54,7 +56,7 @@ const int64_t USEC = 1000LL; const int64_t MSEC = USEC * 1000LL; const int64_t SEC = MSEC * 1000LL; -const int32_t EmulatedFakeCamera3::kAvailableFormats[5] = { +const int32_t EmulatedFakeCamera3::kAvailableFormats[] = { HAL_PIXEL_FORMAT_RAW16, HAL_PIXEL_FORMAT_BLOB, HAL_PIXEL_FORMAT_RGBA_8888, @@ -62,7 +64,8 @@ const int32_t EmulatedFakeCamera3::kAvailableFormats[5] = { // These are handled by YCbCr_420_888 // HAL_PIXEL_FORMAT_YV12, // HAL_PIXEL_FORMAT_YCrCb_420_SP, - HAL_PIXEL_FORMAT_YCbCr_420_888 + HAL_PIXEL_FORMAT_YCbCr_420_888, + HAL_PIXEL_FORMAT_Y16 }; /** @@ -163,6 +166,8 @@ status_t EmulatedFakeCamera3::connectCamera(hw_device_t** device) { mAeState = ANDROID_CONTROL_AE_STATE_INACTIVE; mAfState = ANDROID_CONTROL_AF_STATE_INACTIVE; mAwbState = ANDROID_CONTROL_AWB_STATE_INACTIVE; + mAeCounter = 0; + mAeTargetExposureTime = kNormalExposureTime; mAeCurrentExposureTime = kNormalExposureTime; mAeCurrentSensitivity = kNormalSensitivity; @@ -376,6 +381,12 @@ const camera_metadata_t* EmulatedFakeCamera3::constructDefaultRequestSettings( return NULL; } + if (!hasCapability(BACKWARD_COMPATIBLE) && type != CAMERA3_TEMPLATE_PREVIEW) { + ALOGE("%s: Template %d not supported w/o BACKWARD_COMPATIBLE capability", + __FUNCTION__, type); + return NULL; + } + /** * Cache is not just an optimization - pointer returned has to live at * least as long as the camera device instance does. @@ -388,9 +399,6 @@ const camera_metadata_t* EmulatedFakeCamera3::constructDefaultRequestSettings( /** android.request */ - static const uint8_t requestType = ANDROID_REQUEST_TYPE_CAPTURE; - settings.update(ANDROID_REQUEST_TYPE, &requestType, 1); - static const uint8_t metadataMode = ANDROID_REQUEST_METADATA_MODE_FULL; settings.update(ANDROID_REQUEST_METADATA_MODE, &metadataMode, 1); @@ -402,167 +410,176 @@ const camera_metadata_t* EmulatedFakeCamera3::constructDefaultRequestSettings( /** android.lens */ - static const float focusDistance = 0; - settings.update(ANDROID_LENS_FOCUS_DISTANCE, &focusDistance, 1); - - static const float aperture = 2.8f; - settings.update(ANDROID_LENS_APERTURE, &aperture, 1); - static const float focalLength = 5.0f; settings.update(ANDROID_LENS_FOCAL_LENGTH, &focalLength, 1); - static const float filterDensity = 0; - settings.update(ANDROID_LENS_FILTER_DENSITY, &filterDensity, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const float focusDistance = 0; + settings.update(ANDROID_LENS_FOCUS_DISTANCE, &focusDistance, 1); - static const uint8_t opticalStabilizationMode = - ANDROID_LENS_OPTICAL_STABILIZATION_MODE_OFF; - settings.update(ANDROID_LENS_OPTICAL_STABILIZATION_MODE, - &opticalStabilizationMode, 1); + static const float aperture = 2.8f; + settings.update(ANDROID_LENS_APERTURE, &aperture, 1); - // FOCUS_RANGE set only in frame + static const float filterDensity = 0; + settings.update(ANDROID_LENS_FILTER_DENSITY, &filterDensity, 1); + + static const uint8_t opticalStabilizationMode = + ANDROID_LENS_OPTICAL_STABILIZATION_MODE_OFF; + settings.update(ANDROID_LENS_OPTICAL_STABILIZATION_MODE, + &opticalStabilizationMode, 1); + + // FOCUS_RANGE set only in frame + } /** android.sensor */ - static const int64_t exposureTime = 10 * MSEC; - settings.update(ANDROID_SENSOR_EXPOSURE_TIME, &exposureTime, 1); + if (hasCapability(MANUAL_SENSOR)) { + static const int64_t exposureTime = 10 * MSEC; + settings.update(ANDROID_SENSOR_EXPOSURE_TIME, &exposureTime, 1); - static const int64_t frameDuration = 33333333L; // 1/30 s - settings.update(ANDROID_SENSOR_FRAME_DURATION, &frameDuration, 1); + static const int64_t frameDuration = 33333333L; // 1/30 s + settings.update(ANDROID_SENSOR_FRAME_DURATION, &frameDuration, 1); - static const int32_t sensitivity = 100; - settings.update(ANDROID_SENSOR_SENSITIVITY, &sensitivity, 1); + static const int32_t sensitivity = 100; + settings.update(ANDROID_SENSOR_SENSITIVITY, &sensitivity, 1); + } // TIMESTAMP set only in frame /** android.flash */ - static const uint8_t flashMode = ANDROID_FLASH_MODE_OFF; - settings.update(ANDROID_FLASH_MODE, &flashMode, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t flashMode = ANDROID_FLASH_MODE_OFF; + settings.update(ANDROID_FLASH_MODE, &flashMode, 1); - static const uint8_t flashPower = 10; - settings.update(ANDROID_FLASH_FIRING_POWER, &flashPower, 1); + static const uint8_t flashPower = 10; + settings.update(ANDROID_FLASH_FIRING_POWER, &flashPower, 1); - static const int64_t firingTime = 0; - settings.update(ANDROID_FLASH_FIRING_TIME, &firingTime, 1); + static const int64_t firingTime = 0; + settings.update(ANDROID_FLASH_FIRING_TIME, &firingTime, 1); + } /** Processing block modes */ - uint8_t hotPixelMode = 0; - uint8_t demosaicMode = 0; - uint8_t noiseMode = 0; - uint8_t shadingMode = 0; - uint8_t colorMode = 0; - uint8_t tonemapMode = 0; - uint8_t edgeMode = 0; - switch (type) { - case CAMERA3_TEMPLATE_STILL_CAPTURE: - // fall-through - case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT: - // fall-through - case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG: - hotPixelMode = ANDROID_HOT_PIXEL_MODE_HIGH_QUALITY; - demosaicMode = ANDROID_DEMOSAIC_MODE_HIGH_QUALITY; - noiseMode = ANDROID_NOISE_REDUCTION_MODE_HIGH_QUALITY; - shadingMode = ANDROID_SHADING_MODE_HIGH_QUALITY; - colorMode = ANDROID_COLOR_CORRECTION_MODE_HIGH_QUALITY; - tonemapMode = ANDROID_TONEMAP_MODE_HIGH_QUALITY; - edgeMode = ANDROID_EDGE_MODE_HIGH_QUALITY; - break; - case CAMERA3_TEMPLATE_PREVIEW: - // fall-through - case CAMERA3_TEMPLATE_VIDEO_RECORD: - // fall-through - default: - hotPixelMode = ANDROID_HOT_PIXEL_MODE_FAST; - demosaicMode = ANDROID_DEMOSAIC_MODE_FAST; - noiseMode = ANDROID_NOISE_REDUCTION_MODE_FAST; - shadingMode = ANDROID_SHADING_MODE_FAST; - colorMode = ANDROID_COLOR_CORRECTION_MODE_FAST; - tonemapMode = ANDROID_TONEMAP_MODE_FAST; - edgeMode = ANDROID_EDGE_MODE_FAST; - break; + if (hasCapability(MANUAL_POST_PROCESSING)) { + uint8_t hotPixelMode = 0; + uint8_t demosaicMode = 0; + uint8_t noiseMode = 0; + uint8_t shadingMode = 0; + uint8_t colorMode = 0; + uint8_t tonemapMode = 0; + uint8_t edgeMode = 0; + switch (type) { + case CAMERA3_TEMPLATE_STILL_CAPTURE: + // fall-through + case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT: + // fall-through + case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG: + hotPixelMode = ANDROID_HOT_PIXEL_MODE_HIGH_QUALITY; + demosaicMode = ANDROID_DEMOSAIC_MODE_HIGH_QUALITY; + noiseMode = ANDROID_NOISE_REDUCTION_MODE_HIGH_QUALITY; + shadingMode = ANDROID_SHADING_MODE_HIGH_QUALITY; + colorMode = ANDROID_COLOR_CORRECTION_MODE_HIGH_QUALITY; + tonemapMode = ANDROID_TONEMAP_MODE_HIGH_QUALITY; + edgeMode = ANDROID_EDGE_MODE_HIGH_QUALITY; + break; + case CAMERA3_TEMPLATE_PREVIEW: + // fall-through + case CAMERA3_TEMPLATE_VIDEO_RECORD: + // fall-through + default: + hotPixelMode = ANDROID_HOT_PIXEL_MODE_FAST; + demosaicMode = ANDROID_DEMOSAIC_MODE_FAST; + noiseMode = ANDROID_NOISE_REDUCTION_MODE_FAST; + shadingMode = ANDROID_SHADING_MODE_FAST; + colorMode = ANDROID_COLOR_CORRECTION_MODE_FAST; + tonemapMode = ANDROID_TONEMAP_MODE_FAST; + edgeMode = ANDROID_EDGE_MODE_FAST; + break; + } + settings.update(ANDROID_HOT_PIXEL_MODE, &hotPixelMode, 1); + settings.update(ANDROID_DEMOSAIC_MODE, &demosaicMode, 1); + settings.update(ANDROID_NOISE_REDUCTION_MODE, &noiseMode, 1); + settings.update(ANDROID_SHADING_MODE, &shadingMode, 1); + settings.update(ANDROID_COLOR_CORRECTION_MODE, &colorMode, 1); + settings.update(ANDROID_TONEMAP_MODE, &tonemapMode, 1); + settings.update(ANDROID_EDGE_MODE, &edgeMode, 1); } - settings.update(ANDROID_HOT_PIXEL_MODE, &hotPixelMode, 1); - settings.update(ANDROID_DEMOSAIC_MODE, &demosaicMode, 1); - settings.update(ANDROID_NOISE_REDUCTION_MODE, &noiseMode, 1); - settings.update(ANDROID_SHADING_MODE, &shadingMode, 1); - settings.update(ANDROID_COLOR_CORRECTION_MODE, &colorMode, 1); - settings.update(ANDROID_TONEMAP_MODE, &tonemapMode, 1); - settings.update(ANDROID_EDGE_MODE, &edgeMode, 1); - - /** android.noise */ - - static const uint8_t noiseStrength = 5; - settings.update(ANDROID_NOISE_REDUCTION_STRENGTH, &noiseStrength, 1); /** android.colorCorrection */ - static const camera_metadata_rational colorTransform[9] = { - {1,1}, {0,1}, {0,1}, - {0,1}, {1,1}, {0,1}, - {0,1}, {0,1}, {1,1} - }; - settings.update(ANDROID_COLOR_CORRECTION_TRANSFORM, colorTransform, 9); + if (hasCapability(MANUAL_POST_PROCESSING)) { + static const camera_metadata_rational colorTransform[9] = { + {1,1}, {0,1}, {0,1}, + {0,1}, {1,1}, {0,1}, + {0,1}, {0,1}, {1,1} + }; + settings.update(ANDROID_COLOR_CORRECTION_TRANSFORM, colorTransform, 9); - static const float colorGains[4] = { - 1.0f, 1.0f, 1.0f, 1.0f - }; - settings.update(ANDROID_COLOR_CORRECTION_GAINS, colorGains, 4); + static const float colorGains[4] = { + 1.0f, 1.0f, 1.0f, 1.0f + }; + settings.update(ANDROID_COLOR_CORRECTION_GAINS, colorGains, 4); + } /** android.tonemap */ - static const float tonemapCurve[4] = { - 0.f, 0.f, - 1.f, 1.f - }; - settings.update(ANDROID_TONEMAP_CURVE_RED, tonemapCurve, 4); - settings.update(ANDROID_TONEMAP_CURVE_GREEN, tonemapCurve, 4); - settings.update(ANDROID_TONEMAP_CURVE_BLUE, tonemapCurve, 4); - - /** android.edge */ - static const uint8_t edgeStrength = 5; - settings.update(ANDROID_EDGE_STRENGTH, &edgeStrength, 1); + if (hasCapability(MANUAL_POST_PROCESSING)) { + static const float tonemapCurve[4] = { + 0.f, 0.f, + 1.f, 1.f + }; + settings.update(ANDROID_TONEMAP_CURVE_RED, tonemapCurve, 4); + settings.update(ANDROID_TONEMAP_CURVE_GREEN, tonemapCurve, 4); + settings.update(ANDROID_TONEMAP_CURVE_BLUE, tonemapCurve, 4); + } /** android.scaler */ - static const int32_t cropRegion[4] = { - 0, 0, (int32_t)Sensor::kResolution[0], (int32_t)Sensor::kResolution[1] - }; - settings.update(ANDROID_SCALER_CROP_REGION, cropRegion, 4); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const int32_t cropRegion[4] = { + 0, 0, (int32_t)Sensor::kResolution[0], (int32_t)Sensor::kResolution[1] + }; + settings.update(ANDROID_SCALER_CROP_REGION, cropRegion, 4); + } /** android.jpeg */ - static const uint8_t jpegQuality = 80; - settings.update(ANDROID_JPEG_QUALITY, &jpegQuality, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t jpegQuality = 80; + settings.update(ANDROID_JPEG_QUALITY, &jpegQuality, 1); - static const int32_t thumbnailSize[2] = { - 640, 480 - }; - settings.update(ANDROID_JPEG_THUMBNAIL_SIZE, thumbnailSize, 2); + static const int32_t thumbnailSize[2] = { + 640, 480 + }; + settings.update(ANDROID_JPEG_THUMBNAIL_SIZE, thumbnailSize, 2); - static const uint8_t thumbnailQuality = 80; - settings.update(ANDROID_JPEG_THUMBNAIL_QUALITY, &thumbnailQuality, 1); + static const uint8_t thumbnailQuality = 80; + settings.update(ANDROID_JPEG_THUMBNAIL_QUALITY, &thumbnailQuality, 1); - static const double gpsCoordinates[2] = { - 0, 0 - }; - settings.update(ANDROID_JPEG_GPS_COORDINATES, gpsCoordinates, 2); + static const double gpsCoordinates[2] = { + 0, 0 + }; + settings.update(ANDROID_JPEG_GPS_COORDINATES, gpsCoordinates, 2); - static const uint8_t gpsProcessingMethod[32] = "None"; - settings.update(ANDROID_JPEG_GPS_PROCESSING_METHOD, gpsProcessingMethod, 32); + static const uint8_t gpsProcessingMethod[32] = "None"; + settings.update(ANDROID_JPEG_GPS_PROCESSING_METHOD, gpsProcessingMethod, 32); - static const int64_t gpsTimestamp = 0; - settings.update(ANDROID_JPEG_GPS_TIMESTAMP, &gpsTimestamp, 1); + static const int64_t gpsTimestamp = 0; + settings.update(ANDROID_JPEG_GPS_TIMESTAMP, &gpsTimestamp, 1); - static const int32_t jpegOrientation = 0; - settings.update(ANDROID_JPEG_ORIENTATION, &jpegOrientation, 1); + static const int32_t jpegOrientation = 0; + settings.update(ANDROID_JPEG_ORIENTATION, &jpegOrientation, 1); + } /** android.stats */ - static const uint8_t faceDetectMode = - ANDROID_STATISTICS_FACE_DETECT_MODE_OFF; - settings.update(ANDROID_STATISTICS_FACE_DETECT_MODE, &faceDetectMode, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t faceDetectMode = + ANDROID_STATISTICS_FACE_DETECT_MODE_OFF; + settings.update(ANDROID_STATISTICS_FACE_DETECT_MODE, &faceDetectMode, 1); - static const uint8_t hotPixelMapMode = - ANDROID_STATISTICS_HOT_PIXEL_MAP_MODE_OFF; - settings.update(ANDROID_STATISTICS_HOT_PIXEL_MAP_MODE, &hotPixelMapMode, 1); + static const uint8_t hotPixelMapMode = + ANDROID_STATISTICS_HOT_PIXEL_MAP_MODE_OFF; + settings.update(ANDROID_STATISTICS_HOT_PIXEL_MAP_MODE, &hotPixelMapMode, 1); + } // faceRectangles, faceScores, faceLandmarks, faceIds, histogram, // sharpnessMap only in frames @@ -600,28 +617,6 @@ const camera_metadata_t* EmulatedFakeCamera3::constructDefaultRequestSettings( ANDROID_CONTROL_MODE_AUTO; settings.update(ANDROID_CONTROL_MODE, &controlMode, 1); - static const uint8_t effectMode = ANDROID_CONTROL_EFFECT_MODE_OFF; - settings.update(ANDROID_CONTROL_EFFECT_MODE, &effectMode, 1); - - static const uint8_t sceneMode = ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY; - settings.update(ANDROID_CONTROL_SCENE_MODE, &sceneMode, 1); - - const uint8_t aeMode = (type == CAMERA3_TEMPLATE_MANUAL) ? - ANDROID_CONTROL_AE_MODE_OFF : - ANDROID_CONTROL_AE_MODE_ON; - settings.update(ANDROID_CONTROL_AE_MODE, &aeMode, 1); - - static const uint8_t aeLock = ANDROID_CONTROL_AE_LOCK_OFF; - settings.update(ANDROID_CONTROL_AE_LOCK, &aeLock, 1); - - static const int32_t controlRegions[5] = { - 0, 0, 0, 0, 0 - }; - settings.update(ANDROID_CONTROL_AE_REGIONS, controlRegions, 5); - - static const int32_t aeExpCompensation = 0; - settings.update(ANDROID_CONTROL_AE_EXPOSURE_COMPENSATION, &aeExpCompensation, 1); - int32_t aeTargetFpsRange[2] = { 5, 30 }; @@ -630,67 +625,93 @@ const camera_metadata_t* EmulatedFakeCamera3::constructDefaultRequestSettings( } settings.update(ANDROID_CONTROL_AE_TARGET_FPS_RANGE, aeTargetFpsRange, 2); - static const uint8_t aeAntibandingMode = - ANDROID_CONTROL_AE_ANTIBANDING_MODE_AUTO; - settings.update(ANDROID_CONTROL_AE_ANTIBANDING_MODE, &aeAntibandingMode, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { - static const uint8_t aePrecaptureTrigger = ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE; - settings.update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER, &aePrecaptureTrigger, 1); + static const uint8_t effectMode = ANDROID_CONTROL_EFFECT_MODE_OFF; + settings.update(ANDROID_CONTROL_EFFECT_MODE, &effectMode, 1); - const uint8_t awbMode = (type == CAMERA3_TEMPLATE_MANUAL) ? - ANDROID_CONTROL_AWB_MODE_OFF : - ANDROID_CONTROL_AWB_MODE_AUTO; - settings.update(ANDROID_CONTROL_AWB_MODE, &awbMode, 1); + static const uint8_t sceneMode = ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY; + settings.update(ANDROID_CONTROL_SCENE_MODE, &sceneMode, 1); - static const uint8_t awbLock = ANDROID_CONTROL_AWB_LOCK_OFF; - settings.update(ANDROID_CONTROL_AWB_LOCK, &awbLock, 1); + const uint8_t aeMode = (type == CAMERA3_TEMPLATE_MANUAL) ? + ANDROID_CONTROL_AE_MODE_OFF : + ANDROID_CONTROL_AE_MODE_ON; + settings.update(ANDROID_CONTROL_AE_MODE, &aeMode, 1); + + static const uint8_t aeLock = ANDROID_CONTROL_AE_LOCK_OFF; + settings.update(ANDROID_CONTROL_AE_LOCK, &aeLock, 1); + + static const int32_t controlRegions[5] = { + 0, 0, 0, 0, 0 + }; + settings.update(ANDROID_CONTROL_AE_REGIONS, controlRegions, 5); + + static const int32_t aeExpCompensation = 0; + settings.update(ANDROID_CONTROL_AE_EXPOSURE_COMPENSATION, &aeExpCompensation, 1); - uint8_t afMode = 0; - switch (type) { - case CAMERA3_TEMPLATE_PREVIEW: - afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; - break; - case CAMERA3_TEMPLATE_STILL_CAPTURE: - afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; - break; - case CAMERA3_TEMPLATE_VIDEO_RECORD: - afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_VIDEO; - break; - case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT: - afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_VIDEO; - break; - case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG: - afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; - break; - case CAMERA3_TEMPLATE_MANUAL: - afMode = ANDROID_CONTROL_AF_MODE_OFF; - break; - default: - afMode = ANDROID_CONTROL_AF_MODE_AUTO; - break; - } - settings.update(ANDROID_CONTROL_AF_MODE, &afMode, 1); - settings.update(ANDROID_CONTROL_AF_REGIONS, controlRegions, 5); + static const uint8_t aeAntibandingMode = + ANDROID_CONTROL_AE_ANTIBANDING_MODE_AUTO; + settings.update(ANDROID_CONTROL_AE_ANTIBANDING_MODE, &aeAntibandingMode, 1); - static const uint8_t afTrigger = ANDROID_CONTROL_AF_TRIGGER_IDLE; - settings.update(ANDROID_CONTROL_AF_TRIGGER, &afTrigger, 1); + static const uint8_t aePrecaptureTrigger = ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE; + settings.update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER, &aePrecaptureTrigger, 1); - static const uint8_t vstabMode = - ANDROID_CONTROL_VIDEO_STABILIZATION_MODE_OFF; - settings.update(ANDROID_CONTROL_VIDEO_STABILIZATION_MODE, &vstabMode, 1); + const uint8_t awbMode = (type == CAMERA3_TEMPLATE_MANUAL) ? + ANDROID_CONTROL_AWB_MODE_OFF : + ANDROID_CONTROL_AWB_MODE_AUTO; + settings.update(ANDROID_CONTROL_AWB_MODE, &awbMode, 1); - static const uint8_t blackLevelLock = ANDROID_BLACK_LEVEL_LOCK_OFF; - settings.update(ANDROID_BLACK_LEVEL_LOCK, &blackLevelLock, 1); + static const uint8_t awbLock = ANDROID_CONTROL_AWB_LOCK_OFF; + settings.update(ANDROID_CONTROL_AWB_LOCK, &awbLock, 1); - static const uint8_t lensShadingMapMode = ANDROID_STATISTICS_LENS_SHADING_MAP_MODE_OFF; - settings.update(ANDROID_STATISTICS_LENS_SHADING_MAP_MODE, &lensShadingMapMode, 1); + uint8_t afMode = 0; + switch (type) { + case CAMERA3_TEMPLATE_PREVIEW: + afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; + break; + case CAMERA3_TEMPLATE_STILL_CAPTURE: + afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; + break; + case CAMERA3_TEMPLATE_VIDEO_RECORD: + afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_VIDEO; + break; + case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT: + afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_VIDEO; + break; + case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG: + afMode = ANDROID_CONTROL_AF_MODE_CONTINUOUS_PICTURE; + break; + case CAMERA3_TEMPLATE_MANUAL: + afMode = ANDROID_CONTROL_AF_MODE_OFF; + break; + default: + afMode = ANDROID_CONTROL_AF_MODE_AUTO; + break; + } + settings.update(ANDROID_CONTROL_AF_MODE, &afMode, 1); + + settings.update(ANDROID_CONTROL_AF_REGIONS, controlRegions, 5); - static const uint8_t aberrationMode = ANDROID_COLOR_CORRECTION_ABERRATION_MODE_FAST; - settings.update(ANDROID_COLOR_CORRECTION_ABERRATION_MODE, &aberrationMode, 1); + static const uint8_t afTrigger = ANDROID_CONTROL_AF_TRIGGER_IDLE; + settings.update(ANDROID_CONTROL_AF_TRIGGER, &afTrigger, 1); - static const int32_t testPatternMode = ANDROID_SENSOR_TEST_PATTERN_MODE_OFF; - settings.update(ANDROID_SENSOR_TEST_PATTERN_MODE, &testPatternMode, 1); + static const uint8_t vstabMode = + ANDROID_CONTROL_VIDEO_STABILIZATION_MODE_OFF; + settings.update(ANDROID_CONTROL_VIDEO_STABILIZATION_MODE, &vstabMode, 1); + + static const uint8_t blackLevelLock = ANDROID_BLACK_LEVEL_LOCK_OFF; + settings.update(ANDROID_BLACK_LEVEL_LOCK, &blackLevelLock, 1); + + static const uint8_t lensShadingMapMode = ANDROID_STATISTICS_LENS_SHADING_MAP_MODE_OFF; + settings.update(ANDROID_STATISTICS_LENS_SHADING_MAP_MODE, &lensShadingMapMode, 1); + + static const uint8_t aberrationMode = ANDROID_COLOR_CORRECTION_ABERRATION_MODE_FAST; + settings.update(ANDROID_COLOR_CORRECTION_ABERRATION_MODE, &aberrationMode, 1); + + static const int32_t testPatternMode = ANDROID_SENSOR_TEST_PATTERN_MODE_OFF; + settings.update(ANDROID_SENSOR_TEST_PATTERN_MODE, &testPatternMode, 1); + } mDefaultTemplates[type] = settings.release(); @@ -818,10 +839,14 @@ status_t EmulatedFakeCamera3::processCaptureRequest( nsecs_t frameDuration; uint32_t sensitivity; bool needJpeg = false; + camera_metadata_entry_t entry; - exposureTime = settings.find(ANDROID_SENSOR_EXPOSURE_TIME).data.i64[0]; - frameDuration = settings.find(ANDROID_SENSOR_FRAME_DURATION).data.i64[0]; - sensitivity = settings.find(ANDROID_SENSOR_SENSITIVITY).data.i32[0]; + entry = settings.find(ANDROID_SENSOR_EXPOSURE_TIME); + exposureTime = (entry.count > 0) ? entry.data.i64[0] : Sensor::kExposureTimeRange[0]; + entry = settings.find(ANDROID_SENSOR_FRAME_DURATION); + frameDuration = (entry.count > 0)? entry.data.i64[0] : Sensor::kFrameDurationRange[0]; + entry = settings.find(ANDROID_SENSOR_SENSITIVITY); + sensitivity = (entry.count > 0) ? entry.data.i32[0] : Sensor::kSensitivityRange[0]; if (exposureTime > frameDuration) { frameDuration = exposureTime + Sensor::kMinVerticalBlank; @@ -846,6 +871,7 @@ status_t EmulatedFakeCamera3::processCaptureRequest( destBuf.height = srcBuf.stream->height; destBuf.format = privBuffer->format; // Use real private format destBuf.stride = srcBuf.stream->width; // TODO: query from gralloc + destBuf.dataSpace = srcBuf.stream->data_space; destBuf.buffer = srcBuf.buffer; if (destBuf.format == HAL_PIXEL_FORMAT_BLOB) { @@ -990,8 +1016,8 @@ status_t EmulatedFakeCamera3::getCameraCapabilities() { * property doesn't exist, it is assumed to list FULL. */ char prop[PROPERTY_VALUE_MAX]; if (property_get(key, prop, NULL) > 0) { - char **saveptr = nullptr; - char *cap = strtok_r(prop, " ,", saveptr); + char *saveptr = nullptr; + char *cap = strtok_r(prop, " ,", &saveptr); while (cap != NULL) { for (int i = 0; i < NUM_CAPABILITIES; i++) { if (!strcasecmp(cap, sAvailableCapabilitiesStrings[i])) { @@ -999,26 +1025,39 @@ status_t EmulatedFakeCamera3::getCameraCapabilities() { break; } } - cap = strtok_r(NULL, " ,", saveptr); + cap = strtok_r(NULL, " ,", &saveptr); } if (mCapabilities.size() == 0) { ALOGE("qemu.sf.back_camera_caps had no valid capabilities: %s", prop); } } - // Default to FULL_LEVEL if nothing is defined + // Default to FULL_LEVEL plus RAW if nothing is defined if (mCapabilities.size() == 0) { mCapabilities.add(FULL_LEVEL); + mCapabilities.add(RAW); } // Add level-based caps if (hasCapability(FULL_LEVEL)) { - mCapabilities.add(BACKWARD_COMPATIBLE); mCapabilities.add(BURST_CAPTURE); mCapabilities.add(READ_SENSOR_SETTINGS); mCapabilities.add(MANUAL_SENSOR); mCapabilities.add(MANUAL_POST_PROCESSING); }; + // Backwards-compatible is required for most other caps + // Not required for DEPTH_OUTPUT, though. + if (hasCapability(BURST_CAPTURE) || + hasCapability(READ_SENSOR_SETTINGS) || + hasCapability(RAW) || + hasCapability(MANUAL_SENSOR) || + hasCapability(MANUAL_POST_PROCESSING) || + hasCapability(PRIVATE_REPROCESSING) || + hasCapability(YUV_REPROCESSING) || + hasCapability(CONSTRAINED_HIGH_SPEED_VIDEO)) { + mCapabilities.add(BACKWARD_COMPATIBLE); + } + ALOGI("Camera %d capabilities:", mCameraID); for (size_t i = 0; i < mCapabilities.size(); i++) { ALOGI(" %s", sAvailableCapabilitiesStrings[mCapabilities[i]]); @@ -1043,62 +1082,24 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { res = info.update(name, varptr, count); \ if (res != OK) return res - // android.lens - - // 5 cm min focus distance for back camera, infinity (fixed focus) for front - const float minFocusDistance = mFacingBack ? 1.0/0.05 : 0.0; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_MINIMUM_FOCUS_DISTANCE, - &minFocusDistance, 1); - - // 5 m hyperfocal distance for back camera, infinity (fixed focus) for front - const float hyperFocalDistance = mFacingBack ? 1.0/5.0 : 0.0; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_HYPERFOCAL_DISTANCE, - &minFocusDistance, 1); - - static const float focalLength = 3.30f; // mm - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_FOCAL_LENGTHS, - &focalLength, 1); - static const float aperture = 2.8f; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_APERTURES, - &aperture, 1); - static const float filterDensity = 0; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_FILTER_DENSITIES, - &filterDensity, 1); - static const uint8_t availableOpticalStabilization = - ANDROID_LENS_OPTICAL_STABILIZATION_MODE_OFF; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_OPTICAL_STABILIZATION, - &availableOpticalStabilization, 1); - - static const int32_t lensShadingMapSize[] = {1, 1}; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_SHADING_MAP_SIZE, lensShadingMapSize, - sizeof(lensShadingMapSize)/sizeof(int32_t)); - - static const uint8_t lensFacing = mFacingBack ? - ANDROID_LENS_FACING_BACK : ANDROID_LENS_FACING_FRONT; - ADD_STATIC_ENTRY(ANDROID_LENS_FACING, &lensFacing, 1); - - static const uint8_t lensFocusCalibration = - ANDROID_LENS_INFO_FOCUS_DISTANCE_CALIBRATION_APPROXIMATE; - ADD_STATIC_ENTRY(ANDROID_LENS_INFO_FOCUS_DISTANCE_CALIBRATION, &lensFocusCalibration, 1); - // android.sensor - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_EXPOSURE_TIME_RANGE, - Sensor::kExposureTimeRange, 2); + if (hasCapability(MANUAL_SENSOR)) { - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_MAX_FRAME_DURATION, - &Sensor::kFrameDurationRange[1], 1); + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_EXPOSURE_TIME_RANGE, + Sensor::kExposureTimeRange, 2); - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_SENSITIVITY_RANGE, - Sensor::kSensitivityRange, - sizeof(Sensor::kSensitivityRange) - /sizeof(int32_t)); + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_MAX_FRAME_DURATION, + &Sensor::kFrameDurationRange[1], 1); - ADD_STATIC_ENTRY(ANDROID_SENSOR_MAX_ANALOG_SENSITIVITY, - &Sensor::kSensitivityRange[1], 1); + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_SENSITIVITY_RANGE, + Sensor::kSensitivityRange, + sizeof(Sensor::kSensitivityRange) + /sizeof(int32_t)); - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_COLOR_FILTER_ARRANGEMENT, - &Sensor::kColorFilterArrangement, 1); + ADD_STATIC_ENTRY(ANDROID_SENSOR_MAX_ANALOG_SENSITIVITY, + &Sensor::kSensitivityRange[1], 1); + } static const float sensorPhysicalSize[2] = {3.20f, 2.40f}; // mm ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_PHYSICAL_SIZE, @@ -1110,242 +1111,371 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_ACTIVE_ARRAY_SIZE, (int32_t*)Sensor::kActiveArray, 4); - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_WHITE_LEVEL, - (int32_t*)&Sensor::kMaxRawValue, 1); + static const int32_t orientation = 90; // Aligned with 'long edge' + ADD_STATIC_ENTRY(ANDROID_SENSOR_ORIENTATION, &orientation, 1); + + static const uint8_t timestampSource = ANDROID_SENSOR_INFO_TIMESTAMP_SOURCE_REALTIME; + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_TIMESTAMP_SOURCE, ×tampSource, 1); + + if (hasCapability(RAW)) { + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_COLOR_FILTER_ARRANGEMENT, + &Sensor::kColorFilterArrangement, 1); + + ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_WHITE_LEVEL, + (int32_t*)&Sensor::kMaxRawValue, 1); - static const int32_t blackLevelPattern[4] = { + static const int32_t blackLevelPattern[4] = { (int32_t)Sensor::kBlackLevel, (int32_t)Sensor::kBlackLevel, (int32_t)Sensor::kBlackLevel, (int32_t)Sensor::kBlackLevel - }; - ADD_STATIC_ENTRY(ANDROID_SENSOR_BLACK_LEVEL_PATTERN, - blackLevelPattern, sizeof(blackLevelPattern)/sizeof(int32_t)); - - static const int32_t orientation = 90; // Aligned with 'long edge' - ADD_STATIC_ENTRY(ANDROID_SENSOR_ORIENTATION, &orientation, 1); + }; + ADD_STATIC_ENTRY(ANDROID_SENSOR_BLACK_LEVEL_PATTERN, + blackLevelPattern, sizeof(blackLevelPattern)/sizeof(int32_t)); + } - static const int32_t availableTestPatternModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const int32_t availableTestPatternModes[] = { ANDROID_SENSOR_TEST_PATTERN_MODE_OFF - }; - ADD_STATIC_ENTRY(ANDROID_SENSOR_AVAILABLE_TEST_PATTERN_MODES, - availableTestPatternModes, sizeof(availableTestPatternModes)/sizeof(int32_t)); + }; + ADD_STATIC_ENTRY(ANDROID_SENSOR_AVAILABLE_TEST_PATTERN_MODES, + availableTestPatternModes, sizeof(availableTestPatternModes)/sizeof(int32_t)); + } - static const uint8_t timestampSource = ANDROID_SENSOR_INFO_TIMESTAMP_SOURCE_REALTIME; - ADD_STATIC_ENTRY(ANDROID_SENSOR_INFO_TIMESTAMP_SOURCE, ×tampSource, 1); + // android.lens + + static const float focalLength = 3.30f; // mm + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_FOCAL_LENGTHS, + &focalLength, 1); + + if (hasCapability(BACKWARD_COMPATIBLE)) { + // 5 cm min focus distance for back camera, infinity (fixed focus) for front + const float minFocusDistance = mFacingBack ? 1.0/0.05 : 0.0; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_MINIMUM_FOCUS_DISTANCE, + &minFocusDistance, 1); + + // 5 m hyperfocal distance for back camera, infinity (fixed focus) for front + const float hyperFocalDistance = mFacingBack ? 1.0/5.0 : 0.0; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_HYPERFOCAL_DISTANCE, + &minFocusDistance, 1); + + static const float aperture = 2.8f; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_APERTURES, + &aperture, 1); + static const float filterDensity = 0; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_FILTER_DENSITIES, + &filterDensity, 1); + static const uint8_t availableOpticalStabilization = + ANDROID_LENS_OPTICAL_STABILIZATION_MODE_OFF; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_AVAILABLE_OPTICAL_STABILIZATION, + &availableOpticalStabilization, 1); + + static const int32_t lensShadingMapSize[] = {1, 1}; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_SHADING_MAP_SIZE, lensShadingMapSize, + sizeof(lensShadingMapSize)/sizeof(int32_t)); + + static const uint8_t lensFocusCalibration = + ANDROID_LENS_INFO_FOCUS_DISTANCE_CALIBRATION_APPROXIMATE; + ADD_STATIC_ENTRY(ANDROID_LENS_INFO_FOCUS_DISTANCE_CALIBRATION, &lensFocusCalibration, 1); + } + + if (hasCapability(DEPTH_OUTPUT)) { + // These could be included for non-DEPTH capability as well, but making this variable for + // testing coverage + + // 90 degree rotation to align with long edge of a phone device that's by default portrait + static const float qO[] = { 0.707107f, 0.f, 0.f, 0.707107f}; + + // Either a 180-degree rotation for back-facing, or no rotation for front-facing + const float qF[] = {(mFacingBack ? 0.f : 1.f), 0, (!mFacingBack ? 1.f : 0.f), 0}; + + // Quarternion product, orientation change then facing + const float lensPoseRotation[] = {qO[0]*qF[0] - qO[1]*qF[1] - qO[2]*qF[2] - qO[3]*qF[3], + qO[0]*qF[1] + qO[1]*qF[0] + qO[2]*qF[3] - qO[3]*qF[2], + qO[0]*qF[2] + qO[2]*qF[0] + qO[1]*qF[3] - qO[3]*qF[1], + qO[0]*qF[3] + qO[3]*qF[0] + qO[1]*qF[2] - qO[2]*qF[1]}; + + ADD_STATIC_ENTRY(ANDROID_LENS_POSE_ROTATION, lensPoseRotation, + sizeof(lensPoseRotation)/sizeof(float)); + + // Only one camera facing each way, so 0 translation needed to the center of the 'main' + // camera + static const float lensPoseTranslation[] = {0.f, 0.f, 0.f}; + + ADD_STATIC_ENTRY(ANDROID_LENS_POSE_TRANSLATION, lensPoseTranslation, + sizeof(lensPoseTranslation)/sizeof(float)); + + // Intrinsics are 'ideal' (f_x, f_y, c_x, c_y, s) match focal length and active array size + float f_x = focalLength * Sensor::kActiveArray[2] / sensorPhysicalSize[0]; + float f_y = focalLength * Sensor::kActiveArray[3] / sensorPhysicalSize[1]; + float c_x = Sensor::kActiveArray[2] / 2.f; + float c_y = Sensor::kActiveArray[3] / 2.f; + float s = 0.f; + const float lensIntrinsics[] = { f_x, f_y, c_x, c_y, s }; + + ADD_STATIC_ENTRY(ANDROID_LENS_INTRINSIC_CALIBRATION, lensIntrinsics, + sizeof(lensIntrinsics)/sizeof(float)); + + // No radial or tangential distortion + + float lensRadialDistortion[] = {1.0f, 0.f, 0.f, 0.f, 0.f, 0.f}; + + ADD_STATIC_ENTRY(ANDROID_LENS_RADIAL_DISTORTION, lensRadialDistortion, + sizeof(lensRadialDistortion)/sizeof(float)); + + } + + + static const uint8_t lensFacing = mFacingBack ? + ANDROID_LENS_FACING_BACK : ANDROID_LENS_FACING_FRONT; + ADD_STATIC_ENTRY(ANDROID_LENS_FACING, &lensFacing, 1); // android.flash static const uint8_t flashAvailable = 0; ADD_STATIC_ENTRY(ANDROID_FLASH_INFO_AVAILABLE, &flashAvailable, 1); - static const int64_t flashChargeDuration = 0; - ADD_STATIC_ENTRY(ANDROID_FLASH_INFO_CHARGE_DURATION, &flashChargeDuration, 1); - // android.tonemap - static const int32_t tonemapCurvePoints = 128; - ADD_STATIC_ENTRY(ANDROID_TONEMAP_MAX_CURVE_POINTS, &tonemapCurvePoints, 1); + if (hasCapability(MANUAL_POST_PROCESSING)) { + static const int32_t tonemapCurvePoints = 128; + ADD_STATIC_ENTRY(ANDROID_TONEMAP_MAX_CURVE_POINTS, &tonemapCurvePoints, 1); - static const uint8_t availableToneMapModes[] = { + static const uint8_t availableToneMapModes[] = { ANDROID_TONEMAP_MODE_CONTRAST_CURVE, ANDROID_TONEMAP_MODE_FAST, ANDROID_TONEMAP_MODE_HIGH_QUALITY - }; - ADD_STATIC_ENTRY(ANDROID_TONEMAP_AVAILABLE_TONE_MAP_MODES, availableToneMapModes, - sizeof(availableToneMapModes)); + }; + ADD_STATIC_ENTRY(ANDROID_TONEMAP_AVAILABLE_TONE_MAP_MODES, availableToneMapModes, + sizeof(availableToneMapModes)); + } // android.scaler - if (mFacingBack) { - - const int32_t availableStreamConfigurationsBack[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_BLOB, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT - }; - ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS, - availableStreamConfigurationsBack, - sizeof(availableStreamConfigurationsBack)/sizeof(int32_t)); - - const int64_t availableMinFrameDurationsBack[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] - }; - ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_MIN_FRAME_DURATIONS, - availableMinFrameDurationsBack, - sizeof(availableMinFrameDurationsBack)/sizeof(int64_t)); - - const int64_t availableStallDurationsBack[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, 0, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, 0, - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, 0, - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, 0, - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, 0, - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, 0, - HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] - }; - ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_STALL_DURATIONS, - availableStallDurationsBack, - sizeof(availableStallDurationsBack)/sizeof(int64_t)); - } else { + const std::vector availableStreamConfigurationsBasic = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_BLOB, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT + }; + const std::vector availableStreamConfigurationsRaw = { + HAL_PIXEL_FORMAT_RAW16, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT + }; + const std::vector availableStreamConfigurationsBurst = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT + }; - const int32_t availableStreamConfigurationsFront[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT, - HAL_PIXEL_FORMAT_BLOB, 640, 480, ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT - }; + std::vector availableStreamConfigurations; + + if (hasCapability(BACKWARD_COMPATIBLE)) { + availableStreamConfigurations.insert(availableStreamConfigurations.end(), + availableStreamConfigurationsBasic.begin(), + availableStreamConfigurationsBasic.end()); + } + if (hasCapability(RAW)) { + availableStreamConfigurations.insert(availableStreamConfigurations.end(), + availableStreamConfigurationsRaw.begin(), + availableStreamConfigurationsRaw.end()); + } + if (hasCapability(BURST_CAPTURE)) { + availableStreamConfigurations.insert(availableStreamConfigurations.end(), + availableStreamConfigurationsBurst.begin(), + availableStreamConfigurationsBurst.end()); + } + + if (availableStreamConfigurations.size() > 0) { ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS, - availableStreamConfigurationsFront, - sizeof(availableStreamConfigurationsFront)/sizeof(int32_t)); - - const int64_t availableMinFrameDurationsFront[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] - }; + &availableStreamConfigurations[0], + availableStreamConfigurations.size()); + } + + const std::vector availableMinFrameDurationsBasic = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] + }; + const std::vector availableMinFrameDurationsRaw = { + HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0] + }; + const std::vector availableMinFrameDurationsBurst = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, Sensor::kFrameDurationRange[0], + }; + + std::vector availableMinFrameDurations; + + if (hasCapability(BACKWARD_COMPATIBLE)) { + availableMinFrameDurations.insert(availableMinFrameDurations.end(), + availableMinFrameDurationsBasic.begin(), + availableMinFrameDurationsBasic.end()); + } + if (hasCapability(RAW)) { + availableMinFrameDurations.insert(availableMinFrameDurations.end(), + availableMinFrameDurationsRaw.begin(), + availableMinFrameDurationsRaw.end()); + } + if (hasCapability(BURST_CAPTURE)) { + availableMinFrameDurations.insert(availableMinFrameDurations.end(), + availableMinFrameDurationsBurst.begin(), + availableMinFrameDurationsBurst.end()); + } + + if (availableMinFrameDurations.size() > 0) { ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_MIN_FRAME_DURATIONS, - availableMinFrameDurationsFront, - sizeof(availableMinFrameDurationsFront)/sizeof(int64_t)); - - const int64_t availableStallDurationsFront[] = { - HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0], - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, 0, - HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, 0, - HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, 0, - HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, 0, - HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, 0, - HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, 0, - HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] - }; + &availableMinFrameDurations[0], + availableMinFrameDurations.size()); + } + + const std::vector availableStallDurationsBasic = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 320, 240, 0, + HAL_PIXEL_FORMAT_YCbCr_420_888, 320, 240, 0, + HAL_PIXEL_FORMAT_RGBA_8888, 320, 240, 0, + HAL_PIXEL_FORMAT_BLOB, 640, 480, Sensor::kFrameDurationRange[0] + }; + const std::vector availableStallDurationsRaw = { + HAL_PIXEL_FORMAT_RAW16, 640, 480, Sensor::kFrameDurationRange[0] + }; + const std::vector availableStallDurationsBurst = { + HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED, 640, 480, 0, + HAL_PIXEL_FORMAT_YCbCr_420_888, 640, 480, 0, + HAL_PIXEL_FORMAT_RGBA_8888, 640, 480, 0 + }; + + std::vector availableStallDurations; + + if (hasCapability(BACKWARD_COMPATIBLE)) { + availableStallDurations.insert(availableStallDurations.end(), + availableStallDurationsBasic.begin(), + availableStallDurationsBasic.end()); + } + if (hasCapability(RAW)) { + availableStallDurations.insert(availableStallDurations.end(), + availableStallDurationsRaw.begin(), + availableStallDurationsRaw.end()); + } + if (hasCapability(BURST_CAPTURE)) { + availableStallDurations.insert(availableStallDurations.end(), + availableStallDurationsBurst.begin(), + availableStallDurationsBurst.end()); + } + + if (availableStallDurations.size() > 0) { ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_STALL_DURATIONS, - availableStallDurationsFront, - sizeof(availableStallDurationsFront)/sizeof(int64_t)); + &availableStallDurations[0], + availableStallDurations.size()); } - static const uint8_t croppingType = ANDROID_SCALER_CROPPING_TYPE_FREEFORM; - ADD_STATIC_ENTRY(ANDROID_SCALER_CROPPING_TYPE, - &croppingType, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t croppingType = ANDROID_SCALER_CROPPING_TYPE_FREEFORM; + ADD_STATIC_ENTRY(ANDROID_SCALER_CROPPING_TYPE, + &croppingType, 1); - static const float maxZoom = 10; - ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_MAX_DIGITAL_ZOOM, - &maxZoom, 1); + static const float maxZoom = 10; + ADD_STATIC_ENTRY(ANDROID_SCALER_AVAILABLE_MAX_DIGITAL_ZOOM, + &maxZoom, 1); + } // android.jpeg - static const int32_t jpegThumbnailSizes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const int32_t jpegThumbnailSizes[] = { 0, 0, 160, 120, 320, 240 - }; - ADD_STATIC_ENTRY(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES, - jpegThumbnailSizes, sizeof(jpegThumbnailSizes)/sizeof(int32_t)); + }; + ADD_STATIC_ENTRY(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES, + jpegThumbnailSizes, sizeof(jpegThumbnailSizes)/sizeof(int32_t)); - static const int32_t jpegMaxSize = JpegCompressor::kMaxJpegSize; - ADD_STATIC_ENTRY(ANDROID_JPEG_MAX_SIZE, &jpegMaxSize, 1); + static const int32_t jpegMaxSize = JpegCompressor::kMaxJpegSize; + ADD_STATIC_ENTRY(ANDROID_JPEG_MAX_SIZE, &jpegMaxSize, 1); + } // android.stats - static const uint8_t availableFaceDetectModes[] = { - ANDROID_STATISTICS_FACE_DETECT_MODE_OFF, - ANDROID_STATISTICS_FACE_DETECT_MODE_SIMPLE, - ANDROID_STATISTICS_FACE_DETECT_MODE_FULL - }; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_AVAILABLE_FACE_DETECT_MODES, - availableFaceDetectModes, - sizeof(availableFaceDetectModes)); - - static const int32_t maxFaceCount = 8; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_MAX_FACE_COUNT, - &maxFaceCount, 1); - - static const int32_t histogramSize = 64; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_HISTOGRAM_BUCKET_COUNT, - &histogramSize, 1); - - static const int32_t maxHistogramCount = 1000; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_MAX_HISTOGRAM_COUNT, - &maxHistogramCount, 1); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableFaceDetectModes[] = { + ANDROID_STATISTICS_FACE_DETECT_MODE_OFF, + ANDROID_STATISTICS_FACE_DETECT_MODE_SIMPLE, + ANDROID_STATISTICS_FACE_DETECT_MODE_FULL + }; + ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_AVAILABLE_FACE_DETECT_MODES, + availableFaceDetectModes, + sizeof(availableFaceDetectModes)); - static const int32_t sharpnessMapSize[2] = {64, 64}; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_SHARPNESS_MAP_SIZE, - sharpnessMapSize, sizeof(sharpnessMapSize)/sizeof(int32_t)); + static const int32_t maxFaceCount = 8; + ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_MAX_FACE_COUNT, + &maxFaceCount, 1); - static const int32_t maxSharpnessMapValue = 1000; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_MAX_SHARPNESS_MAP_VALUE, - &maxSharpnessMapValue, 1); - static const uint8_t availableShadingMapModes[] = { + static const uint8_t availableShadingMapModes[] = { ANDROID_STATISTICS_LENS_SHADING_MAP_MODE_OFF - }; - ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_AVAILABLE_LENS_SHADING_MAP_MODES, - availableShadingMapModes, sizeof(availableShadingMapModes)); + }; + ADD_STATIC_ENTRY(ANDROID_STATISTICS_INFO_AVAILABLE_LENS_SHADING_MAP_MODES, + availableShadingMapModes, sizeof(availableShadingMapModes)); + } // android.sync - static const int32_t maxLatency = ANDROID_SYNC_MAX_LATENCY_PER_FRAME_CONTROL; + static const int32_t maxLatency = + hasCapability(FULL_LEVEL) ? ANDROID_SYNC_MAX_LATENCY_PER_FRAME_CONTROL : 3; ADD_STATIC_ENTRY(ANDROID_SYNC_MAX_LATENCY, &maxLatency, 1); // android.control - static const uint8_t availableControlModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableControlModes[] = { ANDROID_CONTROL_MODE_OFF, ANDROID_CONTROL_MODE_AUTO, ANDROID_CONTROL_MODE_USE_SCENE_MODE - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_MODES, - availableControlModes, sizeof(availableControlModes)); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_MODES, + availableControlModes, sizeof(availableControlModes)); + } else { + static const uint8_t availableControlModes[] = { + ANDROID_CONTROL_MODE_AUTO + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_MODES, + availableControlModes, sizeof(availableControlModes)); + } static const uint8_t availableSceneModes[] = { - ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY + hasCapability(BACKWARD_COMPATIBLE) ? + ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY : + ANDROID_CONTROL_SCENE_MODE_DISABLED }; ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_SCENE_MODES, availableSceneModes, sizeof(availableSceneModes)); - static const uint8_t availableEffects[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableEffects[] = { ANDROID_CONTROL_EFFECT_MODE_OFF - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_EFFECTS, - availableEffects, sizeof(availableEffects)); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_EFFECTS, + availableEffects, sizeof(availableEffects)); + } - static const int32_t max3aRegions[] = {/*AE*/ 1,/*AWB*/ 0,/*AF*/ 1}; - ADD_STATIC_ENTRY(ANDROID_CONTROL_MAX_REGIONS, - max3aRegions, sizeof(max3aRegions)/sizeof(max3aRegions[0])); + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const int32_t max3aRegions[] = {/*AE*/ 1,/*AWB*/ 0,/*AF*/ 1}; + ADD_STATIC_ENTRY(ANDROID_CONTROL_MAX_REGIONS, + max3aRegions, sizeof(max3aRegions)/sizeof(max3aRegions[0])); - static const uint8_t availableAeModes[] = { + static const uint8_t availableAeModes[] = { ANDROID_CONTROL_AE_MODE_OFF, ANDROID_CONTROL_AE_MODE_ON - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_AVAILABLE_MODES, - availableAeModes, sizeof(availableAeModes)); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_AVAILABLE_MODES, + availableAeModes, sizeof(availableAeModes)); - static const camera_metadata_rational exposureCompensationStep = { + static const camera_metadata_rational exposureCompensationStep = { 1, 3 - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_COMPENSATION_STEP, - &exposureCompensationStep, 1); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_COMPENSATION_STEP, + &exposureCompensationStep, 1); - int32_t exposureCompensationRange[] = {-9, 9}; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_COMPENSATION_RANGE, - exposureCompensationRange, - sizeof(exposureCompensationRange)/sizeof(int32_t)); + int32_t exposureCompensationRange[] = {-9, 9}; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_COMPENSATION_RANGE, + exposureCompensationRange, + sizeof(exposureCompensationRange)/sizeof(int32_t)); + } static const int32_t availableTargetFpsRanges[] = { 5, 30, 15, 30, 15, 15, 30, 30 @@ -1354,29 +1484,37 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { availableTargetFpsRanges, sizeof(availableTargetFpsRanges)/sizeof(int32_t)); - static const uint8_t availableAntibandingModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableAntibandingModes[] = { ANDROID_CONTROL_AE_ANTIBANDING_MODE_OFF, ANDROID_CONTROL_AE_ANTIBANDING_MODE_AUTO - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES, - availableAntibandingModes, sizeof(availableAntibandingModes)); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES, + availableAntibandingModes, sizeof(availableAntibandingModes)); + } + + static const uint8_t aeLockAvailable = hasCapability(BACKWARD_COMPATIBLE) ? + ANDROID_CONTROL_AE_LOCK_AVAILABLE_TRUE : ANDROID_CONTROL_AE_LOCK_AVAILABLE_FALSE; - static const uint8_t aeLockAvailable = ANDROID_CONTROL_AE_LOCK_AVAILABLE_TRUE; ADD_STATIC_ENTRY(ANDROID_CONTROL_AE_LOCK_AVAILABLE, &aeLockAvailable, 1); - static const uint8_t availableAwbModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableAwbModes[] = { ANDROID_CONTROL_AWB_MODE_OFF, ANDROID_CONTROL_AWB_MODE_AUTO, ANDROID_CONTROL_AWB_MODE_INCANDESCENT, ANDROID_CONTROL_AWB_MODE_FLUORESCENT, ANDROID_CONTROL_AWB_MODE_DAYLIGHT, ANDROID_CONTROL_AWB_MODE_SHADE - }; - ADD_STATIC_ENTRY(ANDROID_CONTROL_AWB_AVAILABLE_MODES, - availableAwbModes, sizeof(availableAwbModes)); + }; + ADD_STATIC_ENTRY(ANDROID_CONTROL_AWB_AVAILABLE_MODES, + availableAwbModes, sizeof(availableAwbModes)); + } + + static const uint8_t awbLockAvailable = hasCapability(BACKWARD_COMPATIBLE) ? + ANDROID_CONTROL_AWB_LOCK_AVAILABLE_TRUE : ANDROID_CONTROL_AWB_LOCK_AVAILABLE_FALSE; - static const uint8_t awbLockAvailable = ANDROID_CONTROL_AWB_LOCK_AVAILABLE_TRUE; ADD_STATIC_ENTRY(ANDROID_CONTROL_AWB_LOCK_AVAILABLE, &awbLockAvailable, 1); @@ -1392,37 +1530,52 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { ANDROID_CONTROL_AF_MODE_OFF }; - if (mFacingBack) { + if (mFacingBack && hasCapability(BACKWARD_COMPATIBLE)) { ADD_STATIC_ENTRY(ANDROID_CONTROL_AF_AVAILABLE_MODES, - availableAfModesBack, sizeof(availableAfModesBack)); + availableAfModesBack, sizeof(availableAfModesBack)); } else { ADD_STATIC_ENTRY(ANDROID_CONTROL_AF_AVAILABLE_MODES, - availableAfModesFront, sizeof(availableAfModesFront)); + availableAfModesFront, sizeof(availableAfModesFront)); } static const uint8_t availableVstabModes[] = { - ANDROID_CONTROL_VIDEO_STABILIZATION_MODE_OFF + ANDROID_CONTROL_VIDEO_STABILIZATION_MODE_OFF }; ADD_STATIC_ENTRY(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES, availableVstabModes, sizeof(availableVstabModes)); // android.colorCorrection - static const uint8_t availableAberrationModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableAberrationModes[] = { ANDROID_COLOR_CORRECTION_ABERRATION_MODE_OFF, ANDROID_COLOR_CORRECTION_ABERRATION_MODE_FAST, ANDROID_COLOR_CORRECTION_ABERRATION_MODE_HIGH_QUALITY - }; - ADD_STATIC_ENTRY(ANDROID_COLOR_CORRECTION_AVAILABLE_ABERRATION_MODES, - availableAberrationModes, sizeof(availableAberrationModes)); - + }; + ADD_STATIC_ENTRY(ANDROID_COLOR_CORRECTION_AVAILABLE_ABERRATION_MODES, + availableAberrationModes, sizeof(availableAberrationModes)); + } else { + static const uint8_t availableAberrationModes[] = { + ANDROID_COLOR_CORRECTION_ABERRATION_MODE_OFF, + }; + ADD_STATIC_ENTRY(ANDROID_COLOR_CORRECTION_AVAILABLE_ABERRATION_MODES, + availableAberrationModes, sizeof(availableAberrationModes)); + } // android.edge - static const uint8_t availableEdgeModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableEdgeModes[] = { ANDROID_EDGE_MODE_OFF, ANDROID_EDGE_MODE_FAST, ANDROID_EDGE_MODE_HIGH_QUALITY - }; - ADD_STATIC_ENTRY(ANDROID_EDGE_AVAILABLE_EDGE_MODES, - availableEdgeModes, sizeof(availableEdgeModes)); + }; + ADD_STATIC_ENTRY(ANDROID_EDGE_AVAILABLE_EDGE_MODES, + availableEdgeModes, sizeof(availableEdgeModes)); + } else { + static const uint8_t availableEdgeModes[] = { + ANDROID_EDGE_MODE_OFF + }; + ADD_STATIC_ENTRY(ANDROID_EDGE_AVAILABLE_EDGE_MODES, + availableEdgeModes, sizeof(availableEdgeModes)); + } // android.info @@ -1435,21 +1588,74 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { // android.noiseReduction - static const uint8_t availableNoiseReductionModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableNoiseReductionModes[] = { ANDROID_NOISE_REDUCTION_MODE_OFF, ANDROID_NOISE_REDUCTION_MODE_FAST, ANDROID_NOISE_REDUCTION_MODE_HIGH_QUALITY - }; - ADD_STATIC_ENTRY(ANDROID_NOISE_REDUCTION_AVAILABLE_NOISE_REDUCTION_MODES, - availableNoiseReductionModes, sizeof(availableNoiseReductionModes)); + }; + ADD_STATIC_ENTRY(ANDROID_NOISE_REDUCTION_AVAILABLE_NOISE_REDUCTION_MODES, + availableNoiseReductionModes, sizeof(availableNoiseReductionModes)); + } else { + static const uint8_t availableNoiseReductionModes[] = { + ANDROID_NOISE_REDUCTION_MODE_OFF, + }; + ADD_STATIC_ENTRY(ANDROID_NOISE_REDUCTION_AVAILABLE_NOISE_REDUCTION_MODES, + availableNoiseReductionModes, sizeof(availableNoiseReductionModes)); + } + + // android.depth + + if (hasCapability(DEPTH_OUTPUT)) { + + static const int32_t maxDepthSamples = 100; + ADD_STATIC_ENTRY(ANDROID_DEPTH_MAX_DEPTH_SAMPLES, + &maxDepthSamples, 1); + + static const int32_t availableDepthStreamConfigurations[] = { + HAL_PIXEL_FORMAT_Y16, 160, 120, ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS_OUTPUT, + HAL_PIXEL_FORMAT_BLOB, maxDepthSamples,1, ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS_OUTPUT + }; + ADD_STATIC_ENTRY(ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS, + availableDepthStreamConfigurations, + sizeof(availableDepthStreamConfigurations)/sizeof(int32_t)); + + static const int64_t availableDepthMinFrameDurations[] = { + HAL_PIXEL_FORMAT_Y16, 160, 120, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_BLOB, maxDepthSamples,1, Sensor::kFrameDurationRange[0] + }; + ADD_STATIC_ENTRY(ANDROID_DEPTH_AVAILABLE_DEPTH_MIN_FRAME_DURATIONS, + availableDepthMinFrameDurations, + sizeof(availableDepthMinFrameDurations)/sizeof(int64_t)); + + static const int64_t availableDepthStallDurations[] = { + HAL_PIXEL_FORMAT_Y16, 160, 120, Sensor::kFrameDurationRange[0], + HAL_PIXEL_FORMAT_BLOB, maxDepthSamples,1, Sensor::kFrameDurationRange[0] + }; + ADD_STATIC_ENTRY(ANDROID_DEPTH_AVAILABLE_DEPTH_STALL_DURATIONS, + availableDepthStallDurations, + sizeof(availableDepthStallDurations)/sizeof(int64_t)); + + uint8_t depthIsExclusive = ANDROID_DEPTH_DEPTH_IS_EXCLUSIVE_FALSE; + ADD_STATIC_ENTRY(ANDROID_DEPTH_DEPTH_IS_EXCLUSIVE, + &depthIsExclusive, 1); + } // android.shading - static const uint8_t availableShadingModes[] = { + if (hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t availableShadingModes[] = { ANDROID_SHADING_MODE_OFF, ANDROID_SHADING_MODE_FAST, ANDROID_SHADING_MODE_HIGH_QUALITY - }; - ADD_STATIC_ENTRY(ANDROID_SHADING_AVAILABLE_MODES, availableShadingModes, - sizeof(availableShadingModes)); + }; + ADD_STATIC_ENTRY(ANDROID_SHADING_AVAILABLE_MODES, availableShadingModes, + sizeof(availableShadingModes)); + } else { + static const uint8_t availableShadingModes[] = { + ANDROID_SHADING_MODE_OFF + }; + ADD_STATIC_ENTRY(ANDROID_SHADING_AVAILABLE_MODES, availableShadingModes, + sizeof(availableShadingModes)); + } // android.request @@ -1520,16 +1726,26 @@ status_t EmulatedFakeCamera3::constructStaticInfo() { // Add a few more result keys. Must be kept up to date with the various places that add these Vector availableResultKeys(availableRequestKeys); - availableResultKeys.add(ANDROID_CONTROL_AE_STATE); - availableResultKeys.add(ANDROID_CONTROL_AF_STATE); - availableResultKeys.add(ANDROID_CONTROL_AWB_STATE); - availableResultKeys.add(ANDROID_FLASH_STATE); - availableResultKeys.add(ANDROID_LENS_STATE); - availableResultKeys.add(ANDROID_LENS_FOCUS_RANGE); + if (hasCapability(BACKWARD_COMPATIBLE)) { + availableResultKeys.add(ANDROID_CONTROL_AE_STATE); + availableResultKeys.add(ANDROID_CONTROL_AF_STATE); + availableResultKeys.add(ANDROID_CONTROL_AWB_STATE); + availableResultKeys.add(ANDROID_FLASH_STATE); + availableResultKeys.add(ANDROID_LENS_STATE); + availableResultKeys.add(ANDROID_LENS_FOCUS_RANGE); + availableResultKeys.add(ANDROID_SENSOR_ROLLING_SHUTTER_SKEW); + availableResultKeys.add(ANDROID_STATISTICS_SCENE_FLICKER); + } + + if (hasCapability(DEPTH_OUTPUT)) { + availableResultKeys.add(ANDROID_LENS_POSE_ROTATION); + availableResultKeys.add(ANDROID_LENS_POSE_TRANSLATION); + availableResultKeys.add(ANDROID_LENS_INTRINSIC_CALIBRATION); + availableResultKeys.add(ANDROID_LENS_RADIAL_DISTORTION); + } + availableResultKeys.add(ANDROID_REQUEST_PIPELINE_DEPTH); availableResultKeys.add(ANDROID_SENSOR_TIMESTAMP); - availableResultKeys.add(ANDROID_SENSOR_ROLLING_SHUTTER_SKEW); - availableResultKeys.add(ANDROID_STATISTICS_SCENE_FLICKER); ADD_STATIC_ENTRY(ANDROID_REQUEST_AVAILABLE_RESULT_KEYS, availableResultKeys.array(), availableResultKeys.size()); @@ -1563,13 +1779,6 @@ status_t EmulatedFakeCamera3::process3A(CameraMetadata &settings) { } uint8_t controlMode = e.data.u8[0]; - e = settings.find(ANDROID_CONTROL_SCENE_MODE); - if (e.count == 0) { - ALOGE("%s: No scene mode entry!", __FUNCTION__); - return BAD_VALUE; - } - uint8_t sceneMode = e.data.u8[0]; - if (controlMode == ANDROID_CONTROL_MODE_OFF) { mAeState = ANDROID_CONTROL_AE_STATE_INACTIVE; mAfState = ANDROID_CONTROL_AF_STATE_INACTIVE; @@ -1577,6 +1786,19 @@ status_t EmulatedFakeCamera3::process3A(CameraMetadata &settings) { update3A(settings); return OK; } else if (controlMode == ANDROID_CONTROL_MODE_USE_SCENE_MODE) { + if (!hasCapability(BACKWARD_COMPATIBLE)) { + ALOGE("%s: Can't use scene mode when BACKWARD_COMPATIBLE not supported!", + __FUNCTION__); + return BAD_VALUE; + } + + e = settings.find(ANDROID_CONTROL_SCENE_MODE); + if (e.count == 0) { + ALOGE("%s: No scene mode entry!", __FUNCTION__); + return BAD_VALUE; + } + uint8_t sceneMode = e.data.u8[0]; + switch(sceneMode) { case ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY: mFacePriority = true; @@ -1610,11 +1832,11 @@ status_t EmulatedFakeCamera3::doFakeAE(CameraMetadata &settings) { camera_metadata_entry e; e = settings.find(ANDROID_CONTROL_AE_MODE); - if (e.count == 0) { + if (e.count == 0 && hasCapability(BACKWARD_COMPATIBLE)) { ALOGE("%s: No AE mode entry!", __FUNCTION__); return BAD_VALUE; } - uint8_t aeMode = e.data.u8[0]; + uint8_t aeMode = (e.count > 0) ? e.data.u8[0] : (uint8_t)ANDROID_CONTROL_AE_MODE_ON; switch (aeMode) { case ANDROID_CONTROL_AE_MODE_OFF: @@ -1632,11 +1854,7 @@ status_t EmulatedFakeCamera3::doFakeAE(CameraMetadata &settings) { } e = settings.find(ANDROID_CONTROL_AE_LOCK); - if (e.count == 0) { - ALOGE("%s: No AE lock entry!", __FUNCTION__); - return BAD_VALUE; - } - bool aeLocked = (e.data.u8[0] == ANDROID_CONTROL_AE_LOCK_ON); + bool aeLocked = (e.count > 0) ? (e.data.u8[0] == ANDROID_CONTROL_AE_LOCK_ON) : false; e = settings.find(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER); bool precaptureTrigger = false; @@ -1730,11 +1948,11 @@ status_t EmulatedFakeCamera3::doFakeAF(CameraMetadata &settings) { camera_metadata_entry e; e = settings.find(ANDROID_CONTROL_AF_MODE); - if (e.count == 0) { + if (e.count == 0 && hasCapability(BACKWARD_COMPATIBLE)) { ALOGE("%s: No AF mode entry!", __FUNCTION__); return BAD_VALUE; } - uint8_t afMode = e.data.u8[0]; + uint8_t afMode = (e.count > 0) ? e.data.u8[0] : (uint8_t)ANDROID_CONTROL_AF_MODE_OFF; e = settings.find(ANDROID_CONTROL_AF_TRIGGER); typedef camera_metadata_enum_android_control_af_trigger af_trigger_t; @@ -1939,11 +2157,11 @@ status_t EmulatedFakeCamera3::doFakeAWB(CameraMetadata &settings) { camera_metadata_entry e; e = settings.find(ANDROID_CONTROL_AWB_MODE); - if (e.count == 0) { + if (e.count == 0 && hasCapability(BACKWARD_COMPATIBLE)) { ALOGE("%s: No AWB mode entry!", __FUNCTION__); return BAD_VALUE; } - uint8_t awbMode = e.data.u8[0]; + uint8_t awbMode = (e.count > 0) ? e.data.u8[0] : (uint8_t)ANDROID_CONTROL_AWB_MODE_AUTO; // TODO: Add white balance simulation @@ -1969,7 +2187,7 @@ status_t EmulatedFakeCamera3::doFakeAWB(CameraMetadata &settings) { void EmulatedFakeCamera3::update3A(CameraMetadata &settings) { - if (mAeState != ANDROID_CONTROL_AE_STATE_INACTIVE) { + if (mAeMode != ANDROID_CONTROL_AE_MODE_OFF) { settings.update(ANDROID_SENSOR_EXPOSURE_TIME, &mAeCurrentExposureTime, 1); settings.update(ANDROID_SENSOR_SENSITIVITY, @@ -2133,7 +2351,7 @@ bool EmulatedFakeCamera3::ReadoutThread::threadLoop() { while(buf != mCurrentRequest.buffers->end()) { bool goodBuffer = true; if ( buf->stream->format == - HAL_PIXEL_FORMAT_BLOB) { + HAL_PIXEL_FORMAT_BLOB && buf->stream->data_space != HAL_DATASPACE_DEPTH) { Mutex::Autolock jl(mJpegLock); if (mJpegWaiting) { // This shouldn't happen, because processCaptureRequest should @@ -2177,24 +2395,47 @@ bool EmulatedFakeCamera3::ReadoutThread::threadLoop() { camera3_capture_result result; - static const uint8_t sceneFlicker = ANDROID_STATISTICS_SCENE_FLICKER_NONE; - mCurrentRequest.settings.update(ANDROID_STATISTICS_SCENE_FLICKER, - &sceneFlicker, 1); + if (mParent->hasCapability(BACKWARD_COMPATIBLE)) { + static const uint8_t sceneFlicker = ANDROID_STATISTICS_SCENE_FLICKER_NONE; + mCurrentRequest.settings.update(ANDROID_STATISTICS_SCENE_FLICKER, + &sceneFlicker, 1); + + static const uint8_t flashState = ANDROID_FLASH_STATE_UNAVAILABLE; + mCurrentRequest.settings.update(ANDROID_FLASH_STATE, + &flashState, 1); - static const uint8_t flashState = ANDROID_FLASH_STATE_UNAVAILABLE; - mCurrentRequest.settings.update(ANDROID_FLASH_STATE, - &flashState, 1); + nsecs_t rollingShutterSkew = Sensor::kFrameDurationRange[0]; + mCurrentRequest.settings.update(ANDROID_SENSOR_ROLLING_SHUTTER_SKEW, + &rollingShutterSkew, 1); + + float focusRange[] = { 1.0f/5.0f, 0 }; // 5 m to infinity in focus + mCurrentRequest.settings.update(ANDROID_LENS_FOCUS_RANGE, + focusRange, sizeof(focusRange)/sizeof(float)); + } + + if (mParent->hasCapability(DEPTH_OUTPUT)) { + camera_metadata_entry_t entry; + + find_camera_metadata_entry(mParent->mCameraInfo, ANDROID_LENS_POSE_TRANSLATION, &entry); + mCurrentRequest.settings.update(ANDROID_LENS_POSE_TRANSLATION, + entry.data.f, entry.count); + + find_camera_metadata_entry(mParent->mCameraInfo, ANDROID_LENS_POSE_ROTATION, &entry); + mCurrentRequest.settings.update(ANDROID_LENS_POSE_ROTATION, + entry.data.f, entry.count); + + find_camera_metadata_entry(mParent->mCameraInfo, ANDROID_LENS_INTRINSIC_CALIBRATION, &entry); + mCurrentRequest.settings.update(ANDROID_LENS_INTRINSIC_CALIBRATION, + entry.data.f, entry.count); + + find_camera_metadata_entry(mParent->mCameraInfo, ANDROID_LENS_RADIAL_DISTORTION, &entry); + mCurrentRequest.settings.update(ANDROID_LENS_RADIAL_DISTORTION, + entry.data.f, entry.count); + } mCurrentRequest.settings.update(ANDROID_SENSOR_TIMESTAMP, &captureTime, 1); - nsecs_t rollingShutterSkew = Sensor::kFrameDurationRange[0]; - mCurrentRequest.settings.update(ANDROID_SENSOR_ROLLING_SHUTTER_SKEW, - &rollingShutterSkew, 1); - - float focusRange[] = { 1.0f/5.0f, 0 }; // 5 m to infinity in focus - mCurrentRequest.settings.update(ANDROID_LENS_FOCUS_RANGE, - focusRange, sizeof(focusRange)/sizeof(float)); // JPEGs take a stage longer const uint8_t pipelineDepth = needJpeg ? kMaxBufferCount : kMaxBufferCount - 1; diff --git a/camera/fake-pipeline2/Base.h b/camera/fake-pipeline2/Base.h index 057629b..724b3f9 100644 --- a/camera/fake-pipeline2/Base.h +++ b/camera/fake-pipeline2/Base.h @@ -37,6 +37,7 @@ struct StreamBuffer { int streamId; uint32_t width, height; uint32_t format; + uint32_t dataSpace; uint32_t stride; buffer_handle_t *buffer; uint8_t *img; diff --git a/camera/fake-pipeline2/Sensor.cpp b/camera/fake-pipeline2/Sensor.cpp index ac3961f..61c7f28 100644 --- a/camera/fake-pipeline2/Sensor.cpp +++ b/camera/fake-pipeline2/Sensor.cpp @@ -339,19 +339,23 @@ bool Sensor::threadLoop() { captureRGBA(b.img, gain, b.stride); break; case HAL_PIXEL_FORMAT_BLOB: - // Add auxillary buffer of the right size - // Assumes only one BLOB (JPEG) buffer in - // mNextCapturedBuffers - StreamBuffer bAux; - bAux.streamId = 0; - bAux.width = b.width; - bAux.height = b.height; - bAux.format = HAL_PIXEL_FORMAT_RGB_888; - bAux.stride = b.width; - bAux.buffer = NULL; - // TODO: Reuse these - bAux.img = new uint8_t[b.width * b.height * 3]; - mNextCapturedBuffers->push_back(bAux); + if (b.dataSpace != HAL_DATASPACE_DEPTH) { + // Add auxillary buffer of the right size + // Assumes only one BLOB (JPEG) buffer in + // mNextCapturedBuffers + StreamBuffer bAux; + bAux.streamId = 0; + bAux.width = b.width; + bAux.height = b.height; + bAux.format = HAL_PIXEL_FORMAT_RGB_888; + bAux.stride = b.width; + bAux.buffer = NULL; + // TODO: Reuse these + bAux.img = new uint8_t[b.width * b.height * 3]; + mNextCapturedBuffers->push_back(bAux); + } else { + captureDepthCloud(b.img); + } break; case HAL_PIXEL_FORMAT_YCrCb_420_SP: captureNV21(b.img, gain, b.stride); @@ -360,6 +364,9 @@ bool Sensor::threadLoop() { // TODO: ALOGE("%s: Format %x is TODO", __FUNCTION__, b.format); break; + case HAL_PIXEL_FORMAT_Y16: + captureDepth(b.img, gain, b.stride); + break; default: ALOGE("%s: Unknown format %x, no output", __FUNCTION__, b.format); @@ -543,4 +550,61 @@ void Sensor::captureNV21(uint8_t *img, uint32_t gain, uint32_t stride) { ALOGVV("NV21 sensor image captured"); } +void Sensor::captureDepth(uint8_t *img, uint32_t gain, uint32_t stride) { + float totalGain = gain/100.0 * kBaseGainFactor; + // In fixed-point math, calculate scaling factor to 13bpp millimeters + int scale64x = 64 * totalGain * 8191 / kMaxRawValue; + uint32_t inc = kResolution[0] / stride; + + for (unsigned int y = 0, outY = 0; y < kResolution[1]; y += inc, outY++ ) { + mScene.setReadoutPixel(0, y); + uint16_t *px = ((uint16_t*)img) + outY * stride; + for (unsigned int x = 0; x < kResolution[0]; x += inc) { + uint32_t depthCount; + // TODO: Make up real depth scene instead of using green channel + // as depth + const uint32_t *pixel = mScene.getPixelElectrons(); + depthCount = pixel[Scene::Gr] * scale64x; + + *px++ = depthCount < 8191*64 ? depthCount / 64 : 0; + for (unsigned int j = 1; j < inc; j++) + mScene.getPixelElectrons(); + } + // TODO: Handle this better + //simulatedTime += kRowReadoutTime; + } + ALOGVV("Depth sensor image captured"); +} + +void Sensor::captureDepthCloud(uint8_t *img) { + + android_depth_points *cloud = reinterpret_cast(img); + + cloud->num_points = 16; + + // TODO: Create point cloud values that match RGB scene + const int FLOATS_PER_POINT = 4; + const float JITTER_STDDEV = 0.1f; + for (size_t y = 0, i = 0; y < 4; y++) { + for (size_t x = 0; x < 4; x++, i++) { + float randSampleX = std::rand() * (2.5f / (1.0f + RAND_MAX)) - 1.25f; + randSampleX *= JITTER_STDDEV; + + float randSampleY = std::rand() * (2.5f / (1.0f + RAND_MAX)) - 1.25f; + randSampleY *= JITTER_STDDEV; + + float randSampleZ = std::rand() * (2.5f / (1.0f + RAND_MAX)) - 1.25f; + randSampleZ *= JITTER_STDDEV; + + cloud->xyzc_points[i * FLOATS_PER_POINT + 0] = x - 1.5f + randSampleX; + cloud->xyzc_points[i * FLOATS_PER_POINT + 1] = y - 1.5f + randSampleY; + cloud->xyzc_points[i * FLOATS_PER_POINT + 2] = 3.f + randSampleZ; + cloud->xyzc_points[i * FLOATS_PER_POINT + 3] = 0.8f; + } + } + + ALOGVV("Depth point cloud captured"); + +} + } // namespace android diff --git a/camera/fake-pipeline2/Sensor.h b/camera/fake-pipeline2/Sensor.h index 7cc7b4a..720fbc2 100644 --- a/camera/fake-pipeline2/Sensor.h +++ b/camera/fake-pipeline2/Sensor.h @@ -235,6 +235,9 @@ class Sensor: private Thread, public virtual RefBase { void captureRGBA(uint8_t *img, uint32_t gain, uint32_t stride); void captureRGB(uint8_t *img, uint32_t gain, uint32_t stride); void captureNV21(uint8_t *img, uint32_t gain, uint32_t stride); + void captureDepth(uint8_t *img, uint32_t gain, uint32_t stride); + void captureDepthCloud(uint8_t *img); + }; } diff --git a/opengl/system/gralloc/gralloc.cpp b/opengl/system/gralloc/gralloc.cpp index 9659e3d..ef18511 100644 --- a/opengl/system/gralloc/gralloc.cpp +++ b/opengl/system/gralloc/gralloc.cpp @@ -212,10 +212,11 @@ static int gralloc_alloc(alloc_device_t* dev, glType = GL_UNSIGNED_SHORT_5_6_5; break; case HAL_PIXEL_FORMAT_RAW16: + case HAL_PIXEL_FORMAT_Y16: bpp = 2; align = 16*bpp; if (! ((sw_read || hw_cam_read) && (sw_write || hw_cam_write) ) ) { - // Raw sensor data only goes between camera and CPU + // Raw sensor data or Y16 only goes between camera and CPU return -EINVAL; } // Not expecting to actually create any GL surfaces for this -- cgit v1.2.3