1. Problem Background
When testing USB camera for photo and video recording functionality using the system camera RK3576-SDK/packages/apps/Camera2
on the RK3576
platform with Android 14 system, the following issue was discovered:
【Issue】The USB camera preview orientation is inconsistent between photo mode and video mode, with video preview showing left-right mirroring.
2. Root Cause Analysis
In the Android Camera
system, mirroring logic typically depends on the LENS_FACING
metadata field:
ANDROID_LENS_FACING_FRONT / BACK / EXTERNAL
Cameras of type LENS_FACING_EXTERNAL
generally do not perform mirroring by default. However, in practice, some camera apps or legacy system logic might process EXTERNAL cameras exactly like front-facing cameras, leading to incorrect preview mirroring.
3. Solutions
3.1. Solution One: Modify Camera Orientation in HAL Layer Camera HAL
In RK’s Camera HAL implementation, the default facing
setting for USB cameras is ANDROID_LENS_FACING_EXTERNAL
:
Location:
hardware/rockchip/camera_aidl/device/ExternalCameraDevice.cpp
Modifications:
--- a/device/ExternalCameraDevice.cpp
+++ b/device/ExternalCameraDevice.cpp
@@ -482,7 +482,8 @@ status_t ExternalCameraDevice::initDefaultCharsKeys(
const uint8_t opticalStabilizationMode = ANDROID_LENS_OPTICAL_STABILIZATION_MODE_OFF;
UPDATE(ANDROID_LENS_INFO_AVAILABLE_OPTICAL_STABILIZATION, &opticalStabilizationMode, 1);
- const uint8_t facing = ANDROID_LENS_FACING_EXTERNAL;
+ //const uint8_t facing = ANDROID_LENS_FACING_EXTERNAL;
+ const uint8_t facing = ANDROID_LENS_FACING_BACK;
UPDATE(ANDROID_LENS_FACING, &facing, 1);
Notes
- This method affects other camera type recognition logic
- Not suitable for scenarios requiring classification evaluation based on EXTERNAL type
3.2. (Recommended) Solution Two: Keep EXTERNAL Type, Disable Mirror Logic for USB Camera in App Layer
If you want to maintain HAL standard semantics, you can handle it at the camera application layer:
Location:
packages/apps/Camera2/src/com/android/camera/TextureViewHelper.java
Modifications:
--- a/src/com/android/camera/TextureViewHelper.java
+++ b/src/com/android/camera/TextureViewHelper.java
@@ -347,7 +347,6 @@ public class TextureViewHelper implements TextureView.SurfaceTextureListener,
Log.e(TAG, "TransformViewHelper does not support Camera API2");
}
// Only apply this fix when Current Active Module is Photo module AND
// Phone is Nexus4 The enhancement fix b/20694189 to original fix to
// b/19271661 ensures that the fix should only be applied when:
@@ -367,6 +366,21 @@ public class TextureViewHelper implements TextureView.SurfaceTextureListener,
CameraDeviceInfo.Characteristics info = mCameraProvider.getCharacteristics(cameraId);
matrix = info.getPreviewTransform(mOrientation, new RectF(0, 0, mWidth, mHeight),
mCaptureLayoutHelper.getPreviewRect());
+
+ int moduleIndex = mAppController.getCurrentModuleIndex();
+ boolean isRecordingModule = (moduleIndex == 1);
+ String cameraIdStr = cameraKey.toString().toLowerCase();
+ //boolean isUsbCamera = cameraIdStr.contains("usb") || cameraIdStr.contains("external");
+ boolean isUsbCamera = cameraIdStr.contains("api2='0'"); //This needs to be modified to correctly identify USB cameras, api2='0' is based on actual printout in neardi, for reference only!
+ if (isUsbCamera && isRecordingModule) {
+ Log.v(TAG, "USB camera recording: remove mirror transform");
+ matrix.postScale(-1f, 1f, mWidth / 2f, mHeight / 2f);
+ }
Advantages
- No need to modify HAL layer, better system compatibility
- Only affects target scenarios, precise logic