package com.radiola.ui.charts

import android.content.Intent
import android.net.Uri
import androidx.compose.animation.animateColorAsState
import androidx.compose.animation.core.tween
import androidx.compose.foundation.ExperimentalFoundationApi
import androidx.compose.foundation.background
import androidx.compose.foundation.basicMarquee
import androidx.compose.foundation.clickable
import androidx.compose.foundation.horizontalScroll
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.rememberScrollState
import androidx.compose.foundation.layout.*
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.LazyRow
import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.lazy.itemsIndexed
import androidx.compose.foundation.shape.CircleShape
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.*
import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.hapticfeedback.HapticFeedbackType
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.platform.LocalHapticFeedback
import androidx.compose.ui.text.SpanStyle
import androidx.compose.ui.text.buildAnnotatedString
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.text.withStyle
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import androidx.hilt.navigation.compose.hiltViewModel
import coil.compose.AsyncImage
import com.composables.icons.lucide.*
import com.radiola.domain.model.ChartEntry
import com.radiola.domain.model.ChartPeriod
import com.radiola.domain.model.ChartTrend
import com.radiola.domain.model.DeeplinkService
import com.radiola.domain.model.StatPoint
import com.radiola.domain.model.TrackStats
import com.radiola.ui.components.EmptyState
import com.radiola.ui.components.PopularityChart
import com.radiola.ui.components.crossfadeModel
import com.radiola.ui.components.serviceLogoRes
import com.radiola.ui.lyrics.LyricsSheet
import com.radiola.ui.theme.Motion
import com.radiola.ui.theme.RadiolaTheme
import com.radiola.ui.theme.pressScale
import java.text.DecimalFormat

@OptIn(ExperimentalFoundationApi::class, ExperimentalMaterial3Api::class)
@Composable
fun ChartsScreen(
    modifier: Modifier = Modifier,
    viewModel: ChartsViewModel = hiltViewModel()
) {
    val colors = RadiolaTheme.colors
    val period by viewModel.period.collectAsState()
    val charts by viewModel.charts.collectAsState()
    val genres by viewModel.genres.collectAsState()
    val selectedGenre by viewModel.selectedGenre.collectAsState()
    val isLoadingCharts by viewModel.isLoadingCharts.collectAsState()
    val selectedStats by viewModel.selectedTrackStats.collectAsState()
    val isLoadingStats by viewModel.isLoadingStats.collectAsState()

    Column(
        modifier = modifier
            .fillMaxSize()
            .background(colors.bgBase)
    ) {
        // Двухцветный заголовок
        Column(modifier = Modifier.padding(horizontal = 20.dp)) {
            Text(
                text = buildAnnotatedString {
                    withStyle(SpanStyle(color = colors.textPrimary)) { append("Ча") }
                    withStyle(SpanStyle(color = colors.accent)) { append("рты") }
                },
                style = MaterialTheme.typography.headlineLarge,
                modifier = Modifier.padding(top = 20.dp, bottom = 2.dp)
            )
            Text(
                text = "Популярное на всех станциях",
                style = MaterialTheme.typography.bodyMedium,
                color = colors.textSecondary,
                modifier = Modifier.padding(bottom = 16.dp)
            )
        }

        // Сегменты периода (стиль FilterChips)
        PeriodSelector(
            selected = period,
            onSelect = viewModel::selectPeriod
        )

        // Фильтр по жанру (если бэкенд уже накопил жанры)
        if (genres.isNotEmpty()) {
            Spacer(Modifier.height(10.dp))
            GenreSelector(
                genres = genres,
                selected = selectedGenre,
                onSelect = viewModel::selectGenre
            )
        }

        Spacer(Modifier.height(12.dp))

        // Список чартов
        if (isLoadingCharts) {
            Box(Modifier.fillMaxSize(), contentAlignment = Alignment.Center) {
                CircularProgressIndicator(color = colors.accent)
            }
        } else if (charts.isEmpty()) {
            EmptyState(
                message = "Чарты пока недоступны",
                icon = Lucide.TrendingUp
            )
        } else {
            LazyColumn(
                modifier = Modifier.fillMaxSize(),
                contentPadding = PaddingValues(bottom = 88.dp)
            ) {
                itemsIndexed(
                    items = charts,
                    key = { _, entry -> entry.trackId }
                ) { _, entry ->
                    ChartRow(
                        entry = entry,
                        modifier = Modifier.animateItemPlacement(),
                        onClick = { viewModel.selectTrack(entry.trackId) }
                    )
                    HorizontalDivider(
                        color = colors.border.copy(alpha = 0.4f),
                        thickness = 0.5.dp,
                        modifier = Modifier.padding(horizontal = 20.dp)
                    )
                }
            }
        }
    }

    // Детальная карточка — ModalBottomSheet
    if (selectedStats != null || isLoadingStats) {
        TrackDetailSheet(
            stats = selectedStats,
            isLoading = isLoadingStats,
            onDismiss = viewModel::clearSelection,
            onToggleLike = { viewModel.toggleLike(it) }
        )
    }
}

