Search code examples
androidsurface

How to grab a picture from a Surface


I am pretty new to Android so I hope I can get some directions here.
I have a 360 camera running on Android 7.0. It includes a SDK to get access to the live stitched images. In this SDK there is a function to set a Surface where the output from the stitched images will be directed to.
This is the function provided by the SDK:

public static void SDK.setSurface(Surface inputSurface)

I want to grab an image from that surface every second.
How do I create the right kind of Surface? And how do I grab images from this Surface?

Any help is highly appreciated!


Solution

  • Since I found the answer I might share it here too.
    I have create a class which works like a charm. This is what I used:

    class Capture: ImageReader.OnImageAvailableListener{
    
    private var mImageReader: ImageReader? = null
    private var mThreadHandler: HandlerThread? = null
    
    fun start() {
        if (!init) {
            if (mImageReader != null) {
                mImageReader?.close()
                mImageReader = null
            }
            if (mThreadHandler != null) {
                mThreadHandler?.quitSafely()
                mThreadHandler = null
            }
            mThreadHandler = HandlerThread("prev")
            mThreadHandler?.start()
            mImageReader = ImageReader.newInstance(width, height, PixelFormat.RGBA_8888, 5)
            mImageReader?.setOnImageAvailableListener(this, Handler(mThreadHandler?.getLooper()))
    
            SDK.setSurface(if (mImageReader == null) null else mImageReader?.getSurface())
            init = true
        }
    }
    
    override fun onImageAvailable(reader: ImageReader) {
        val image = reader.acquireLatestImage()
        val height = image.height
        val stride = image.planes[0].rowStride / image.planes[0].pixelStride
        captureCallback(
            stride,
            height,
            image.timestamp,
            image.planes[0].buffer
        )
        image.close()
    }
    
    
    fun stop() {
        if (init) {
            if (mImageReader != null) {
                mImageReader!!.close()
                mImageReader = null
            }
            if (mThreadHandler != null) {
                mThreadHandler!!.quitSafely()
                mThreadHandler = null
            }
            SDK.setSurface(null)
        }
        init = false
    }
    
    fun captureCallback(width: Int, Height: Int, timestamp: Long, data: ByteBuffer) {
        // do something with data
    }
    

    } `