import React, { useEffect, useMemo, useState, useRef } from 'react';
import { Checkbox, message, Popover } from 'antd';
import classNames from 'classnames';
import _ from 'lodash';
import { config } from './base/config';
import { getEditComponent, getFormat, setFormat } from './base';
import s from './Cell.less';
import { CellProps, CellDataProps } from './interface';
import FormHelper from '../utils/formHelper';
import firstIcon from '../assets/first.png';
import secondIcon from '../assets/second.png';
import thirdIcon from '../assets/third.png';
import expandIcon from '../assets/extend.png';
import { transferAttr } from './base/_utils/transferAttr';
import { emptyModel } from '@/submodule/components/apolloTable/component/base/_utils/setFormatter';

const Cell = (props: CellProps) => {
    const {
        columnConfig,
        cellClassName,
        cellStyle,
        record,
        columnData,
        value: cellData,
        emitChangeCell,
        columnIndex,
        rowIndex,
        paginationConfig,
        showIndex,
        showExpand,
        emptyPlaceholder,
        cellEditable,
        rowSelection,
        columns,
        contentMenu,
    } = props;
    const {
        columnType,
        columnName,
        requiredFlag,
        renderDetailCell,
        renderEditCell,
        cellRenderProps,
        readOnlyFlag,
    } = columnConfig;
    const cellUnit = useRef(null);
    const [status, setStatus] = useState('detail');

    useEffect(() => {
        setStatus('detail');
    }, [cellData]);

    const changeCellData = (changedValue: any, option?: any) => {};
    const emitChangeCellData = (changedValue: any, optionValue: any) => {
        let temp: CellDataProps[] = [];
        cellData.map((item: CellDataProps) => {
            temp.push({ text: item.text, value: item.value });
        });
        if (temp.length === 0) {
            temp = emptyModel;
        }

        if (_.isEqual(temp, changedValue)) {
            setStatus('detail');
            return;
        }
        changeValue(changedValue, optionValue);
    };

    const changeValue = async (changedValue: any, optionValue: any) => {
        // 校验必填项
        if (requiredFlag) {
            if (!changedValue || changedValue.length === 0) {
                message.error('该字段为必填项');
                return;
            }
            if (changedValue.length === 1) {
                const data = changedValue[0];
                if (!data.value && !data.text) {
                    message.error('该字段为必填项');
                    return;
                }
            }
        }
        const extraData = FormHelper.changeTableData({
            item: columnConfig,
            changedKey: columnName,
            changedValue,
            originValue: optionValue,
        });
        extraData.push({
            columnCode: columnName,
            cellValueList: changedValue,
        });
        if (typeof emitChangeCell === 'function') {
            emitChangeCell({
                rowId: record.id,
                value: extraData,
            });
        }
        setStatus('detail');
    };
    // 添加行hover样式
    const onMouseEnter = () => {
        const doms = document.querySelectorAll(`.row_${rowIndex}`);
        doms.forEach((dom) => {
            dom.classList.add(s.hover);
        });
    };
    // 去除行hover样式
    const onMouseLeave = () => {
        const doms = document.querySelectorAll(`.row_${rowIndex}`);
        doms.forEach((dom) => {
            dom.classList.remove(s.hover);
        });
    };

    const selfRenderDetailCell = () => {
        // 数据为空
        let empty =
            !cellData || cellData.length === 0 || (cellData.length === 1 && !cellData[0].text && !cellData[0].value);
        let detailConfig;
        if (typeof renderDetailCell === 'function') {
            detailConfig = renderDetailCell({ cellData, rowData: record, columnConfig });
            empty = false;
        } else {
            detailConfig = config[String(columnType)] || config['1'];
        }
        const DetailComp: any = detailConfig.detailComp;

        const newProps = {
            ...(detailConfig.componentAttr || {}),
            ...(columnConfig.columnAttrObj || {}),
        };
        const transferColumn = transferAttr(columnType, newProps);

        const style: any = {};
        const { current = 1, pageSize = 20 } = paginationConfig || {};
        // 构造序号
        const getIndex = () => {
            // if (current === 1) {
            //     let src = '';
            //     switch (rowIndex) {
            //         case 0:
            //             src = firstIcon;
            //             break;
            //         case 1:
            //             src = secondIcon;
            //             break;
            //         case 2:
            //             src = thirdIcon;
            //             break;
            //         default:
            //             return rowIndex + 1;
            //     }
            //     return <img className={s.icon} alt="" src={src} />;
            // }
            return (current - 1) * pageSize + rowIndex + 1;
        };
        // 获取当前行在所选列表中的index
        const getCheckedIndex = () => {
            if (!rowSelection) {
                return -1;
            }
            const { selectedRows } = rowSelection;
            const index =
                selectedRows &&
                selectedRows.findIndex((item: any) => {
                    return item.id === record.id;
                });
            return index;
        };
        // 构造行复选框
        const getCheckbox = () => {
            const { selectedRows, onChange } = rowSelection;
            const index = getCheckedIndex();
            const checked = index > -1;
            const onToggle = () => {
                if (typeof onChange === 'function') {
                    const data = _.cloneDeep(selectedRows);
                    if (checked) {
                        data.splice(index, 1);
                    } else {
                        data.push(record);
                    }
                    onChange(data);
                }
            };
            return <Checkbox checked={checked} onClick={onToggle} />;
        };

        const { dynamicCellConfigDTO } = columnData;
        const detail = (
            <div
                className={s.detailCell}
                onClick={() => {
                    // 不可编辑状态
                    if (!cellEditable || readOnlyFlag || (dynamicCellConfigDTO && dynamicCellConfigDTO.readonlyFlag)) {
                        return false;
                    }
                    // 获取当前节点的选中状态
                    const dom = cellUnit.current;
                    let selected = false;
                    if (dom && dom.getAttribute('data-selected-cell')) {
                        selected = dom.getAttribute('data-selected-cell') === '1';
                    }
                    if (selected) {
                        // 当前已选中，则进入编辑状态
                        setStatus('edit');
                        if (dom) {
                            // 给当前dom添加编辑状态
                            dom.setAttribute('data-editing-cell', '1');
                        }
                    } else {
                        // 否则进入选中状态
                        if (dom) {
                            // 先清除所有dom的选中状态及样式
                            const doms = document.querySelectorAll('.cellUnit');
                            if (doms) {
                                doms.forEach((item) => {
                                    item.setAttribute('data-selected-cell', '0');
                                    item.classList.remove(s.selected);
                                });
                            }
                            // 给当前dom添加选中状态
                            dom.setAttribute('data-selected-cell', '1');
                            // 给当前dom添加选中样式
                            dom.classList.add(s.selected);
                        }
                    }
                }}
                style={style}
            >
                {rowSelection && columnIndex === 0 && (
                    <div className={classNames(s.checkbox, showIndex && s.hasNum, getCheckedIndex() > -1 && s.checked)}>
                        {getCheckbox()}
                    </div>
                )}
                {showIndex && columnIndex === 0 && (
                    <div
                        className={classNames(
                            s.num,
                            rowSelection && s.hasCheckbox,
                            getCheckedIndex() > -1 && s.checked,
                        )}
                    >
                        {getIndex()}
                    </div>
                )}
                {showExpand && columnIndex === 0 && (
                    <div className={s.expand}>
                        <img
                            onClick={(e: any) => {
                                e.stopPropagation();
                                e.nativeEvent.stopImmediatePropagation();
                                showExpand({ rowId: record.id });
                            }}
                            className={s.expandIcon}
                            alt=""
                            src={expandIcon}
                        />
                    </div>
                )}
                {empty ? (
                    emptyPlaceholder || '-'
                ) : (
                    <div className={s.content}>
                        <DetailComp
                            value={cellData}
                            columns={columns}
                            rowData={record}
                            columnConfig={columnConfig}
                            componentAttr={transferColumn}
                            formatter={detailConfig.getFormatter}
                            cellRenderProps={cellRenderProps}
                            changeEdit={() => {
                                setStatus('edit');
                            }}
                        />
                    </div>
                )}
            </div>
        );

        return contentMenu ? (
            <Popover
                overlayClassName={s.menuPop}
                trigger="contextMenu"
                placement="rightTop"
                content={
                    <div role="presentation" className={style.menuContainer}>
                        {contentMenu.map((item: any, i: number) => {
                            return (
                                <div
                                    key={i}
                                    role="presentation"
                                    className={style.menu}
                                    onClick={item.onClick.bind(null, record)}
                                >
                                    {item.label}
                                </div>
                            );
                        })}
                    </div>
                }
            >
                {detail}
            </Popover>
        ) : (
            detail
        );
    };

    const selfRenderEditCell = () => {
        let editConfig: any;
        if (typeof renderEditCell === 'function') {
            editConfig = renderEditCell({ cellData, rowData: record, columnConfig });
        } else {
            editConfig = config[String(columnType)] || config['1'];
        }

        const EditComp: any = editConfig.cellComp;
        const transferColumn = transferAttr(columnType, {
            ...(editConfig.componentAttr || {}),
            ...(columnConfig.columnAttrObj || {}),
        });
        const newProps = {
            ...(transferColumn || {}),
        };
        return (
            <div className={s.editCell}>
                <EditComp
                    value={getFormat(editConfig, columnConfig, cellData)}
                    {...newProps}
                    columnConfig={columnConfig}
                    onChange={changeCellData}
                    rowData={record}
                    onEmitChange={(changedValue: any, optionValue: any) => {
                        const value = setFormat(editConfig, columnConfig, changedValue, optionValue);
                        emitChangeCellData(value, optionValue);
                    }}
                    style={{
                        minHeight: cellStyle.height,
                        borderRadius: 0,
                    }}
                />
            </div>
        );
    };

    return (
        <div
            className={classNames('cellUnit', `row_${rowIndex}`, `col_${columnIndex}`, cellClassName)}
            style={cellStyle}
            id={`cellUnit_${rowIndex}_${columnIndex}`}
            data-selected-cell="0"
            data-editing-cell="0"
            onMouseEnter={onMouseEnter}
            onMouseLeave={onMouseLeave}
            ref={cellUnit}
        >
            {status === 'detail' && selfRenderDetailCell()}
            {status === 'edit' && selfRenderEditCell()}
        </div>
    );
};

export default Cell;