// ---- Селектор периода ----

@Composable
private fun PeriodSelector(
    selected: ChartPeriod,
    onSelect: (ChartPeriod) -> Unit
) {
    val colors = RadiolaTheme.colors
    LazyRow(
        horizontalArrangement = Arrangement.spacedBy(9.dp),
        contentPadding = PaddingValues(horizontal = 20.dp)
    ) {
        items(ChartPeriod.entries) { p ->
            PeriodChip(
                label = p.label,
                selected = selected == p,
                onClick = { onSelect(p) }
            )
        }
    }
}

@Composable
private fun PeriodChip(label: String, selected: Boolean, onClick: () -> Unit) {
    val colors = RadiolaTheme.colors
    val bg by animateColorAsState(
        targetValue = if (selected) colors.accent else colors.surface2,
        animationSpec = tween(Motion.Medium),
        label = "periodChipBg"
    )
    val fg by animateColorAsState(
        targetValue = if (selected) colors.bgBase else colors.textSecondary,
        animationSpec = tween(Motion.Medium),
        label = "periodChipFg"
    )
    Text(
        text = label,
        color = fg,
        fontWeight = FontWeight.SemiBold,
        style = MaterialTheme.typography.labelLarge,
        modifier = Modifier
            .clip(RoundedCornerShape(18.dp))
            .background(bg)
            .clickable(
                interactionSource = remember { MutableInteractionSource() },
                indication = null,
                onClick = onClick
            )
            .padding(horizontal = 16.dp, vertical = 9.dp)
    )
}

// ---- Селектор жанра ----

@Composable
private fun GenreSelector(
    genres: List<String>,
    selected: String?,
    onSelect: (String?) -> Unit
) {
    LazyRow(
        horizontalArrangement = Arrangement.spacedBy(9.dp),
        contentPadding = PaddingValues(horizontal = 20.dp)
    ) {
        item {
            PeriodChip(
                label = "Все",
                selected = selected == null,
                onClick = { onSelect(null) }
            )
        }
        items(genres) { genre ->
            PeriodChip(
                label = genre,
                selected = selected == genre,
                onClick = { onSelect(genre) }
            )
        }
    }
}

// ---- Строка чарта ----

