package com.webtoonviewer.ui

import android.app.Activity
import android.content.Intent
import android.graphics.Bitmap
import android.os.Bundle
import android.util.Log
import android.view.View
import android.view.WindowInsets
import android.widget.ImageButton
import android.widget.TextView
import android.widget.Toast
import androidx.activity.OnBackPressedCallback
import androidx.activity.enableEdgeToEdge
import androidx.appcompat.app.AppCompatActivity
import androidx.constraintlayout.widget.ConstraintLayout
import androidx.lifecycle.lifecycleScope
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import com.webtoonviewer.R
import com.webtoonviewer.db.Book
import com.webtoonviewer.network.SmbClientHelper
import com.webtoonviewer.repository.BookRepository
import com.webtoonviewer.storage.StorageManager
import com.webtoonviewer.ui.adapter.ImageAdapter
import com.webtoonviewer.ui.component.SmoothScroller
import com.webtoonviewer.utils.CommonUtils.getEpisodeIndexFromEpisode
import com.webtoonviewer.utils.CommonUtils.getEpisodeNameFromEpisode
import com.webtoonviewer.utils.CommonUtils.getEllipsizedText
import com.webtoonviewer.utils.SharedPreferencesHelper
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import java.io.File


class ImagesActivity : AppCompatActivity() {

    private val bookRepository: BookRepository = BookRepository(this)
    private val smbClientHelper: SmbClientHelper = SmbClientHelper(this)
    private val bookIdPreferences: SharedPreferencesHelper = SharedPreferencesHelper(this, "book_id")
    private val speedPreference: SharedPreferencesHelper = SharedPreferencesHelper(this, "auto_scroll_speed")

    private lateinit var recyclerView: RecyclerView
    private lateinit var imageAdapter: ImageAdapter
    private lateinit var currentChapter: String
    private lateinit var title: String
    private lateinit var book: Book

    private lateinit var topBar: ConstraintLayout
    private lateinit var bottomBar: ConstraintLayout
    private var isControlsVisible = true

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        enableEdgeToEdge()
        window.insetsController?.hide(WindowInsets.Type.systemBars())
        setContentView(R.layout.activity_images)

        recyclerView = findViewById(R.id.recyclerViewImagesList)
        recyclerView.layoutManager = LinearLayoutManager(this)
        imageAdapter = ImageAdapter(mutableListOf())  {
            toggleControlsVisibility()
        }
        recyclerView.adapter = imageAdapter
        recyclerView.layoutManager = LinearLayoutManager(this)

        recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
            override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
                super.onScrolled(recyclerView, dx, dy)
                hideBars()

                // Get the height of the RecyclerView and its content
                val recyclerViewHeight = recyclerView.height
                val recyclerViewContentHeight = recyclerView.computeVerticalScrollRange()
                val recyclerViewScrollY = recyclerView.computeVerticalScrollOffset()

