Loading api/current.txt +16 −0 Original line number Diff line number Diff line Loading @@ -15488,6 +15488,7 @@ package android.hardware.camera2 { method public <T> T get(android.hardware.camera2.CameraCharacteristics.Key<T>); method public java.util.List<android.hardware.camera2.CaptureRequest.Key<?>> getAvailableCaptureRequestKeys(); method public java.util.List<android.hardware.camera2.CaptureResult.Key<?>> getAvailableCaptureResultKeys(); method public java.util.List<android.hardware.camera2.CaptureRequest.Key<?>> getAvailableSessionKeys(); method public java.util.List<android.hardware.camera2.CameraCharacteristics.Key<?>> getKeys(); field public static final android.hardware.camera2.CameraCharacteristics.Key<int[]> COLOR_CORRECTION_AVAILABLE_ABERRATION_MODES; field public static final android.hardware.camera2.CameraCharacteristics.Key<int[]> CONTROL_AE_AVAILABLE_ANTIBANDING_MODES; Loading Loading @@ -15586,6 +15587,7 @@ package android.hardware.camera2 { method public abstract void close(); method public abstract android.hardware.camera2.CaptureRequest.Builder createCaptureRequest(int) throws android.hardware.camera2.CameraAccessException; method public abstract void createCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public void createCaptureSession(android.hardware.camera2.params.SessionConfiguration) throws android.hardware.camera2.CameraAccessException; method public abstract void createCaptureSessionByOutputConfigurations(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public abstract void createConstrainedHighSpeedCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public abstract android.hardware.camera2.CaptureRequest.Builder createReprocessCaptureRequest(android.hardware.camera2.TotalCaptureResult) throws android.hardware.camera2.CameraAccessException; Loading Loading @@ -16129,6 +16131,20 @@ package android.hardware.camera2.params { field public static final int RED = 0; // 0x0 } public final class SessionConfiguration { ctor public SessionConfiguration(int, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler); method public android.os.Handler getHandler(); method public android.hardware.camera2.params.InputConfiguration getInputConfiguration(); method public java.util.List<android.hardware.camera2.params.OutputConfiguration> getOutputConfigurations(); method public android.hardware.camera2.CaptureRequest getSessionParameters(); method public int getSessionType(); method public android.hardware.camera2.CameraCaptureSession.StateCallback getStateCallback(); method public void setInputConfiguration(android.hardware.camera2.params.InputConfiguration); method public void setSessionParameters(android.hardware.camera2.CaptureRequest); field public static final int SESSION_HIGH_SPEED = 1; // 0x1 field public static final int SESSION_REGULAR = 0; // 0x0 } public final class StreamConfigurationMap { method public android.util.Size[] getHighResolutionOutputSizes(int); method public android.util.Range<java.lang.Integer>[] getHighSpeedVideoFpsRanges(); core/java/android/hardware/camera2/CameraCharacteristics.java +105 −0 Original line number Diff line number Diff line Loading @@ -21,6 +21,7 @@ import android.annotation.Nullable; import android.hardware.camera2.impl.CameraMetadataNative; import android.hardware.camera2.impl.PublicKey; import android.hardware.camera2.impl.SyntheticKey; import android.hardware.camera2.params.SessionConfiguration; import android.hardware.camera2.utils.TypeReference; import android.util.Rational; Loading Loading @@ -169,6 +170,7 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri private final CameraMetadataNative mProperties; private List<CameraCharacteristics.Key<?>> mKeys; private List<CaptureRequest.Key<?>> mAvailableRequestKeys; private List<CaptureRequest.Key<?>> mAvailableSessionKeys; private List<CaptureResult.Key<?>> mAvailableResultKeys; /** Loading Loading @@ -250,6 +252,67 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri return mKeys; } /** * <p>Returns a subset of {@link #getAvailableCaptureRequestKeys} keys that the * camera device can pass as part of the capture session initialization.</p> * * <p>This list includes keys that are difficult to apply per-frame and * can result in unexpected delays when modified during the capture session * lifetime. Typical examples include parameters that require a * time-consuming hardware re-configuration or internal camera pipeline * change. For performance reasons we suggest clients to pass their initial * values as part of {@link SessionConfiguration#setSessionParameters}. Once * the camera capture session is enabled it is also recommended to avoid * changing them from their initial values set in * {@link SessionConfiguration#setSessionParameters }. * Control over session parameters can still be exerted in capture requests * but clients should be aware and expect delays during their application. * An example usage scenario could look like this:</p> * <ul> * <li>The camera client starts by quering the session parameter key list via * {@link android.hardware.camera2.CameraCharacteristics#getAvailableSessionKeys }.</li> * <li>Before triggering the capture session create sequence, a capture request * must be built via {@link CameraDevice#createCaptureRequest } using an * appropriate template matching the particular use case.</li> * <li>The client should go over the list of session parameters and check * whether some of the keys listed matches with the parameters that * they intend to modify as part of the first capture request.</li> * <li>If there is no such match, the capture request can be passed * unmodified to {@link SessionConfiguration#setSessionParameters }.</li> * <li>If matches do exist, the client should update the respective values * and pass the request to {@link SessionConfiguration#setSessionParameters }.</li> * <li>After the capture session initialization completes the session parameter * key list can continue to serve as reference when posting or updating * further requests. As mentioned above further changes to session * parameters should ideally be avoided, if updates are necessary * however clients could expect a delay/glitch during the * parameter switch.</li> * </ul> * * <p>The list returned is not modifiable, so any attempts to modify it will throw * a {@code UnsupportedOperationException}.</p> * * <p>Each key is only listed once in the list. The order of the keys is undefined.</p> * * @return List of keys that can be passed during capture session initialization. In case the * camera device doesn't support such keys the list can be null. */ @SuppressWarnings({"unchecked"}) public List<CaptureRequest.Key<?>> getAvailableSessionKeys() { if (mAvailableSessionKeys == null) { Object crKey = CaptureRequest.Key.class; Class<CaptureRequest.Key<?>> crKeyTyped = (Class<CaptureRequest.Key<?>>)crKey; int[] filterTags = get(REQUEST_AVAILABLE_SESSION_KEYS); if (filterTags == null) { return null; } mAvailableSessionKeys = getAvailableKeyList(CaptureRequest.class, crKeyTyped, filterTags); } return mAvailableSessionKeys; } /** * Returns the list of keys supported by this {@link CameraDevice} for querying * with a {@link CaptureRequest}. Loading Loading @@ -1570,6 +1633,48 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri public static final Key<int[]> REQUEST_AVAILABLE_CHARACTERISTICS_KEYS = new Key<int[]>("android.request.availableCharacteristicsKeys", int[].class); /** * <p>A subset of the available request keys that the camera device * can pass as part of the capture session initialization.</p> * <p>This is a subset of android.request.availableRequestKeys which * contains a list of keys that are difficult to apply per-frame and * can result in unexpected delays when modified during the capture session * lifetime. Typical examples include parameters that require a * time-consuming hardware re-configuration or internal camera pipeline * change. For performance reasons we advise clients to pass their initial * values as part of {@link SessionConfiguration#setSessionParameters }. Once * the camera capture session is enabled it is also recommended to avoid * changing them from their initial values set in * {@link SessionConfiguration#setSessionParameters }. * Control over session parameters can still be exerted in capture requests * but clients should be aware and expect delays during their application. * An example usage scenario could look like this:</p> * <ul> * <li>The camera client starts by quering the session parameter key list via * {@link android.hardware.camera2.CameraCharacteristics#getAvailableSessionKeys }.</li> * <li>Before triggering the capture session create sequence, a capture request * must be built via {@link CameraDevice#createCaptureRequest } using an * appropriate template matching the particular use case.</li> * <li>The client should go over the list of session parameters and check * whether some of the keys listed matches with the parameters that * they intend to modify as part of the first capture request.</li> * <li>If there is no such match, the capture request can be passed * unmodified to {@link SessionConfiguration#setSessionParameters }.</li> * <li>If matches do exist, the client should update the respective values * and pass the request to {@link SessionConfiguration#setSessionParameters }.</li> * <li>After the capture session initialization completes the session parameter * key list can continue to serve as reference when posting or updating * further requests. As mentioned above further changes to session * parameters should ideally be avoided, if updates are necessary * however clients could expect a delay/glitch during the * parameter switch.</li> * </ul> * <p>This key is available on all devices.</p> * @hide */ public static final Key<int[]> REQUEST_AVAILABLE_SESSION_KEYS = new Key<int[]>("android.request.availableSessionKeys", int[].class); /** * <p>The list of image formats that are supported by this * camera device for output streams.</p> Loading core/java/android/hardware/camera2/CameraDevice.java +21 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ import static android.hardware.camera2.ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_ import android.hardware.camera2.params.InputConfiguration; import android.hardware.camera2.params.StreamConfigurationMap; import android.hardware.camera2.params.OutputConfiguration; import android.hardware.camera2.params.SessionConfiguration; import android.os.Handler; import android.view.Surface; Loading Loading @@ -810,6 +811,26 @@ public abstract class CameraDevice implements AutoCloseable { @Nullable Handler handler) throws CameraAccessException; /** * <p>Create a new {@link CameraCaptureSession} using a {@link SessionConfiguration} helper * object that aggregates all supported parameters.</p> * * @param config A session configuration (see {@link SessionConfiguration}). * * @throws IllegalArgumentException In case the session configuration is invalid; or the output * configurations are empty. * @throws CameraAccessException In case the camera device is no longer connected or has * encountered a fatal error. * @see #createCaptureSession(List, CameraCaptureSession.StateCallback, Handler) * @see #createCaptureSessionByOutputConfigurations * @see #createReprocessableCaptureSession * @see #createConstrainedHighSpeedCaptureSession */ public void createCaptureSession( SessionConfiguration config) throws CameraAccessException { throw new UnsupportedOperationException("No default implementation"); } /** * <p>Create a {@link CaptureRequest.Builder} for new capture requests, * initialized with template for a target use case. The settings are chosen Loading core/java/android/hardware/camera2/impl/CameraCaptureSessionImpl.java +2 −1 Original line number Diff line number Diff line Loading @@ -800,7 +800,8 @@ public class CameraCaptureSessionImpl extends CameraCaptureSession try { // begin transition to unconfigured mDeviceImpl.configureStreamsChecked(/*inputConfig*/null, /*outputs*/null, /*operatingMode*/ ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } catch (CameraAccessException e) { // OK: do not throw checked exceptions. Log.e(TAG, mIdString + "Exception while unconfiguring outputs: ", e); Loading core/java/android/hardware/camera2/impl/CameraDeviceImpl.java +44 −15 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ import android.hardware.camera2.TotalCaptureResult; import android.hardware.camera2.params.InputConfiguration; import android.hardware.camera2.params.OutputConfiguration; import android.hardware.camera2.params.ReprocessFormatsMap; import android.hardware.camera2.params.SessionConfiguration; import android.hardware.camera2.params.StreamConfigurationMap; import android.hardware.camera2.utils.SubmitInfo; import android.hardware.camera2.utils.SurfaceUtils; Loading Loading @@ -362,7 +363,7 @@ public class CameraDeviceImpl extends CameraDevice outputConfigs.add(new OutputConfiguration(s)); } configureStreamsChecked(/*inputConfig*/null, outputConfigs, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } Loading @@ -382,12 +383,13 @@ public class CameraDeviceImpl extends CameraDevice * @param outputs a list of one or more surfaces, or {@code null} to unconfigure * @param operatingMode If the stream configuration is for a normal session, * a constrained high speed session, or something else. * @param sessionParams Session parameters. * @return whether or not the configuration was successful * * @throws CameraAccessException if there were any unexpected problems during configuration */ public boolean configureStreamsChecked(InputConfiguration inputConfig, List<OutputConfiguration> outputs, int operatingMode) List<OutputConfiguration> outputs, int operatingMode, CaptureRequest sessionParams) throws CameraAccessException { // Treat a null input the same an empty list if (outputs == null) { Loading Loading @@ -463,7 +465,11 @@ public class CameraDeviceImpl extends CameraDevice } } mRemoteDevice.endConfigure(operatingMode); if (sessionParams != null) { mRemoteDevice.endConfigure(operatingMode, sessionParams.getNativeCopy()); } else { mRemoteDevice.endConfigure(operatingMode, null); } success = true; } catch (IllegalArgumentException e) { Loading Loading @@ -499,7 +505,7 @@ public class CameraDeviceImpl extends CameraDevice outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(null, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading @@ -515,7 +521,7 @@ public class CameraDeviceImpl extends CameraDevice List<OutputConfiguration> currentOutputs = new ArrayList<>(outputConfigurations); createCaptureSessionInternal(null, currentOutputs, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/null); } @Override Loading @@ -535,7 +541,7 @@ public class CameraDeviceImpl extends CameraDevice outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(inputConfig, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading Loading @@ -563,7 +569,8 @@ public class CameraDeviceImpl extends CameraDevice currentOutputs.add(new OutputConfiguration(output)); } createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading @@ -574,16 +581,13 @@ public class CameraDeviceImpl extends CameraDevice throw new IllegalArgumentException( "Output surface list must not be null and the size must be no more than 2"); } StreamConfigurationMap config = getCharacteristics().get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP); SurfaceUtils.checkConstrainedHighSpeedSurfaces(outputs, /*fpsRange*/null, config); List<OutputConfiguration> outConfigurations = new ArrayList<>(outputs.size()); for (Surface surface : outputs) { outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(null, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_MODE); /*operatingMode*/ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_MODE, /*sessionParams*/ null); } @Override Loading @@ -596,13 +600,30 @@ public class CameraDeviceImpl extends CameraDevice for (OutputConfiguration output : outputs) { currentOutputs.add(new OutputConfiguration(output)); } createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, operatingMode); createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, operatingMode, /*sessionParams*/ null); } @Override public void createCaptureSession(SessionConfiguration config) throws CameraAccessException { if (config == null) { throw new IllegalArgumentException("Invalid session configuration"); } List<OutputConfiguration> outputConfigs = config.getOutputConfigurations(); if (outputConfigs == null) { throw new IllegalArgumentException("Invalid output configurations"); } createCaptureSessionInternal(config.getInputConfiguration(), outputConfigs, config.getStateCallback(), config.getHandler(), config.getSessionType(), config.getSessionParameters()); } private void createCaptureSessionInternal(InputConfiguration inputConfig, List<OutputConfiguration> outputConfigurations, CameraCaptureSession.StateCallback callback, Handler handler, int operatingMode) throws CameraAccessException { int operatingMode, CaptureRequest sessionParams) throws CameraAccessException { synchronized(mInterfaceLock) { if (DEBUG) { Log.d(TAG, "createCaptureSessionInternal"); Loading Loading @@ -630,7 +651,7 @@ public class CameraDeviceImpl extends CameraDevice try { // configure streams and then block until IDLE configureSuccess = configureStreamsChecked(inputConfig, outputConfigurations, operatingMode); operatingMode, sessionParams); if (configureSuccess == true && inputConfig != null) { input = mRemoteDevice.getInputSurface(); } Loading @@ -646,6 +667,14 @@ public class CameraDeviceImpl extends CameraDevice // Fire onConfigured if configureOutputs succeeded, fire onConfigureFailed otherwise. CameraCaptureSessionCore newSession = null; if (isConstrainedHighSpeed) { ArrayList<Surface> surfaces = new ArrayList<>(outputConfigurations.size()); for (OutputConfiguration outConfig : outputConfigurations) { surfaces.add(outConfig.getSurface()); } StreamConfigurationMap config = getCharacteristics().get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP); SurfaceUtils.checkConstrainedHighSpeedSurfaces(surfaces, /*fpsRange*/null, config); newSession = new CameraConstrainedHighSpeedCaptureSessionImpl(mNextSessionId++, callback, handler, this, mDeviceHandler, configureSuccess, mCharacteristics); Loading Loading
api/current.txt +16 −0 Original line number Diff line number Diff line Loading @@ -15488,6 +15488,7 @@ package android.hardware.camera2 { method public <T> T get(android.hardware.camera2.CameraCharacteristics.Key<T>); method public java.util.List<android.hardware.camera2.CaptureRequest.Key<?>> getAvailableCaptureRequestKeys(); method public java.util.List<android.hardware.camera2.CaptureResult.Key<?>> getAvailableCaptureResultKeys(); method public java.util.List<android.hardware.camera2.CaptureRequest.Key<?>> getAvailableSessionKeys(); method public java.util.List<android.hardware.camera2.CameraCharacteristics.Key<?>> getKeys(); field public static final android.hardware.camera2.CameraCharacteristics.Key<int[]> COLOR_CORRECTION_AVAILABLE_ABERRATION_MODES; field public static final android.hardware.camera2.CameraCharacteristics.Key<int[]> CONTROL_AE_AVAILABLE_ANTIBANDING_MODES; Loading Loading @@ -15586,6 +15587,7 @@ package android.hardware.camera2 { method public abstract void close(); method public abstract android.hardware.camera2.CaptureRequest.Builder createCaptureRequest(int) throws android.hardware.camera2.CameraAccessException; method public abstract void createCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public void createCaptureSession(android.hardware.camera2.params.SessionConfiguration) throws android.hardware.camera2.CameraAccessException; method public abstract void createCaptureSessionByOutputConfigurations(java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public abstract void createConstrainedHighSpeedCaptureSession(java.util.List<android.view.Surface>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler) throws android.hardware.camera2.CameraAccessException; method public abstract android.hardware.camera2.CaptureRequest.Builder createReprocessCaptureRequest(android.hardware.camera2.TotalCaptureResult) throws android.hardware.camera2.CameraAccessException; Loading Loading @@ -16129,6 +16131,20 @@ package android.hardware.camera2.params { field public static final int RED = 0; // 0x0 } public final class SessionConfiguration { ctor public SessionConfiguration(int, java.util.List<android.hardware.camera2.params.OutputConfiguration>, android.hardware.camera2.CameraCaptureSession.StateCallback, android.os.Handler); method public android.os.Handler getHandler(); method public android.hardware.camera2.params.InputConfiguration getInputConfiguration(); method public java.util.List<android.hardware.camera2.params.OutputConfiguration> getOutputConfigurations(); method public android.hardware.camera2.CaptureRequest getSessionParameters(); method public int getSessionType(); method public android.hardware.camera2.CameraCaptureSession.StateCallback getStateCallback(); method public void setInputConfiguration(android.hardware.camera2.params.InputConfiguration); method public void setSessionParameters(android.hardware.camera2.CaptureRequest); field public static final int SESSION_HIGH_SPEED = 1; // 0x1 field public static final int SESSION_REGULAR = 0; // 0x0 } public final class StreamConfigurationMap { method public android.util.Size[] getHighResolutionOutputSizes(int); method public android.util.Range<java.lang.Integer>[] getHighSpeedVideoFpsRanges();
core/java/android/hardware/camera2/CameraCharacteristics.java +105 −0 Original line number Diff line number Diff line Loading @@ -21,6 +21,7 @@ import android.annotation.Nullable; import android.hardware.camera2.impl.CameraMetadataNative; import android.hardware.camera2.impl.PublicKey; import android.hardware.camera2.impl.SyntheticKey; import android.hardware.camera2.params.SessionConfiguration; import android.hardware.camera2.utils.TypeReference; import android.util.Rational; Loading Loading @@ -169,6 +170,7 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri private final CameraMetadataNative mProperties; private List<CameraCharacteristics.Key<?>> mKeys; private List<CaptureRequest.Key<?>> mAvailableRequestKeys; private List<CaptureRequest.Key<?>> mAvailableSessionKeys; private List<CaptureResult.Key<?>> mAvailableResultKeys; /** Loading Loading @@ -250,6 +252,67 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri return mKeys; } /** * <p>Returns a subset of {@link #getAvailableCaptureRequestKeys} keys that the * camera device can pass as part of the capture session initialization.</p> * * <p>This list includes keys that are difficult to apply per-frame and * can result in unexpected delays when modified during the capture session * lifetime. Typical examples include parameters that require a * time-consuming hardware re-configuration or internal camera pipeline * change. For performance reasons we suggest clients to pass their initial * values as part of {@link SessionConfiguration#setSessionParameters}. Once * the camera capture session is enabled it is also recommended to avoid * changing them from their initial values set in * {@link SessionConfiguration#setSessionParameters }. * Control over session parameters can still be exerted in capture requests * but clients should be aware and expect delays during their application. * An example usage scenario could look like this:</p> * <ul> * <li>The camera client starts by quering the session parameter key list via * {@link android.hardware.camera2.CameraCharacteristics#getAvailableSessionKeys }.</li> * <li>Before triggering the capture session create sequence, a capture request * must be built via {@link CameraDevice#createCaptureRequest } using an * appropriate template matching the particular use case.</li> * <li>The client should go over the list of session parameters and check * whether some of the keys listed matches with the parameters that * they intend to modify as part of the first capture request.</li> * <li>If there is no such match, the capture request can be passed * unmodified to {@link SessionConfiguration#setSessionParameters }.</li> * <li>If matches do exist, the client should update the respective values * and pass the request to {@link SessionConfiguration#setSessionParameters }.</li> * <li>After the capture session initialization completes the session parameter * key list can continue to serve as reference when posting or updating * further requests. As mentioned above further changes to session * parameters should ideally be avoided, if updates are necessary * however clients could expect a delay/glitch during the * parameter switch.</li> * </ul> * * <p>The list returned is not modifiable, so any attempts to modify it will throw * a {@code UnsupportedOperationException}.</p> * * <p>Each key is only listed once in the list. The order of the keys is undefined.</p> * * @return List of keys that can be passed during capture session initialization. In case the * camera device doesn't support such keys the list can be null. */ @SuppressWarnings({"unchecked"}) public List<CaptureRequest.Key<?>> getAvailableSessionKeys() { if (mAvailableSessionKeys == null) { Object crKey = CaptureRequest.Key.class; Class<CaptureRequest.Key<?>> crKeyTyped = (Class<CaptureRequest.Key<?>>)crKey; int[] filterTags = get(REQUEST_AVAILABLE_SESSION_KEYS); if (filterTags == null) { return null; } mAvailableSessionKeys = getAvailableKeyList(CaptureRequest.class, crKeyTyped, filterTags); } return mAvailableSessionKeys; } /** * Returns the list of keys supported by this {@link CameraDevice} for querying * with a {@link CaptureRequest}. Loading Loading @@ -1570,6 +1633,48 @@ public final class CameraCharacteristics extends CameraMetadata<CameraCharacteri public static final Key<int[]> REQUEST_AVAILABLE_CHARACTERISTICS_KEYS = new Key<int[]>("android.request.availableCharacteristicsKeys", int[].class); /** * <p>A subset of the available request keys that the camera device * can pass as part of the capture session initialization.</p> * <p>This is a subset of android.request.availableRequestKeys which * contains a list of keys that are difficult to apply per-frame and * can result in unexpected delays when modified during the capture session * lifetime. Typical examples include parameters that require a * time-consuming hardware re-configuration or internal camera pipeline * change. For performance reasons we advise clients to pass their initial * values as part of {@link SessionConfiguration#setSessionParameters }. Once * the camera capture session is enabled it is also recommended to avoid * changing them from their initial values set in * {@link SessionConfiguration#setSessionParameters }. * Control over session parameters can still be exerted in capture requests * but clients should be aware and expect delays during their application. * An example usage scenario could look like this:</p> * <ul> * <li>The camera client starts by quering the session parameter key list via * {@link android.hardware.camera2.CameraCharacteristics#getAvailableSessionKeys }.</li> * <li>Before triggering the capture session create sequence, a capture request * must be built via {@link CameraDevice#createCaptureRequest } using an * appropriate template matching the particular use case.</li> * <li>The client should go over the list of session parameters and check * whether some of the keys listed matches with the parameters that * they intend to modify as part of the first capture request.</li> * <li>If there is no such match, the capture request can be passed * unmodified to {@link SessionConfiguration#setSessionParameters }.</li> * <li>If matches do exist, the client should update the respective values * and pass the request to {@link SessionConfiguration#setSessionParameters }.</li> * <li>After the capture session initialization completes the session parameter * key list can continue to serve as reference when posting or updating * further requests. As mentioned above further changes to session * parameters should ideally be avoided, if updates are necessary * however clients could expect a delay/glitch during the * parameter switch.</li> * </ul> * <p>This key is available on all devices.</p> * @hide */ public static final Key<int[]> REQUEST_AVAILABLE_SESSION_KEYS = new Key<int[]>("android.request.availableSessionKeys", int[].class); /** * <p>The list of image formats that are supported by this * camera device for output streams.</p> Loading
core/java/android/hardware/camera2/CameraDevice.java +21 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ import static android.hardware.camera2.ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_ import android.hardware.camera2.params.InputConfiguration; import android.hardware.camera2.params.StreamConfigurationMap; import android.hardware.camera2.params.OutputConfiguration; import android.hardware.camera2.params.SessionConfiguration; import android.os.Handler; import android.view.Surface; Loading Loading @@ -810,6 +811,26 @@ public abstract class CameraDevice implements AutoCloseable { @Nullable Handler handler) throws CameraAccessException; /** * <p>Create a new {@link CameraCaptureSession} using a {@link SessionConfiguration} helper * object that aggregates all supported parameters.</p> * * @param config A session configuration (see {@link SessionConfiguration}). * * @throws IllegalArgumentException In case the session configuration is invalid; or the output * configurations are empty. * @throws CameraAccessException In case the camera device is no longer connected or has * encountered a fatal error. * @see #createCaptureSession(List, CameraCaptureSession.StateCallback, Handler) * @see #createCaptureSessionByOutputConfigurations * @see #createReprocessableCaptureSession * @see #createConstrainedHighSpeedCaptureSession */ public void createCaptureSession( SessionConfiguration config) throws CameraAccessException { throw new UnsupportedOperationException("No default implementation"); } /** * <p>Create a {@link CaptureRequest.Builder} for new capture requests, * initialized with template for a target use case. The settings are chosen Loading
core/java/android/hardware/camera2/impl/CameraCaptureSessionImpl.java +2 −1 Original line number Diff line number Diff line Loading @@ -800,7 +800,8 @@ public class CameraCaptureSessionImpl extends CameraCaptureSession try { // begin transition to unconfigured mDeviceImpl.configureStreamsChecked(/*inputConfig*/null, /*outputs*/null, /*operatingMode*/ ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } catch (CameraAccessException e) { // OK: do not throw checked exceptions. Log.e(TAG, mIdString + "Exception while unconfiguring outputs: ", e); Loading
core/java/android/hardware/camera2/impl/CameraDeviceImpl.java +44 −15 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ import android.hardware.camera2.TotalCaptureResult; import android.hardware.camera2.params.InputConfiguration; import android.hardware.camera2.params.OutputConfiguration; import android.hardware.camera2.params.ReprocessFormatsMap; import android.hardware.camera2.params.SessionConfiguration; import android.hardware.camera2.params.StreamConfigurationMap; import android.hardware.camera2.utils.SubmitInfo; import android.hardware.camera2.utils.SurfaceUtils; Loading Loading @@ -362,7 +363,7 @@ public class CameraDeviceImpl extends CameraDevice outputConfigs.add(new OutputConfiguration(s)); } configureStreamsChecked(/*inputConfig*/null, outputConfigs, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } Loading @@ -382,12 +383,13 @@ public class CameraDeviceImpl extends CameraDevice * @param outputs a list of one or more surfaces, or {@code null} to unconfigure * @param operatingMode If the stream configuration is for a normal session, * a constrained high speed session, or something else. * @param sessionParams Session parameters. * @return whether or not the configuration was successful * * @throws CameraAccessException if there were any unexpected problems during configuration */ public boolean configureStreamsChecked(InputConfiguration inputConfig, List<OutputConfiguration> outputs, int operatingMode) List<OutputConfiguration> outputs, int operatingMode, CaptureRequest sessionParams) throws CameraAccessException { // Treat a null input the same an empty list if (outputs == null) { Loading Loading @@ -463,7 +465,11 @@ public class CameraDeviceImpl extends CameraDevice } } mRemoteDevice.endConfigure(operatingMode); if (sessionParams != null) { mRemoteDevice.endConfigure(operatingMode, sessionParams.getNativeCopy()); } else { mRemoteDevice.endConfigure(operatingMode, null); } success = true; } catch (IllegalArgumentException e) { Loading Loading @@ -499,7 +505,7 @@ public class CameraDeviceImpl extends CameraDevice outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(null, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading @@ -515,7 +521,7 @@ public class CameraDeviceImpl extends CameraDevice List<OutputConfiguration> currentOutputs = new ArrayList<>(outputConfigurations); createCaptureSessionInternal(null, currentOutputs, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/null); } @Override Loading @@ -535,7 +541,7 @@ public class CameraDeviceImpl extends CameraDevice outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(inputConfig, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading Loading @@ -563,7 +569,8 @@ public class CameraDeviceImpl extends CameraDevice currentOutputs.add(new OutputConfiguration(output)); } createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE); callback, handler, /*operatingMode*/ICameraDeviceUser.NORMAL_MODE, /*sessionParams*/ null); } @Override Loading @@ -574,16 +581,13 @@ public class CameraDeviceImpl extends CameraDevice throw new IllegalArgumentException( "Output surface list must not be null and the size must be no more than 2"); } StreamConfigurationMap config = getCharacteristics().get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP); SurfaceUtils.checkConstrainedHighSpeedSurfaces(outputs, /*fpsRange*/null, config); List<OutputConfiguration> outConfigurations = new ArrayList<>(outputs.size()); for (Surface surface : outputs) { outConfigurations.add(new OutputConfiguration(surface)); } createCaptureSessionInternal(null, outConfigurations, callback, handler, /*operatingMode*/ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_MODE); /*operatingMode*/ICameraDeviceUser.CONSTRAINED_HIGH_SPEED_MODE, /*sessionParams*/ null); } @Override Loading @@ -596,13 +600,30 @@ public class CameraDeviceImpl extends CameraDevice for (OutputConfiguration output : outputs) { currentOutputs.add(new OutputConfiguration(output)); } createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, operatingMode); createCaptureSessionInternal(inputConfig, currentOutputs, callback, handler, operatingMode, /*sessionParams*/ null); } @Override public void createCaptureSession(SessionConfiguration config) throws CameraAccessException { if (config == null) { throw new IllegalArgumentException("Invalid session configuration"); } List<OutputConfiguration> outputConfigs = config.getOutputConfigurations(); if (outputConfigs == null) { throw new IllegalArgumentException("Invalid output configurations"); } createCaptureSessionInternal(config.getInputConfiguration(), outputConfigs, config.getStateCallback(), config.getHandler(), config.getSessionType(), config.getSessionParameters()); } private void createCaptureSessionInternal(InputConfiguration inputConfig, List<OutputConfiguration> outputConfigurations, CameraCaptureSession.StateCallback callback, Handler handler, int operatingMode) throws CameraAccessException { int operatingMode, CaptureRequest sessionParams) throws CameraAccessException { synchronized(mInterfaceLock) { if (DEBUG) { Log.d(TAG, "createCaptureSessionInternal"); Loading Loading @@ -630,7 +651,7 @@ public class CameraDeviceImpl extends CameraDevice try { // configure streams and then block until IDLE configureSuccess = configureStreamsChecked(inputConfig, outputConfigurations, operatingMode); operatingMode, sessionParams); if (configureSuccess == true && inputConfig != null) { input = mRemoteDevice.getInputSurface(); } Loading @@ -646,6 +667,14 @@ public class CameraDeviceImpl extends CameraDevice // Fire onConfigured if configureOutputs succeeded, fire onConfigureFailed otherwise. CameraCaptureSessionCore newSession = null; if (isConstrainedHighSpeed) { ArrayList<Surface> surfaces = new ArrayList<>(outputConfigurations.size()); for (OutputConfiguration outConfig : outputConfigurations) { surfaces.add(outConfig.getSurface()); } StreamConfigurationMap config = getCharacteristics().get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP); SurfaceUtils.checkConstrainedHighSpeedSurfaces(surfaces, /*fpsRange*/null, config); newSession = new CameraConstrainedHighSpeedCaptureSessionImpl(mNextSessionId++, callback, handler, this, mDeviceHandler, configureSuccess, mCharacteristics); Loading