//
//  TitleTextField.swift

//
//  Created by Leon on 2025/7/18.
//

import SnapKit
import UIKit

class TitleTextField: UIView {
    // MARK: - Properties

    var titleLabel: UILabel
    var textfield: CLTextField
    var supportLabel: UILabel

    var placeholder: String? {
        didSet {
            textfield.placeholder = placeholder
        }
    }
    var errorMsg: String?
    var minLimit: Int = 0
    var maxLimit: Int = 0 {
        didSet{
            textfield.limit.maxCharacterNumber = maxLimit
        }
    }
    
    private var stackV: UIStackView
    private var tapQueryBlock: (() -> Void)?

    // MARK: - Initialization

    override init(frame: CGRect) {
        titleLabel = UILabel()
        textfield = CLTextField()
        supportLabel = UILabel()
        stackV = UIStackView()

        super.init(frame: frame)

        initialViews()
        setupEvent()
    }

    @available(*, unavailable)
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    // MARK: - Setup

    private func initialViews() {
        // Configure stack view
        stackV.axis = .vertical
        stackV.alignment = .leading
        stackV.spacing = 12
        addSubview(stackV)
        stackV.snp.makeConstraints { make in
            make.top.bottom.leading.trailing.equalTo(self)
        }

        // Configure title label
        titleLabel.font = CLSystemToken.typography(token: .tlm).font! // EPSystemToken.typography(.txtLabelM).font
        titleLabel.textColor = .c.ctpn

        // Configure text field
        

        // Configure support label
        supportLabel.numberOfLines = 0
        supportLabel.font = CLSystemToken.typography(token: .tbs).font!
        supportLabel.textColor = .c.ctsn

        // Default state
        supportLabel.isHidden = true

        // Add subviews to stack
        stackV.addArrangedSubview(titleLabel)
        stackV.addArrangedSubview(textfield)
        stackV.addArrangedSubview(supportLabel)

        // Additional constraints
        titleLabel.snp.makeConstraints { make in
            make.right.lessThanOrEqualTo(stackV)
        }

        textfield.snp.makeConstraints { make in
            make.leading.trailing.equalTo(stackV)
        }
    }

