Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 47ac3499 authored by Zhijun He's avatar Zhijun He
Browse files

Camera2: fix high speed output surface format check

Preview surface default format is not ImageFormat.PRIVATE, the check need to
take this into consideration.

Change-Id: Ib99e64f7781dd15cc5634c66b2d5e5ab2a2d7d6c
parent e687929f
Loading
Loading
Loading
Loading
+24 −7
Original line number Diff line number Diff line
@@ -1924,6 +1924,28 @@ public class CameraDeviceImpl extends CameraDevice {
        return mCharacteristics;
    }

    /**
     * A high speed output surface can only be preview or hardware encoder surface.
     *
     * @param surface The high speed output surface to be checked.
     */
    private void checkHighSpeedSurfaceFormat(Surface surface) {
        // TODO: remove this override since the default format should be
        // ImageFormat.PRIVATE. b/9487482
        final int HAL_FORMAT_RGB_START = 1; // HAL_PIXEL_FORMAT_RGBA_8888 from graphics.h
        final int HAL_FORMAT_RGB_END = 5; // HAL_PIXEL_FORMAT_BGRA_8888 from graphics.h
        int surfaceFormat = SurfaceUtils.getSurfaceFormat(surface);
        if (surfaceFormat >= HAL_FORMAT_RGB_START &&
                surfaceFormat <= HAL_FORMAT_RGB_END) {
            surfaceFormat = ImageFormat.PRIVATE;
        }

        if (surfaceFormat != ImageFormat.PRIVATE) {
            throw new IllegalArgumentException("Surface format(" + surfaceFormat + ") is not"
                    + " for preview or hardware video encoding!");
        }
    }

    private void checkConstrainedHighSpeedSurfaces(Collection<Surface> surfaces,
            Range<Integer> fpsRange) {
        if (surfaces == null || surfaces.size() == 0 || surfaces.size() > 2) {
@@ -1948,15 +1970,10 @@ public class CameraDeviceImpl extends CameraDevice {
        }

        for (Surface surface : surfaces) {
            checkHighSpeedSurfaceFormat(surface);

            // Surface size must be supported high speed sizes.
            Size surfaceSize = SurfaceUtils.getSurfaceSize(surface);
            int surfaceFormat = SurfaceUtils.getSurfaceFormat(surface);

            if (surfaceFormat != ImageFormat.PRIVATE) {
                throw new IllegalArgumentException("Surface format is not for preview or"
                        + " hardware video encoding" + surfaceFormat);
            }

            if (!highSpeedSizes.contains(surfaceSize)) {
                throw new IllegalArgumentException("Surface size " + surfaceSize.toString() + " is"
                        + " not part of the high speed supported size list " +
+2 −2
Original line number Diff line number Diff line
@@ -565,7 +565,7 @@ public class LegacyCameraDevice implements AutoCloseable {
            throw new IllegalArgumentException("Surface was abandoned", e);
        }

        return previewConsumer && (surfaceFormat == ImageFormat.PRIVATE);
        return previewConsumer;
    }

    public static boolean isVideoEncoderConsumer(Surface output) {
@@ -583,7 +583,7 @@ public class LegacyCameraDevice implements AutoCloseable {
            throw new IllegalArgumentException("Surface was abandoned", e);
        }

        return videoEncoderConsumer && (surfaceFormat == ImageFormat.PRIVATE);
        return videoEncoderConsumer;
    }

    /**
+4 −2
Original line number Diff line number Diff line
@@ -16,6 +16,7 @@

package android.hardware.camera2.utils;

import android.graphics.ImageFormat;
import android.hardware.camera2.legacy.LegacyCameraDevice;
import android.hardware.camera2.legacy.LegacyExceptionUtils.BufferQueueAbandonedException;
import android.util.Size;
@@ -27,7 +28,7 @@ import android.view.Surface;
public class SurfaceUtils {

    /**
     * Check if a surface is for preview consumer.
     * Check if a surface is for preview consumer based on consumer end point Gralloc usage flags.
     *
     * @param surface The surface to be checked.
     * @return true if the surface is for preview consumer, false otherwise.
@@ -37,7 +38,8 @@ public class SurfaceUtils {
    }

    /**
     * Check if the surface is for hardware video encoder consumer.
     * Check if the surface is for hardware video encoder consumer based on consumer end point
     * Gralloc usage flags.
     *
     * @param surface The surface to be checked.
     * @return true if the surface is for hardware video encoder consumer, false otherwise.