import React, { ChangeEvent, useState } from 'react'
import { TfiPlus } from 'react-icons/tfi';
import { Genre, GenreProportion } from '../../../../api/models/Types';
import {  useQuery } from 'react-query';
import ErrorField from '../../../common/error/ErrorField';
import ErrorInput from '../../../common/error/ErrorInput';
import { DeepEqual } from '../../../../common/Helper';
import GenreProportionItemEditComponent, { IsGenreValid } from './GenreProportionItemEditComponent';
import { genresQueryKey } from '../../../library/edit/genre/GenreListEditComponent';
import { GetGenreList } from '../../../../api/GenreApi';

export interface GenreProportionEditComponentProps{
	genresProportions: Array<GenreProportion> | null | undefined,
	dataLoadingError: Error | null,
	createGenreProportionPercentage: (genreProportionPercentage: GenreProportion) => Promise<string | undefined>,
	editGenreProportionPercentage: (genreProportionPercentage: GenreProportion, proportionPercentage: number | null) => Promise<string | undefined>,
	deleteGenreProportionPercentage: (genreProportionPercentage: GenreProportion) => Promise<string | undefined>,
	forceRefresh: () => void,
}

export default function GenreProportionEditComponent(props: GenreProportionEditComponentProps) {
	const { data: genresData, isLoading: genresIsLoading, isError: genresIsError, error: genresError } = useQuery(genresQueryKey, GetGenreList);

	const [createNewGenreProportionPercentageError, setCreateNewGenreProportionPercentageError] = useState<string | null>();

	const [genreProportions, setGenreProportions] = useState<Array<GenreProportion>>([]);
	const [genreIdProportionPercentage, setGenreIdProportionPercentage] = useState<[genreId: string | null, proportionPercentage: number | null]>();

	const selectGenre = (id?: string | null) => {
		setGenreIdProportionPercentage(
			[
				(id == genreIdProportionPercentage?.[0] ? null : id) ?? null,
				genreIdProportionPercentage?.[1] ?? null,
			]
		);
	};

	const onProportionPercentageChange = (event : ChangeEvent<HTMLInputElement>) => {
		const proportion = parseInt(event.target.value);
		setGenreIdProportionPercentage(
			[
				genreIdProportionPercentage?.[0] ?? null,
				!Number.isNaN(proportion) ? proportion : null,
			]
		);
	}

	const [editingGenreProportion, SetEditingGenreProportion] = useState<GenreProportion | null>(null);
	const SetEditing = (genreProportion: GenreProportion, value: boolean) => {
		if (DeepEqual(genreProportion, editingGenreProportion) || !value){
			SetEditingGenreProportion(null);
		}
		else{
			SetEditingGenreProportion(genreProportion);
		}
	};

	const [deletingGenreProportion, SetDeletingGenreProportion] = useState<GenreProportion | null>(null);
	const SetDeleting = (genreProportion: GenreProportion, value: boolean) => {
		if (DeepEqual(genreProportion, deletingGenreProportion) || !value){
			SetDeletingGenreProportion(null);
		}
		else{
			SetDeletingGenreProportion(genreProportion);
		}
	};

	React.useEffect(() => {
			setGenreIdProportionPercentage( [ null, null, ] );
			setGenreProportions( props.genresProportions ?? [] );
		}, [props]);

	const valueMax = 10;
	
	return (
		<>
			<ErrorField error={createNewGenreProportionPercentageError}>
				<div className="input-group">
					<ErrorInput error={createNewGenreProportionPercentageError ?? (genresError as Error | null)?.message}>
						<select className="form-select" aria-label="Жанр" value={genreIdProportionPercentage?.[0] ?? ''}
							disabled={genresError != null || genresData == null|| genresData?.length == 0} onChange={(event) => selectGenre(event.target.value)}>
							<option value={''} >Выберите жанр</option>
							{!(genresIsError || genresIsLoading) && genresData &&
								React.Children.toArray(
									genresData.map((item) => 
										<option value={item.id}>
											{item.name}
										</option>
									))
								}
							{/* <option value="2">Два</option> */}
						</select>
					</ErrorInput>

					<ErrorInput error={createNewGenreProportionPercentageError}>
						<input type="number" min={0} max={valueMax} className="form-control" id="newAnimeTitleName" placeholder="Доля жанра" onChange={onProportionPercentageChange} value={genreIdProportionPercentage?.[1] ?? ''} />
					</ErrorInput>

					<ErrorInput error={createNewGenreProportionPercentageError} errorClassses={'btn-danger'}>
						{/* <button id='btn_add_name' type="submit" className='btn btn-primary' */}
						<button type="submit" className='btn btn-primary'
							disabled={!IsGenreValid(genreIdProportionPercentage?.[0])}
							onClick={() => {
								if (IsGenreValid(genreIdProportionPercentage?.[0])){
									props.createGenreProportionPercentage({
										genre: genresData?.find(q => q.id == genreIdProportionPercentage![0]),
										proportion: genreIdProportionPercentage![1],
									} as GenreProportion)
										.then(() => {
											setCreateNewGenreProportionPercentageError(null);
											setGenreIdProportionPercentage([ null, null ]);
											props.forceRefresh();
										})
										.catch((error: unknown) =>{
											setCreateNewGenreProportionPercentageError((error as Error)?.message);
											//console.error(error);
										});
								}
							}}>
								<span><TfiPlus /></span>
						</button>
					</ErrorInput>
				</div>
			</ErrorField>

			<hr />

			<ul className="list-group gap-2">
				{
					ShowItems(
						{
							genreProportions: genreProportions ?? [],
							genres: genresData ?? [],
							isLoading: genresIsLoading,
							isError: props.dataLoadingError != null,
							error: props.dataLoadingError,
							setDeleting: SetDeleting,
							isDeleting: (proportionPercentage: GenreProportion | null) => DeepEqual(deletingGenreProportion, proportionPercentage),
							deleteGenreProportion: props.deleteGenreProportionPercentage,
							setEditing: SetEditing,
							isEdited: (proportionPercentage: GenreProportion | null) => DeepEqual(editingGenreProportion, proportionPercentage),
							editGenreProportion: props.editGenreProportionPercentage,
							valueMax: valueMax,
							forceRefresh: props.forceRefresh,
						}, genresData) 
				}
			</ul>
		</>
	)
}