                // Check if the RecyclerView has scrolled to the bottom
                if (recyclerViewContentHeight <= recyclerViewHeight + recyclerViewScrollY) {
                    showBars()
                }
            }
        })

        topBar = findViewById(R.id.imagePageTopBar)
        bottomBar = findViewById(R.id.imagePageBottomBar)

        currentChapter = intent.getStringExtra("selectedChapter") ?: ""
        title = intent.getStringExtra("selectedTitle") ?: ""
        val thumbnail = intent.getStringExtra("thumbnail") ?: ""
        val position = intent.getIntExtra("position", 0)
        val offset = intent.getIntExtra("offset", 0)

        val chapterTextView: TextView = findViewById(R.id.textViewImagePageChapter)
        chapterTextView.post {
            chapterTextView.text = getEllipsizedText(
                chapterTextView, getEpisodeNameFromEpisode(currentChapter)
                )
            }

        lifecycleScope.launch {
            book = getBook()
            if (position == 0 && offset == 0) {
                loadImagesIncrementally()
            } else {
                loadImagesAllAtOnce(position, offset)
            }
        }

        val btnPrev: ImageButton = findViewById(R.id.btnImagePagePrev)
        btnPrev.setOnClickListener {
            if (hasPrevChapter(currentChapter)) {
                val newChapter = getPrevChapter(currentChapter)
                currentChapter = newChapter
                imageAdapter.initImages()
                loadImagesAllAtOnce(-1, -1)
                chapterTextView.post {
                    chapterTextView.text = getEllipsizedText(
                        chapterTextView, getEpisodeNameFromEpisode(currentChapter)
                    )
                }
            } else {
                Toast.makeText(this@ImagesActivity, "这是最初的章节。", Toast.LENGTH_SHORT).show()
            }
        }

        val btnNext: ImageButton = findViewById(R.id.btnImagePageNext)
        btnNext.setOnClickListener {
            Log.d("ithi", "currentChapter: $currentChapter")

            if (hasNextChapter(currentChapter)) {
                val newChapter = getNextChapter(currentChapter)
                currentChapter = newChapter
                imageAdapter.initImages()
                loadImagesIncrementally()
                scrollToTop()
                chapterTextView.post {
                    chapterTextView.text = getEllipsizedText(
                        chapterTextView, getEpisodeNameFromEpisode(currentChapter)
                    )
                }
                lifecycleScope.launch {
                    savePosition()
                }
            }  else {
                Toast.makeText(this@ImagesActivity, "这已经是最后一话了。", Toast.LENGTH_SHORT).show()
            }
        }

        val btnBack: ImageButton = findViewById(R.id.btnImagePageBack)
        btnBack.setOnClickListener {
            returnToLastActivity()
        }

        val btnHome: ImageButton = findViewById(R.id.btnImagePageHome)
        btnHome.setOnClickListener {
            val intent = Intent(this, MainActivity::class.java)
            intent.putExtra("bookmarkUpdated", book.title)
            startActivity(intent)
        }

        val btnList: ImageButton = findViewById(R.id.btnImagePageList)
        btnList.setOnClickListener {
            val intent = Intent(this@ImagesActivity, EpisodesActivity::class.java)
            intent.putExtra("selectedTitle", title)
            intent.putExtra("thumbnail", thumbnail)
            startActivity(intent)
        }

        val btnPlay: ImageButton = findViewById(R.id.btnImagePagePlay)
        btnPlay.setOnClickListener {
            val bottomOffset = calculateBottomOffset()
            val speed = speedPreference.readData(title, "1x")
            smoothScrollToBottomWithOffset(bottomOffset, speed)
        }

        val btnMenu: ImageButton = findViewById(R.id.btnImagePageMenu)

        btnMenu.setOnClickListener {
            val dialog = DialogAutoScrollSpeedFragment.newInstance(title)
            dialog.isCancelable = true
            dialog.show(supportFragmentManager, "DialogAutoScrollSpeedFragment")
        }

        onBackPressedDispatcher.addCallback(this, object: OnBackPressedCallback(true) {
            override fun handleOnBackPressed() {
                returnToLastActivity()
            }
        })
    }

    private fun loadImagesIncrementally() {
        if (book.isLocal == 1) {
            loadImagesAllAtOnce(0, 0)
        } else {
            lifecycleScope.launch {
                var isConnect = false
                try {
                    isConnect = smbClientHelper.connect()
                    if (isConnect) {
                        val newImagePaths = getImagePathsFromShare()
                        newImagePaths.forEach {
                            val bitmap = loadImageFromShare(it)
                            if (bitmap != null) {
                                imageAdapter.addImage(bitmap)
                            }
                        }
                    }
                } finally {
                    if (isConnect) {
                        smbClientHelper.disconnect()
                    }
                }
            }
        }
    }

    private fun loadImagesAllAtOnce(position: Int, offset: Int) {
        if (book.isLocal == 1) {
            lifecycleScope.launch {
                val newImagePaths = getImagePathsFromStorage(book.title, currentChapter)
                val bitmaps = withContext(Dispatchers.IO) {
                    newImagePaths.mapNotNull { loadImageFromStorage(it) }
                }
                imageAdapter.updateImages(bitmaps)
                if (position == -1 && offset == -1) {
                    val newPosition = bitmaps.size - 1
                    val newOffset = calculateBottomOffset()
                    scrollToPosition(newPosition, newOffset)
                } else {
                    scrollToPosition(position, offset)
                }
            }
        } else {
            lifecycleScope.launch {
                var isConnect = false
                try {
                    isConnect = smbClientHelper.connect()
                    if (isConnect) {
                        val newImagePaths = getImagePathsFromShare()
                        val bitmaps = withContext(Dispatchers.IO) {
                            newImagePaths.mapNotNull { loadImageFromShare(it) }
                        }
                        imageAdapter.updateImages(bitmaps)
                        if (position == -1 && offset == -1) {
                            val newPosition = bitmaps.size - 1
                            val newOffset = calculateBottomOffset()
                            scrollToPosition(newPosition, newOffset)
                        } else {
                            scrollToPosition(position, offset)
                        }
                    }
                } finally {
                    if (isConnect) {
                        smbClientHelper.disconnect()
                    }
                }
            }
        }
    }

    private suspend fun getImagePathsFromShare(): MutableList<String> {
        return smbClientHelper.getImagePathsFromShare(title, currentChapter)
    }

    private suspend fun loadImageFromShare(imagePath: String): Bitmap? {
        return smbClientHelper.loadImageFromShare(imagePath)
    }

    private fun getImagePathsFromStorage(title: String, chapter: String): MutableList<File> {
        return StorageManager.getImagePaths(this, title, chapter)
    }

    private fun loadImageFromStorage(imagePath: File): Bitmap? {
        return StorageManager.loadImage(imagePath)
    }

    private suspend fun getBook(): Book {
        return withContext(Dispatchers.IO) {
            val bookId = bookIdPreferences.readData(title, "0").toInt()
            bookRepository.getBookById(bookId)!!
        }
    }

    private fun hasPrevChapter(selectedChapter: String): Boolean {
        val chapterIndex = getEpisodeIndexFromEpisode(selectedChapter)
        return chapterIndex > 0
    }

    private fun hasNextChapter(selectedChapter: String): Boolean {
        val chapters = book.chapters
        val chapterIndex = getEpisodeIndexFromEpisode(selectedChapter)
        return chapterIndex < chapters.size - 1
    }

    private fun getPrevChapter(selectedChapter: String): String {
        val chapters = book.chapters
        val chapterIndex = getEpisodeIndexFromEpisode(selectedChapter)
        return chapters[chapterIndex - 1]
    }

    private fun getNextChapter(selectedChapter: String): String {
        val chapters = book.chapters
        val chapterIndex = getEpisodeIndexFromEpisode(selectedChapter)
        return chapters[chapterIndex + 1]
    }

    private fun generateChapterName(): String {
        val chapter = getEpisodeNameFromEpisode(currentChapter)
        if (chapter.contains(" ")) {
            val parts = chapter.split(" ")
            if (parts.size == 2) {
                return parts[0]
            } else if (parts.size >= 3) {
                return parts[0] + parts[parts.size - 1]
            }
        } else if (chapter.length > 5) {
            return chapter.substring(0, 4) + "..."
        }
        return chapter
    }

    private suspend fun savePosition() {
        withContext(Dispatchers.IO) {
            val layoutManager = recyclerView.layoutManager as? LinearLayoutManager
            layoutManager?.let {
                val scrollPosition = it.findFirstVisibleItemPosition()
                val topView = recyclerView.getChildAt(0)
                val topOffset = topView?.top ?: 0
                bookRepository.updateBookmarkById(book.id, currentChapter, scrollPosition,topOffset)
            }
        }
    }

    private fun scrollToTop() {
        (recyclerView.layoutManager  as LinearLayoutManager).scrollToPosition(0)
    }

    private fun scrollToPosition(position: Int, offset: Int) {
        (recyclerView.layoutManager  as LinearLayoutManager).scrollToPositionWithOffset(position, offset)
    }

    private fun toggleControlsVisibility() {
        if (isControlsVisible) {
            hideBars()
        } else {
            showBars()
        }
    }

    private fun hideBars() {
        topBar.visibility = View.GONE
        bottomBar.visibility = View.GONE
        isControlsVisible = false
        window.insetsController?.hide(WindowInsets.Type.systemBars())
    }

    private fun showBars() {
        topBar.visibility = View.VISIBLE
        bottomBar.visibility = View.VISIBLE
        isControlsVisible = true
    }

    private fun calculateBottomOffset(): Int {
        val layoutManager = recyclerView.layoutManager as LinearLayoutManager
        val lastVisibleItemPosition = layoutManager.findLastVisibleItemPosition()
        val lastVisibleItemView = layoutManager.findViewByPosition(lastVisibleItemPosition)

        val recyclerViewHeight = recyclerView.height
        val bottomOffset = if (lastVisibleItemView != null) {
            recyclerViewHeight - (lastVisibleItemView.bottom - lastVisibleItemView.top)
        } else {
            0
        }

        return bottomOffset
    }

    private fun smoothScrollToBottomWithOffset(offset: Int, speed: String) {
        val layoutManager = recyclerView.layoutManager as? LinearLayoutManager ?: return
        val smoothScroller = SmoothScroller(this, offset, speed)

        // 设置滚动到最后一项并添加底部偏移量
        smoothScroller.targetPosition = imageAdapter.itemCount - 1
        layoutManager.startSmoothScroll(smoothScroller)
    }

    override fun onSaveInstanceState(outState: Bundle) {
        super.onSaveInstanceState(outState)
        lifecycleScope.launch {
            savePosition()
        }
    }

    override fun onPause() {
        super.onPause()
        lifecycleScope.launch {
            savePosition()
        }
    }

    override fun onDestroy() {
        super.onDestroy()
        lifecycleScope.launch {
            savePosition()
            smbClientHelper.disconnect()
        }
    }

    private fun returnToLastActivity() {
        val resultIntent = Intent().apply {
            putExtra("bookmarkUpdated", book.title)
        }
        setResult(Activity.RESULT_OK, resultIntent)
        finish()
    }
}