import {
    athenaConfig,
    athenaConfigOptions
} from '../../../global/athena-config.js';

import {
    downscaleImageQuality,
    setTemporaryVisualImage,
    storeImageToIndexedDb
} from './visual-similarity-search.js';

import { handleCloseCameraElements } from './camera-capture/camera-capture-helper.js';

const globalElementsObject = () =>
{
    return {
        pasteUrlInputContainer: document.querySelector('.visual-similarity__paste-url-input-container'),
        pasteUrlInput: document.querySelector('#visual-similarity__input'),
        pasteUrlClipboard: document.querySelector('#visual-similarity__paste-url-paste-icon'),
        pasteUrlContainer: document.querySelector('#visual-similarity__paste-url-search-container'),
        pasteUrlXIcon: document.querySelector('#visual-similarity__paste-url-x-icon'),
        pasteUrlSearch: document.querySelector('.visual-similarity__paste-url-search-label'),
        pasteUrlError: document.querySelector('.visual-similarity__paste-url-error-message'),
        previewImage: document.querySelector('#preview-image'),
        infoContainer: document.querySelector('.visual-similarity-info__container')
    }
}

const initializePasteFromClipboard = () =>
{
    const {
        pasteUrlInput,
        pasteUrlXIcon,
        pasteUrlClipboard
    } = globalElementsObject();

    pasteUrlClipboard?.addEventListener('click', async () => {
        try {
            if(!pasteUrlInput) return;

            removeError();
            pasteUrlInput.value = await navigator.clipboard.readText();

            showCancelInputButton(
                pasteUrlInput,
                pasteUrlXIcon,
                pasteUrlClipboard
            );
        } catch (error) {
            console.error(`AthenaXAI: Issue with paste from clipboard: ${error}`);
        }
    })
}

const validateUrl = (url) =>
{
    const pattern = /(https?:\/\/.*\.(?:png|jpg))/i;
    return pattern.test(url);
}

const validateInput = (pasteUrlInput) =>
{
    if(!pasteUrlInput.length) {
        return [
            false,
            'That link is not an image'
        ]
    }

    const isUrlValid = validateUrl(pasteUrlInput);

    return [
        isUrlValid,
        !isUrlValid ? 'That link is not an image' : ''
    ]
}

const fetchImageFromUrl = async (pasteUrlInput) =>
{
    try {
        const response = await fetch(`${athenaConfig.pasteUrlExternalProxy}${pasteUrlInput}`);
        if (!response.ok) {
            console.error(`AthenaXAi: Failed to fetch image: ${response.statusText}`);
            return null;
        }

        const blob = await response.blob();

        return new Promise((resolve, reject) => {
            const reader = new FileReader();
            reader.onloadend = () => resolve(reader.result);
            reader.onerror = () => reject('AthenaXAi: Error converting image to base64');
            reader.readAsDataURL(blob);
        });
    } catch (error) {
        console.error(`AthenaXAi: Error fetching image from url: ${error}`);
        return null;
    }
};

const initializePasteUrlSearch = () =>
{
    const {
        pasteUrlSearch,
        pasteUrlInput,
        pasteUrlError,
        previewImage,
        infoContainer,
        pasteUrlInputContainer
    } = globalElementsObject();

    pasteUrlInput?.addEventListener('keydown', function(event){
        if(event.keyCode == 13){
            window.setTimeout(function(){
                pasteUrlSearch?.click();
            }, 100)
        }
    });

    pasteUrlSearch?.addEventListener('click', async () => {
        sessionStorage.removeItem('athenaVisualConversionChannel');

        const [valid, message] = validateInput(pasteUrlInput.value);
        if(!valid) {
            if(!pasteUrlError) return;

            pasteUrlError?.classList.contains('athena-helper-hide') &&
            pasteUrlError?.classList.remove('athena-helper-hide');

            !pasteUrlInputContainer?.classList.contains('visual-similarity__paste-url-input-error') &&
            pasteUrlInputContainer?.classList.add('visual-similarity__paste-url-input-error');

            pasteUrlError.innerHTML = message;
            return;
        }

        sessionStorage.setItem('athenaVisualConversionChannel', 'image_url');

        const base64Image = await fetchImageFromUrl(pasteUrlInput.value);
        if(!base64Image) {
            if(!pasteUrlError) return;

            pasteUrlError?.classList.contains('athena-helper-hide') &&
            pasteUrlError?.classList.remove('athena-helper-hide');

            !pasteUrlInputContainer?.classList.contains('visual-similarity__paste-url-input-error') &&
            pasteUrlInputContainer?.classList.add('visual-similarity__paste-url-input-error');

            pasteUrlError.innerHTML = 'Fetching image failed <span style="font-size: 25px;">◔̯◔</span>';
            return;
        }

        downscaleImageQuality(
            base64Image,
            athenaConfigOptions.imageQuality,
            async (result) => {
                await setTemporaryVisualImage(result);
                await storeImageToIndexedDb(false, result);
                handleCloseCameraElements(true);

                previewImage.src = result;

                athenaConfigOptions.cropper?.destroy();
                athenaConfigOptions.cropper = new athenaConfigOptions.cropperInstance(previewImage, {
                    viewMode: 2,
                    aspectRatio: 'Free',
                    minContainerHeight: 300,
                    minCanvasHeight: 300,
                    autoCropArea: 0.99
                });

                infoContainer?.classList.add('athena-helper-hide');
            });

    });
}

