package de.tsschulz.tt_tagebuch.app.ui

import android.app.Activity
import android.content.Context
import android.content.Intent
import android.graphics.Bitmap
import android.net.Uri
import androidx.activity.compose.rememberLauncherForActivityResult
import androidx.activity.result.ActivityResultLauncher
import androidx.activity.result.contract.ActivityResultContracts
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.platform.LocalContext
import androidx.core.content.FileProvider
import com.yalantis.ucrop.UCrop
import java.io.File

private fun cropCacheDir(context: Context): File =
    File(context.cacheDir, "member_crop").also { it.mkdirs() }

/**
 * Kopiert die gewählte [Uri] in eine Cache-Datei (FileProvider), damit UCrop zuverlässig lesen kann.
 */
fun copyPickedImageToCacheForCrop(context: Context, source: Uri, memberId: Int): Uri {
    val dir = cropCacheDir(context)
    val inFile = File(dir, "pick-$memberId-${System.currentTimeMillis()}.jpg")
    context.contentResolver.openInputStream(source)?.use { input ->
        inFile.outputStream().use { output -> input.copyTo(output) }
    }
    return FileProvider.getUriForFile(
        context,
        "${context.packageName}.fileprovider",
        inFile,
    )
}

fun createCropOutputUri(context: Context, memberId: Int): Pair<File, Uri> {
    val dir = cropCacheDir(context)
    val outFile = File(dir, "crop-out-$memberId-${System.currentTimeMillis()}.jpg")
    if (outFile.exists()) outFile.delete()
    outFile.createNewFile()
    val uri = FileProvider.getUriForFile(
        context,
        "${context.packageName}.fileprovider",
        outFile,
    )
    return outFile to uri
}

fun buildMemberPortraitCropIntent(context: Context, sourceUri: Uri, destinationUri: Uri): Intent {
    val options = UCrop.Options().apply {
        setCompressionFormat(Bitmap.CompressFormat.JPEG)
        setCompressionQuality(90)
        setHideBottomControls(false)
        setFreeStyleCropEnabled(true)
    }
    return UCrop.of(sourceUri, destinationUri)
        .withAspectRatio(1f, 1f)
        .withMaxResultSize(2048, 2048)
        .withOptions(options)
        .getIntent(context)
        .apply {
            addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION or Intent.FLAG_GRANT_WRITE_URI_PERMISSION)
        }
}

@Composable
fun rememberMemberPortraitCropLauncher(
    onCropped: (ByteArray) -> Unit,
    onCancelledOrError: (() -> Unit)? = null,
): ActivityResultLauncher<Intent> {
    val context = LocalContext.current
    val appContext = remember(context) { context.applicationContext }
    return rememberLauncherForActivityResult(ActivityResultContracts.StartActivityForResult()) { result ->
        if (result.resultCode != Activity.RESULT_OK || result.data == null) {
            onCancelledOrError?.invoke()
            return@rememberLauncherForActivityResult
        }
        val data = result.data!!
        if (UCrop.getError(data) != null) {
            onCancelledOrError?.invoke()
            return@rememberLauncherForActivityResult
        }
        val outUri = UCrop.getOutput(data) ?: run {
            onCancelledOrError?.invoke()
            return@rememberLauncherForActivityResult
        }
        runCatching {
            appContext.contentResolver.openInputStream(outUri)?.use { it.readBytes() }
        }.getOrNull()?.let { onCropped(it) } ?: onCancelledOrError?.invoke()
    }
}
