package com.laseroptek.raman.ui.screens.main

import android.content.res.Configuration
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.derivedStateOf
import androidx.compose.runtime.getValue
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel
import androidx.navigation.NavHostController
import androidx.navigation.compose.currentBackStackEntryAsState
import androidx.navigation.compose.rememberNavController
import com.laseroptek.raman.R
import com.laseroptek.raman.const.AlertType
import com.laseroptek.raman.const.ERROR_TABLE
import com.laseroptek.raman.const.WARNING_TABLE
import com.laseroptek.raman.data.datasource.db.RamanDatabase
import com.laseroptek.raman.data.source.db.RamanDatabaseService
import com.laseroptek.raman.navigation.NavigationItem
import com.laseroptek.raman.navigation.NavigationSideBar
import com.laseroptek.raman.navigation.Routes
import com.laseroptek.raman.navigation.graphs.MainNavGraph
import com.laseroptek.raman.navigation.navigationItemsLists
import com.laseroptek.raman.repository.DatabaseRepository
import com.laseroptek.raman.repository.PreferenceRepository
import com.laseroptek.raman.repository.SerialPortRepository
import com.laseroptek.raman.ui.screens.config.engineer.EngineerPasswordPopup
import com.laseroptek.raman.ui.screens.config.language.LanguageView
import com.laseroptek.raman.ui.screens.config.time.TimeSettingPopup
import com.laseroptek.raman.ui.screens.home.count.ResetLaserCountPopup
import com.laseroptek.raman.ui.screens.home.dcd.DcdSettingPopup
import com.laseroptek.raman.ui.screens.home.energy.EnergyDetectPopup
import com.laseroptek.raman.ui.screens.home.preset.PresetLoadPopup
import com.laseroptek.raman.ui.screens.home.preset.PresetSavePopup
import com.laseroptek.raman.ui.screens.home.standby.StandByPopup
import com.laseroptek.raman.utils.DefaultDispatcherProvider
import timber.log.Timber

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun MainView(
    mainNavController: NavHostController = rememberNavController(),
    //currentRoute: String? = null,
    innerPadding: PaddingValues = PaddingValues(0.dp),
    mainViewModel: MainViewModel = hiltViewModel(),
    items: List<NavigationItem> = navigationItemsLists,
    onItemClick: (NavigationItem) -> Unit = {},
) {
    val navBackStackEntry by mainNavController.currentBackStackEntryAsState()
    val currentRoute by remember(navBackStackEntry) {
        derivedStateOf {
            navBackStackEntry?.destination?.route
        }
    }

    val warning by mainViewModel.warning.collectAsState()
    val error by mainViewModel.error.collectAsState()

    Box {
        // Layer 1: Full Background Image (Bottom-most layer)
        Image(
            painter = painterResource(id = R.drawable.background),
            contentDescription = "Background Image",
            modifier = Modifier.fillMaxSize(),
            contentScale = ContentScale.Crop
        )

        // Layer 2: Main Screen Content
        // This is the main content area, it should be drawn before the UI controls.
        MainNavGraph(
            mainNavController = mainNavController,
            innerPadding = innerPadding,
            mainViewModel = mainViewModel,
        )

        // Layer 3: Left Navigation Bar (On top of MainNavGraph)
        // Hide on Engineer and Lock screens
        if (currentRoute != Routes.Engineer.route && currentRoute != Routes.Lock.route) {
            NavigationSideBar(
                items = items,
                currentRoute = currentRoute,
                innerPadding = innerPadding,
                onItemClick = onItemClick,
                modifier = Modifier
                    .align(Alignment.CenterStart)
            )
        }

        // Layer 4: TopBar (On top of everything so far)
        if (currentRoute != Routes.Lock.route) {
            MainTopBar(
                mainViewModel = mainViewModel,
                onClickWarning = {
                    mainViewModel.showWarningPopup = true
                }
            )
        }

        // androidx.constraintlayout.helper.widget.Layer 5 & 6: Modal Popups (Top-most layers)
        // These should always be last so they appear on top of all other UI.
        // Remember to wrap them in FullScreen to block background touches.

        ///////////////////////////////////////////////////////////////////////////////////////////
        // Popups

        // Error over TopBar
        if (error.code != 0) {
            AlertView(
                type = AlertType.ERROR,
                title = stringResource(R.string.error_title),
                description = stringResource(
                    ERROR_TABLE[ error.code ]
                ),
                onClick = {
                    Timber.d("Convert to run: ${error.code}")
                }
            )
        }

        // Warning over TopBar
        else if (mainViewModel.showWarningPopup) {
            AlertView(
                type = AlertType.WARNING,
                title = stringResource(R.string.warning_title),
                description = stringResource(
                    WARNING_TABLE [ warning.code ]
                ),
                onClick = {
                    mainViewModel.showWarningPopup = false
                    Timber.d("showWarningPopup: ${mainViewModel.showWarningPopup}")
                }
            )
        }

        else if (mainViewModel.showEnergyDetectPopup) {
            EnergyDetectPopup(
                title = stringResource(R.string.enery_check_title),
                mainViewModel = mainViewModel,
                onClick = {
                    mainViewModel.showEnergyDetectPopup = false
                }
            )
        }

        else if (mainViewModel.showPresetLoadPopup) {
            PresetLoadPopup(
                title = stringResource(R.string.load_title),
                mainViewModel = mainViewModel,
                /*
                presetList = mainViewModel.presetList,
                //selectedPresetIndex = mainViewModel.tmpSelectedPresetIndex,
                */
                onClick = {
                    mainViewModel.showPresetLoadPopup = false
                }
            )
        }

        else if (mainViewModel.showPresetSavePopup) {
            PresetSavePopup(
                mainViewModel = mainViewModel,
                onClick = { ok ->
                    // reset selected preset index
                    if (ok) {
                        mainViewModel.setSelectedPresetIndex(0)
                    }
                    mainViewModel.showPresetSavePopup = false
                }
            )
        }

        else if (mainViewModel.showDcdSettingPopup) {
            DcdSettingPopup(
                mainViewModel = mainViewModel,
                onDismiss = {
                    mainViewModel.showDcdSettingPopup = false
                }
            )
        }

        else if (mainViewModel.showResetLaserCountPopup) {
            ResetLaserCountPopup(
                title = stringResource(R.string.reset_laser_count_title),
                onClick = { okValue ->
                    Timber.d("ResetLaserCountPopup: $okValue")
                    if (okValue) {
                        mainViewModel.setLaserCount(0)
                        //mainViewModel.saveLaserCountToPreference()
                    }
                    mainViewModel.showResetLaserCountPopup = false
                }
            )
        }

        else  if (mainViewModel.showStandByPopup) {
            StandByPopup(
                //mainViewModel = mainViewModel,
                //description = stringResource(R.string.stand_by_message),
                onClick = {
                    mainViewModel.txLaserStatusEntry(0x53) // send standBy

                    mainViewModel.showStandByPopup = false
                }
            )
        }

        else if (mainViewModel.showTimeSettingPopup) {
            TimeSettingPopup(
                onDismiss = {
                    mainViewModel.showTimeSettingPopup = false
                }
            )
        }

        else if (mainViewModel.showEngineerPasswordPopup) {
            EngineerPasswordPopup(
                title = stringResource(R.string.engineer_mode_password),
                onClick = { result ->
                    if (result) {
                        //mainViewModel.showEngineerModePopup.value = true
                        mainNavController.navigate(Routes.Engineer.route)
                    }
                    mainViewModel.showEngineerPasswordPopup = false
                }
            )
        }

        else if (mainViewModel.showLanguageScreen) {
            LanguageView(
                //showLanguageScreen =  showLanguageScreen,
                //mainViewModel = mainViewModel
                onClick = { ok ->
                    mainViewModel.showLanguageScreen = false
                }
            )
        }
    }
}


@Preview(
    apiLevel = 34,
    uiMode = Configuration.UI_MODE_NIGHT_NO,
    showBackground = false,
    device = "spec:width=1920dp,height=1080dp,dpi=150,isRound=false,chinSize=0dp,orientation=landscape"
)
@Composable
fun PreviewMain(
    mainViewModel:MainViewModel = MainViewModel(
        preferenceRepository = PreferenceRepository(LocalContext.current),
        serialPortRepository = SerialPortRepository.createWithFakeRepository(),
        databaseRepository = DatabaseRepository(RamanDatabaseService(RamanDatabase.getInstance(LocalContext.current))),
        dispatcherProvider = DefaultDispatcherProvider(),
        applicationContext = LocalContext.current
    )
) {
    mainViewModel.showEnergyDetectPopup = false
    MainView(
        mainViewModel = mainViewModel,
    )
}
