diff --git a/camera/ndk/impl/ACameraMetadata.cpp b/camera/ndk/impl/ACameraMetadata.cpp index 0ff78abe01..18c5d3c3f3 100644 --- a/camera/ndk/impl/ACameraMetadata.cpp +++ b/camera/ndk/impl/ACameraMetadata.cpp @@ -528,6 +528,7 @@ ACameraMetadata::isCaptureRequestTag(const uint32_t tag) { case ACAMERA_LENS_OPTICAL_STABILIZATION_MODE: case ACAMERA_NOISE_REDUCTION_MODE: case ACAMERA_SCALER_CROP_REGION: + case ACAMERA_SCALER_ROTATE_AND_CROP: case ACAMERA_SENSOR_EXPOSURE_TIME: case ACAMERA_SENSOR_FRAME_DURATION: case ACAMERA_SENSOR_SENSITIVITY: diff --git a/camera/ndk/include/camera/NdkCameraMetadataTags.h b/camera/ndk/include/camera/NdkCameraMetadataTags.h index 8b371db9c9..bd259ebec0 100644 --- a/camera/ndk/include/camera/NdkCameraMetadataTags.h +++ b/camera/ndk/include/camera/NdkCameraMetadataTags.h @@ -3690,6 +3690,108 @@ typedef enum acamera_metadata_tag { ACAMERA_SCALER_AVAILABLE_RECOMMENDED_INPUT_OUTPUT_FORMATS_MAP = // int32 ACAMERA_SCALER_START + 15, + /** + *

List of rotate-and-crop modes for ACAMERA_SCALER_ROTATE_AND_CROP that are supported by this camera device.

+ * + * @see ACAMERA_SCALER_ROTATE_AND_CROP + * + *

Type: byte[n]

+ * + *

This tag may appear in: + *

+ * + *

This entry lists the valid modes for ACAMERA_SCALER_ROTATE_AND_CROP for this camera device.

+ *

Starting with API level 30, all devices will list at least ROTATE_AND_CROP_NONE. + * Devices with support for rotate-and-crop will additionally list at least + * ROTATE_AND_CROP_AUTO and ROTATE_AND_CROP_90.

+ * + * @see ACAMERA_SCALER_ROTATE_AND_CROP + */ + ACAMERA_SCALER_AVAILABLE_ROTATE_AND_CROP_MODES = // byte[n] + ACAMERA_SCALER_START + 16, + /** + *

Whether a rotation-and-crop operation is applied to processed + * outputs from the camera.

+ * + *

Type: byte (acamera_metadata_enum_android_scaler_rotate_and_crop_t)

+ * + *

This tag may appear in: + *

+ * + *

This control is primarily intended to help camera applications with no support for + * multi-window modes to work correctly on devices where multi-window scenarios are + * unavoidable, such as foldables or other devices with variable display geometry or more + * free-form window placement (such as laptops, which often place portrait-orientation apps + * in landscape with pillarboxing).

+ *

If supported, the default value is ROTATE_AND_CROP_AUTO, which allows the camera API + * to enable backwards-compatibility support for applications that do not support resizing + * / multi-window modes, when the device is in fact in a multi-window mode (such as inset + * portrait on laptops, or on a foldable device in some fold states). In addition, + * ROTATE_AND_CROP_NONE and ROTATE_AND_CROP_90 will always be available if this control + * is supported by the device. If not supported, devices API level 30 or higher will always + * list only ROTATE_AND_CROP_NONE.

+ *

When CROP_AUTO is in use, and the camera API activates backward-compatibility mode, + * several metadata fields will also be parsed differently to ensure that coordinates are + * correctly handled for features like drawing face detection boxes or passing in + * tap-to-focus coordinates. The camera API will convert positions in the active array + * coordinate system to/from the cropped-and-rotated coordinate system to make the + * operation transparent for applications. The following controls are affected:

+ * + *

Capture results will contain the actual value selected by the API; + * ROTATE_AND_CROP_AUTO will never be seen in a capture result.

+ *

Applications can also select their preferred cropping mode, either to opt out of the + * backwards-compatibility treatment, or to use the cropping feature themselves as needed. + * In this case, no coordinate translation will be done automatically, and all controls + * will continue to use the normal active array coordinates.

+ *

Cropping and rotating is done after the application of digital zoom (via either + * ACAMERA_SCALER_CROP_REGION or ACAMERA_CONTROL_ZOOM_RATIO), but before each individual + * output is further cropped and scaled. It only affects processed outputs such as + * YUV, PRIVATE, and JPEG. It has no effect on RAW outputs.

+ *

When CROP_90 or CROP_270 are selected, there is a significant loss to the field of + * view. For example, with a 4:3 aspect ratio output of 1600x1200, CROP_90 will still + * produce 1600x1200 output, but these buffers are cropped from a vertical 3:4 slice at the + * center of the 4:3 area, then rotated to be 4:3, and then upscaled to 1600x1200. Only + * 56.25% of the original FOV is still visible. In general, for an aspect ratio of w:h, + * the crop and rotate operation leaves (h/w)^2 of the field of view visible. For 16:9, + * this is ~31.6%.

+ *

As a visual example, the figure below shows the effect of ROTATE_AND_CROP_90 on the + * outputs for the following parameters:

+ * + *

Effect of ROTATE_AND_CROP_90

+ *

With these settings, the regions of the active array covered by the output streams are:

+ * + *

Since the buffers are rotated, the buffers as seen by the application are:

+ * + * + * @see ACAMERA_CONTROL_AE_REGIONS + * @see ACAMERA_CONTROL_AF_REGIONS + * @see ACAMERA_CONTROL_AWB_REGIONS + * @see ACAMERA_CONTROL_ZOOM_RATIO + * @see ACAMERA_SCALER_CROP_REGION + */ + ACAMERA_SCALER_ROTATE_AND_CROP = // byte (acamera_metadata_enum_android_scaler_rotate_and_crop_t) + ACAMERA_SCALER_START + 17, ACAMERA_SCALER_END, /** @@ -8212,6 +8314,51 @@ typedef enum acamera_metadata_enum_acamera_scaler_available_recommended_stream_c } acamera_metadata_enum_android_scaler_available_recommended_stream_configurations_t; +// ACAMERA_SCALER_ROTATE_AND_CROP +typedef enum acamera_metadata_enum_acamera_scaler_rotate_and_crop { + /** + *

No rotate and crop is applied. Processed outputs are in the sensor orientation.

+ */ + ACAMERA_SCALER_ROTATE_AND_CROP_NONE = 0, + + /** + *

Processed images are rotated by 90 degrees clockwise, and then cropped + * to the original aspect ratio.

+ */ + ACAMERA_SCALER_ROTATE_AND_CROP_90 = 1, + + /** + *

Processed images are rotated by 180 degrees. Since the aspect ratio does not + * change, no cropping is performed.

+ */ + ACAMERA_SCALER_ROTATE_AND_CROP_180 = 2, + + /** + *

Processed images are rotated by 270 degrees clockwise, and then cropped + * to the original aspect ratio.

+ */ + ACAMERA_SCALER_ROTATE_AND_CROP_270 = 3, + + /** + *

The camera API automatically selects the best concrete value for + * rotate-and-crop based on the application's support for resizability and the current + * multi-window mode.

+ *

If the application does not support resizing but the display mode for its main + * Activity is not in a typical orientation, the camera API will set ROTATE_AND_CROP_90 + * or some other supported rotation value, depending on device configuration, + * to ensure preview and captured images are correctly shown to the user. Otherwise, + * ROTATE_AND_CROP_NONE will be selected.

+ *

When a value other than NONE is selected, several metadata fields will also be parsed + * differently to ensure that coordinates are correctly handled for features like drawing + * face detection boxes or passing in tap-to-focus coordinates. The camera API will + * convert positions in the active array coordinate system to/from the cropped-and-rotated + * coordinate system to make the operation transparent for applications.

+ *

No coordinate mapping will be done when the application selects a non-AUTO mode.

+ */ + ACAMERA_SCALER_ROTATE_AND_CROP_AUTO = 4, + +} acamera_metadata_enum_android_scaler_rotate_and_crop_t; + // ACAMERA_SENSOR_REFERENCE_ILLUMINANT1 typedef enum acamera_metadata_enum_acamera_sensor_reference_illuminant1 {