/* eslint-disable no-unused-vars */
import React from 'react';
import {
    Form,
    MarketSelector,
    getContinents,
    SegmentedInput,
} from '@theorchard/suite-components';
import { GlyphIcon } from '@theorchard/suite-icons';
import cx from 'classnames';
import { useSortable } from '@dnd-kit/sortable';
import { CSS } from '@dnd-kit/utilities';
import { TransactionTypeGroupAdmin } from 'src/apollo/definitions/globalTypes';
import { useStoreList } from 'src/apollo/queries/stores';
import {
    useTransactionTypeGroups,
    useTransactionTypes,
} from 'src/apollo/queries/transaction-types';
import { ServiceMultiSelect } from 'src/components/shared/service-multiselect';
import { TransactionTypeMultiSelect } from 'src/components/shared/transaction-type-multiselect';
import {
    CONTRACT_TERM_RATE,
    CONTRACT_TERM_RATE_ERROR_MSG,
} from 'src/constants';
import { sanitizeDecimalInput } from 'src/utils/sanitize-decimal-input';
import type { AbacusDistroContractTermCondition } from 'src/types/abacus-contract-term';
import type { AbacusContractTermsInputErrors } from 'src/types/abacus-contract-terms-distro-input-errors';
import './styles.scss';

interface Option {
    label: string;
    value: string;
}

interface Props {
    condition: AbacusDistroContractTermCondition;
    // eslint-disable-next-line no-unused-vars
    dragAndDropCondition: (dragIndex: number, hoverIndex: number) => void;
    index: number;
    isDraggable?: boolean;
    conditions: AbacusDistroContractTermCondition[];
    onChange: (
        // eslint-disable-next-line no-unused-vars
        index: number,
        name: string,
        value: string | number | string[] | undefined
    ) => void;
    onDelete: (
        condition: AbacusDistroContractTermCondition,
        index: number
    ) => void;
    setErrors: React.Dispatch<
        React.SetStateAction<AbacusContractTermsInputErrors>
    >;
    setIsSaveDisabled?: React.Dispatch<React.SetStateAction<boolean>>;
}

