import React, { useState, useRef, useEffect } from 'react';
import { useMutation } from '@apollo/react-hooks';
import cx from 'classnames';

import { RemoveSelectedSong, RemoveSelectedSongVariables } from 'src/definitions/RemoveSelectedSong';
import REMOVE_SELECTED_SONG from 'src/mutations/removeSelectedSong.gql';
import { useComparisonFilters } from 'src/queries';
import SoundRecordingSearch from 'src/components/soundRecordingSearch';
import SelectSong from './selectSong/SelectSong';
import SelectedSong from './selectedSong';


const CLASSNAME = 'SongSelection';
const CLASSNAME_SEARCH = `${CLASSNAME}-search`;
const CLASSNAME_SEARCH_COMPONENT = `${CLASSNAME_SEARCH}-component`;

const SongSelection = () => {
    const [isSearchVisible, setSearchVisibility] = useState(false);
    const searchRef = useRef<HTMLDivElement>(null);
    const { selectedSongIds } = useComparisonFilters();
    const [removeSelectedSong] = useMutation<RemoveSelectedSong, RemoveSelectedSongVariables>(REMOVE_SELECTED_SONG);

    const hideSearch = (e: Event) => {
        if (searchRef.current && !searchRef.current.contains(e.target as Element))
            setSearchVisibility(false);
    };
    const captureEscape = (e: KeyboardEvent) => {
        if (e.key === 'Escape' || e.key === 'Esc')
            setSearchVisibility(false);
    };
    const removeEventHandlers = () => {
        document.removeEventListener('click', hideSearch, true);
        document.removeEventListener('keydown', captureEscape, true);
    };

    useEffect(() => {
        if (isSearchVisible) {
            document.addEventListener('click', hideSearch, true);
            document.addEventListener('keydown', captureEscape, true);
        } else
            removeEventHandlers();
        return () => removeEventHandlers();
    }, [isSearchVisible]);
    useEffect(() => (
        () => removeEventHandlers()
    ), []);

    const searchContainerClass = cx(
        CLASSNAME_SEARCH,
        { [`${CLASSNAME_SEARCH}-centered`]: selectedSongIds.length === 0 }
    );
    const searchComponentClass = cx(
        CLASSNAME_SEARCH_COMPONENT,
        { [`${CLASSNAME_SEARCH_COMPONENT}-small`]: selectedSongIds.length > 1 }
    );

    return (
        <>
            <div className={CLASSNAME}>
                {selectedSongIds.map((isrc: string, index) => (
                    <SelectedSong key={isrc} isrc={isrc} index={index} onRemove={id => removeSelectedSong({ variables: { id } })} />
                ))}
                {selectedSongIds.length < 4
                    && <SelectSong setSearchVisibility={setSearchVisibility} />}

            </div>
            {isSearchVisible && (
                <div className={searchContainerClass}>
                    <div ref={searchRef} className={searchComponentClass}>
                        <SoundRecordingSearch setSearchVisibility={setSearchVisibility} />
                    </div>
                </div>
            )}
        </>
    );
};

export default SongSelection;
