Search code examples
androidkotlincamerasurfaceview

Open the front camera(kotlin)


I have the following code which opens the rear camera in SurfaceView when the activity is opened. Now I want to know how to change this code to open the front camera instead of the rear camera and I have given access to the front camera in the manifest.

And I don't want to go to camera using Intent

Thankful

    class mirrorActivity : AppCompatActivity(), SurfaceHolder.Callback {
       private lateinit var binding: ActivityMirrorBinding
       private var surfaceHolder: SurfaceHolder? = null
       private var camera: Camera? = null
       private val neededPermissions = arrayOf(CAMERA)
       override fun onCreate(savedInstanceState: Bundle?) {
          super.onCreate(savedInstanceState)
          binding = ActivityMirrorBinding.inflate(layoutInflater)
          setContentView(binding.root)
          val result = checkPermission()
          if (result) {
            setupSurfaceHolder()
          }
    }
      private fun checkPermission(): Boolean {
          val currentAPIVersion = Build.VERSION.SDK_INT
          if (currentAPIVersion >= Build.VERSION_CODES.M) {
             val permissionsNotGranted = ArrayList<String>()
             for (permission in neededPermissions) {
                 if (ContextCompat.checkSelfPermission( this,  permission) 
                            !=PackageManager.PERMISSION_GRANTED){
                    permissionsNotGranted.add(permission)
                }
            }
            if (permissionsNotGranted.size > 0) {
                var shouldShowAlert = false
                for (permission in permissionsNotGranted) {
                    shouldShowAlert =
                       ActivityCompat.shouldShowRequestPermissionRationale(this, permission)
                }
                val arr = arrayOfNulls<String>(permissionsNotGranted.size)
                val permissions = permissionsNotGranted.toArray(arr)
                if (shouldShowAlert) {
                    showPermissionAlert(permissions)
                } else {
                    requestPermissions(permissions)
                }
                return false
            }
        }
        return true
    }
    private fun showPermissionAlert(permissions: Array<String?>) {
        val alertBuilder = AlertDialog.Builder(this)
        alertBuilder.setCancelable(true)
        alertBuilder.setTitle("Permission Required")
        alertBuilder.setMessage("You must grant permission to access camera and external storage to run this application")
        alertBuilder.setPositiveButton(R.string.no_data) { _, _ -> requestPermissions(permissions) }
        val alert = alertBuilder.create()
        alert.show()
    }
    private fun requestPermissions(permissions: Array<String?>) {
        ActivityCompat.requestPermissions(this, permissions, REQUEST_CODE)
    }
    override fun onRequestPermissionsResult(
        requestCode: Int,
        permissions: Array<String>,
        grantResults: IntArray
    ) {
        when (requestCode) {
            REQUEST_CODE -> {
                for (result in grantResults) {
                    if (result == PackageManager.PERMISSION_DENIED) {
                        //t
                        binding.showPermissionMsg.visibility = View.VISIBLE
                        return
                    }
                }
                setupSurfaceHolder() } }
        super.onRequestPermissionsResult(requestCode, permissions, grantResults)
    }
    private fun setupSurfaceHolder() {
        surfaceHolder = binding.surfaceView.holder
        binding.surfaceView.holder.addCallback(this)

    }
    override fun surfaceCreated(surfaceHolder: SurfaceHolder) {
        startCamera()
    }
    private fun startCamera() {
        camera = Camera.open()
        camera!!.setDisplayOrientation(90)
        try {
            camera!!.setPreviewDisplay(surfaceHolder)
            camera!!.startPreview()
        } catch (e: IOException) {
            e.printStackTrace()
        }
    }
    override fun surfaceChanged(surfaceHolder: SurfaceHolder, i: Int, i1: Int, i2: Int) {
        resetCamera()
    }
    private fun resetCamera() {
        if (surfaceHolder!!.surface == null) {
            return
        }
        camera!!.stopPreview()
        try {
            camera!!.setPreviewDisplay(surfaceHolder)
        } catch (e: IOException) {
            e.printStackTrace()
        }
        camera!!.startPreview()
    }

    override fun surfaceDestroyed(surfaceHolder: SurfaceHolder) {
        releaseCamera()
    }

    private fun releaseCamera() {
        camera!!.stopPreview()
        camera!!.release()
        camera = null
    }

    companion object {
        const val REQUEST_CODE = 100
    }
}

Solution

  • You can use Camera.CameraInfo.CAMERA_FACING_FRONT for the front camera and Camera.CameraInfo.CAMERA_FACING_BACK for the back camera, you can use them in your code the following :

    private int currentCameraId = Camera.CameraInfo.CAMERA_FACING_FRONT;
    

    or

    private int currentCameraId = Camera.CameraInfo.CAMERA_FACING_BACK;
    

    And set it like this :

    Camera.open(currentCameraId)
    

    Also, put the whole camera code in the onResume() method