package uz.uzinfocom.myid

import android.content.Intent
import android.graphics.Bitmap
import android.util.Base64
import io.flutter.plugin.common.MethodChannel
import io.flutter.plugin.common.PluginRegistry
import uz.myid.android.sdk.capture.MyIdClient
import uz.myid.android.sdk.capture.MyIdException
import uz.myid.android.sdk.capture.MyIdResult
import uz.myid.android.sdk.capture.MyIdResultListener
import uz.myid.android.sdk.capture.model.MyIdGraphicFieldType
import uz.myid.android.sdk.capture.model.MyIdImageFormat
import java.io.ByteArrayOutputStream

class MyIdSdkActivityListener(
    private val client: MyIdClient
) : PluginRegistry.ActivityResultListener {

    private var flutterResult: MethodChannel.Result? = null

    fun setCurrentFlutterResult(result: MethodChannel.Result?) {
        this.flutterResult = result
    }

    override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?): Boolean {
        client.handleActivityResult(resultCode, object : MyIdResultListener {
            override fun onSuccess(result: MyIdResult) {
                if (flutterResult != null) {
                    try {
                        val bitmap =
                            result.getGraphicFieldImageByType(MyIdGraphicFieldType.FACE_PORTRAIT)

                        val response = Response(
                            code = result.code,
                            comparison = result.comparison,
                            base64 = bitmap?.toBase64()
                        )
                        flutterResult?.success(response.toMap())
                    } catch (e: Exception) {
                        val response = Response(
                            code = result.code,
                            comparison = result.comparison
                        )
                        flutterResult?.success(response.toMap())
                    } finally {
                        flutterResult = null
                    }
                }
            }

            override fun onError(exception: MyIdException) {
                if (flutterResult != null) {
                    flutterResult?.error(
                        "error",
                        "${exception.code} - ${exception.message}",
                        null
                    )
                    flutterResult = null
                }
            }

            override fun onUserExited() {
                if (flutterResult != null) {
                    flutterResult?.error(
                        "cancel",
                        "User canceled flow",
                        null
                    )
                    flutterResult = null
                }
            }
        })
        return true
    }

    private fun Bitmap?.toBase64(
        format: MyIdImageFormat = MyIdImageFormat.JPG
    ): String? {
        this ?: return null

        return Base64.encodeToString(toByteArray(format), Base64.DEFAULT)
    }

    private fun Bitmap.toByteArray(
        format: MyIdImageFormat,
        quality: Int = 100
    ): ByteArray? {
        val compressFormat = when (format) {
            MyIdImageFormat.JPG -> Bitmap.CompressFormat.JPEG
            MyIdImageFormat.PNG -> Bitmap.CompressFormat.PNG
        }

        ByteArrayOutputStream().use { stream ->
            compress(compressFormat, quality, stream)
            return stream.toByteArray()
        }
    }
}