You need to initialize TextureView
before opening a camera.
TextureView
is for displaying the image from camera on the device.
However, you cannot use it unless the texture is ready, either because the screen is currently off or it is initializing.
You should check mTextureView.isAvailable()
before opening your camera. Else you will mTextureView.setSurfaceTextureListener()
.
And open your camera in the callback method onSurfaceTextureListener
.
Before opening your camera you should check for a camera permission first.
Next, you initialize a cameraManager through
CameraManager manager = (CameraManager) activity.getSystemService(Context.CAMERA_SERVICE);
This manager is our hero.
- It knows metadata of your camera devices.
- It can initialize camera.
manager.getCameraIdList();
Usually, it will return 0 and 1.
- 0 means it is your back camera.
- 1 for your front camera.
CameraCharacteristics characteristics = manager.getCameraCharacteristics(cameraId);
Available characteristics including:
CameraCharacteristics.Key(android.colorCorrection.availableAberrationModes)
CameraCharacteristics.Key(android.control.aeAvailableAntibandingModes)
CameraCharacteristics.Key(android.control.aeAvailableModes)
CameraCharacteristics.Key(android.control.aeAvailableTargetFpsRanges)
CameraCharacteristics.Key(android.control.aeCompensationRange)
CameraCharacteristics.Key(android.control.aeCompensationStep)
CameraCharacteristics.Key(android.control.aeLockAvailable)
CameraCharacteristics.Key(android.control.afAvailableModes)
CameraCharacteristics.Key(android.control.availableEffects)
CameraCharacteristics.Key(android.control.availableModes)
CameraCharacteristics.Key(android.control.availableSceneModes)
CameraCharacteristics.Key(android.control.availableVideoStabilizationModes)
CameraCharacteristics.Key(android.control.awbAvailableModes)
CameraCharacteristics.Key(android.control.awbLockAvailable)
CameraCharacteristics.Key(android.control.maxRegionsAe)
CameraCharacteristics.Key(android.control.maxRegionsAf)
CameraCharacteristics.Key(android.control.maxRegionsAwb)
CameraCharacteristics.Key(android.flash.info.available)
CameraCharacteristics.Key(android.info.supportedHardwareLevel)
CameraCharacteristics.Key(android.jpeg.availableThumbnailSizes)
CameraCharacteristics.Key(android.lens.facing)
CameraCharacteristics.Key(android.lens.info.availableFocalLengths)
CameraCharacteristics.Key(android.noiseReduction.availableNoiseReductionModes)
CameraCharacteristics.Key(android.request.availableCapabilities)
CameraCharacteristics.Key(android.request.maxNumOutputProc)
CameraCharacteristics.Key(android.request.maxNumOutputProcStalling)
CameraCharacteristics.Key(android.request.maxNumOutputRaw)
CameraCharacteristics.Key(android.request.partialResultCount)
CameraCharacteristics.Key(android.request.pipelineMaxDepth)
CameraCharacteristics.Key(android.scaler.availableMaxDigitalZoom)
CameraCharacteristics.Key(android.scaler.croppingType)
CameraCharacteristics.Key(android.scaler.streamConfigurationMap)
CameraCharacteristics.Key(android.sensor.availableTestPatternModes)
CameraCharacteristics.Key(android.sensor.info.activeArraySize)
CameraCharacteristics.Key(android.sensor.info.physicalSize)
CameraCharacteristics.Key(android.sensor.info.pixelArraySize)
CameraCharacteristics.Key(android.sensor.info.timestampSource)
CameraCharacteristics.Key(android.sensor.orientation)
CameraCharacteristics.Key(android.statistics.info.availableFaceDetectModes)
CameraCharacteristics.Key(android.statistics.info.maxFaceCount)
CameraCharacteristics.Key(android.sync.maxLatency)
you can get this key list from
characteristics.getKeys();
characteristics.get(CameraCharacteristics.INFO_SUPPORTED_HARDWARE_LEVEL)
You can check it by comparing with built-in integer. e.g.,
characteristics.get(CameraCharacteristics.INFO_SUPPORTED_HARDWARE_LEVEL) == CameraCharacteristics.INFO_SUPPORTED_HARDWARE_LEVEL_FULL
From my observation, Pixel Phone 2016 is CameraCharacteristics.INFO_SUPPORTED_HARDWARE_LEVEL_3
.
My OnePlus One is CameraCharacteristics.INFO_SUPPORTED_HARDWARE_LEVEL_LEGACY
.
Various hardware supports allow different capabilities.
- LEGACY devices operate in a backwards-compatibility mode for older Android devices, and have very limited capabilities.
- LIMITED devices represent the baseline feature set, and may also include additional capabilities that are subsets of FULL.
- FULL devices additionally support per-frame manual control of sensor, flash, lens and post-processing settings, and image capture at a high rate.
- LEVEL_3 devices additionally support YUV reprocessing and RAW image capture, along with additional output stream configurations.
StreamConfigurationMap map = characteristics.get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP);
StreamConfiguration(
Outputs(
[w: 4160, h: 3120, format: JPEG(256), min_duration: 0, stall: 1121523200],
[w: 4160, h: 2340, format: JPEG(256), min_duration: 0, stall: 891142400],
[w: 4000, h: 3000, format: JPEG(256), min_duration: 0, stall: 1052000000],
[w: 4096, h: 2160, format: JPEG(256), min_duration: 0, stall: 828162560],
[w: 3200, h: 2400, format: JPEG(256), min_duration: 0, stall: 745280000],
[w: 3200, h: 1800, format: JPEG(256), min_duration: 0, stall: 608960000],
[w: 2592, h: 1944, format: JPEG(256), min_duration: 0, stall: 557758208],
[w: 2048, h: 1536, format: JPEG(256), min_duration: 0, stall: 423346688],
[w: 1920, h: 1080, format: JPEG(256), min_duration: 0, stall: 347225600],
[w: 1600, h: 1200, format: JPEG(256), min_duration: 0, stall: 336320000],
[w: 1280, h: 768, format: JPEG(256), min_duration: 0, stall: 269795840],
[w: 1280, h: 720, format: JPEG(256), min_duration: 0, stall: 265433600],
[w: 1024, h: 768, format: JPEG(256), min_duration: 0, stall: 255836672],
[w: 800, h: 600, format: JPEG(256), min_duration: 0, stall: 234080000],
[w: 800, h: 480, format: JPEG(256), min_duration: 0, stall: 227264000],
[w: 720, h: 480, format: JPEG(256), min_duration: 0, stall: 224537600],
[w: 640, h: 480, format: JPEG(256), min_duration: 0, stall: 221811200],
[w: 320, h: 240, format: JPEG(256), min_duration: 0, stall: 205452800],
[w: 1440, h: 1080, format: PRIVATE(34), min_duration: 0, stall: 0],
[w: 1280, h: 720, format: PRIVATE(34), min_duration: 0, stall: 0],
[w: 720, h: 480, format: PRIVATE(34), min_duration: 0, stall: 0],
[w: 640, h: 480, format: PRIVATE(34), min_duration: 0, stall: 0],
[w: 320, h: 240, format: PRIVATE(34), min_duration: 0, stall: 0],
[w: 1440, h: 1080, format: YUV_420_888(35), min_duration: 0, stall: 0],
[w: 1280, h: 720, format: YUV_420_888(35), min_duration: 0, stall: 0],
[w: 720, h: 480, format: YUV_420_888(35), min_duration: 0, stall: 0],
[w: 640, h: 480, format: YUV_420_888(35), min_duration: 0, stall: 0],
[w: 320, h: 240, format: YUV_420_888(35), min_duration: 0, stall: 0],
[w: 1440, h: 1080, format: YV12(842094169), min_duration: 0, stall: 0],
[w: 1280, h: 720, format: YV12(842094169), min_duration: 0, stall: 0],
[w: 720, h: 480, format: YV12(842094169), min_duration: 0, stall: 0],
[w: 640, h: 480, format: YV12(842094169), min_duration: 0, stall: 0],
[w: 320, h: 240, format: YV12(842094169), min_duration: 0, stall: 0]),
HighResolutionOutputs(),
Inputs(),
ValidOutputFormatsForInput(),
HighSpeedVideoConfigurations()
)
When you rotate your screen, your camera angle will not automatically rotate the preview picture with you. You need to transform your picture accordingly, specifically image size, aspect ratio and angle.
Matrix
TheMatrix
class is the same as the Matrix(maths) that you may have a brief glance and forget it long ago.- This matrix will be applied with your picture/your bitmap/your area or in our case our
TextureView
. - With this you can change its aspect ratio, rotate image or move it.
- My assumption is that this 3x3 dimension gets to do matrix multiplication with each pixel on your picture.
- Each pixel will have a matrix of 1x3 dimension:
At the upper left most pixel of the picture. x=0, y=0. 1 is for its math purpose. Nothing comprehensible here. Check my source if you have doubt about the 1.
[0]
[0]
[1]
- This matrix is 3x3 dimension.
[1.0 0.0 0.0]
[0.0 1.0 0.0]
[0.0 0.0 1.0]
Which has an explanation as follows:
[MSCALE_X MSKEW_X MTRANS_X]
[MSKEW_Y MSCALE_Y MTRANS_Y]
[MPERSP_0 MPERSP_1 MPERSP_2]
- Scale X and Scale Y = How will you scale x-axis and y-axis. E.g., Write the 1.5 and you have your picture zoom in 150%
- Skew X and Skew Y = How will you rotate your picture. This one is some kind of trigonometry. We cannot make sense it in normal programmer language. Good news. We have a proxy method named
matrix.setRotation(angle);
. And the matrix will add this skew value for you. - __Translation X and Translation Y = How will you move your picture horizontally (X) or vertically (Y). E.g., After we rotate picture we should move our picture to the right so that it won't stay at the left side of the screen.
- Perspective 0, 1, 2 = This is for 3D Image. This is out of our scope here.
- First param is cameraId 0 for back and 1 for front camera
- Second is
CameraDevice.StateCallback
which contains callback ofCameraDevice
. onOpened()
onDisconnected()
andonError
- Third is
Handler
. This can be null. In this case we use it to handle photo saving.
manager.openCamera(mCameraId, mStateCallback, mBackgroundHandler);
After you open your camera, it won't open right away.
You have to handle it with its callback inside.
When the camera opened, we create a camerePreview which is rendered on TextureView
.
private final CameraDevice.StateCallback mStateCallback = new CameraDevice.StateCallback() {
@Override
public void onOpened(@NonNull CameraDevice cameraDevice) {
// This method is called when the camera is opened. We start camera preview here.
mCameraOpenCloseLock.release();
mCameraDevice = cameraDevice;
createCameraPreviewSession();
}
@Override
public void onDisconnected(@NonNull CameraDevice cameraDevice) {
mCameraOpenCloseLock.release();
cameraDevice.close();
mCameraDevice = null;
}
@Override
public void onError(@NonNull CameraDevice cameraDevice, int error) {
mCameraOpenCloseLock.release();
cameraDevice.close();
mCameraDevice = null;
Activity activity = getActivity();
if (null != activity) {
activity.finish();
}
}
};
````
### createCameraPreviewSession
Camera Preview won't be so simple, we can apply camera effect, adjust exposure and apply them to preview
To build those effects you need a `CaptureRequest` which is built by `CaptureRequest.Builder`
This is done inside CaptureSession.
####HARD LAZY TO STUDY MORE