    private func setupEvent() {
        // No events in the original, kept as a placeholder
        
        textfield.addTarget(self, action: #selector(textDidChanged(_:)), for: .editingChanged)
    }

    // MARK: - Public Methods

    func showNormalSupportMsg(_ string: String) {
        supportLabel.isHidden = false
        supportLabel.textColor = .c.ctsn // EPSystemToken.tsn
        supportLabel.text = string
    }

    func showWarningMsg(_ string: String) {
        supportLabel.isHidden = false
        supportLabel.textColor = .c.cwvn // EPSystemToken.wvn
        supportLabel.text = string
    }

    func showErrorMsg(_ string: String) {
        supportLabel.isHidden = false
        supportLabel.textColor = .c.civn // EPSystemToken.color(.importantVariantNormal)
        supportLabel.text = string
        textfield.showAlwayErrorBorder()
    }

    func hideErrorInfo() {
        supportLabel.isHidden = true
        textfield.hideErrorBorder()
    }

    func titleAppendOptionalLabel() {
        // ...
    }

    func setupQueryBtn(block: @escaping () -> Void) {
        tapQueryBlock = block
        let button = UIButton(type: .custom)
        button.setImage(UIImage(named: "query_lightpurple"), for: .normal)
        button.contentMode = .center
        addSubview(button)

        let label = titleLabel
        button.snp.makeConstraints { make in
            make.centerY.equalTo(label)
            make.left.equalTo(label.snp.right).offset(-4)
            make.size.equalTo(CGSize(width: 44, height: 44))
        }

        button.addTarget(self, action: #selector(queryButtonTapped), for: .touchUpInside)
    }

    func setupEmailMode() {
        textfield.autocapitalizationType = .none
        textfield.autocorrectionType = .no
        textfield.keyboardType = .emailAddress
        textfield.placeholder = NSLocalizedString("email", comment: "")
        textfield.limit.maxCharacterNumber = 50
    }

    func setupPasswordMode() {
        textfield.autocapitalizationType = .none
        textfield.autocorrectionType = .no
        textfield.isSecureTextEntry = true
        textfield.keyboardType = .asciiCapable
        textfield.placeholder = NSLocalizedString("password", comment: "")
        textfield.limit.maxCharacterNumber = 15
        textfield.setupRightEyeButton()
        clipsToBounds = true
    }

    func verifyPsswordDataValid(isFinalStep: Bool) -> Bool {
        let text = textfield.text?.trimmingCharacters(in: .whitespacesAndNewlines) ?? ""

        if text.isEmpty {
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("hint_enter_password", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        if text.count < 6 || text.count > 15 {
            if isFinalStep || !textfield.isFirstResponder || text.count > 15 {
                showErrorMsg(NSLocalizedString("password_error_info", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        // Check for digits
        let numPattern = ".*\\d+.*"
        let numPred = NSPredicate(format: "SELF MATCHES %@", numPattern)
        if !numPred.evaluate(with: text) {
            print("Password must contain digits")
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("toast_password_need_6_15_characters", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        // Check for lowercase letters
        let lowerPattern = ".*[a-z]+.*"
        let lowerPred = NSPredicate(format: "SELF MATCHES %@", lowerPattern)
        if !lowerPred.evaluate(with: text) {
            print("Password must contain lowercase letters")
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("toast_password_need_6_15_characters", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        // Check for uppercase letters
        let upperPattern = ".*[A-Z]+.*"
        let upperPred = NSPredicate(format: "SELF MATCHES %@", upperPattern)
        if !upperPred.evaluate(with: text) {
            print("Password must contain uppercase letters")
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("toast_password_need_6_15_characters", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        hideErrorInfo()
        return true
    }

    func verifyOldPsswordDataValid(isFinalStep: Bool) -> Bool {
        let text = textfield.text?.trimmingCharacters(in: .whitespacesAndNewlines) ?? ""

        if text.isEmpty {
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("hint_enter_password", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        if text.count < 6 || text.count > 15 {
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("password_error_info", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        hideErrorInfo()
        return true
    }

    func verifyEmailDataValid(isFinalStep: Bool) -> Bool {
        let text = textfield.text ?? ""

        if text.isEmpty {
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("hint_enter_email", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        if !text.isValidEmail {
            if isFinalStep || !textfield.isFirstResponder {
                showErrorMsg(NSLocalizedString("email_format_incorrect", comment: ""))
            } else {
                hideErrorInfo()
            }
            return false
        }

        return true
    }

    func verifyNewStylePassword(isFinalStep: Bool) -> Bool {
        let text = textfield.text ?? ""
        let textEmpty = text.isEmpty

        var condition1 = true
        var condition2 = true
        var condition3 = true

        // Check length
        if text.count < 6 || text.count > 15 {
            condition1 = false
        }

        // Check for digits
        let numPattern = ".*\\d+.*"
        let numPred = NSPredicate(format: "SELF MATCHES %@", numPattern)
        if !numPred.evaluate(with: text) {
            print("Password must contain digits")
            condition2 = false
        }

        // Check for lowercase letters
        let lowerPattern = ".*[a-z]+.*"
        let lowerPred = NSPredicate(format: "SELF MATCHES %@", lowerPattern)
        if !lowerPred.evaluate(with: text) {
            print("Password must contain lowercase letters")
            condition3 = false
        }

        // Check for uppercase letters
        let upperPattern = ".*[A-Z]+.*"
        let upperPred = NSPredicate(format: "SELF MATCHES %@", upperPattern)
        if !upperPred.evaluate(with: text) {
            print("Password must contain uppercase letters")
            condition3 = false
        }

        let paragraphStyle = NSMutableParagraphStyle()
        paragraphStyle.lineSpacing = 4

        let normalAttributes: [NSAttributedString.Key: Any] = [
            .foregroundColor: UIColor.c.ctsn,
            .font: CLSystemToken.typography(token: .tbs).font!,
            .paragraphStyle: paragraphStyle,
        ]

        let condition1String = "• \(NSLocalizedString("password_count_greater_than_6", comment: ""))"
        let condition2String = "• \(NSLocalizedString("password_contain_numbers", comment: ""))"
        let condition3String = "• \(NSLocalizedString("password_contain_upper_lower_letters", comment: ""))"
        let full = "\(condition1String)\n\(condition2String)\n\(condition3String)"

        let attributedString = NSMutableAttributedString(string: full, attributes: normalAttributes)

        if !textEmpty {
            let greenAttributes: [NSAttributedString.Key: Any] = [.foregroundColor: UIColor.c.cpvn] // EPSystemToken.color(.positiveVariantNormal)
            let redAttributes: [NSAttributedString.Key: Any] = [.foregroundColor: UIColor.c.civn] // EPSystemToken.color(.importantVariantNormal)

            let range1 = (full as NSString).range(of: condition1String)
            let range2 = (full as NSString).range(of: condition2String)
            let range3 = (full as NSString).range(of: condition3String)

            attributedString.addAttributes(condition1 ? greenAttributes : redAttributes, range: range1)
            attributedString.addAttributes(condition2 ? greenAttributes : redAttributes, range: range2)
            attributedString.addAttributes(condition3 ? greenAttributes : redAttributes, range: range3)
        }

        supportLabel.isHidden = false
        supportLabel.attributedText = attributedString

        return condition1 && condition2 && condition3
    }
    
    // MARK: - Actions
    
    @objc private func textDidChanged(_ textField: UITextField) {
        
        if (textField.text ?? "").count < minLimit{
            if let msg = errorMsg{
                showErrorMsg(msg)
            }
        }else{
            hideErrorInfo()
        }
    }

    @objc private func queryButtonTapped() {
        tapQueryBlock?()
    }

    // MARK: - Responder

    override func becomeFirstResponder() -> Bool {
        textfield.becomeFirstResponder()
    }

    override func resignFirstResponder() -> Bool {
        textfield.resignFirstResponder()
    }
}
