Loading media/java/android/media/ImageReader.java +23 −6 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ import android.graphics.ImageFormat; import android.graphics.PixelFormat; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.view.Surface; import java.lang.ref.WeakReference; Loading Loading @@ -130,11 +129,26 @@ public final class ImageReader implements AutoCloseable { } /** * <p>Get the next Image from the ImageReader's queue. Returns {@code null} * if no new image is available.</p> * <p> * Get the next Image from the ImageReader's queue. Returns {@code null} if * no new image is available. * </p> * <p> * This operation will fail by throwing an * {@link Surface.OutOfResourcesException OutOfResourcesException} if too * many images have been acquired with {@link #getNextImage}. In particular * a sequence of {@link #getNextImage} calls greater than {@link #getMaxImages} * without calling {@link Image#close} or {@link #releaseImage} in-between * will exhaust the underlying queue. At such a time, * {@link Surface.OutOfResourcesException OutOfResourcesException} will be * thrown until more images are released with {@link Image#close} or * {@link #releaseImage}. * </p> * * @return a new frame of image data, or {@code null} if no image data is * available. * @throws Surface.OutOfResourcesException if too many images are currently * acquired */ public Image getNextImage() { SurfaceImage si = new SurfaceImage(); Loading Loading @@ -172,6 +186,8 @@ public final class ImageReader implements AutoCloseable { * @param listener the listener that will be run * @param handler The handler on which the listener should be invoked, or null * if the listener should be invoked on the calling thread's looper. * * @throws IllegalArgumentException if no handler specified and the calling thread has no looper */ public void setImageAvailableListener(OnImageAvailableListener listener, Handler handler) { mImageListener = listener; Loading Loading @@ -260,8 +276,9 @@ public final class ImageReader implements AutoCloseable { * Called from Native code when an Event happens. */ private static void postEventFromNative(Object selfRef) { WeakReference weakSelf = (WeakReference)selfRef; final ImageReader ir = (ImageReader)weakSelf.get(); @SuppressWarnings("unchecked") WeakReference<ImageReader> weakSelf = (WeakReference<ImageReader>)selfRef; final ImageReader ir = weakSelf.get(); if (ir == null) { return; } Loading media/jni/android_media_ImageReader.cpp +17 −2 Original line number Diff line number Diff line Loading @@ -44,6 +44,9 @@ using namespace android; static const char* const OutOfResourcesException = "android/view/Surface$OutOfResourcesException"; enum { IMAGE_READER_MAX_NUM_PLANES = 3, }; Loading Loading @@ -609,7 +612,8 @@ static void ImageReader_init(JNIEnv* env, jobject thiz, jobject weakThiz, nativeFormat = Image_getPixelFormat(env, format); sp<BufferQueue> bq = new BufferQueue(); sp<CpuConsumer> consumer = new CpuConsumer(bq, true, maxImages); sp<CpuConsumer> consumer = new CpuConsumer(bq, maxImages, /*controlledByApp*/true); // TODO: throw dvm exOutOfMemoryError? if (consumer == NULL) { jniThrowRuntimeException(env, "Failed to allocate native CpuConsumer"); Loading Loading @@ -702,7 +706,17 @@ static jboolean ImageReader_imageSetup(JNIEnv* env, jobject thiz, status_t res = consumer->lockNextBuffer(buffer); if (res != NO_ERROR) { if (res != BAD_VALUE /*no buffers*/) { ALOGE("%s Fail to lockNextBuffer with error: %d ", __FUNCTION__, res); if (res == NOT_ENOUGH_DATA) { jniThrowException(env, OutOfResourcesException, "Too many outstanding images, close existing images" " to be able to acquire more."); } else { ALOGE("%s Fail to lockNextBuffer with error: %d ", __FUNCTION__, res); jniThrowExceptionFmt(env, "java/lang/IllegalStateException", "Unknown error (%d) when we tried to lock buffer.", res); } } return false; } Loading @@ -714,6 +728,7 @@ static jboolean ImageReader_imageSetup(JNIEnv* env, jobject thiz, ALOGE("crop left: %d, top = %d", lt.x, lt.y); jniThrowException(env, "java/lang/UnsupportedOperationException", "crop left top corner need to at origin"); return false; } // Check if the producer buffer configurations match what ImageReader configured. Loading Loading
media/java/android/media/ImageReader.java +23 −6 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ import android.graphics.ImageFormat; import android.graphics.PixelFormat; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.view.Surface; import java.lang.ref.WeakReference; Loading Loading @@ -130,11 +129,26 @@ public final class ImageReader implements AutoCloseable { } /** * <p>Get the next Image from the ImageReader's queue. Returns {@code null} * if no new image is available.</p> * <p> * Get the next Image from the ImageReader's queue. Returns {@code null} if * no new image is available. * </p> * <p> * This operation will fail by throwing an * {@link Surface.OutOfResourcesException OutOfResourcesException} if too * many images have been acquired with {@link #getNextImage}. In particular * a sequence of {@link #getNextImage} calls greater than {@link #getMaxImages} * without calling {@link Image#close} or {@link #releaseImage} in-between * will exhaust the underlying queue. At such a time, * {@link Surface.OutOfResourcesException OutOfResourcesException} will be * thrown until more images are released with {@link Image#close} or * {@link #releaseImage}. * </p> * * @return a new frame of image data, or {@code null} if no image data is * available. * @throws Surface.OutOfResourcesException if too many images are currently * acquired */ public Image getNextImage() { SurfaceImage si = new SurfaceImage(); Loading Loading @@ -172,6 +186,8 @@ public final class ImageReader implements AutoCloseable { * @param listener the listener that will be run * @param handler The handler on which the listener should be invoked, or null * if the listener should be invoked on the calling thread's looper. * * @throws IllegalArgumentException if no handler specified and the calling thread has no looper */ public void setImageAvailableListener(OnImageAvailableListener listener, Handler handler) { mImageListener = listener; Loading Loading @@ -260,8 +276,9 @@ public final class ImageReader implements AutoCloseable { * Called from Native code when an Event happens. */ private static void postEventFromNative(Object selfRef) { WeakReference weakSelf = (WeakReference)selfRef; final ImageReader ir = (ImageReader)weakSelf.get(); @SuppressWarnings("unchecked") WeakReference<ImageReader> weakSelf = (WeakReference<ImageReader>)selfRef; final ImageReader ir = weakSelf.get(); if (ir == null) { return; } Loading
media/jni/android_media_ImageReader.cpp +17 −2 Original line number Diff line number Diff line Loading @@ -44,6 +44,9 @@ using namespace android; static const char* const OutOfResourcesException = "android/view/Surface$OutOfResourcesException"; enum { IMAGE_READER_MAX_NUM_PLANES = 3, }; Loading Loading @@ -609,7 +612,8 @@ static void ImageReader_init(JNIEnv* env, jobject thiz, jobject weakThiz, nativeFormat = Image_getPixelFormat(env, format); sp<BufferQueue> bq = new BufferQueue(); sp<CpuConsumer> consumer = new CpuConsumer(bq, true, maxImages); sp<CpuConsumer> consumer = new CpuConsumer(bq, maxImages, /*controlledByApp*/true); // TODO: throw dvm exOutOfMemoryError? if (consumer == NULL) { jniThrowRuntimeException(env, "Failed to allocate native CpuConsumer"); Loading Loading @@ -702,7 +706,17 @@ static jboolean ImageReader_imageSetup(JNIEnv* env, jobject thiz, status_t res = consumer->lockNextBuffer(buffer); if (res != NO_ERROR) { if (res != BAD_VALUE /*no buffers*/) { ALOGE("%s Fail to lockNextBuffer with error: %d ", __FUNCTION__, res); if (res == NOT_ENOUGH_DATA) { jniThrowException(env, OutOfResourcesException, "Too many outstanding images, close existing images" " to be able to acquire more."); } else { ALOGE("%s Fail to lockNextBuffer with error: %d ", __FUNCTION__, res); jniThrowExceptionFmt(env, "java/lang/IllegalStateException", "Unknown error (%d) when we tried to lock buffer.", res); } } return false; } Loading @@ -714,6 +728,7 @@ static jboolean ImageReader_imageSetup(JNIEnv* env, jobject thiz, ALOGE("crop left: %d, top = %d", lt.x, lt.y); jniThrowException(env, "java/lang/UnsupportedOperationException", "crop left top corner need to at origin"); return false; } // Check if the producer buffer configurations match what ImageReader configured. Loading