Skip to main content

Handling camera picture

Once a picture has been taken, whether automatically by the Auto Snapping feature or manually by the user, you have to handle the image data by implementing the method abstract fun onPictureTaken(image: ByteArray, imageOrientation: Int) of the PictureCallback class. In this method you receive the image byte array of the original picture data and the image orientation value.

It is important to understand that this image data represents the original picture and not the cropped document image.

To get the cropped document image, you have to perform document contour detection on the original image and apply the cropping operation by using the ContourDetector class:

cameraView.addPictureCallback(object : PictureCallback() {   override fun onPictureTaken(image: ByteArray, captureInfo: CaptureInfo) {        fun restartCamera() {            // Continue with the camera preview to scan the next image:            cameraView.post {                cameraView.continuousFocus()                cameraView.startPreview()            }        }
        // Decode image byte array to Bitmap, and rotate according to orientation:        val imageProcessor: ImageProcessor = ScanbotSDK(context).imageProcessor()        val bitmap = imageProcessor.processJpeg(image, RotateOperation(captureInfo.imageOrientation))
        if (bitmap == null) {            // license or feature is not available            restartCamera()            return        }
        // Run document contour detection on original image:        val detector: ContourDetector = ScanbotSDK(context).createContourDetector()        detector.detect(bitmap)        val detectedPolygon = detector.polygonF        if (detectedPolygon != null) {            // And crop using detected polygon to get the final document image:            val documentImage = imageProcessor.processBitmap(bitmap, CropOperation(detectedPolygon))
            // Work with the final document image (store it as a file, etc)            // ...
            restartCamera()        }    }})

Handling the image orientation#

The value of the captureInfo.imageOrientation parameter requires a special handling on some Android devices. It represents the image orientation based on the current device orientation. On most Android devices the value of captureInfo.imageOrientation will be 0, but on some devices (like the most Samsung devices) the value will be 90. You have to handle this value accordingly and rotate the original image. See the example code above or our example app.

FinderPictureCallback#

The user has an ability to use an "advanced" version of PictureCallback - FinderPictureCallback, that binds the FinderOverlayView feature, ImageProcessor and the camera snapping mechanism. This callback automatically crops a part of the snapped image which is visible in the Finder view and rotates the cropped image according to the imageOrientation value.

To instantiate FinderPictureCallback the user has to pass an instance of ImageProcessor to the FinderPictureCallback's constuctor. As a result, the user will get an image in a Bitmap format in the abstract fun onPictureTaken(image: Bitmap?, captureInfo: CaptureInfo) method of the FinderPictureCallback.

val scanbotSDK = ScanbotSDK(this)cameraView.addPictureCallback(object : FinderPictureCallback(scanbotSDK.imageProcessor()) {   override fun onPictureTaken(image: Bitmap?, captureInfo: CaptureInfo) {        // Work with the final image (store it as file, etc)        // ...
        // Continue with the camera preview to scan the next image:        cameraView.post {            cameraView.continuousFocus()            cameraView.startPreview()        }    }})