@OptIn(ExperimentalFoundationApi::class)
@Composable
private fun ChartRow(
    entry: ChartEntry,
    modifier: Modifier = Modifier,
    onClick: () -> Unit
) {
    val colors = RadiolaTheme.colors
    val interaction = remember { MutableInteractionSource() }

    Row(
        modifier = modifier
            .fillMaxWidth()
            .pressScale(interactionSource = interaction)
            .clickable(interactionSource = interaction, indication = null, onClick = onClick)
            .padding(horizontal = 20.dp, vertical = 12.dp),
        verticalAlignment = Alignment.CenterVertically,
        horizontalArrangement = Arrangement.spacedBy(12.dp)
    ) {
        // Номер ранга
        val rankColor = when (entry.rank) {
            1, 2, 3 -> colors.accent
            else -> colors.textMuted
        }
        Text(
            text = entry.rank.toString(),
            style = MaterialTheme.typography.titleMedium.copy(
                fontWeight = FontWeight.Bold,
                fontSize = 18.sp
            ),
            color = rankColor,
            modifier = Modifier.width(30.dp)
        )

        // Обложка трека
        Box(
            modifier = Modifier
                .size(50.dp)
                .clip(RoundedCornerShape(8.dp))
                .background(colors.surface2)
        ) {
            if (entry.coverUrl != null) {
                AsyncImage(
                    model = crossfadeModel(entry.coverUrl),
                    contentDescription = "${entry.artist} — ${entry.song}",
                    contentScale = ContentScale.Crop,
                    modifier = Modifier.fillMaxSize()
                )
            } else {
                Icon(
                    imageVector = Lucide.Music,
                    contentDescription = null,
                    tint = colors.textMuted,
                    modifier = Modifier
                        .size(22.dp)
                        .align(Alignment.Center)
                )
            }
        }

        // Название + исполнитель
        Column(
            modifier = Modifier.weight(1f),
            verticalArrangement = Arrangement.spacedBy(2.dp)
        ) {
            Text(
                text = entry.song,
                style = MaterialTheme.typography.titleMedium,
                color = colors.textPrimary,
                maxLines = 1,
                overflow = TextOverflow.Ellipsis
            )
            Text(
                text = entry.artist,
                style = MaterialTheme.typography.bodyMedium,
                color = colors.textSecondary,
                maxLines = 1,
                overflow = TextOverflow.Ellipsis
            )
        }

        // Правая часть: иконка тренда + число проигрываний
        Column(
            horizontalAlignment = Alignment.End,
            verticalArrangement = Arrangement.spacedBy(4.dp)
        ) {
            TrendIcon(trend = entry.trend)
            Text(
                text = formatPlays(entry.plays),
                style = MaterialTheme.typography.labelSmall,
                color = colors.textMuted
            )
        }
    }
}

@Composable
private fun TrendIcon(trend: ChartTrend) {
    val colors = RadiolaTheme.colors
    when (trend) {
        ChartTrend.UP -> Icon(
            imageVector = Lucide.TrendingUp,
            contentDescription = "Рост",
            tint = colors.accent,
            modifier = Modifier.size(16.dp)
        )
        ChartTrend.DOWN -> Icon(
            imageVector = Lucide.TrendingDown,
            contentDescription = "Падение",
            tint = colors.live,
            modifier = Modifier.size(16.dp)
        )
        ChartTrend.NEW -> Icon(
            imageVector = Lucide.Sparkles,
            contentDescription = "Новинка",
            tint = colors.accent,
            modifier = Modifier.size(16.dp)
        )
        ChartTrend.SAME -> Icon(
            imageVector = Lucide.Minus,
            contentDescription = "Без изменений",
            tint = colors.textMuted,
            modifier = Modifier.size(16.dp)
        )
    }
}

// ---- Детальная карточка трека ----

