<template>
    <div
        ref="toast"
        class="border-1 border-gray-2 bg-white rounded-md p-4 mt-4 mb-4 pointer-events-auto"
        :style="styles">
        <div :class="['max-w-48', 'border-l-5', 'pl-4', 'relative', colour]">
            <svg
                xmlns="http://www.w3.org/2000/svg"
                viewBox="0 -960 960 960"
                class="h-4 absolute right-0 hover:text-red-7 cursor-pointer"
                @click="handleClickClose">
                <path
                    d="m249-207-42-42 231-231-231-231 42-42 231 231 231-231 42 42-231 231 231 231-42 42-231-231-231 231Z"
                    fill="currentColor" />
            </svg>
            <h5 class="mt-0 mb-2" v-if="title && title.length > 0">
                {{ title }}
            </h5>
            <div class="flex">
                <svg
                    v-if="props.loader"
                    xmlns="http://www.w3.org/2000/svg"
                    viewBox="0 0 24 24"
                    class="spin">
                    <path d="M12,4V2A10,10 0 0,0 2,12H4A8,8 0 0,1 12,4Z" />
                </svg>
                <p class="text-xs">
                    {{ content }}
                </p>
            </div>
        </div>
    </div>
</template>

<script setup lang="ts">
import { onMounted, ref } from "vue";
import { useToastStore } from "../store/ToastStore";

const props = defineProps({
    id: {
        type: Number,
        required: true,
    },
    title: {
        type: String,
        default: "",
        required: false,
    },
    type: {
        type: String,
        default: "primary",
        required: false,
    },
    content: {
        type: String,
        required: true,
    },
    loader: {
        type: Boolean,
        required: false,
        default: false,
    },
});

const toastStore = useToastStore();
const toast = ref(null);
let colour = "";
let height = 40;
let hideTimeoutID: number | null = null;

const styles = ref({
    transition: "opacity 0.2s ease-in, margin 0.2s ease-in",
    opacity: 0,
    marginTop: "40px",
});

switch (props.type) {
    case "primary":
        colour = "border-sky-5";
        break;
    case "danger":
        colour = "border-red-7";
        break;
    case "success":
        colour = "border-green-7";
        break;
    case "warning":
        colour = "border-yellow-4";
        break;
}

const handleClickClose = () => {
    if (hideTimeoutID != null) {
        window.clearTimeout(hideTimeoutID);
        hideTimeoutID = null;
    }
    removeToast();
};

const removeToast = () => {
    styles.value.opacity = 0;
    styles.value.marginTop = `-${height}px`;
    window.setTimeout(() => {
        toastStore.clearToast(props.id);
    }, 500);
};

if (!props.loader) {
    onMounted(() => {
        window.setTimeout(() => {
            styles.value.opacity = 1;
            styles.value.marginTop = "0";

            if (toast.value != null) {
                const styles = window.getComputedStyle(toast.value);
                const marginBottom = parseFloat(styles.marginBottom);
                height = toast.value.offsetHeight + marginBottom || 0;
            }

            hideTimeoutID = window.setTimeout(() => {
                hideTimeoutID = null;
                removeToast();
            }, 8000);
        }, 200);
    });
}
</script>
