<template>
  <q-dialog ref="dialogRef" @hide="onDialogHide">
    <q-card class="q-dialog-plugin dialog-form-card treasury-dialog-card">
      <DefaultDialogHeader
        :title="launch ? 'Editar movimentação' : 'Nova movimentação'"
        @close="onDialogCancel"
      />

      <DefaultForm
        ref="formRef"
        @submit="onOKClick"
      >
        <q-scroll-area
          ref="scrollAreaRef"
          class="dialog-form-scroll dialog-form-scroll--sm"
        >
          <q-card-section class="row q-col-gutter-md q-px-lg q-pt-md q-pb-sm">
            <DefaultSelect
              v-model="form.transaction_type"
              v-model:error="validationErrors.transaction_type"
              class="col-12"
              emit-value
              label="Tipo"
              map-options
              outlined
              :options="transactionTypeOptions"
              :rules="[inputRules.required]"
            />

            <DefaultInput
              v-model="form.description"
              v-model:error="validationErrors.description"
              class="col-12"
              label="Descrição"
              outlined
              :rules="[inputRules.required, maxLengthRule(1000)]"
            />

            <DefaultCurrencyInput
              v-model="form.amount"
              v-model:error="validationErrors.amount"
              class="col-12 col-sm-6"
              label="Valor"
              outlined
              :rules="[inputRules.required, positiveAmountRule]"
            />

            <DefaultInputDatePicker
              v-model="form.launch_date"
              v-model:error="validationErrors.launch_date"
              v-model:untreated-date="form.launch_date_iso"
              class="col-12 col-sm-6"
              label="Data"
            />
          </q-card-section>
        </q-scroll-area>

        <q-card-actions
          align="right"
          class="q-px-lg q-pt-md q-pb-lg q-gutter-sm"
        >
          <q-btn
            color="primary"
            label="Cancelar"
            no-caps
            outline
            @click="onDialogCancel"
          />

          <q-btn
            color="primary"
            label="Salvar"
            no-caps
            type="submit"
            :loading="loading"
          />
        </q-card-actions>
      </DefaultForm>
    </q-card>
  </q-dialog>
</template>

<script setup>
import {
  createTreasuryLaunchMe,
  updateTreasuryLaunchMe,
} from "src/api/treasury";

import { useDialogPluginComponent } from "quasar";
import { useForm } from "src/composables/useForm";
import { useInputRules } from "src/composables/useInputRules";
import { useScroll } from "src/composables/useScroll";
import { useSubmitHandler } from "src/composables/useSubmitHandler";
import { useTemplateRef } from "vue";

import DefaultCurrencyInput from "src/components/defaults/DefaultCurrencyInput.vue";
import DefaultDialogHeader from "src/components/defaults/DefaultDialogHeader.vue";
import DefaultForm from "src/components/defaults/DefaultForm.vue";
import DefaultInput from "src/components/defaults/DefaultInput.vue";
import DefaultInputDatePicker from "src/components/defaults/DefaultInputDatePicker.vue";
import DefaultSelect from "src/components/defaults/DefaultSelect.vue";

defineEmits([...useDialogPluginComponent.emits]);

const props = defineProps({
  accountId: {
    type: Number,
    required: true,
  },
  launch: {
    type: Object,
    default: null,
  },
});

const { dialogRef, onDialogHide, onDialogOK, onDialogCancel } =
  useDialogPluginComponent();

const { inputRules } = useInputRules();
const { scrollToComponent } = useScroll();

const formRef = useTemplateRef("formRef");
const scrollAreaRef = useTemplateRef("scrollAreaRef");

const transactionTypeOptions = [
  {
    label: "Entrada",
    value: "entrada",
  },
  {
    label: "Saída",
    value: "saida",
  },
];

const { form, getUpdatedFields } = useForm({
  amount: props.launch?.amount ?? 0,
  description: props.launch?.description ?? "",

  launch_date: props.launch?.launch_date
    ? props.launch.launch_date.split("-").reverse().join("/")
    : new Date().toLocaleDateString("pt-BR"),

  launch_date_iso:
    props.launch?.launch_date ?? new Date().toISOString().slice(0, 10),

  transaction_type: props.launch?.transaction_type ?? "entrada",
});

const maxLengthRule = (max) => (value) =>
  String(value ?? "").length <= max ||
  `Informe no máximo ${max} caracteres.`;

const positiveAmountRule = (value) =>
  Number(value) > 0 || "Informe um valor maior que zero.";

const {
  loading,
  validationErrors,
  execute,
} = useSubmitHandler({
  containerRef: scrollAreaRef,
  formRef,
  onSuccess: () => {
    onDialogOK(true);
  },
  scrollFn: scrollToComponent,
});

const onOKClick = async () => {
  const payload = {
    account_id: props.accountId,
    amount: form.amount,
    description: form.description,
    launch_date: form.launch_date_iso,
    transaction_type: form.transaction_type,
  };

  await execute(() => {
    if (!props.launch) {
      return createTreasuryLaunchMe(payload);
    }

    const changedFields = getUpdatedFields.value;
    const updatePayload = {};

    if ("transaction_type" in changedFields) {
      updatePayload.transaction_type = form.transaction_type;
    }

    if ("description" in changedFields) {
      updatePayload.description = form.description;
    }

    if ("amount" in changedFields) {
      updatePayload.amount = form.amount;
    }

    if (
      "launch_date_iso" in changedFields ||
      "launch_date" in changedFields
    ) {
      updatePayload.launch_date = form.launch_date_iso;
    }

    return updateTreasuryLaunchMe(
      props.launch.id,
      updatePayload,
    );
  });
};
</script>

<style scoped>
.treasury-dialog-card {
  width: 480px;
  max-width: calc(100vw - 32px);
}
</style>