export const ContractTermConditionForm: React.FC<Props> = ({
    condition,
    index,
    isDraggable = false,
    conditions,
    onChange,
    onDelete,
    setErrors,
}) => {
    const { data: stores } = useStoreList();
    const { data: transactionTypes } = useTransactionTypes();
    const { data: transactionTypeGroups } = useTransactionTypeGroups(
        TransactionTypeGroupAdmin.CONTRACT_ADMIN
    );

    const updateError = (
        field: keyof AbacusContractTermsInputErrors,
        message?: string
    ) => {
        setErrors(prev => {
            if (message) {
                return { ...prev, [field]: message };
            } else {
                const { [field]: _, ...rest } = prev;
                return rest;
            }
        });
    };

    const handleFormChange = (name: string, value: string) => {
        onChange(index, name, value);
    };

    const handleFormChangeValidation = (
        fieldName: string,
        inputValue: string | null | undefined
    ) => {
        if (fieldName === 'termRate') {
            const normalized = inputValue?.trim();
            if (!normalized || !CONTRACT_TERM_RATE.test(normalized)) {
                updateError(
                    'termRate' as keyof AbacusContractTermsInputErrors,
                    CONTRACT_TERM_RATE_ERROR_MSG
                );
            } else {
                updateError(
                    'termRate' as keyof AbacusContractTermsInputErrors,
                    undefined
                );
            }
        }
    };

    const {
        attributes,
        listeners,
        setNodeRef,
        transform,
        transition,
        isDragging,
    } = useSortable({ id: condition.priority });

    const style = isDraggable
        ? { transform: CSS.Transform.toString(transform), transition }
        : undefined;

    const isDeleteDisabled =
        conditions.filter(c => c.contractTermConditionId !== null).length ===
            1 && condition.contractTermConditionId !== null;

    return (
        <Form.Row
            className={cx(
                'ContractTermsDistroFormFields-ContractTermsConditionsForm-row',
                { isDragging }
            )}
            id={`condition-${condition.priority}`}
            ref={isDraggable ? setNodeRef : undefined}
            style={style}
            data-testid="contractTermConditionRow"
            {...(isDraggable ? attributes : {})}
            {...(isDraggable ? listeners : {})}
        >
            <div
                className="priorityControl"
                data-testid="contractTermConditionDragIcon"
            >
                {isDraggable && <GlyphIcon name="drag" size={16} />}{' '}
                {condition.priority}
            </div>

            <TransactionTypeMultiSelect
                onChange={(selected: Option[] | null) =>
                    onChange(
                        index,
                        'transactionTypes',
                        selected?.map(o => o.value) || []
                    )
                }
                placeholder="All"
                selectedValue={
                    Array.isArray(condition.conditions)
                        ? []
                        : (condition.conditions?.transactionTypes ?? [])
                }
                transactionTypes={(
                    transactionTypes?.transactionTypes || []
                ).map(type => ({
                    label: `${type.txnTypeCode} - ${type.txnTypeName}`,
                    value: type.txnTypeId,
                }))}
                transactionTypeGroups={(
                    transactionTypeGroups?.transactionTypeGroups || []
                ).map(group => ({
                    transactionTypeGroupName: group.transactionTypeGroupName,
                    transactionTypeIds: group.transactionTypes.map(
                        type => type.txnTypeId
                    ),
                }))}
            />

            <ServiceMultiSelect
                services={
                    stores?.deliveryStoresV2.items.map(store => ({
                        label: store.name,
                        value: store.id,
                    })) || []
                }
                onChange={(selected: Option[] | null) =>
                    onChange(index, 'stores', selected?.map(o => o.value) || [])
                }
                placeholder="All"
                selectedValue={
                    Array.isArray(condition.conditions)
                        ? []
                        : (condition.conditions?.stores ?? [])
                }
            />

            <MarketSelector
                className="contractTermConditionCountry"
                id={`countries-${index}`}
                quickSelections={[...getContinents()]}
                onChange={selected =>
                    onChange(
                        index,
                        'countries',
                        selected?.map(c => c.alpha3) || []
                    )
                }
                name="countries"
                placeholder="All"
                selectedValue={
                    Array.isArray(condition.conditions)
                        ? []
                        : (condition.conditions?.countries ?? [])
                }
                requireApply={false}
            />

            <div className="contractTermConditionRate">
                <SegmentedInput testId="termRate-segmentedInput">
                    <Form.Control
                        data-testid="termRate"
                        name="termRate"
                        type="text"
                        value={
                            condition.termRate ? String(condition.termRate) : ''
                        }
                        onBlur={(e: React.FocusEvent<HTMLInputElement>) => {
                            const input = e.target.value;
                            if (CONTRACT_TERM_RATE.test(input)) {
                                const padded = Number(input).toFixed(2);
                                handleFormChange(e.target.name, padded);
                            }
                            handleFormChangeValidation(e.target.name, input);
                        }}
                        onChange={e => {
                            const formatted = sanitizeDecimalInput(
                                e.target.value
                            );
                            handleFormChange(e.target.name, formatted);
                        }}
                        onPaste={(
                            e: React.ClipboardEvent<HTMLInputElement>
                        ) => {
                            e.preventDefault();
                            const pasted =
                                e.clipboardData.getData('Text') || '';
                            const formatted = sanitizeDecimalInput(pasted);
                            handleFormChange('termRate', formatted);
                        }}
                        placeholder="Input Value"
                    />
                    <SegmentedInput.Static>%</SegmentedInput.Static>
                </SegmentedInput>

                <div
                    className={cx('deleteTermCondition', {
                        disableDelete: isDeleteDisabled,
                    })}
                    data-testid="contractTermConditionDeleteIcon"
                    onClick={() =>
                        !isDeleteDisabled && onDelete(condition, index)
                    }
                >
                    <GlyphIcon name="trash" size={16} />
                </div>
            </div>
        </Form.Row>
    );
};
