package eu.darken.bluemusic.main.ui.settings.general

import android.annotation.SuppressLint
import dagger.hilt.android.lifecycle.HiltViewModel
import eu.darken.bluemusic.common.coroutine.DispatcherProvider
import eu.darken.bluemusic.common.datastore.value
import eu.darken.bluemusic.common.debug.logging.log
import eu.darken.bluemusic.common.debug.logging.logTag
import eu.darken.bluemusic.common.flow.SingleEventFlow
import eu.darken.bluemusic.common.flow.combine
import eu.darken.bluemusic.common.hasApiLevel
import eu.darken.bluemusic.common.locale.LocaleManager
import eu.darken.bluemusic.common.navigation.Nav
import eu.darken.bluemusic.common.navigation.NavigationController
import eu.darken.bluemusic.common.theming.ThemeColor
import eu.darken.bluemusic.common.theming.ThemeMode
import eu.darken.bluemusic.common.theming.ThemeState
import eu.darken.bluemusic.common.theming.ThemeStyle
import eu.darken.bluemusic.common.theming.themeState
import eu.darken.bluemusic.common.ui.ViewModel4
import eu.darken.bluemusic.common.upgrade.UpgradeRepo
import eu.darken.bluemusic.common.upgrade.isProForUi
import eu.darken.bluemusic.main.core.GeneralSettings
import kotlinx.coroutines.flow.flowOf
import javax.inject.Inject

@HiltViewModel
class GeneralSettingsViewModel
@Inject
constructor(
    dispatcherProvider: DispatcherProvider,
    navCtrl: NavigationController,
    private val generalSettings: GeneralSettings,
    private val localeManager: LocaleManager,
    private val upgradeRepo: UpgradeRepo,
) : ViewModel4(dispatcherProvider, logTag("Settings", "General", "ViewModel"), navCtrl) {

    val events = SingleEventFlow<GeneralSettingsDialog>()

    val state = combine(
        generalSettings.themeState,
        flowOf(hasApiLevel(33)),
        upgradeRepo.upgradeInfo,
    ) { themeState, languageSwitcher, upgradeInfo ->
        State(
            themeState = themeState,
            showLanguageSwitcher = languageSwitcher,
            isUpgraded = upgradeInfo.isPro,
        )
    }
        .asStateFlow()

    @SuppressLint("NewApi")
    fun showLanguagePicker() = launch {
        log(tag) { "showLanguagePicker()" }
        if (hasApiLevel(33)) {
            localeManager.showLanguagePicker()
        } else {
            throw IllegalStateException("This should not be clickable below API 33...")
        }
    }

    // The three theme rows render their Pro badge off the passively collected state, which reports
    // non-Pro while billing is still settling. The tap route is gated separately so a paying user
    // who taps during that window opens the picker instead of being sent to the upgrade screen.
    fun onThemeRowClicked(dialog: GeneralSettingsDialog) = launch {
        log(tag) { "onThemeRowClicked($dialog)" }
        if (!upgradeRepo.isProForUi()) {
            navTo(Nav.Main.Upgrade())
            return@launch
        }
        events.emit(dialog)
    }

    fun updateThemeMode(mode: ThemeMode) = launch {
        log(tag) { "updateThemeMode($mode)" }
        generalSettings.themeMode.value(mode)
    }

    fun updateThemeStyle(style: ThemeStyle) = launch {
        log(tag) { "updateThemeStyle($style)" }
        generalSettings.themeStyle.value(style)
    }

    fun updateThemeColor(color: ThemeColor) = launch {
        log(tag) { "updateThemeColor($color)" }
        generalSettings.themeColor.value(color)
    }

    data class State(
        val themeState: ThemeState = ThemeState(),
        val filePreviews: Boolean = false,
        val showLanguageSwitcher: Boolean = false,
        val updateCheckEnabled: Boolean = false,
        val motdEnabled: Boolean = false,
        val confirmExitEnabled: Boolean = true,
        val isUpgraded: Boolean = false,
    )
}
