package com.miya.fastcashier.ui

import android.content.Intent
import android.os.Bundle
import android.text.Editable
import android.text.TextUtils
import android.text.TextWatcher
import android.view.View
import android.view.inputmethod.EditorInfo
import android.widget.EditText
import androidx.appcompat.app.AppCompatActivity
import androidx.lifecycle.Observer
import androidx.lifecycle.ViewModelProvider
import com.miya.fastcashier.databinding.ActivityLoginBinding
import com.miya.fastcashier.service.AccountService
import com.miya.fastcashier.utils.clickWithTrigger
import com.miya.fastcashier.utils.withTrigger
import com.miya.fastcashier.viewmodel.LoginViewModel
import com.tencent.mmkv.MMKV




class LoginActivity : AppCompatActivity() {

    private lateinit var loginViewModel: LoginViewModel
    private lateinit var binding: ActivityLoginBinding

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityLoginBinding.inflate(layoutInflater)
        setContentView(binding.root)

        val username = binding.username
        val password = binding.password
        val loading = binding.loading
        val login = binding.login
        val tvErrInfo = binding.tvErrInfo

        val kv = MMKV.defaultMMKV()

        loginViewModel = ViewModelProvider(this)
            .get(LoginViewModel::class.java)

        loginViewModel.loginLiveData.observe(this) { result ->

            loading.visibility = View.GONE

            result.getOrElse {
                tvErrInfo.text = it.message
                tvErrInfo.visibility = View.VISIBLE
                return@observe
            }

            result.getOrNull().also {
                it?.let { it1 ->

                    kv.encode("username",username.text.toString())
                    kv.encode("password",password.text.toString())

                    AccountService.setUserName(username.text.toString())
                    AccountService.setAccountInfo(it1)

                    val intent = Intent()
                    intent.setClass(this@LoginActivity, MainActivity::class.java)
                    startActivity(intent)

                    finish()
                }
            }
        }

        loginViewModel.loginFormState.observe(this@LoginActivity, Observer {
            val loginState = it ?: return@Observer

            login.isEnabled = loginState.isDataValid

            if (loginState.usernameError != null) {
                username.error = getString(loginState.usernameError)
            }
            if (loginState.passwordError != null && !TextUtils.isEmpty(password.text)) {
                password.error = getString(loginState.passwordError)
            }
        })

        username.apply {
            afterTextChanged {
                loginViewModel.loginDataChanged(
                    username.text.toString(),
                    password.text.toString()
                )
            }
            setOnEditorActionListener { _, actionId, _ ->
                when (actionId) {
                    EditorInfo.IME_ACTION_NEXT ->{
                        password.requestFocus()
                        password.text?.let { password.setSelection(it.length) };
                    }
                }
                false
            }
        }

        password.apply {
            afterTextChanged {
                loginViewModel.loginDataChanged(
                    username.text.toString(),
                    password.text.toString()
                )
            }

            setOnEditorActionListener { _, actionId, _ ->
                when (actionId) {
                    EditorInfo.IME_ACTION_DONE ->{
                        loading.visibility = View.VISIBLE;
                        loginViewModel.login(
                            username.text.toString(),
                            password.text.toString()
                        )
                    }
                }
                false
            }

            binding.login.clickWithTrigger {
                loading.visibility = View.VISIBLE
                loginViewModel.login(username.text.toString(), password.text.toString())
            }
        }

         kv.decodeString("username")?.let {
             username.setText(it)
         }
        kv.decodeString("password")?.let {
            password.setText(it)
        }

        if(!TextUtils.isEmpty(username.text)
            && !TextUtils.isEmpty(password.text)){
            loading.visibility = View.VISIBLE;
            loginViewModel.login(username.text.toString(), password.text.toString())
        }

    }

    /**
     * Extension function to simplify setting an afterTextChanged action to EditText components.
     */
    private fun EditText.afterTextChanged(afterTextChanged: (String) -> Unit) {
        this.addTextChangedListener(object : TextWatcher {
            override fun afterTextChanged(editable: Editable?) {
                afterTextChanged.invoke(editable.toString())
            }

            override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {}

            override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {}
        })
    }
}