@OptIn(ExperimentalMaterial3Api::class, ExperimentalFoundationApi::class)
@Composable
private fun TrackDetailSheet(
    stats: TrackStats?,
    isLoading: Boolean,
    onDismiss: () -> Unit,
    onToggleLike: (String) -> Unit
) {
    val colors = RadiolaTheme.colors
    val context = LocalContext.current
    val haptic = LocalHapticFeedback.current
    var showLyrics by remember { mutableStateOf(false) }

    ModalBottomSheet(
        onDismissRequest = onDismiss,
        containerColor = colors.elevated,
        sheetState = rememberModalBottomSheetState(skipPartiallyExpanded = true)
    ) {
        if (isLoading || stats == null) {
            Box(
                modifier = Modifier
                    .fillMaxWidth()
                    .height(280.dp),
                contentAlignment = Alignment.Center
            ) {
                CircularProgressIndicator(color = colors.accent)
            }
        } else {
            LazyColumn(
                contentPadding = PaddingValues(bottom = 32.dp)
            ) {
                item {
                    // Большая обложка
                    Box(
                        modifier = Modifier
                            .fillMaxWidth()
                            .height(200.dp)
                            .background(colors.surface2)
                    ) {
                        if (stats.coverUrl != null) {
                            AsyncImage(
                                model = crossfadeModel(stats.coverUrl),
                                contentDescription = "${stats.artist} — ${stats.song}",
                                contentScale = ContentScale.Crop,
                                modifier = Modifier.fillMaxSize()
                            )
                        } else {
                            Icon(
                                imageVector = Lucide.Music,
                                contentDescription = null,
                                tint = colors.textMuted,
                                modifier = Modifier
                                    .size(48.dp)
                                    .align(Alignment.Center)
                            )
                        }
                    }

                    Spacer(Modifier.height(16.dp))

                    // Название + исполнитель
                    Column(modifier = Modifier.padding(horizontal = 20.dp)) {
                        Text(
                            text = stats.song,
                            style = MaterialTheme.typography.headlineLarge,
                            color = colors.textPrimary,
                            maxLines = 1,
                            modifier = Modifier.basicMarquee()
                        )
                        Text(
                            text = stats.artist,
                            style = MaterialTheme.typography.titleLarge,
                            color = colors.textSecondary,
                            maxLines = 1,
                            overflow = TextOverflow.Ellipsis
                        )
                        if (stats.album != null) {
                            Text(
                                text = stats.album,
                                style = MaterialTheme.typography.bodyMedium,
                                color = colors.textMuted,
                                modifier = Modifier.padding(top = 2.dp)
                            )
                        }
                        // Лейбл · Год (либо дата релиза как запасной вариант)
                        val metaLine = buildList {
                            stats.label?.let { add(it) }
                            stats.year?.let { add(it.toString()) }
                        }.joinToString(" · ").ifEmpty {
                            stats.releaseDate?.let { "Вышел: $it" } ?: ""
                        }
                        if (metaLine.isNotEmpty()) {
                            Text(
                                text = metaLine,
                                style = MaterialTheme.typography.labelSmall,
                                color = colors.textMuted,
                                modifier = Modifier.padding(top = 2.dp)
                            )
                        }

                        // Жанр + стили
                        val genreTags = buildList {
                            stats.genre?.let { add(it) }
                            addAll(stats.styles)
                        }.distinct()
                        if (genreTags.isNotEmpty()) {
                            Spacer(Modifier.height(10.dp))
                            GenreTags(tags = genreTags)
                        }

                        Spacer(Modifier.height(16.dp))

                        // Ряд метрик
                        MetricsRow(stats)

                        Spacer(Modifier.height(20.dp))

                        // График популярности
                        if (stats.playsTimeline.size >= 2) {
                            Text(
                                text = "Популярность за 30 дней",
                                style = MaterialTheme.typography.labelLarge,
                                color = colors.textSecondary,
                                modifier = Modifier.padding(bottom = 8.dp)
                            )
                            PopularityChart(
                                points = stats.playsTimeline,
                                modifier = Modifier
                                    .fillMaxWidth()
                                    .height(90.dp)
                                    .clip(RoundedCornerShape(8.dp))
                                    .background(colors.surface2)
                                    .padding(horizontal = 8.dp, vertical = 12.dp)
                            )
                            Spacer(Modifier.height(20.dp))
                        }

                        // Кнопка лайка
                        LikeButton(
                            isLiked = stats.isLiked,
                            likesCount = stats.totalLikes,
                            onClick = {
                                haptic.performHapticFeedback(HapticFeedbackType.LongPress)
                                onToggleLike(stats.trackId)
                            }
                        )

                        Spacer(Modifier.height(20.dp))

                        // Кнопка «Текст песни» — открывает встроенный экран
                        OutlinedButton(
                            onClick = { showLyrics = true },
                            modifier = Modifier.fillMaxWidth(),
                            shape = RoundedCornerShape(12.dp),
                            colors = ButtonDefaults.outlinedButtonColors(
                                contentColor = colors.textSecondary
                            ),
                            border = androidx.compose.foundation.BorderStroke(
                                1.dp, colors.border
                            )
                        ) {
                            Icon(
                                imageVector = Lucide.FileText,
                                contentDescription = null,
                                modifier = Modifier.size(16.dp)
                            )
                            Spacer(Modifier.width(8.dp))
                            Text("Текст песни")
                        }

                        Spacer(Modifier.height(20.dp))
                    }

                    // Кнопки музыкальных сервисов
                    Text(
                        text = "Слушать в сервисе",
                        style = MaterialTheme.typography.labelLarge,
                        color = colors.textSecondary,
                        modifier = Modifier.padding(horizontal = 20.dp, vertical = 0.dp)
                    )
                    Spacer(Modifier.height(12.dp))
                }

                // Сетка сервисов
                items(DeeplinkService.entries) { service ->
                    ServiceRow(
                        service = service,
                        onClick = {
                            val url = service.buildSearchUrl(stats.artist, stats.song)
                            val intent = Intent(Intent.ACTION_VIEW, Uri.parse(url))
                            context.startActivity(Intent.createChooser(intent, "Открыть в..."))
                        }
                    )
                }
            }
        }
    }

    // Шторка текста песни поверх детальной карточки
    if (showLyrics && stats != null) {
        ModalBottomSheet(
            onDismissRequest = { showLyrics = false },
            containerColor = colors.bgBase,
            sheetState = rememberModalBottomSheetState(skipPartiallyExpanded = true)
        ) {
            LyricsSheet(
                artist = stats.artist,
                song = stats.song
            )
        }
    }
}

