import {
  isValidFieldSize,
  isValidInputTextField,
  isValidPhoneNumber,
  isValidPostcodeField,
  updateStylingError
} from "./utils/validation";
import errorMessages from "./utils/errorMesages";
import {scrollToElement, trimFields} from "./utils/helpers";

var Wick = window.Wick || {};

Wick.AddressBook = {
  el: {
    $addressBook: $('.address-book'),
    addressCard: '.address-card',
    addressCardInformation: '.address-card__information',
    deleteAddressModal: '.delete-modal',
    deleteAddressLink: '.link--delete',
    deleteModalContent: '.delete-modal .address-info__data',
    deleteModalContinue: '.delete-modal .btn-continue',
    addressForm: '.address-book__form',
    btnCancel: '.address-book__form [data-action="cancel-form"]',
    btnSaveForm: '.address-book__form [data-action="save-form"]',
    $firstName: $('#firstName'),
    $surName: $('#lastName'),
    $addressLookupQuery: $('#address-lookup-query'),
    $addressLine1: $('#address-line-1'),
    $addressLine2: $('#address-line-2'),
    $townCity: $('#town-city'),
    $postCode: $('#postcode_additional'),
    $mobilePhone: $('#mobile-telephone'),
    $homePhone: $('#home-telephone'),
    formRow: '.form-row',
    formRowError: '.form-row__error'
  },
  getFieldsConfigurations: function () {
    return [
      {
        input: Wick.AddressBook.el.$firstName,
        validator: [isValidFieldSize, isValidInputTextField],
        error: errorMessages.errorName,
      },
      {
        input: Wick.AddressBook.el.$surName,
        validator: [isValidFieldSize, isValidInputTextField],
        error: errorMessages.errorSurname,
      },
      {
        input: Wick.AddressBook.el.$addressLookupQuery,
        validator: isValidFieldSize,
        error: errorMessages.errorAddress,
      },
      {
        input: Wick.AddressBook.el.$addressLine1,
        validator: [isValidFieldSize, isValidInputTextField],
        error: errorMessages.errorAddressLine1,
      },
      {
        input: Wick.AddressBook.el.$addressLine2,
        validator: isValidInputTextField,
        error: errorMessages.errorAddressLine2,
        required: false
      },
      {
        input: Wick.AddressBook.el.$townCity,
        validator: [isValidFieldSize, isValidInputTextField],
        error: errorMessages.errorTown,
      },
      {
        input: Wick.AddressBook.el.$postCode,
        validator: [isValidFieldSize, isValidPostcodeField],
        error: errorMessages.errorPostcode,
      },
      {
        input: Wick.AddressBook.el.$mobilePhone,
        validator: [isValidFieldSize, isValidPhoneNumber],
        error: [errorMessages.errorMobilePhoneEmpty, errorMessages.errorMobilePhone],
      },
      {
        input: Wick.AddressBook.el.$homePhone,
        validator: isValidPhoneNumber,
        error: errorMessages.errorHomePhone,
        required: false
      }
    ];
  },
  validateInput: function (input, validatorFunction, errorMsg) {
    const value = $(input).val();
    let isValid = true;

    const validators = Array.isArray(validatorFunction) ? validatorFunction : [validatorFunction];
    const errors = Array.isArray(errorMsg) ? errorMsg : [errorMsg];

    for (let index = 0; index < validators.length; index++) {
      const validator = validators[index];
      const isFieldValid = validator(value);

      if (!isFieldValid) {
        const currentErrorMessage = index < errors.length ? errors[index] : errors[0];
        updateStylingError(input, isFieldValid, currentErrorMessage);

        isValid = false;
        break;
      }
    }

    if (isValid) {
      updateStylingError(input, true, '');
    }

    return isValid;
  },
  validateForm: function () {
    trimFields();
    let isValid = true;
    const fields = Wick.AddressBook.getFieldsConfigurations();

    fields.forEach((field) => {
      const value = field.input.val();
      const required = field.required !== false;

      if (!required && !value) {
        updateStylingError(field.input, true, '');
        return;
      }

      isValid =
        Wick.AddressBook.validateInput(field.input, field.validator, field.error) && isValid;
    });

    return isValid;
  },
  handleFormSubmit: function () {
    $(Wick.AddressBook.el.addressForm).on('submit', function (event) {
      event.preventDefault();

      if (Wick.AddressBook.validateForm()) {
        Wick.LeaveEvent.proceedBrowserLeave = false;
        $(Wick.AddressBook.el.btnSaveForm).attr('disabled', true);
        event.target.submit();
      } else {
        const targetElement = $(Wick.AddressBook.el.formRowError).closest(Wick.AddressBook.el.formRow)[0];

        scrollToElement(targetElement);
      }
    });
  },
  deleteAddress() {
    $(Wick.AddressBook.el.deleteAddressLink).on('click', function (e) {
      e.preventDefault();

      const $clickedLink = $(this);
      const href = $clickedLink.attr('data-link');

      const $addressCard = $(this).closest(Wick.AddressBook.el.addressCard);
      const cardInfo = $addressCard.find(Wick.AddressBook.el.addressCardInformation).html();

      $(Wick.AddressBook.el.deleteModalContent).html(cardInfo);

      $(Wick.AddressBook.el.deleteModalContinue).on('click', function () {
        window.location.href = href;
      });

      Wick.AddressBook.showModal();
    });
  },
  showModal() {
    $(Wick.AddressBook.el.deleteAddressModal).modal('show');
  },
  clearModal() {
    $(Wick.AddressBook.el.deleteAddressModal).on('hidden.bs.modal', function () {
      $(this).find(Wick.AddressBook.el.addressCardInformation).html('');
    });
  },
  init () {
    Wick.LeaveEvent.bindEvent(
      Wick.AddressBook.el.addressForm,
      Wick.AddressBook.el.btnCancel,
    );
    Wick.AddressBook.deleteAddress();
    Wick.AddressBook.clearModal();
    Wick.AddressBook.handleFormSubmit();
  }
}

$(document).ready(function () {
  if (!Wick.AddressBook.el.$addressBook.length) {
    return;
  }

  Wick.AddressBook.init();
});
