/**
 * Form fields multi-select component to be used in the inspector controls
 */

/**
 * WordPress provides React during the page load. This is for TypeScript type checking only.
 *
 * Importing React from @wordpress/element causes "Cannot read property 'createElement' of undefined"
 */
import React from 'react';

import { withSelect } from '@wordpress/data';
import { ASMSelectControl, ASMSelectControlItem, ASMSelectControlProps } from '../../components/controls-inspector/sidebar/ASMSelectControl';
import { TextControl } from '@wordpress/components';
import { __ } from '@wordpress/i18n';

function FilterFieldOptions( props: { item: ASMSelectControlItem, meta: ASMSelectControlItem[ 'meta' ], setMeta: ( meta: ASMSelectControlItem[ 'meta' ] ) => void } ) : JSX.Element {
	const { item, meta, setMeta } = props;

	return <>
		<TextControl
			value={ meta?.label }
			onChange={ ( value ) =>
				setMeta( { ...meta, label: value } )
			}
			label={ __( 'Custom Label', 'gp-entry-blocks' ) }
		/>
	</>;
}

interface FilterFieldsControlProps extends BlockProps< any > {
	label: string;
}

function FilterFieldsControl(
	props: FilterFieldsControlProps & {
		formFields: {
			id: string
			label: string,
			displayOnly: boolean,
			[ key: string ]: any
		}[];
	}
) {
	function onChange( val ) {
		props.setAttributes( { filters: val } );
	}

	const items: ASMSelectControlProps[ 'items' ] = [
		{
			type: 'all',
			label: __( 'Search All', 'gp-entry-blocks' ),
		},
		...props.formFields.map( ( formField ) => {
			if ( formField.displayOnly ) {
				return undefined;
			}

			const { filterBlockUnsupportedInputTypes: unsupportedInputTypes } = window.GPEB;
			const inputType = formField?.inputType || formField.type;

			if ( unsupportedInputTypes.indexOf( inputType ) !== -1 ) {
				return undefined;
			}

			return {
				type: 'field',
				allowMultiple: 'fieldId',
				meta: {
					fieldId: formField.id,
				},
				label: formField.label,
				group: __( 'Fields', 'gp-entry-blocks' ),
				allowSorting: true,
			};
		} ),
	].filter( Boolean );

	return (
		<ASMSelectControl
			onChange={ onChange }
			items={ items }
			placeholder={ __( 'Select a Filter Field', 'gp-entry-blocks' ) }
			value={ props.attributes.filters ?? [] }
			label={ props.label }
			id="gpeb-filter-selector"
			itemOptions={ FilterFieldOptions }
			itemOptionsModalTitle={ __( 'Filter Field Options', 'gp-entry-blocks' ) }
		/>
	);
}

export default withSelect<
	{ formFields: { id: string; label: string }[] },
	FilterFieldsControlProps
	>( ( select, ownProps ) => {
		return {
			formFields: select( 'gp-entry-blocks' ).getFormFields(
				ownProps.context[ 'gp-entry-blocks/formId' ]
			),
		};
	} )( FilterFieldsControl );