// ---- Чипы жанра/стилей на детальной ----

@Composable
private fun GenreTags(tags: List<String>) {
    val colors = RadiolaTheme.colors
    Row(
        modifier = Modifier.horizontalScroll(rememberScrollState()),
        horizontalArrangement = Arrangement.spacedBy(8.dp)
    ) {
        tags.forEach { tag ->
            Text(
                text = tag,
                style = MaterialTheme.typography.labelMedium,
                color = colors.accent,
                fontWeight = FontWeight.Medium,
                modifier = Modifier
                    .clip(RoundedCornerShape(8.dp))
                    .background(colors.accent.copy(alpha = 0.12f))
                    .padding(horizontal = 10.dp, vertical = 5.dp)
            )
        }
    }
}

// ---- Метрики трека ----

@Composable
private fun MetricsRow(stats: TrackStats) {
    val colors = RadiolaTheme.colors
    Row(
        horizontalArrangement = Arrangement.spacedBy(8.dp),
        modifier = Modifier.fillMaxWidth()
    ) {
        MetricChip(
            label = formatPlays(stats.totalPlays),
            description = "проигрываний",
            modifier = Modifier.weight(1f)
        )
        MetricChip(
            label = formatPlays(stats.totalLikes),
            description = "лайков",
            modifier = Modifier.weight(1f)
        )
        if (stats.peakRank != null) {
            MetricChip(
                label = "#${stats.peakRank}",
                description = "пик",
                modifier = Modifier.weight(1f)
            )
        }
    }
}

