<script setup lang="ts">
import type { ChartData } from 'chart.js';
import { Bar } from 'vue-chartjs';
import { colors } from '@/types/graphs';
import type { Iteration } from '@/types/perceptron';

const props = defineProps<{
    iterations: Iteration[];
}>();

/**
 * Return the datasets of the iterations with the form { label: `Exemple ${exampleIndex}`, data: [error for iteration 1, error for iteration 2, ...] }
 */
function getPerceptronErrorsPerIteration(): ChartData<
    'bar',
    (number | [number, number] | null)[]
>[] {
    const datasets: ChartData<'bar', (number | [number, number] | null)[]>[] =
        [];

    const backgroundColors = colors;

    props.iterations.forEach((iteration) => {
        const exampleLabel = `Exemple ${iteration.exampleIndex}`;
        let dataset = datasets.find((d) => d.label === exampleLabel);
        if (!dataset) {
            dataset = {
                label: exampleLabel,
                data: [],
                backgroundColor:
                    backgroundColors[
                        iteration.exampleIndex % backgroundColors.length
                    ],
            };
            datasets.push(dataset);
        }
        dataset.data.push(iteration.error);
    });

    // Sort dataset by label (Exemple 0, Exemple 1, ...)
    datasets.sort((a, b) => {
        const aIndex = parseInt(a.label.split(' ')[1]);
        const bIndex = parseInt(b.label.split(' ')[1]);
        return aIndex - bIndex;
    });

    return datasets;
}
</script>

<template>
    <Bar
        class="flex"
        :options="{
            responsive: true,
            maintainAspectRatio: true,
            plugins: {
                title: {
                    display: true,
                    text: 'Nombre d\'erreurs par itération',
                },
            },
            scales: {
                x: {
                    stacked: true,
                    min: 0,
                },
                y: {
                    stacked: true,
                    beginAtZero: true,
                },
            },
        }"
        :data="{
            labels: props.iterations.reduce((labels, iteration) => {
                if (!labels.includes(`Itération ${iteration.iteration}`)) {
                    labels.push(`Itération ${iteration.iteration}`);
                }
                return labels;
            }, [] as string[]),
            datasets: getPerceptronErrorsPerIteration(),
        }"
    />
</template>