export const removeError = () =>
{
    const { pasteUrlError, pasteUrlInputContainer} = globalElementsObject();

    if(!pasteUrlError) return;
    pasteUrlError.innerText = '';

    !pasteUrlError?.classList.contains('athena-helper-hide') &&
    pasteUrlError?.classList.add('athena-helper-hide');

    pasteUrlInputContainer?.classList.contains('visual-similarity__paste-url-input-error') &&
    pasteUrlInputContainer?.classList.remove('visual-similarity__paste-url-input-error');
}

const showCancelInputButton = (
    pasteUrlInput,
    pasteUrlXIcon,
    pasteUrlClipboard
) =>
{
    const valueLength = pasteUrlInput.value.length > 0;
    if(valueLength) {
        pasteUrlXIcon?.classList.contains('athena-helper-hide') &&
        pasteUrlXIcon?.classList.remove('athena-helper-hide');

        !pasteUrlClipboard?.classList.contains('athena-helper-hide') &&
        pasteUrlClipboard?.classList.add('athena-helper-hide');
    } else {
        !pasteUrlXIcon?.classList.contains('athena-helper-hide') &&
        pasteUrlXIcon?.classList.add('athena-helper-hide');

        pasteUrlClipboard?.classList.contains('athena-helper-hide') &&
        pasteUrlClipboard?.classList.remove('athena-helper-hide');
    }
}

const cancelInputEventListener = () =>
{
    const {
        pasteUrlInput,
        pasteUrlXIcon,
        pasteUrlClipboard
    } = globalElementsObject();

    pasteUrlXIcon?.addEventListener('click', () => {
        pasteUrlInput.value = '';

        removeError();
        showCancelInputButton(
            pasteUrlInput,
            pasteUrlXIcon,
            pasteUrlClipboard
        );
    });
}

const removeErrorEventListener = () =>
{
    const {
        pasteUrlInput,
        pasteUrlXIcon,
        pasteUrlClipboard
    } = globalElementsObject();

    pasteUrlInput?.addEventListener('keydown', () => {
        removeError();
        showCancelInputButton(
            pasteUrlInput,
            pasteUrlXIcon,
            pasteUrlClipboard
        );
    });
}

const initializeDragAndDropText = () =>
{
    document.addEventListener('AthenaDragAndDropTextEvent', (event) => {
        const {
            pasteUrlInput,
            pasteUrlXIcon,
            pasteUrlClipboard
        } = globalElementsObject();

        const {
            text
        } = event.detail;

        pasteUrlInput.value = text;

        removeError();
        showCancelInputButton(
            pasteUrlInput,
            pasteUrlXIcon,
            pasteUrlClipboard
        );
    });
}

export default function inputImagePasteUrl()
{
    const {
        pasteUrlContainer
    } = globalElementsObject();

    if(athenaConfig.visualSearchPasteUrl) {
        pasteUrlContainer.classList.contains('athena-helper-hide') &&
        pasteUrlContainer.classList.remove('athena-helper-hide');

        initializeDragAndDropText();
        initializePasteFromClipboard();
        initializePasteUrlSearch();
        removeErrorEventListener();
        cancelInputEventListener();
    } else {
        !pasteUrlContainer.classList.contains('athena-helper-hide') &&
        pasteUrlContainer.classList.add('athena-helper-hide');
    }
}