@Composable
private fun MetricChip(label: String, description: String, modifier: Modifier = Modifier) {
    val colors = RadiolaTheme.colors
    Column(
        modifier = modifier
            .clip(RoundedCornerShape(10.dp))
            .background(colors.surface2)
            .padding(horizontal = 10.dp, vertical = 8.dp),
        horizontalAlignment = Alignment.CenterHorizontally
    ) {
        Text(
            text = label,
            style = MaterialTheme.typography.titleMedium,
            color = colors.accent,
            fontWeight = FontWeight.Bold
        )
        Text(
            text = description,
            style = MaterialTheme.typography.labelSmall,
            color = colors.textMuted,
            maxLines = 1
        )
    }
}

// ---- Кнопка лайка ----

@Composable
private fun LikeButton(isLiked: Boolean, likesCount: Int, onClick: () -> Unit) {
    val colors = RadiolaTheme.colors
    val heartColor by animateColorAsState(
        targetValue = if (isLiked) colors.live else colors.textMuted,
        animationSpec = tween(Motion.Fast),
        label = "heartColor"
    )
    val interaction = remember { MutableInteractionSource() }
    Row(
        modifier = Modifier
            .fillMaxWidth()
            .clip(RoundedCornerShape(12.dp))
            .background(colors.surface2)
            .pressScale(interactionSource = interaction)
            .clickable(interactionSource = interaction, indication = null, onClick = onClick)
            .padding(horizontal = 16.dp, vertical = 14.dp),
        verticalAlignment = Alignment.CenterVertically,
        horizontalArrangement = Arrangement.spacedBy(10.dp)
    ) {
        Icon(
            imageVector = if (isLiked) Lucide.Heart else Lucide.Heart,
            contentDescription = if (isLiked) "Убрать лайк" else "Поставить лайк",
            tint = heartColor,
            modifier = Modifier.size(22.dp)
        )
        Text(
            text = if (isLiked) "Нравится · ${formatPlays(likesCount)}" else "Нравится · ${formatPlays(likesCount)}",
            style = MaterialTheme.typography.bodyMedium,
            color = heartColor
        )
    }
}

// ---- Строка сервиса ----

@Composable
private fun ServiceRow(service: DeeplinkService, onClick: () -> Unit) {
    val colors = RadiolaTheme.colors
    val interaction = remember { MutableInteractionSource() }
    Row(
        modifier = Modifier
            .fillMaxWidth()
            .pressScale(interactionSource = interaction)
            .clickable(interactionSource = interaction, indication = null, onClick = onClick)
            .padding(horizontal = 20.dp, vertical = 10.dp),
        verticalAlignment = Alignment.CenterVertically,
        horizontalArrangement = Arrangement.spacedBy(14.dp)
    ) {
        Box(
            modifier = Modifier
                .size(40.dp)
                .clip(CircleShape)
                .background(colors.surface2),
            contentAlignment = Alignment.Center
        ) {
            val logoRes = serviceLogoRes(service)
            if (logoRes != null) {
                Icon(
                    painter = androidx.compose.ui.res.painterResource(logoRes),
                    contentDescription = service.displayName,
                    tint = colors.textSecondary,
                    modifier = Modifier.size(20.dp)
                )
            } else {
                Icon(
                    imageVector = Lucide.Music,
                    contentDescription = service.displayName,
                    tint = colors.textSecondary,
                    modifier = Modifier.size(18.dp)
                )
            }
        }
        Text(
            text = service.displayName,
            style = MaterialTheme.typography.bodyMedium,
            color = colors.textPrimary
        )
        Spacer(Modifier.weight(1f))
        Icon(
            imageVector = Lucide.ChevronRight,
            contentDescription = null,
            tint = colors.textMuted,
            modifier = Modifier.size(16.dp)
        )
    }
}

// ---- Утилиты ----

/** Форматирует число проигрываний: 1234 → «1.2k», 1_000_000 → «1.0M». */
private fun formatPlays(value: Int): String {
    val df = DecimalFormat("#.#")
    return when {
        value >= 1_000_000 -> "${df.format(value / 1_000_000.0)}M"
        value >= 1_000 -> "${df.format(value / 1_000.0)}k"
        else -> value.toString()
    }
}
