import { GisState } from "../state.js";
/**
 * @namespace Utils
 */
const Utils = {};

/**
 * 
 * @param {string} galleryId The image gallery's id
 * @param {Object} imagesData
 * @returns {string}
 */
Utils.renderImages = function (galleryId, imagesData) {
    let content = `<div class="content has-text-centered">
        <p class="is-size-5 mt-3">Immagini</p>`;
    content += `
        <div style="max-width: 70%; margin: 0 auto">
            <p class="is-size-6 has-text-centered">Cliccare sull'immagine per aprire la gallery</p>
            <figure class="is-relative is-clickable has-text-centered" id="${galleryId}">
                <img src="img/${imagesData[0].filename}" width="300"/>
                <div class="icon overlay is-flex is-justify-content-center is-align-items-center">
                    <i class="is-flex fa fa-2x fa-play-circle"></i>
                </div>
            </figure>
        </div>
    </div>`;

    return content;
}
/**
 * @param {Object} imagesData
 * @param {HTMLElement} imageContainer
 * @param {Function} galleryGenerator The function that creates the image gallery
 * @param {string} galleryId The image gallery's id
 */
Utils.setImages = function(imagesData, imageContainer, galleryGenerator, galleryId) {
    imageContainer.innerHTML = Utils.renderImages(galleryId);
    galleryGenerator(galleryId, imagesData);
}

/**
 * 
 * @param {Object} data The component's data
 * @param {String} resourceUri The resource URI to be used for API calls
 * @returns {String} The table HTML
 */
Utils.generateDocsTable = async function(data, resourceUri) {
    let record = await Utils.fetchData(`${GisState.apiUrl}/${resourceUri}/${data.id}`);

    // TODO Horrible??
    if (record instanceof Error) return '<p class="has-text-centered">Nessun documento disponibile.</p>';

    const documentation = record.documents.filter(d => d.type === 'documentazione')
    const publications = record.documents.filter(d => d.type === 'pubblicazione');

    let content = `
        <div class="has-bottom-border">
            <div class="p-2">
                <table class="p-4 table is-fullwidth is-striped">
                    <thead>
                        <tr><th colspan=3 class="p-2 has-text-centered is-size-5">Documentazione di archivio</th>
                        <tr><th>Titolo</th><th>Luogo di conservazione</th><th>Download</th></tr>
                    </thead>
                    <tbody>
        `;

    for (const doc of documentation) {
        content += `
            <tr><td>${doc.title}</td><td>${doc.conservationPlace}</td><td><a class="button is-link has-text-white" href="docs/${doc.filename}">
                <i class="fa fa-download mr-2"></i> PDF
            </a></td></tr>
        `;
    }
    if (publications.length) {
        content += `
                </tbody>
                <thead>
                    <tr><th colspan=3 class="p-2 has-text-centered is-size-5">Pubblicazioni del progetto Carta Archeologica</th>
                    <tr><th>Titolo</th><th>Autori</th><th>Download</th></tr>
                </thead>
                <tbody>
        `;
        for (const doc of publications) {
            content += `
                <tr><td>${doc.title}</td><td>${doc.authors}</td><td><a class="button is-link has-text-white" href="docs/${doc.filename}">
                    <i class="fa fa-download mr-2"></i> PDF
                </a></td></tr>
            `;
        }
    }
    content += `
            </tbody>
            </table>
            </div>
        </div>
    `;

    if (publications.length === 0 && documentation.length === 0) {
        content = '<p class="has-text-centered">Nessun documento disponibile.</p>';
    }

    return content;
}

/**
 * 
 * @param {String} recordUri The record URI used for API calls 
 * @param {Number} recordId This record's ID
 * @returns {{citations:String,biblioElements:String[]}}
 */
Utils.buildBibliography = async function(recordUri, recordId) {
    let record = await Utils.fetchData(`${GisState.apiUrl}/${recordUri}/${recordId}`);
    let biblioElements = [];

    let citations = '';

    if (record.bibliography.length) {
        record.bibliography.forEach(record => {
            citations += `
                <span class="is-clickable has-text-link"
                    data-action="click->biblio#open"
                    id="cit-${record.id}">
                    ${record.citation.trim()}
                </span>
            `;

            citations += record.pages?.length ? `, ${record.pages};` : ';';
            
            biblioElements.push(`
                <div class="p-2 mt-2" id="ref-${record.id}">
                    <p class="p-3">${record.reference}</p>
                </div>
                `
            );
        });
    }

    const bibliography = {
        citations: citations.trim().slice(0, -1),
        biblioElements
    }

    return bibliography;
}

/**
 * Parse marker strings (pseudo-shortcodes) and convert them
 * to Stimulus links
 * @param {String} text - The content text from database
 */
Utils.parseMarkers = function(text) {
    const regex = /(?<marker>\[marker coords=\"(?<coords>[\d\s\.]+)\"\ ?(group=\"(?<group>\w+)\")?](?<content>[\s\S]+?)\[\/marker\])/mig;
    
    if (!text) return text;

    let matches = [...text.matchAll(regex)];

    if (matches.length) {
        matches.forEach(match => {
            const replacement = `<a class="has-text-link" data-action="marker#go modal#close tabs#reset marker#goAndOpen" data-controller="marker"
                data-marker-coords-value="${match.groups.coords}"
                data-marker-group-value="${match.groups.group}">${match.groups.content.trim()}</a>`;
            text = text.replace(match.groups.marker, replacement.trim());
        });
    }

    return text;
}

Utils.fetchData = async function(url) {
    return await fetch(url).then(res => res.ok ? res.json() : new Error())
        .catch(err => console.log(err));
}

export default Utils;