diff options
author | Igor Murashkin <iam@google.com> | 2013-09-10 19:35:24 -0700 |
---|---|---|
committer | Igor Murashkin <iam@google.com> | 2013-09-19 19:01:32 -0700 |
commit | 5c9eaf6796a4c972710dd5cd23cdfa334fa8ad2e (patch) | |
tree | c893849f3cfcadebf63c8bd30532f72b4b2fb7ff /core/java/android/hardware | |
parent | af638c4f9daa74b4c8e0905f07e11290f6845abe (diff) | |
download | frameworks_base-5c9eaf6796a4c972710dd5cd23cdfa334fa8ad2e.zip frameworks_base-5c9eaf6796a4c972710dd5cd23cdfa334fa8ad2e.tar.gz frameworks_base-5c9eaf6796a4c972710dd5cd23cdfa334fa8ad2e.tar.bz2 |
camera2: Add more camera device states, make #openCamera async.
* Move CAMERA_IN_USE, MAX_CAMERAS_IN_USE to StateListener#onError
* Copy CAMERA_DISABLED to StateListener#onError
Bug: 10360518
Change-Id: Idd8cf42e1511d12682018588b2b413116cf65116
Diffstat (limited to 'core/java/android/hardware')
4 files changed, 348 insertions, 81 deletions
diff --git a/core/java/android/hardware/camera2/CameraAccessException.java b/core/java/android/hardware/camera2/CameraAccessException.java index e08d1e6..1af575f 100644 --- a/core/java/android/hardware/camera2/CameraAccessException.java +++ b/core/java/android/hardware/camera2/CameraAccessException.java @@ -29,22 +29,24 @@ import android.util.AndroidException; public class CameraAccessException extends AndroidException { /** * The camera device is in use already + * @hide */ - public static final int CAMERA_IN_USE = 1; + public static final int CAMERA_IN_USE = 4; /** * The system-wide limit for number of open cameras has been reached, * and more camera devices cannot be opened until previous instances are * closed. + * @hide */ - public static final int MAX_CAMERAS_IN_USE = 2; + public static final int MAX_CAMERAS_IN_USE = 5; /** * The camera is disabled due to a device policy, and cannot be opened. * * @see android.app.admin.DevicePolicyManager#setCameraDisabled(android.content.ComponentName, boolean) */ - public static final int CAMERA_DISABLED = 3; + public static final int CAMERA_DISABLED = 1; /** * The camera device is removable and has been disconnected from the Android @@ -52,7 +54,23 @@ public class CameraAccessException extends AndroidException { * is no longer valid, or the camera service has shut down the connection due to a * higher-priority access request for the camera device. */ - public static final int CAMERA_DISCONNECTED = 4; + public static final int CAMERA_DISCONNECTED = 2; + + /** + * The camera device is currently in the error state. + * + * <p>The camera has failed to open or has failed at a later time + * as a result of some non-user interaction. Refer to + * {@link CameraDevice.StateListener#onError} for the exact + * nature of the error.</p> + * + * <p>No further calls to the camera will succeed. Clean up + * the camera with {@link CameraDevice#close} and try + * handling the error in order to successfully re-open the camera. + * </p> + * + */ + public static final int CAMERA_ERROR = 3; /** * A deprecated HAL version is in use. @@ -68,10 +86,9 @@ public class CameraAccessException extends AndroidException { /** * The reason for the failure to access the camera. * - * @see #CAMERA_IN_USE - * @see #MAX_CAMERAS_IN_USE * @see #CAMERA_DISABLED * @see #CAMERA_DISCONNECTED + * @see #CAMERA_ERROR */ public final int getReason() { return mReason; @@ -105,12 +122,15 @@ public class CameraAccessException extends AndroidException { return "The system-wide limit for number of open cameras has been reached, " + "and more camera devices cannot be opened until previous instances " + "are closed."; + case CAMERA_DISCONNECTED: + return "The camera device is removable and has been disconnected from the " + + "Android device, or the camera service has shut down the connection due " + + "to a higher-priority access request for the camera device."; case CAMERA_DISABLED: return "The camera is disabled due to a device policy, and cannot be opened."; - case CAMERA_DISCONNECTED: - return "The camera device is removable and has been disconnected from the Android" + - " device, or the camera service has shut down the connection due to a " + - "higher-priority access request for the camera device."; + case CAMERA_ERROR: + return "The camera device is currently in the error state; " + + "no further calls to it will succeed."; } return null; } diff --git a/core/java/android/hardware/camera2/CameraDevice.java b/core/java/android/hardware/camera2/CameraDevice.java index 0c13b0f..f047b0d 100644 --- a/core/java/android/hardware/camera2/CameraDevice.java +++ b/core/java/android/hardware/camera2/CameraDevice.java @@ -137,7 +137,9 @@ public interface CameraDevice extends AutoCloseable { * * @return the static properties of the camera * - * @throws CameraAccessException if the camera device is no longer connected + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera device has been closed * * @see CameraManager#getCameraProperties */ @@ -218,23 +220,31 @@ public interface CameraDevice extends AutoCloseable { * * <p>To reach an idle state without cancelling any submitted captures, first * stop any repeating request/burst with {@link #stopRepeating}, and then - * wait for the {@link CameraDeviceListener#onCameraIdle} callback to be + * wait for the {@link StateListener#onIdle} callback to be * called. To idle as fast as possible, use {@link #flush} and wait for the * idle callback.</p> * * <p>Using larger resolution outputs, or more outputs, can result in slower * output rate from the device.</p> * + * <p>Configuring the outputs with an empty or null list will transition + * the camera into an {@link StateListener#onUnconfigured unconfigured state}. + * </p> + * + * <p>Calling configureOutputs with the same arguments as the last call to + * configureOutputs has no effect.</p> + * * @param outputs The new set of Surfaces that should be made available as * targets for captured image data. * * @throws IllegalArgumentException if the set of output Surfaces do not * meet the requirements - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device is not idle, or has - * encountered a fatal error + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera device is not idle, or + * if the camera device has been closed * - * @see CameraDeviceListener#onCameraIdle + * @see StateListener#onIdle * @see #stopRepeating * @see #flush */ @@ -255,9 +265,9 @@ public interface CameraDevice extends AutoCloseable { * * @throws IllegalArgumentException if the templateType is not in the list * of supported templates. - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera device has been closed * * @see #TEMPLATE_PREVIEW * @see #TEMPLATE_RECORD @@ -295,9 +305,10 @@ public interface CameraDevice extends AutoCloseable { * {@code null} to use the current thread's {@link android.os.Looper * looper}. * - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is currently busy or unconfigured, + * or the camera device has been closed. * @throws IllegalArgumentException If the request targets Surfaces not * currently configured as outputs. Or if the handler is null, the listener * is not null, and the calling thread has no looper. @@ -335,9 +346,10 @@ public interface CameraDevice extends AutoCloseable { * {@code null} to use the current thread's {@link android.os.Looper * looper}. * - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is currently busy or unconfigured, + * or the camera device has been closed. * @throws IllegalArgumentException If the requests target Surfaces not * currently configured as outputs. Or if the handler is null, the listener * is not null, and the calling thread has no looper. @@ -387,10 +399,10 @@ public interface CameraDevice extends AutoCloseable { * {@code null} to use the current thread's {@link android.os.Looper * looper}. * - * @throws CameraAccessException if the camera device is no longer - * connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is currently busy or unconfigured, + * or the camera device has been closed. * @throws IllegalArgumentException If the requests reference Surfaces not * currently configured as outputs. Or if the handler is null, the listener * is not null, and the calling thread has no looper. @@ -442,9 +454,10 @@ public interface CameraDevice extends AutoCloseable { * {@code null} to use the current thread's {@link android.os.Looper * looper}. * - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is currently busy or unconfigured, + * or the camera device has been closed. * @throws IllegalArgumentException If the requests reference Surfaces not * currently configured as outputs. Or if the handler is null, the listener * is not null, and the calling thread has no looper. @@ -467,21 +480,17 @@ public interface CameraDevice extends AutoCloseable { * <p>Any currently in-flight captures will still complete, as will any * burst that is mid-capture. To ensure that the device has finished * processing all of its capture requests and is in idle state, wait for the - * {@link CameraDeviceListener#onCameraIdle} callback after calling this + * {@link StateListener#onIdle} callback after calling this * method..</p> * - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed or the - * device has encountered a fatal error. + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is currently busy or unconfigured, + * or the camera device has been closed. * * @see #setRepeatingRequest * @see #setRepeatingBurst - * @see CameraDeviceListener#onCameraIdle - * - * @throws CameraAccessException if the camera device is no longer connected - * @throws IllegalStateException if the camera device has been closed, the - * device has encountered a fatal error, or if there is an active repeating - * request or burst. + * @see StateListener#onIdle */ public void stopRepeating() throws CameraAccessException; @@ -519,7 +528,7 @@ public interface CameraDevice extends AutoCloseable { * {@link CaptureListener}.</p> * * <p>If the camera device is idle when the listener is set, then the - * {@link CameraDeviceListener#onCameraIdle} method will be immediately called, + * {@link StateListener#onIdle} method will be immediately called, * even if the device has never been active before. * </p> * @@ -530,8 +539,10 @@ public interface CameraDevice extends AutoCloseable { * * @throws IllegalArgumentException if handler is null, the listener is * not null, and the calling thread has no looper + * + * @hide */ - public void setDeviceListener(CameraDeviceListener listener, Handler handler); + public void setDeviceListener(StateListener listener, Handler handler); /** * Flush all captures currently pending and in-progress as fast as @@ -558,7 +569,11 @@ public interface CameraDevice extends AutoCloseable { * configurations, or for cancelling long in-progress requests (such as a * multi-second capture).</p> * - * @throws CameraAccessException if the camera device is no longer connected + * @throws CameraAccessException if the camera device is no longer connected or has + * encountered a fatal error + * @throws IllegalStateException if the camera is not idle/active, + * or the camera device has been closed. + * * @see #setRepeatingRequest * @see #setRepeatingBurst * @see #configureOutputs @@ -569,10 +584,9 @@ public interface CameraDevice extends AutoCloseable { * Close the connection to this camera device. After this call, all calls to * the camera device interface will throw a {@link IllegalStateException}, * except for calls to close(). - * @throws Exception */ @Override - public void close() throws Exception; + public void close(); // TODO: We should decide on the behavior of in-flight requests should be on close. /** @@ -687,37 +701,190 @@ public interface CameraDevice extends AutoCloseable { * * @see #setDeviceListener */ - public static abstract class CameraDeviceListener { + public static abstract class StateListener { + /** + * An error code that can be reported by {@link #onError} + * indicating that the camera device is in use already. + * + * <p> + * This error can be produced when opening the camera fails. + * </p> + * + * @see #onError + */ + public static final int ERROR_CAMERA_IN_USE = 1; /** - * An error code that can be reported by {@link #onCameraError} + * An error code that can be reported by {@link #onError} + * indicating that the camera device could not be opened + * because there are too many other open camera devices. + * + * <p> + * The system-wide limit for number of open cameras has been reached, + * and more camera devices cannot be opened until previous instances are + * closed. + * </p> + * + * <p> + * This error can be produced when opening the camera fails. + * </p> + * + * @see #onError + */ + public static final int ERROR_MAX_CAMERAS_IN_USE = 2; + + /** + * An error code that can be reported by {@link #onError} + * indicating that the camera device could not be opened due to a device + * policy. + * + * @see android.app.admin.DevicePolicyManager#setCameraDisabled(android.content.ComponentName, boolean) + * @see #onError + */ + public static final int ERROR_CAMERA_DISABLED = 3; + + /** + * An error code that can be reported by {@link #onError} * indicating that the camera device has encountered a fatal error. * * <p>The camera device needs to be re-opened to be used again.</p> * - * @see #onCameraDeviceError + * @see #onError */ - public static final int ERROR_CAMERA_DEVICE = 1; + public static final int ERROR_CAMERA_DEVICE = 4; /** - * An error code that can be reported by {@link #onCameraError} + * An error code that can be reported by {@link #onError} * indicating that the camera service has encountered a fatal error. * * <p>The Android device may need to be shut down and restarted to restore * camera function, or there may be a persistent hardware problem.</p> * - * @see #onCameraDeviceError + * <p>An attempt at recovery <i>may</i> be possible by closing the + * CameraDevice and the CameraManager, and trying to acquire all resources + * again from scratch.</p> + * + * @see #onError + */ + public static final int ERROR_CAMERA_SERVICE = 5; + + /** + * The method called when a camera device has finished opening. + * + * <p>An opened camera will immediately afterwards transition into + * {@link #onUnconfigured}.</p> + * + * @param camera the camera device that has become opened + */ + public abstract void onOpened(CameraDevice camera); // Must implement + + /** + * The method called when a camera device has no outputs configured. + * + * <p>An unconfigured camera device needs to be configured with + * {@link CameraDevice#configureOutputs} before being able to + * submit any capture request.</p> + * + * <p>This state may be entered by a newly opened camera or by + * calling {@link CameraDevice#configureOutputs} with a null/empty + * list of Surfaces when idle.</p> + * + * <p>Any attempts to submit a capture request while in this state + * will result in an {@link IllegalStateException} being thrown.</p> + * + * <p>The default implementation of this method does nothing.</p> + * + * @param camera the camera device has that become unconfigured + */ + public void onUnconfigured(CameraDevice camera) { + // Default empty implementation + } + + /** + * The method called when a camera device begins processing + * {@link CaptureRequest capture requests}. + * + * <p>A camera may not be re-configured while in this state. The camera + * will transition to the idle state once all pending captures have + * completed. If a repeating request is set, the camera will remain active + * until it is cleared and the remaining requests finish processing. To + * transition to the idle state as quickly as possible, call {@link #flush()}, + * which will idle the camera device as quickly as possible, likely canceling + * most in-progress captures.</p> + * + * <p>All calls except for {@link CameraDevice#configureOutputs} are + * legal while in this state. + * </p> + * + * <p>The default implementation of this method does nothing.</p> + * + * @param camera the camera device that has become active + * + * @see CameraDevice#capture + * @see CameraDevice#captureBurst + * @see CameraDevice#setRepeatingBurst + * @see CameraDevice#setRepeatingRequest + */ + public void onActive(CameraDevice camera) { + // Default empty implementation + } + + /** + * The method called when a camera device is busy. + * + * <p>A camera becomes busy while it's outputs are being configured + * (after a call to {@link CameraDevice#configureOutputs} or while it's + * being flushed (after a call to {@link CameraDevice#flush}.</p> + * + * <p>Once the on-going operations are complete, the camera will automatically + * transition into {@link #onIdle} if there is at least one configured output, + * or {@link #onUnconfigured} otherwise.</p> + * + * <p>Any attempts to manipulate the camera while its is busy + * will result in an {@link IllegalStateException} being thrown.</p> + * + * <p>Only the following methods are valid to call while in this state: + * <ul> + * <li>{@link CameraDevice#getId}</li> + * <li>{@link CameraDevice#createCaptureRequest}</li> + * <li>{@link CameraDevice#close}</li> + * </ul> + * </p> + * + * <p>The default implementation of this method does nothing.</p> + * + * @param camera the camera device that has become busy + * + * @see CameraDevice#configureOutputs + * @see CameraDevice#flush + */ + public void onBusy(CameraDevice camera) { + // Default empty implementation + } + + /** + * The method called when a camera device has been closed with + * {@link CameraDevice#close}. + * + * <p>Any attempt to call methods on this CameraDevice in the + * future will throw a {@link IllegalStateException}.</p> + * + * <p>The default implementation of this method does nothing.</p> + * + * @param camera the camera device that has become closed */ - public static final int ERROR_CAMERA_SERVICE = 2; + public void onClosed(CameraDevice camera) { + // Default empty implementation + } /** * The method called when a camera device has finished processing all * submitted capture requests and has reached an idle state. * - * <p>An idle camera device can have its outputs changed by calling - * {@link CameraDevice#configureOutputs}.</p> + * <p>An idle camera device can have its outputs changed by calling {@link + * CameraDevice#configureOutputs}, which will transition it into the busy state.</p> * - * <p>To idle and reconfigure outputs without cancelling any submitted + * <p>To idle and reconfigure outputs without canceling any submitted * capture requests, the application needs to clear its repeating * request/burst, if set, with {@link CameraDevice#stopRepeating}, and * then wait for this callback to be called before calling {@link @@ -725,7 +892,7 @@ public interface CameraDevice extends AutoCloseable { * * <p>To idle and reconfigure a camera device as fast as possible, the * {@link CameraDevice#flush} method can be used, which will discard all - * pending and in-progess capture requests. Once the {@link + * pending and in-progress capture requests. Once the {@link * CameraDevice#flush} method is called, the application must wait for * this callback to fire before calling {@link * CameraDevice#configureOutputs}.</p> @@ -738,7 +905,7 @@ public interface CameraDevice extends AutoCloseable { * @see CameraDevice#stopRepeating * @see CameraDevice#flush */ - public void onCameraIdle(CameraDevice camera) { + public void onIdle(CameraDevice camera) { // Default empty implementation } @@ -746,6 +913,9 @@ public interface CameraDevice extends AutoCloseable { * The method called when a camera device is no longer available for * use. * + * <p>This callback may be called instead of {@link #onOpened} + * if opening the camera fails.</p> + * * <p>Any attempt to call methods on this CameraDevice will throw a * {@link CameraAccessException}. The disconnection could be due to a * change in security policy or permissions; the physical disconnection @@ -759,25 +929,32 @@ public interface CameraDevice extends AutoCloseable { * <p>The default implementation logs a notice to the system log * about the disconnection.</p> * + * <p>You should clean up the camera with {@link CameraDevice#close} after + * this happens, as it is not recoverable until opening the camera again + * after it becomes {@link CameraManager.AvailabilityListener#onCameraAvailable available}. + * </p> + * * @param camera the device that has been disconnected */ - public void onCameraDisconnected(CameraDevice camera) { - Log.i("CameraListener", - String.format("Camera device %s disconnected", camera.getId())); - } + public abstract void onDisconnected(CameraDevice camera); // Must implement /** * The method called when a camera device has encountered a serious error. * + * <p>This callback may be called instead of {@link #onOpened} + * if opening the camera fails.</p> + * * <p>This indicates a failure of the camera device or camera service in * some way. Any attempt to call methods on this CameraDevice in the - * future will throw a {@link java.lang.IllegalStateException}.</p> + * future will throw a {@link CameraAccessException} with the + * {@link CameraAccessException#CAMERA_ERROR CAMERA_ERROR} reason. + * </p> * * <p>There may still be capture completion or camera stream listeners * that will be called after this error is received.</p> * - * <p>The default implementation logs an error to the system log about - * the camera failure.</p> + * <p>You should clean up the camera with {@link CameraDevice#close} after + * this happens. Further attempts at recovery are error-code specific.</p> * * @param camera The device reporting the error * @param error The error code, one of the @@ -785,11 +962,9 @@ public interface CameraDevice extends AutoCloseable { * * @see #ERROR_CAMERA_DEVICE * @see #ERROR_CAMERA_SERVICE + * @see #ERROR_CAMERA_DISABLED + * @see #ERROR_CAMERA_IN_USE */ - public void onCameraError(CameraDevice camera, int error) { - Log.e("CameraListener", - String.format("Camera device %s has encountered an error: %d", - camera.getId(), error)); - } + public abstract void onError(CameraDevice camera, int error); // Must implement } } diff --git a/core/java/android/hardware/camera2/CameraManager.java b/core/java/android/hardware/camera2/CameraManager.java index 4ad9259..29895ef 100644 --- a/core/java/android/hardware/camera2/CameraManager.java +++ b/core/java/android/hardware/camera2/CameraManager.java @@ -58,7 +58,7 @@ public final class CameraManager { private final ICameraService mCameraService; private ArrayList<String> mDeviceIdList; - private ArrayMap<AvailabilityListener, Handler> mListenerMap = + private final ArrayMap<AvailabilityListener, Handler> mListenerMap = new ArrayMap<AvailabilityListener, Handler>(); private final Context mContext; @@ -201,8 +201,7 @@ public final class CameraManager { * @see #getCameraIdList * @see android.app.admin.DevicePolicyManager#setCameraDisabled */ - public CameraDevice openCamera(String cameraId) throws CameraAccessException { - + private CameraDevice openCamera(String cameraId) throws CameraAccessException { try { synchronized (mLock) { @@ -237,6 +236,79 @@ public final class CameraManager { } /** + * Open a connection to a camera with the given ID. + * + * <p>Use {@link #getCameraIdList} to get the list of available camera + * devices. Note that even if an id is listed, open may fail if the device + * is disconnected between the calls to {@link #getCameraIdList} and + * {@link #openCamera}.</p> + * + * <p>If the camera successfully opens after this function call returns, + * {@link CameraDevice.StateListener#onOpened} will be invoked with the + * newly opened {@link CameraDevice} in the unconfigured state.</p> + * + * <p>If the camera becomes disconnected during initialization + * after this function call returns, + * {@link CameraDevice.StateListener#onDisconnected} with a + * {@link CameraDevice} in the disconnected state (and + * {@link CameraDevice.StateListener#onOpened} will be skipped).</p> + * + * <p>If the camera fails to initialize after this function call returns, + * {@link CameraDevice.StateListener#onError} will be invoked with a + * {@link CameraDevice} in the error state (and + * {@link CameraDevice.StateListener#onOpened} will be skipped).</p> + * + * @param cameraId + * The unique identifier of the camera device to open + * @param listener + * The listener which is invoked once the camera is opened + * @param handler + * The handler on which the listener should be invoked, or + * {@code null} to use the current thread's {@link android.os.Looper looper}. + * + * @throws CameraAccessException if the camera is disabled by device policy, + * or the camera has become or was disconnected. + * + * @throws IllegalArgumentException if cameraId or the listener was null, + * or the cameraId does not match any currently or previously available + * camera device. + * + * @throws SecurityException if the application does not have permission to + * access the camera + * + * @see #getCameraIdList + * @see android.app.admin.DevicePolicyManager#setCameraDisabled + */ + public void openCamera(String cameraId, final CameraDevice.StateListener listener, + Handler handler) + throws CameraAccessException { + + if (cameraId == null) { + throw new IllegalArgumentException("cameraId was null"); + } else if (listener == null) { + throw new IllegalArgumentException("listener was null"); + } else if (handler == null) { + if (Looper.myLooper() != null) { + handler = new Handler(); + } else { + throw new IllegalArgumentException( + "Looper doesn't exist in the calling thread"); + } + } + + final CameraDevice camera = openCamera(cameraId); + camera.setDeviceListener(listener, handler); + + // TODO: make truly async in the camera service + handler.post(new Runnable() { + @Override + public void run() { + listener.onOpened(camera); + } + }); + } + + /** * Interface for listening to camera devices becoming available or * unavailable. * @@ -265,7 +337,7 @@ public final class CameraManager { * * <p>If an application had an active CameraDevice instance for the * now-disconnected camera, that application will receive a - * {@link CameraDevice.CameraDeviceListener#onCameraDisconnected disconnection error}.</p> + * {@link CameraDevice.StateListener#onDisconnected disconnection error}.</p> * * <p>The default implementation of this method does nothing.</p> * @@ -403,6 +475,7 @@ public final class CameraManager { if (isAvailable(status)) { handler.post( new Runnable() { + @Override public void run() { listener.onCameraAvailable(id); } @@ -410,6 +483,7 @@ public final class CameraManager { } else { handler.post( new Runnable() { + @Override public void run() { listener.onCameraUnavailable(id); } diff --git a/core/java/android/hardware/camera2/impl/CameraDevice.java b/core/java/android/hardware/camera2/impl/CameraDevice.java index 995555a..efbd769 100644 --- a/core/java/android/hardware/camera2/impl/CameraDevice.java +++ b/core/java/android/hardware/camera2/impl/CameraDevice.java @@ -55,7 +55,7 @@ public class CameraDevice implements android.hardware.camera2.CameraDevice { private final Object mLock = new Object(); private final CameraDeviceCallbacks mCallbacks = new CameraDeviceCallbacks(); - private CameraDeviceListener mDeviceListener; + private StateListener mDeviceListener; private Handler mDeviceHandler; private final SparseArray<CaptureListenerHolder> mCaptureListenerMap = @@ -292,7 +292,7 @@ public class CameraDevice implements android.hardware.camera2.CameraDevice { } @Override - public void setDeviceListener(CameraDeviceListener listener, Handler handler) { + public void setDeviceListener(StateListener listener, Handler handler) { synchronized (mLock) { mDeviceListener = listener; mDeviceHandler = handler; @@ -314,7 +314,7 @@ public class CameraDevice implements android.hardware.camera2.CameraDevice { } @Override - public void close() throws Exception { + public void close() { // TODO: every method should throw IllegalStateException after close has been called @@ -325,7 +325,7 @@ public class CameraDevice implements android.hardware.camera2.CameraDevice { mRemoteDevice.disconnect(); } } catch (CameraRuntimeException e) { - throw e.asChecked(); + Log.e(TAG, "Exception while closing: ", e.asChecked()); } catch (RemoteException e) { // impossible } @@ -339,8 +339,6 @@ public class CameraDevice implements android.hardware.camera2.CameraDevice { protected void finalize() throws Throwable { try { close(); - } catch (CameraRuntimeException e) { - Log.e(TAG, "Got error while trying to finalize, ignoring: " + e.getMessage()); } finally { super.finalize(); |