
import React from 'react';
import Icon from '@ant-design/icons';
import { Form } from 'kts-components-antd-x3';
import { ReactComponent as PlusSvg } from './svg/plus.svg'
import { AutoComplete, Select, Button, Input, Spin, Tooltip, InputProps } from 'kts-xui';
import { WrappedFormUtils } from 'kts-components-antd-x3/lib/form/Form';
import { getItemNameWithShorthand } from '../../../../../tools/itemName';
import { IGood, LineAttributeType } from '../../../../../InvoiceController';
import Invoice from '../../../../..';
import TitleText from './ui/TitleText';
import ItemNameInput from './ui/ItemNameInput';
import {
  onChangeQuantity,
  onChangePriceIncludeTax,
  onChangePriceExcludeTax,
  onChangeLineAmountIncludeTax,
  onChangeLineAmountExcludeTax,
  onChangeTaxRate,
  onChangeItemName,
} from './autoFillFn';
import Drag from './ui/Drag';
import { nonScientificNotation } from '../../../../../tools/calculate';

export default (form: WrappedFormUtils) => {
  const { getFieldDecorator, getFieldValue } = form;

  const controller = Invoice.useInvoiceController();

  /** 是否含税 */
  const isTaxIncluded = controller.useMemo(e => e.goodsListState.isTaxIncluded, []);

  /** 组件模式 */
  const model = controller.useMemo(e => e.model, []);

  /** 是否显示我方 */
  const isMyShow = controller.useMemo(e => e.goodsListState.isMyShow, []);

  /** 正在编辑的货物 */
  const editGood = controller.useMemo((e) => e.goodsListState.editGood, []);

  /** 是否启用拖拽 */
  const isStart = controller.useMemo((e) => e.goodsListState.drag.isStart, []);

  /** 禁用字段 */
  const disableds = controller.useMemo((e) => e.stakeholder.disableds || [], []);

  /** 搜索条件 */
  const searchValue = controller.useMemo((e) => e.goodsListState.searchValue, []);

  /** 税率列表 */
  const taxRateList = controller.useMemo((e) => e.goodsListState.taxRateList, []);

  /** 单位列表 */
  const unitList = controller.useMemo((e) => e.goodsListState.unitList, []);

  /** 商品表格补充配置 */
  const columnsReplenish = controller.useMemo((e) => e.goodsListState.columnsReplenish, []);

  /** 扣除额 */
  const deduction = controller.useMemo((e) => e.goodsListState.deduction, []);

  /** 计算中启动字段 */
  const changeField = controller.useMemo((e) => e.calculatingField, []);

  /** 计算中启动字段 */
  const setChangeField = React.useCallback((value: string) => controller.run(async s => { s.calculatingField = value }), []);

  const onNumberValueChange = React.useCallback((e) => {
    const value = e?.target?.value;
    if (value) {
      return value.replace(/[^0-9-\.]/g, '');
    }
  }, [])

  /** 获取补充校验规则 */
  const getReplenishRules = React.useCallback((id: string) => {
    return columnsReplenish[id] ? columnsReplenish[id].rules || [] : []
  }, [columnsReplenish])

  /** 金额整数位限制,不传默认9位 */
  const priceIntegerDigit = controller.useMemo((e) => e.priceIntegerDigit || 9, []);

  /** 表头 */
  const columns = React.useMemo(() => {
    return [
      {
        title: ' ',
        key: 'drag',
        width: 40,
        align: 'center',
        render: (_: any, record: IGood) => <Drag record={record} />
      },
      {
        title: '序号',
        key: 'serialNo',
        dataIndex: 'serialNo',
        width: 50,
        render: (e: number) => <span style={{ padding: '0 10px' }}>{e}</span>,
      },
      {
        title: <TitleText required >项目名称</TitleText>,
        key: 'itemName',
        render: (_: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('itemName')) {
            return (
              <Form.Item>
                <div style={{ display: 'flex' }} >
                  {getFieldDecorator('itemName', {
                    initialValue: isMyShow ? record.itemNameSelf : record.itemName,
                    rules: [
                      ...getReplenishRules('itemName'),
                      {
                        validator: async (_, __, callback) => {
                          await controller.wait();
                          const value = controller.state.goodsListState.editGood;
                          if (!value?.itemName && !value?.itemNameSelf) {
                            callback('项目名称不能为空');
                          } else {
                            return;
                          }
                        }
                      }
                    ]
                  })(
                    <ItemNameInput
                      editGood={editGood}
                      shorthand={editGood.shorthand}
                      suffix={
                        <Tooltip title="点击从商品管理中添加商品信息">
                          <Button
                            type="link"
                            style={{ padding: 0, width: 20, fontSize: 20, fill: '#0074ff' }}
                            icon={<PlusSvg />}
                            onClick={controller.pipeline(async s => { s.goodsListState.importGoods.isVisibleDrawer = true })}
                          />
                        </Tooltip>
                      }
                      onChange={() => {
                        onChangeItemName(controller, form, record);
                      }}
                    />
                  )}
                </div>
              </Form.Item>
            );
          } else {
            return (
              <span>
                {record.lineAttribute === LineAttributeType.折扣行 ? <span className='goods-list-digtal-discount-tag'>折扣</span> : <></>}
                <MyItemNameDiv
                  valueT={formatSearch(getItemNameWithShorthand({ shorthand: record.shorthand, full: record.itemNameSelf || '' }), searchValue)}
                  valueF={formatSearch(getItemNameWithShorthand({ shorthand: record.shorthand, full: record.itemName || '' }), searchValue)}
                  isMyShow={isMyShow}
                />
              </span>
            )
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['itemModelName']?.rules} >规格型号</TitleText>,
        key: 'itemModelName',
        width: 119,
        render: (_: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('itemModelName')) {
            return (
              <Form.Item>
                {getFieldDecorator('itemModelName', {
                  initialValue: isMyShow ? editGood.itemModelNameSelf : editGood.itemModelName,
                  rules: getReplenishRules('itemModelName'),
                })(
                  <MyInput
                    onChange={async () => {
                      await controller.wait()
                      const key = isMyShow ? 'itemModelNameSelf' : 'itemModelName';
                      const value = {} as any;
                      value[key] = form.getFieldsValue().itemModelName;
                      controller.setEditGood(value);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return (
              <MyItemNameDiv
                valueT={formatSearch(record.itemModelNameSelf, searchValue)}
                valueF={formatSearch(record.itemModelName, searchValue)}
                isMyShow={isMyShow}
              />
            )
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['unit']?.rules} >单位</TitleText>,
        key: 'unit',
        width: 70,
        render: (_: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('unit')) {
            return (
              <Form.Item>
                {getFieldDecorator('unit', {
                  initialValue: editGood.unit,
                  rules: getReplenishRules('unit'),
                })(
                  <AutoComplete
                    style={{ width: '100%' }}
                    dataSource={unitList}
                    onChange={async () => {
                      await controller.wait()
                      controller.setEditGood({ unit: form.getFieldsValue().unit });
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{record.unit}</span>;
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['quantity']?.rules} >数量</TitleText>,
        dataIndex: 'quantity',
        key: 'quantity',
        align: 'right',
        width: 149,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('quantity')) {
            return (
              <Form.Item>
                {getFieldDecorator('quantity', {
                  initialValue: nonScientificNotation(editGood.quantity),
                  getValueFromEvent: onNumberValueChange,
                  rules: [
                    ...getReplenishRules('quantity'),
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '数量必须为数字' },
                    {
                      validator: async (_, value, callback) => {
                        await controller.wait();
                        const isvalue = !!value || value === 0;
                        const isPrice = !!getFieldValue(isTaxIncluded ? 'priceIncludeTax' : 'priceExcludeTax') || getFieldValue(isTaxIncluded ? 'priceIncludeTax' : 'priceExcludeTax') === 0;
                        if (isvalue || isPrice === isvalue) return;
                        callback('请输入数量');
                      }
                    }
                  ],
                })(
                  <MyInput
                    style={{ textAlign: 'right' }}
                    maxLength={16}
                    loading={isCipher(changeField, "quantity")}
                    onChange={async () => {
                      setChangeField('quantity');
                      await onChangeQuantity(controller, form, record);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{nonScientificNotation(value)}</span>;
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['priceIncludeTax']?.rules} >单价(含税)</TitleText>,
        dataIndex: 'priceIncludeTax',
        key: 'priceIncludeTax',
        align: 'right',
        width: 149,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('priceIncludeTax')) {
            return (
              <Form.Item>
                {getFieldDecorator('priceIncludeTax', {
                  initialValue: nonScientificNotation(editGood.priceIncludeTax),
                  getValueFromEvent: onNumberValueChange,
                  rules: [
                    ...getReplenishRules('priceIncludeTax'),
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '单价必须为数字' },
                    {
                      validator: async (_, value, callback) => {
                        await controller.wait();
                        const isQuantity = !!getFieldValue('quantity') || getFieldValue('quantity') === 0;
                        const isvalue = !!value || value === 0;
                        if (isvalue || isQuantity === isvalue) return;
                        callback('请输入单价');
                      }
                    }
                  ],
                })(
                  <MyInput
                    style={{ textAlign: 'right' }}
                    maxLength={16}
                    loading={isCipher(changeField, 'priceIncludeTax')}
                    onChange={() => {
                      setChangeField('priceIncludeTax');
                      onChangePriceIncludeTax(controller, form, record);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{nonScientificNotation(value)}</span>;
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['priceExcludeTax']?.rules} >单价(不含税)</TitleText>,
        dataIndex: 'priceExcludeTax',
        key: 'priceExcludeTax',
        align: 'right',
        width: 149,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('priceExcludeTax')) {
            return (
              <Form.Item>
                {getFieldDecorator('priceExcludeTax', {
                  initialValue: nonScientificNotation(editGood.priceExcludeTax),
                  getValueFromEvent: onNumberValueChange,
                  rules: [
                    ...getReplenishRules('priceExcludeTax'),
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '单价必须为数字' },
                    {
                      validator: async (_, value, callback) => {
                        await controller.wait();
                        const isQuantity = !!getFieldValue('quantity') || getFieldValue('quantity') === 0;
                        const isvalue = !!value || value === 0;
                        if (isvalue || isQuantity === isvalue) return;
                        callback('请输入单价');
                      }
                    }
                  ],
                })(
                  <MyInput
                    style={{ textAlign: 'right' }}
                    maxLength={16}
                    loading={isCipher(changeField, 'priceExcludeTax')}
                    onChange={() => {
                      setChangeField('priceExcludeTax');
                      onChangePriceExcludeTax(controller, form, record);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{nonScientificNotation(value)}</span>;
          }
        },
      },
      {
        title: <TitleText required >金额(含税)</TitleText>,
        dataIndex: 'lineAmountIncludeTax',
        key: 'lineAmountIncludeTax',
        width: 119,
        align: 'right',
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('lineAmountIncludeTax')) {
            return (
              <Form.Item>
                {getFieldDecorator('lineAmountIncludeTax', {
                  initialValue: editGood.lineAmountIncludeTax,
                  getValueFromEvent: onNumberValueChange,
                  rules: [
                    ...getReplenishRules('lineAmountIncludeTax'),
                    { required: true, message: '金额不能为空' },
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '金额必须为数字' },
                    {
                      validator: async (_, value, callback) => {
                        if (`${value}`.split('.')[0].length > priceIntegerDigit) {
                          callback(`金额整数部分不能大于${priceIntegerDigit}位，小数点后最多2位`);
                        }
                      }
                    },
                    {
                      validator: async (_, value, callback) => {
                        if (deduction && parseFloat(value) <= deduction) {
                          callback('扣除额不能大于等于价税合计');
                        }
                      }
                    },
                  ],
                })(
                  <MyInput
                    style={{ textAlign: 'right' }}
                    loading={isCipher(changeField, 'lineAmountIncludeTax')}
                    onChange={() => {
                      setChangeField('lineAmountIncludeTax');
                      onChangeLineAmountIncludeTax(controller, form, record);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{formatSearch(parseFloat(value).toFixed(2), searchValue)}</span>;
          }
        },
      },
      {
        title: <TitleText required >金额(不含税)</TitleText>,
        dataIndex: 'lineAmountExcludeTax',
        key: 'lineAmountExcludeTax',
        align: 'right',
        width: 119,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('lineAmountExcludeTax')) {
            return (
              <Form.Item>
                {getFieldDecorator('lineAmountExcludeTax', {
                  initialValue: editGood.lineAmountExcludeTax,
                  getValueFromEvent: onNumberValueChange,
                  rules: [
                    ...getReplenishRules('lineAmountExcludeTax'),
                    { required: true, message: '金额不能为空' },
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '金额必须为数字' },
                    {
                      validator: async (_, value: string, callback) => {
                        if (`${value}`.split('.')[0].length > priceIntegerDigit) {
                          callback(`金额整数部分不能大于${priceIntegerDigit}位，小数点后最多2位`);
                        }
                      }
                    },
                  ],
                })(
                  <MyInput
                    style={{ textAlign: 'right' }}
                    loading={isCipher(changeField, 'lineAmountExcludeTax')}
                    onChange={() => {
                      setChangeField('lineAmountExcludeTax');
                      onChangeLineAmountExcludeTax(controller, form, record);
                    }}
                  />,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{formatSearch(parseFloat(value).toFixed(2), searchValue)}</span>;
          }
        },
      },
      {
        title: <TitleText required >税率</TitleText>,
        dataIndex: 'taxRate',
        key: 'taxRate',
        align: 'right',
        width: 70,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('taxRate')) {
            return (
              <Form.Item>
                {getFieldDecorator('taxRate', {
                  initialValue: editGood.taxRate,
                  rules: [
                    ...getReplenishRules('taxRate'),
                    { required: true, message: '请选择税率' },
                    { pattern: /^[+-]?(0|([1-9]\d*))(\.\d+)?$/, message: '请选择正确税率' },
                  ],
                })(
                  <Select
                    className="kts-invoice-operate-goods-list-table-tax-rate"
                    // dropdownMenuStyle={{ textAlign: "right" }}
                    showArrow={false}
                    style={{ width: '100%' }}
                    onChange={() => {
                      setChangeField('taxRate');
                      onChangeTaxRate(controller, form, record);
                    }}
                  >
                    {taxRateList.map((e, i) => {
                      return (
                        <Select.Option key={i} value={e}>
                          {e}%
                        </Select.Option>
                      );
                    })}
                  </Select>,
                )}
              </Form.Item>
            );
          } else {
            return <span style={{ padding: '0 10px' }}>{isDutyFree(record) ? '免税' : isNonTaxable(record) ? '不征税' : `${value}%`}</span>;
          }
        },
      },
      {
        title: <TitleText rules={columnsReplenish['taxAmount']?.rules} >税额</TitleText>,
        dataIndex: 'taxAmount',
        key: 'taxAmount',
        align: 'right',
        width: 119,
        render: (value: string, record: IGood) => {
          if (editGood?.$index === record.$index && !disableds.includes('taxAmount')) {
            return getFieldDecorator('taxAmount', {
              initialValue: editGood.taxAmount,
              rules: getReplenishRules('taxAmount'),
            })(<MyDiv loading={isCipher(changeField, 'taxAmount')} />);
          } else {
            return <span style={{ padding: '0 10px' }}>{isDutyFree(record) || isNonTaxable(record) ? '***' : parseFloat(value).toFixed(2)}</span>;
          }
        },
      },
      // {
      //   title: '操作',
      //   key: 'operating',
      //   align: 'right',
      //   width: 130,
      //   fixed: 'right',
      //   render: (_value: string, record: IGood) => <RowMenu key={record.lineAttribute} goods={record} />,
      // },
    ]
      // 含税不含税
      .filter((e) => {
        if (isTaxIncluded) {
          return !(e.key === 'priceExcludeTax' || e.key === 'lineAmountExcludeTax');
        } else {
          return !(e.key === 'priceIncludeTax' || e.key === 'lineAmountIncludeTax');
        }
      })
      // 是否启动拖拽
      .filter(e => e.key !== 'drag' || isStart)
      // 只读
      .filter(e => {
        if (model === 'readOnly') {
          return e.key !== 'operating';
        } else {
          return true;
        }
      })
      .map((e) => {
        return {
          ...e,
          ellipsis: true,
        };
      }) as any[];
  }, [isTaxIncluded, editGood, controller, taxRateList, changeField, deduction, isMyShow, searchValue, model, columnsReplenish, isStart]);

  // React.useEffect(() => {
  //   clearTimeout(t)
  //   const t = setTimeout(() => { setChangeField('') }, 1000);
  //   return () => { clearTimeout(t) }
  // }, [changeField]);

  return columns;
};

/** 字段 */
function isCipher(name?: string, field?: string) {
  if (!name || !field) return false;
  return name !== field;
}

class MyInput extends React.Component<InputProps & { loading?: boolean }> {
  render() {
    if (this.props.loading) {
      return (
        <Spin size="small">
          <Input {...this.props} autoComplete="off" />
        </Spin>
      )
    } else {
      return <Input {...this.props} autoComplete="off" />
    }
  }
}

class MyDiv extends React.Component<{ value?: any, loading?: boolean }> {

  render() {
    if (this.props.loading) {
      return (
        <Spin size="small">
          <span style={{ padding: '0 10px' }}>{this.props.value}</span>
        </Spin>
      )
    } else {
      return <span style={{ padding: '0 10px' }}>{this.props.value}</span>
    }
  }
}

class MyItemNameDiv extends React.Component<{ valueT?: React.ReactNode, valueF?: React.ReactNode, isMyShow: boolean }> {
  render(): React.ReactNode {

    const { isMyShow, valueT, valueF } = this.props;

    if (isMyShow) {
      if (valueT) {
        return (
          <Tooltip title={valueT}>
            <span style={{ ...MyItemNameStyle, color: '#0074ff' }}>{valueT}</span>
          </Tooltip>
        )
      } else {
        return (
          <Tooltip title={valueF}>
            <span style={MyItemNameStyle}>{valueF}</span>
          </Tooltip>
        )
      }
    } else {
      if (valueF) {
        return (
          <Tooltip title={valueF}>
            <span style={MyItemNameStyle}>{valueF}</span>
          </Tooltip>
        )
      } else {
        return (
          <Tooltip title={valueT} style={MyItemNameStyle}>
            <span style={{ ...MyItemNameStyle, color: '#0074ff' }}>{valueT}</span>
          </Tooltip>
        )
      }
    }
  }
}

/** 格式搜索结果 */
function formatSearch(value?: string, search?: string) {
  if (!value || !search) return value;

  const __html = ucoding(value).split(new RegExp(ucoding(search), 'g')).map(e => dcoding(e)).join(`<span class="kts-invoice-operate-goods-list-table-search-protrude" >${search}</span>`);
  return <span dangerouslySetInnerHTML={{ __html }} />
}

/** 编码 */
function ucoding(v: string): string {
  return v.split('').map(e => `U${e.charCodeAt(0)}E`).join('');
}

/** 解码 */
function dcoding(v: string): string {
  return v.split('U').map(e => e ? String.fromCharCode(parseInt(e.replace('E', ''))) : '').join('');
}

/** 是否免税 */
function isDutyFree(record: IGood): boolean {
  return (record.taxFreeType as any) === 1 && record.favouredPolicyName === '免税';
}

/** 是否不征税 */
function isNonTaxable(record: IGood): boolean {
  return (record.taxFreeType as any) === 2 && record.favouredPolicyName === '不征税';
}

const MyItemNameStyle: any = {
  padding: '0px 10px',
  whiteSpace: 'nowrap',
  overflow: 'hidden',
  width: "100%",
  display: 'block',
  textOverflow: 'ellipsis'
}