type ShowGenresProps = {
	genreProportions: Array<GenreProportion>,
	genres: Array<Genre>,
	valueMax: number,
	isLoading: boolean,
	isError: boolean,
	error: Error | null,
	setDeleting: (genreProportion: GenreProportion, value: boolean) => void,
	isDeleting: (genreProportion: GenreProportion | null) => boolean,
	deleteGenreProportion: (genreProportion: GenreProportion) => Promise<string | undefined>,

	setEditing: (genreProportion: GenreProportion, value: boolean) => void,
	isEdited: (genreProportion: GenreProportion | null) => boolean,
	editGenreProportion: (genreProportion: GenreProportion, proportionPercentage: number | null) => Promise<string | undefined>,
	forceRefresh: () => void,
}

function ShowItems(props: ShowGenresProps, languages: Array<Genre> | undefined){
	if (props.isLoading){
		return (
			<>
				<div className="list-group-item placeholder rounded">1. SomeGenre</div>
				<div className="list-group-item placeholder rounded">2. SomeGenre</div>
				<div className="list-group-item placeholder rounded">3. SomeGenre</div>
			</>
		)
	}
	else if (props.isError){
		return (
			<li className="list-group-item card p-0">
				<div className='card-header bg-danger'>
					<h4 className='card-heading'>{props.error?.name ?? 'Unknown error'}</h4>
				</div>
				<div className='card-body bg-danger bg-opacity-50'>
					{/* Error occured during fetching items: */}
					<span>{props.error?.message ?? 'unknown'}</span>
				</div>
			</li>
		)
	}
	else{
		return React.Children.toArray(
			props.genreProportions.map((name: GenreProportion) => {
				return (
					<GenreProportionItemEditComponent
						genreProportion={name}
						genres={languages ?? []}
						// enabled={!item.deleted}
						enabled={true}
						valueMax={props.valueMax}
						setDeleting={props.setDeleting}
						isDeleting={props.isDeleting(name)}
						deleteGenreProportion={props.deleteGenreProportion}
						
						setEditing={props.setEditing}
						isEditing={props.isEdited(name)}
						editGenreProportion={props.editGenreProportion}
						forceRefresh={props.forceRefresh}
						/>
					
				);
			})
		)
	}
}