import Foundation
import SwiftUI
import XMPPSwift

struct RegistrationScreen: View {
    @EnvironmentObject var store: AppStore
    private var state: RegistrationState { store.state.registrationState }

    private enum Field {
        case jid
        case password
    }

    @FocusState private var focus: Field?

    // @State private var jidStr: String = "testman_n@conversations.im "
    // @State private var pass: String = "testman123"
    // @State private var jidStr: String = "testman_n1@test.uwu.do"
    // @State private var pass: String = "testman123"
    // @State private var jidStr: String = "testman_n1@yax.im"
    // @State private var pass: String = "testman123"
    @State private var jidStr: String = ""
    @State private var pass: String = ""

    var body: some View {
        VStack {
            Spacer()
            HStack {
                VStack(alignment: .leading) {
                    //
                    Text(L10n.Accounts.Add.Exist.title)
                        .font(.head1)
                        .foregroundColor(.Main.black)
                        .onTapGesture {
                            focus = nil
                        }
                    Text(L10n.Accounts.Add.Exist.Prompt.jid)
                        .font(.body1)
                        .foregroundColor(.Main.gray)
                        .padding(.top)
                    UniversalInputCollection.TextField(
                        prompt: L10n.Accounts.Add.Exist.Hint.jid,
                        text: $jidStr,
                        focus: $focus,
                        fieldType: .jid,
                        contentType: .emailAddress,
                        keyboardType: .emailAddress,
                        submitLabel: .next,
                        action: {
                            focus = nil
                        }
                    )

                    switch state.serverState {
                    case .connecting:
                        ServerConnectingIndicator(state: .connecting)

                    case .connected:
                        ServerConnectingIndicator(state: .connected)

                    case .error:
                        ServerConnectingIndicator(state: .error)

                    case .idle:
                        EmptyView()
                    }

                    //
                    if state.serverState == .connected {
                        Text(L10n.Accounts.Add.Exist.Prompt.password)
                            .font(.body2)
                            .foregroundColor(.Main.gray)
                        UniversalInputCollection.SecureField(
                            prompt: L10n.Accounts.Add.Exist.Hint.password,
                            text: $pass,
                            focus: $focus,
                            fieldType: .password,
                            submitLabel: .done,
                            action: {
                                focus = nil
                            }
                        )
                    }
                }
            }
            .padding()
            VStack(spacing: 8) {
                Text(L10n.Accounts.Add.or)
                    .font(.body1)
                    .foregroundColor(.Main.gray)
                Button {
                    store.dispatch(.registrationAction(.targetJidChanged(nil)))
                    jidStr = ""
                    pass = ""
                } label: {
                    Text(L10n.Accounts.Add.Exist.Btn.link)
                        .font(.body1)
                        .foregroundColor(.Tango.orangeMedium)
                }
                .disabled(state.serverState == .connecting)
            }

            Spacer()
            if state.clientState == .loginError {
                Text(L10n.Accounts.Add.Exist.loginError)
                    .font(.head2)
                    .foregroundColor(.Tango.redMedium)
                Spacer()
            }
            Button {
                focus = nil
                if let jid = try? JID(jidStr) {
                    xmpp.doAction(.init(jid, .login(pass)))
                    store.dispatch(.registrationAction(.clientStateChanged(.tryingLogin)))
                }
            } label: {
                if state.clientState == .tryingLogin {
                    ProgressView()
                        .progressViewStyle(CircularProgressViewStyle(tint: .white))
                        .scaleEffect(0.5, anchor: .center)
                } else {
                    Text(L10n.Accounts.Add.Exist.Btn.main)
                }
            }
            .buttonStyle(PrimaryButtonStyle())
            .padding(.horizontal, 80)
            .padding(.bottom, 60)
            .disabled(state.serverState != .connected || pass.isEmpty)
        }
        .ignoresSafeArea()
        .background(Color.Main.backgroundLight)
        .onTapGesture {
            focus = nil
        }
        .onChange(of: focus) { val in
            store.dispatch(.registrationAction(.clientStateChanged(.idle)))
            if val != .jid {
                let jid = try? JID(jidStr)
                store.dispatch(.registrationAction(.targetJidChanged(jid)))
            }
        }
    }

    var isFilled: Bool {
        !pass.isEmpty && UniversalInputCollection.Validators.email(jidStr) == nil
    }
}

#if DEBUG
    struct RegistrationScreen_Previews: PreviewProvider {
        static var previews: some View {
            showPreview(stateConfig: { state in
                state.currentFlow = .registration
                state.registrationState.navigation = .addNew
                state.registrationState.serverState = .connected
            })
        }
    }
#endif
