package dev.kaizen.app.ui.effect

import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.material3.MaterialTheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.Shape
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
import dev.kaizen.app.ui.shape.KaizenShapes

/**
 * A frosted-glass surface — the core visual primitive of the Kaizen design system.
 *
 * Android has no `backdrop-filter: blur()` — real refractive blur would require
 * capturing and blurring the layer behind, which is not feasible in Compose's
 * rendering model. Instead, the glass effect is achieved through:
 *
 * 1. Semi-transparent gradient tint (gives the surface body and color identity)
 * 2. Specular border highlight (top-bright, bottom-dim gradient border)
 * 3. Inner top highlight (1dp lit edge, simulates overhead light)
 * 4. Multi-layer shadow stack (floating depth)
 *
 * The blob layer behind (MeshBackground) is what "shows through" the
 * transparency, creating the frosted-glass illusion.
 *
 * See DESIGN.md §4 for the full anatomy and opacity tiers.
 */
@Composable
fun GlassSurface(
    modifier: Modifier = Modifier,
    shape: Shape = KaizenShapes.md,
    tintAlpha: Float = 0.72f,
    shadowStack: ShadowStack = KaizenShadows.level2,
    cornerRadius: Dp = 16.dp,
    content: @Composable BoxScope.() -> Unit,
) {
    val isDark = isSystemInDarkTheme()
    val cs = MaterialTheme.colorScheme

    val glassBg = remember(isDark, tintAlpha) {
        if (isDark) {
            Brush.verticalGradient(
                listOf(
                    Color(0xFF1E293B).copy(alpha = tintAlpha),
                    Color(0xFF0F172A).copy(alpha = (tintAlpha + 0.10f).coerceAtMost(1f)),
                )
            )
        } else {
            Brush.verticalGradient(
                listOf(
                    Color.White.copy(alpha = tintAlpha),
                    Color(0xFFF1F5F9).copy(alpha = (tintAlpha - 0.05f).coerceAtLeast(0f)),
                )
            )
        }
    }

    val glassBorder = remember(isDark) {
        if (isDark) {
            Brush.verticalGradient(
                listOf(Color.White.copy(alpha = 0.16f), Color.White.copy(alpha = 0.03f))
            )
        } else {
            Brush.verticalGradient(
                listOf(Color.White.copy(alpha = 0.55f), Color.Black.copy(alpha = 0.05f))
            )
        }
    }

    Box(
        modifier = modifier
            .kaizenShadow(stack = shadowStack, cornerRadius = cornerRadius)
            .clip(shape)
            .background(glassBg)
            .innerTopHighlight()
            .border(1.2.dp, glassBorder, shape),
        content = content,
    )
}

/**
 * Predefined opacity tiers matching DESIGN.md §4.4.
 * Use these constants with [GlassSurface] instead of ad-hoc alpha values.
 */
object GlassTiers {
    fun sidebar(isDark: Boolean) = if (isDark) 0.88f else 0.92f
    fun input(isDark: Boolean) = if (isDark) 0.75f else 0.74f
    fun pill(isDark: Boolean) = if (isDark) 0.80f else 0.82f
    fun chip(isDark: Boolean) = if (isDark) 0.85f else 0.90f
    fun card(isDark: Boolean) = if (isDark) 0.94f else 0.95f
    fun userBubble(isDark: Boolean) = if (isDark) 0.86f else 0.88f
    fun sheet(isDark: Boolean) = if (isDark) 0.82f else 0.85f
}
