am 492afe90: Merge "Image/Reader/Writer: address API review comments" into mnc-dev
* commit '492afe901459274ea8b9dd52815d3f51dd1f244f': Image/Reader/Writer: address API review comments
This commit is contained in:
@@ -15230,7 +15230,6 @@ package android.media {
|
||||
method public abstract android.media.Image.Plane[] getPlanes();
|
||||
method public abstract long getTimestamp();
|
||||
method public abstract int getWidth();
|
||||
method public boolean isOpaque();
|
||||
method public void setCropRect(android.graphics.Rect);
|
||||
method public void setTimestamp(long);
|
||||
}
|
||||
@@ -15250,9 +15249,7 @@ package android.media {
|
||||
method public int getMaxImages();
|
||||
method public android.view.Surface getSurface();
|
||||
method public int getWidth();
|
||||
method public boolean isOpaque();
|
||||
method public static android.media.ImageReader newInstance(int, int, int, int);
|
||||
method public static android.media.ImageReader newOpaqueInstance(int, int, int);
|
||||
method public void setOnImageAvailableListener(android.media.ImageReader.OnImageAvailableListener, android.os.Handler);
|
||||
}
|
||||
|
||||
@@ -15267,11 +15264,11 @@ package android.media {
|
||||
method public int getMaxImages();
|
||||
method public static android.media.ImageWriter newInstance(android.view.Surface, int);
|
||||
method public void queueInputImage(android.media.Image);
|
||||
method public void setImageListener(android.media.ImageWriter.ImageListener, android.os.Handler);
|
||||
method public void setOnImageReleasedListener(android.media.ImageWriter.OnImageReleasedListener, android.os.Handler);
|
||||
}
|
||||
|
||||
public static abstract interface ImageWriter.ImageListener {
|
||||
method public abstract void onInputImageReleased(android.media.ImageWriter);
|
||||
public static abstract interface ImageWriter.OnImageReleasedListener {
|
||||
method public abstract void onImageReleased(android.media.ImageWriter);
|
||||
}
|
||||
|
||||
public class JetPlayer {
|
||||
|
||||
@@ -16467,7 +16467,6 @@ package android.media {
|
||||
method public abstract android.media.Image.Plane[] getPlanes();
|
||||
method public abstract long getTimestamp();
|
||||
method public abstract int getWidth();
|
||||
method public boolean isOpaque();
|
||||
method public void setCropRect(android.graphics.Rect);
|
||||
method public void setTimestamp(long);
|
||||
}
|
||||
@@ -16487,9 +16486,7 @@ package android.media {
|
||||
method public int getMaxImages();
|
||||
method public android.view.Surface getSurface();
|
||||
method public int getWidth();
|
||||
method public boolean isOpaque();
|
||||
method public static android.media.ImageReader newInstance(int, int, int, int);
|
||||
method public static android.media.ImageReader newOpaqueInstance(int, int, int);
|
||||
method public void setOnImageAvailableListener(android.media.ImageReader.OnImageAvailableListener, android.os.Handler);
|
||||
}
|
||||
|
||||
@@ -16504,11 +16501,11 @@ package android.media {
|
||||
method public int getMaxImages();
|
||||
method public static android.media.ImageWriter newInstance(android.view.Surface, int);
|
||||
method public void queueInputImage(android.media.Image);
|
||||
method public void setImageListener(android.media.ImageWriter.ImageListener, android.os.Handler);
|
||||
method public void setOnImageReleasedListener(android.media.ImageWriter.OnImageReleasedListener, android.os.Handler);
|
||||
}
|
||||
|
||||
public static abstract interface ImageWriter.ImageListener {
|
||||
method public abstract void onInputImageReleased(android.media.ImageWriter);
|
||||
public static abstract interface ImageWriter.OnImageReleasedListener {
|
||||
method public abstract void onImageReleased(android.media.ImageWriter);
|
||||
}
|
||||
|
||||
public class JetPlayer {
|
||||
|
||||
@@ -163,10 +163,12 @@ public abstract class Image implements AutoCloseable {
|
||||
* Get the timestamp associated with this frame.
|
||||
* <p>
|
||||
* The timestamp is measured in nanoseconds, and is normally monotonically
|
||||
* increasing. However, the behavior of the timestamp depends on the source
|
||||
* of this image. See {@link android.hardware.Camera Camera},
|
||||
* {@link android.hardware.camera2.CameraDevice CameraDevice}, {@link MediaPlayer} and
|
||||
* {@link MediaCodec} for more details.
|
||||
* increasing. The timestamps for the images from different sources may have
|
||||
* different timebases therefore may not be comparable. The specific meaning and
|
||||
* timebase of the timestamp depend on the source providing images. See
|
||||
* {@link android.hardware.Camera Camera},
|
||||
* {@link android.hardware.camera2.CameraDevice CameraDevice},
|
||||
* {@link MediaPlayer} and {@link MediaCodec} for more details.
|
||||
* </p>
|
||||
*/
|
||||
public abstract long getTimestamp();
|
||||
@@ -175,9 +177,11 @@ public abstract class Image implements AutoCloseable {
|
||||
* Set the timestamp associated with this frame.
|
||||
* <p>
|
||||
* The timestamp is measured in nanoseconds, and is normally monotonically
|
||||
* increasing. However, the behavior of the timestamp depends on
|
||||
* the destination of this image. See {@link android.hardware.Camera Camera}
|
||||
* , {@link android.hardware.camera2.CameraDevice CameraDevice},
|
||||
* increasing. The timestamps for the images from different sources may have
|
||||
* different timebases therefore may not be comparable. The specific meaning and
|
||||
* timebase of the timestamp depend on the source providing images. See
|
||||
* {@link android.hardware.Camera Camera},
|
||||
* {@link android.hardware.camera2.CameraDevice CameraDevice},
|
||||
* {@link MediaPlayer} and {@link MediaCodec} for more details.
|
||||
* </p>
|
||||
* <p>
|
||||
@@ -195,18 +199,6 @@ public abstract class Image implements AutoCloseable {
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Check if the image is opaque.</p>
|
||||
*
|
||||
* <p>The pixel data of opaque images are not accessible to the application,
|
||||
* and therefore {@link #getPlanes} will return an empty array for an opaque image.
|
||||
* </p>
|
||||
*/
|
||||
public boolean isOpaque() {
|
||||
throwISEIfImageIsInvalid();
|
||||
return false;
|
||||
}
|
||||
|
||||
private Rect mCropRect;
|
||||
|
||||
/**
|
||||
@@ -243,10 +235,11 @@ public abstract class Image implements AutoCloseable {
|
||||
|
||||
/**
|
||||
* Get the array of pixel planes for this Image. The number of planes is
|
||||
* determined by the format of the Image. The application will get an
|
||||
* empty array if the image is opaque because the opaque image pixel data
|
||||
* is not directly accessible. The application can check if an image is
|
||||
* opaque by calling {@link Image#isOpaque}.
|
||||
* determined by the format of the Image. The application will get an empty
|
||||
* array if the image format is {@link android.graphics.ImageFormat#PRIVATE
|
||||
* PRIVATE}, because the image pixel data is not directly accessible. The
|
||||
* application can check the image format by calling
|
||||
* {@link Image#getFormat()}.
|
||||
*/
|
||||
public abstract Plane[] getPlanes();
|
||||
|
||||
|
||||
@@ -67,77 +67,46 @@ public class ImageReader implements AutoCloseable {
|
||||
*/
|
||||
private static final int ACQUIRE_MAX_IMAGES = 2;
|
||||
|
||||
/**
|
||||
* <p>Create a new reader for images of the desired size and format.</p>
|
||||
*
|
||||
* <p>The {@code maxImages} parameter determines the maximum number of {@link Image}
|
||||
* objects that can be be acquired from the {@code ImageReader}
|
||||
* simultaneously. Requesting more buffers will use up more memory, so it is
|
||||
* important to use only the minimum number necessary for the use case.</p>
|
||||
*
|
||||
* <p>The valid sizes and formats depend on the source of the image
|
||||
* data.</p>
|
||||
*
|
||||
* @param width
|
||||
* The default width in pixels of the Images that this reader will produce.
|
||||
* @param height
|
||||
* The default height in pixels of the Images that this reader will produce.
|
||||
* @param format
|
||||
* The format of the Image that this reader will produce. This
|
||||
* must be one of the {@link android.graphics.ImageFormat} or
|
||||
* {@link android.graphics.PixelFormat} constants. Note that
|
||||
* not all formats is supported, like ImageFormat.NV21.
|
||||
* @param maxImages
|
||||
* The maximum number of images the user will want to
|
||||
* access simultaneously. This should be as small as possible to limit
|
||||
* memory use. Once maxImages Images are obtained by the user, one of them
|
||||
* has to be released before a new Image will become available for access
|
||||
* through {@link #acquireLatestImage()} or {@link #acquireNextImage()}.
|
||||
* Must be greater than 0.
|
||||
*
|
||||
* @see Image
|
||||
*/
|
||||
public static ImageReader newInstance(int width, int height, int format, int maxImages) {
|
||||
if (format == ImageFormat.PRIVATE) {
|
||||
throw new IllegalArgumentException("To obtain an opaque ImageReader, please use"
|
||||
+ " newOpaqueInstance rather than newInstance");
|
||||
}
|
||||
return new ImageReader(width, height, format, maxImages);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>
|
||||
* Create a new opaque reader for images of the desired size.
|
||||
* </p>
|
||||
* <p>
|
||||
* An opaque {@link ImageReader} produces images that are not directly
|
||||
* accessible by the application. The application can still acquire images
|
||||
* from an opaque image reader, and send them to the
|
||||
* {@link android.hardware.camera2.CameraDevice camera} for reprocessing via
|
||||
* {@link ImageWriter} interface. However, the {@link Image#getPlanes()
|
||||
* getPlanes()} will return an empty array for opaque images. The
|
||||
* application can check if an existing reader is an opaque reader by
|
||||
* calling {@link #isOpaque()}.
|
||||
* Create a new reader for images of the desired size and format.
|
||||
* </p>
|
||||
* <p>
|
||||
* The {@code maxImages} parameter determines the maximum number of
|
||||
* {@link Image} objects that can be be acquired from the
|
||||
* {@code ImageReader} simultaneously. Requesting more buffers will use up
|
||||
* more memory, so it is important to use only the minimum number necessary.
|
||||
* more memory, so it is important to use only the minimum number necessary
|
||||
* for the use case.
|
||||
* </p>
|
||||
* <p>
|
||||
* The valid sizes and formats depend on the source of the image data.
|
||||
* </p>
|
||||
* <p>
|
||||
* Opaque ImageReaders are more efficient to use when application access to
|
||||
* image data is not necessary, compared to ImageReaders using a non-opaque
|
||||
* format such as {@link ImageFormat#YUV_420_888 YUV_420_888}.
|
||||
* If the {@code format} is {@link ImageFormat#PRIVATE PRIVATE}, the created
|
||||
* {@link ImageReader} will produce images that are not directly accessible
|
||||
* by the application. The application can still acquire images from this
|
||||
* {@link ImageReader}, and send them to the
|
||||
* {@link android.hardware.camera2.CameraDevice camera} for reprocessing via
|
||||
* {@link ImageWriter} interface. However, the {@link Image#getPlanes()
|
||||
* getPlanes()} will return an empty array for {@link ImageFormat#PRIVATE
|
||||
* PRIVATE} format images. The application can check if an existing reader's
|
||||
* format by calling {@link #getImageFormat()}.
|
||||
* </p>
|
||||
* <p>
|
||||
* {@link ImageFormat#PRIVATE PRIVATE} format {@link ImageReader
|
||||
* ImageReaders} are more efficient to use when application access to image
|
||||
* data is not necessary, compared to ImageReaders using other format such
|
||||
* as {@link ImageFormat#YUV_420_888 YUV_420_888}.
|
||||
* </p>
|
||||
*
|
||||
* @param width The default width in pixels of the Images that this reader
|
||||
* will produce.
|
||||
* @param height The default height in pixels of the Images that this reader
|
||||
* will produce.
|
||||
* @param format The format of the Image that this reader will produce. This
|
||||
* must be one of the {@link android.graphics.ImageFormat} or
|
||||
* {@link android.graphics.PixelFormat} constants. Note that not
|
||||
* all formats are supported, like ImageFormat.NV21.
|
||||
* @param maxImages The maximum number of images the user will want to
|
||||
* access simultaneously. This should be as small as possible to
|
||||
* limit memory use. Once maxImages Images are obtained by the
|
||||
@@ -147,8 +116,8 @@ public class ImageReader implements AutoCloseable {
|
||||
* Must be greater than 0.
|
||||
* @see Image
|
||||
*/
|
||||
public static ImageReader newOpaqueInstance(int width, int height, int maxImages) {
|
||||
return new ImageReader(width, height, ImageFormat.PRIVATE, maxImages);
|
||||
public static ImageReader newInstance(int width, int height, int format, int maxImages) {
|
||||
return new ImageReader(width, height, format, maxImages);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -247,23 +216,6 @@ public class ImageReader implements AutoCloseable {
|
||||
return mMaxImages;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>
|
||||
* Check if the {@link ImageReader} is an opaque reader.
|
||||
* </p>
|
||||
* <p>
|
||||
* An opaque image reader produces opaque images, see {@link Image#isOpaque}
|
||||
* for more details.
|
||||
* </p>
|
||||
*
|
||||
* @return true if the ImageReader is opaque.
|
||||
* @see Image#isOpaque
|
||||
* @see ImageReader#newOpaqueInstance
|
||||
*/
|
||||
public boolean isOpaque() {
|
||||
return mFormat == ImageFormat.PRIVATE;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Get a {@link Surface} that can be used to produce {@link Image Images} for this
|
||||
* {@code ImageReader}.</p>
|
||||
@@ -540,11 +492,11 @@ public class ImageReader implements AutoCloseable {
|
||||
* </p>
|
||||
* <p>
|
||||
* This method can be used to achieve zero buffer copy for use cases like
|
||||
* {@link android.hardware.camera2.CameraDevice Camera2 API} OPAQUE and YUV
|
||||
* {@link android.hardware.camera2.CameraDevice Camera2 API} PRIVATE and YUV
|
||||
* reprocessing, where the application can select an output image from
|
||||
* {@link ImageReader} and transfer this image directly to
|
||||
* {@link ImageWriter}, where this image can be consumed by camera directly.
|
||||
* For OPAQUE reprocessing, this is the only way to send input buffers to
|
||||
* For PRIVATE reprocessing, this is the only way to send input buffers to
|
||||
* the {@link android.hardware.camera2.CameraDevice camera} for
|
||||
* reprocessing.
|
||||
* </p>
|
||||
@@ -745,12 +697,6 @@ public class ImageReader implements AutoCloseable {
|
||||
return mPlanes.clone();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isOpaque() {
|
||||
throwISEIfImageIsInvalid();
|
||||
return mFormat == ImageFormat.PRIVATE;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected final void finalize() throws Throwable {
|
||||
try {
|
||||
|
||||
@@ -57,7 +57,7 @@ class ImageUtils {
|
||||
case ImageFormat.RAW_SENSOR:
|
||||
case ImageFormat.RAW10:
|
||||
return 1;
|
||||
case PixelFormat.OPAQUE:
|
||||
case ImageFormat.PRIVATE:
|
||||
return 0;
|
||||
default:
|
||||
throw new UnsupportedOperationException(
|
||||
@@ -70,10 +70,11 @@ class ImageUtils {
|
||||
* Copy source image data to destination Image.
|
||||
* </p>
|
||||
* <p>
|
||||
* Only support the copy between two non-opaque images with same properties
|
||||
* (format, size, etc.). The data from the source image will be copied to
|
||||
* the byteBuffers from the destination Image starting from position zero,
|
||||
* and the destination image will be rewound to zero after copy is done.
|
||||
* Only support the copy between two non-{@link ImageFormat#PRIVATE PRIVATE} format
|
||||
* images with same properties (format, size, etc.). The data from the
|
||||
* source image will be copied to the byteBuffers from the destination Image
|
||||
* starting from position zero, and the destination image will be rewound to
|
||||
* zero after copy is done.
|
||||
* </p>
|
||||
*
|
||||
* @param src The source image to be copied from.
|
||||
@@ -88,8 +89,9 @@ class ImageUtils {
|
||||
if (src.getFormat() != dst.getFormat()) {
|
||||
throw new IllegalArgumentException("Src and dst images should have the same format");
|
||||
}
|
||||
if (src.isOpaque() || dst.isOpaque()) {
|
||||
throw new IllegalArgumentException("Opaque image is not copyable");
|
||||
if (src.getFormat() == ImageFormat.PRIVATE ||
|
||||
dst.getFormat() == ImageFormat.PRIVATE) {
|
||||
throw new IllegalArgumentException("PRIVATE format images are not copyable");
|
||||
}
|
||||
if (!(dst.getOwner() instanceof ImageWriter)) {
|
||||
throw new IllegalArgumentException("Destination image is not from ImageWriter. Only"
|
||||
|
||||
@@ -33,8 +33,8 @@ import java.util.List;
|
||||
/**
|
||||
* <p>
|
||||
* The ImageWriter class allows an application to produce Image data into a
|
||||
* {@link android.view.Surface}, and have it be consumed by another component like
|
||||
* {@link android.hardware.camera2.CameraDevice CameraDevice}.
|
||||
* {@link android.view.Surface}, and have it be consumed by another component
|
||||
* like {@link android.hardware.camera2.CameraDevice CameraDevice}.
|
||||
* </p>
|
||||
* <p>
|
||||
* Several Android API classes can provide input {@link android.view.Surface
|
||||
@@ -54,21 +54,21 @@ import java.util.List;
|
||||
* <p>
|
||||
* If the application already has an Image from {@link ImageReader}, the
|
||||
* application can directly queue this Image into ImageWriter (via
|
||||
* {@link #queueInputImage}), potentially with zero buffer copies. For the opaque
|
||||
* Images produced by an opaque ImageReader (created by
|
||||
* {@link ImageReader#newOpaqueInstance}), this is the only way to send Image
|
||||
* data to ImageWriter, as the Image data aren't accessible by the application.
|
||||
* {@link #queueInputImage}), potentially with zero buffer copies. For the
|
||||
* {@link ImageFormat#PRIVATE PRIVATE} format Images produced by
|
||||
* {@link ImageReader}, this is the only way to send Image data to ImageWriter,
|
||||
* as the Image data aren't accessible by the application.
|
||||
* </p>
|
||||
* Once new input Images are queued into an ImageWriter, it's up to the downstream
|
||||
* components (e.g. {@link ImageReader} or
|
||||
* Once new input Images are queued into an ImageWriter, it's up to the
|
||||
* downstream components (e.g. {@link ImageReader} or
|
||||
* {@link android.hardware.camera2.CameraDevice}) to consume the Images. If the
|
||||
* downstream components cannot consume the Images at least as fast as the
|
||||
* ImageWriter production rate, the {@link #dequeueInputImage} call will eventually
|
||||
* block and the application will have to drop input frames. </p>
|
||||
* ImageWriter production rate, the {@link #dequeueInputImage} call will
|
||||
* eventually block and the application will have to drop input frames. </p>
|
||||
*/
|
||||
public class ImageWriter implements AutoCloseable {
|
||||
private final Object mListenerLock = new Object();
|
||||
private ImageListener mListener;
|
||||
private OnImageReleasedListener mListener;
|
||||
private ListenerHandler mListenerHandler;
|
||||
private long mNativeContext;
|
||||
|
||||
@@ -168,32 +168,34 @@ public class ImageWriter implements AutoCloseable {
|
||||
* This call will block if all available input images have been queued by
|
||||
* the application and the downstream consumer has not yet consumed any.
|
||||
* When an Image is consumed by the downstream consumer and released, an
|
||||
* {@link ImageListener#onInputImageReleased} callback will be fired, which
|
||||
* indicates that there is one input Image available. For non-opaque formats
|
||||
* (({@link ImageWriter#getFormat()} != {@link ImageFormat#PRIVATE})), it is
|
||||
* {@link OnImageReleasedListener#onImageReleased} callback will be fired,
|
||||
* which indicates that there is one input Image available. For non-
|
||||
* {@link ImageFormat#PRIVATE PRIVATE} formats (
|
||||
* {@link ImageWriter#getFormat()} != {@link ImageFormat#PRIVATE}), it is
|
||||
* recommended to dequeue the next Image only after this callback is fired,
|
||||
* in the steady state.
|
||||
* </p>
|
||||
* <p>
|
||||
* If the ImageWriter is opaque ({@link ImageWriter#getFormat()} ==
|
||||
* {@link ImageFormat#PRIVATE}), the image buffer is inaccessible to
|
||||
* the application, and calling this method will result in an
|
||||
* {@link IllegalStateException}. Instead, the application should acquire
|
||||
* opaque images from some other component (e.g. an opaque
|
||||
* If the format of ImageWriter is {@link ImageFormat#PRIVATE PRIVATE} (
|
||||
* {@link ImageWriter#getFormat()} == {@link ImageFormat#PRIVATE}), the
|
||||
* image buffer is inaccessible to the application, and calling this method
|
||||
* will result in an {@link IllegalStateException}. Instead, the application
|
||||
* should acquire images from some other component (e.g. an
|
||||
* {@link ImageReader}), and queue them directly to this ImageWriter via the
|
||||
* {@link ImageWriter#queueInputImage queueInputImage()} method.
|
||||
* </p>
|
||||
*
|
||||
* @return The next available input Image from this ImageWriter.
|
||||
* @throws IllegalStateException if {@code maxImages} Images are currently
|
||||
* dequeued, or the ImageWriter is opaque.
|
||||
* dequeued, or the ImageWriter format is
|
||||
* {@link ImageFormat#PRIVATE PRIVATE}.
|
||||
* @see #queueInputImage
|
||||
* @see Image#close
|
||||
*/
|
||||
public Image dequeueInputImage() {
|
||||
if (mWriterFormat == ImageFormat.PRIVATE) {
|
||||
throw new IllegalStateException(
|
||||
"Opaque ImageWriter doesn't support this operation since opaque images are"
|
||||
"PRIVATE format ImageWriter doesn't support this operation since the images are"
|
||||
+ " inaccessible to the application!");
|
||||
}
|
||||
|
||||
@@ -229,10 +231,10 @@ public class ImageWriter implements AutoCloseable {
|
||||
* </p>
|
||||
* <p>
|
||||
* After this method is called and the downstream consumer consumes and
|
||||
* releases the Image, an {@link ImageListener#onInputImageReleased
|
||||
* onInputImageReleased()} callback will fire. The application can use this
|
||||
* callback to avoid sending Images faster than the downstream consumer
|
||||
* processing rate in steady state.
|
||||
* releases the Image, an {@link OnImageReleasedListener#onImageReleased}
|
||||
* callback will fire. The application can use this callback to avoid
|
||||
* sending Images faster than the downstream consumer processing rate in
|
||||
* steady state.
|
||||
* </p>
|
||||
* <p>
|
||||
* Passing in an Image from some other component (e.g. an
|
||||
@@ -271,12 +273,12 @@ public class ImageWriter implements AutoCloseable {
|
||||
}
|
||||
|
||||
ImageReader prevOwner = (ImageReader) image.getOwner();
|
||||
// Only do the image attach for opaque images for now. Do the image
|
||||
// Only do the image attach for PRIVATE format images for now. Do the image
|
||||
// copy for other formats. TODO: use attach for other formats to
|
||||
// improve the performance, and fall back to copy when attach/detach
|
||||
// fails. Right now, detach is guaranteed to fail as the buffer is
|
||||
// locked when ImageReader#acquireNextImage is called. See bug 19962027.
|
||||
if (image.isOpaque()) {
|
||||
if (image.getFormat() == ImageFormat.PRIVATE) {
|
||||
prevOwner.detachImage(image);
|
||||
attachAndQueueInputImage(image);
|
||||
// This clears the native reference held by the original owner.
|
||||
@@ -319,8 +321,9 @@ public class ImageWriter implements AutoCloseable {
|
||||
* Get the ImageWriter format.
|
||||
* <p>
|
||||
* This format may be different than the Image format returned by
|
||||
* {@link Image#getFormat()}. However, if the ImageWriter is opaque (format
|
||||
* == {@link ImageFormat#PRIVATE}) , the images from it will also be opaque.
|
||||
* {@link Image#getFormat()}. However, if the ImageWriter format is
|
||||
* {@link ImageFormat#PRIVATE PRIVATE}, calling {@link #dequeueInputImage()}
|
||||
* will result in an {@link IllegalStateException}.
|
||||
* </p>
|
||||
*
|
||||
* @return The ImageWriter format.
|
||||
@@ -333,7 +336,7 @@ public class ImageWriter implements AutoCloseable {
|
||||
* ImageWriter callback interface, used to to asynchronously notify the
|
||||
* application of various ImageWriter events.
|
||||
*/
|
||||
public interface ImageListener {
|
||||
public interface OnImageReleasedListener {
|
||||
/**
|
||||
* <p>
|
||||
* Callback that is called when an input Image is released back to
|
||||
@@ -361,7 +364,7 @@ public class ImageWriter implements AutoCloseable {
|
||||
* @see ImageWriter
|
||||
* @see Image
|
||||
*/
|
||||
void onInputImageReleased(ImageWriter writer);
|
||||
void onImageReleased(ImageWriter writer);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -375,7 +378,7 @@ public class ImageWriter implements AutoCloseable {
|
||||
* @throws IllegalArgumentException If no handler specified and the calling
|
||||
* thread has no looper.
|
||||
*/
|
||||
public void setImageListener(ImageListener listener, Handler handler) {
|
||||
public void setOnImageReleasedListener(OnImageReleasedListener listener, Handler handler) {
|
||||
synchronized (mListenerLock) {
|
||||
if (listener != null) {
|
||||
Looper looper = handler != null ? handler.getLooper() : Looper.myLooper();
|
||||
@@ -408,7 +411,7 @@ public class ImageWriter implements AutoCloseable {
|
||||
*/
|
||||
@Override
|
||||
public void close() {
|
||||
setImageListener(null, null);
|
||||
setOnImageReleasedListener(null, null);
|
||||
for (Image image : mDequeuedImages) {
|
||||
image.close();
|
||||
}
|
||||
@@ -431,19 +434,18 @@ public class ImageWriter implements AutoCloseable {
|
||||
* Attach and queue input Image to this ImageWriter.
|
||||
* </p>
|
||||
* <p>
|
||||
* When an Image is from an opaque source (e.g. an opaque ImageReader
|
||||
* created by {@link ImageReader#newOpaqueInstance}), or the source Image is
|
||||
* so large that copying its data is too expensive, this method can be used
|
||||
* to migrate the source Image into ImageWriter without a data copy, and
|
||||
* then queue it to this ImageWriter. The source Image must be detached from
|
||||
* its previous owner already, or this call will throw an
|
||||
* When the format of an Image is {@link ImageFormat#PRIVATE PRIVATE}, or
|
||||
* the source Image is so large that copying its data is too expensive, this
|
||||
* method can be used to migrate the source Image into ImageWriter without a
|
||||
* data copy, and then queue it to this ImageWriter. The source Image must
|
||||
* be detached from its previous owner already, or this call will throw an
|
||||
* {@link IllegalStateException}.
|
||||
* </p>
|
||||
* <p>
|
||||
* After this call, the ImageWriter takes ownership of this Image. This
|
||||
* ownership will automatically be removed from this writer after the
|
||||
* consumer releases this Image, that is, after
|
||||
* {@link ImageListener#onInputImageReleased}. The caller is responsible for
|
||||
* {@link OnImageReleasedListener#onImageReleased}. The caller is responsible for
|
||||
* closing this Image through {@link Image#close()} to free up the resources
|
||||
* held by this Image.
|
||||
* </p>
|
||||
@@ -492,12 +494,12 @@ public class ImageWriter implements AutoCloseable {
|
||||
|
||||
@Override
|
||||
public void handleMessage(Message msg) {
|
||||
ImageListener listener;
|
||||
OnImageReleasedListener listener;
|
||||
synchronized (mListenerLock) {
|
||||
listener = mListener;
|
||||
}
|
||||
if (listener != null) {
|
||||
listener.onInputImageReleased(ImageWriter.this);
|
||||
listener.onImageReleased(ImageWriter.this);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -646,13 +648,6 @@ public class ImageWriter implements AutoCloseable {
|
||||
mTimestamp = timestamp;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isOpaque() {
|
||||
throwISEIfImageIsInvalid();
|
||||
|
||||
return getFormat() == ImageFormat.PRIVATE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Plane[] getPlanes() {
|
||||
throwISEIfImageIsInvalid();
|
||||
|
||||
Reference in New Issue
Block a user