import React, { Fragment, FC, useState, useRef, useEffect } from 'react';
import css from './index.module.css';
import classNames from 'classnames';

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';
import ResizeObserver from 'resize-observer-polyfill';

export interface TableProps {
  tableData: Array<Array<any>>;
  description: string;
}

const Table: FC<TableProps> = ({ tableData }) => {
  const [elementsCount, _] = useState(tableData[0].length);
  const [tabIndex, setTabIndex] = useState(0);
  const tabRef = useRef(null);
  const [activeWidth, setActiveWidth] = useState(0);
  const [columns, setColumns] = useState<Array<string>>(null);

  const setActiveStyle = (index, lastIndex, event): void => {
    setTabIndex(index);
    event.target.parentNode.scrollTo({
      behavior: 'smooth',
      left:
        lastIndex > index
          ? event.target.offsetLeft - (lastIndex - index) * 160
          : event.target.offsetLeft,
    });
  };
  const ro = new ResizeObserver((entries, _) => {
    const containerWidth = entries[0].contentRect.width;
    const sliderWidth =
      containerWidth / (elementsCount - 1) > 160
        ? containerWidth / (elementsCount - 1)
        : 160;
    setActiveWidth(sliderWidth);
  });

  useEffect(() => {
    ro.observe(tabRef.current);
    return (): void => ro.unobserve(tabRef.current);
  }, [tabRef]);

  useEffect(() => {
    setColumns([...tableData.slice(1).map(r => r[0])]);
  }, [tableData]);

  const renderText = (text): any => {
    return text.split('\\n').reduce((children, textSegment, index) => {
      return [...children, index > 0 && <br key={index} />, textSegment];
    }, []);
  };

  return (
    <Fragment>
      <div
        className={classNames(css.table, {
          [css.hide]: elementsCount > 4,
        })}
      >
        {tableData && (
          <>
            {tableData.map((tableRow, index) => {
              return (
                <div
                  key={index + 'header'}
                  className={classNames({
                    [css.table__header]: index === 0,
                    [css.table__row]: index > 0,
                  })}
                >
                  {tableRow.map((item, itemIndex) => {
                    return (
                      <div
                        className={classNames({
                          [css.table__headerItem]: index === 0,
                          [css.table__rowItem]: index > 0,
                        })}
                        key={index + '' + itemIndex}
                      >
                        {renderText(item)}
                      </div>
                    );
                  })}
                </div>
              );
            })}
          </>
        )}
      </div>

      <div
        className={classNames(css.table__tabs, {
          [css.show]: elementsCount > 4,
        })}
        ref={tabRef}
      >
        <Tabs
          className={css.tabs}
          defaultIndex={0}
          onSelect={(index, lastIndex, event): void =>
            setActiveStyle(index, lastIndex, event)
          }
        >
          <TabList className={classNames(css.tabs__list, {})}>
            {tableData[0].slice(1).map((row, index) => {
              return (
                <Tab
                  key={index + 'row'}
                  selectedClassName={css.tabs__listSelected}
                >
                  {row}
                </Tab>
              );
            })}
            <div
              style={{
                width: activeWidth + 'px',
                height: '5px',
                borderRadius: '5px',
                background: '#FF5752',
                position: 'absolute',
                bottom: 0,
                left: 0,
                transform: `translate3d(${activeWidth * tabIndex}px, 0, 0)`,
                zIndex: 2,
                transition: 'transform 0.3s',
              }}
            />
            <div
              className={css.slider}
              style={{ minWidth: (elementsCount - 1) * 160 + 'px' }}
            />
          </TabList>

          {tableData[0].slice(1).map((d, index) => {
            return (
              <TabPanel key={index + 'tab'}>
                {columns &&
                  columns.map((data, colIndex) => {
                    return (
                      <div
                        className={css.tabs__panelItem}
                        key={colIndex + 'item'}
                      >
                        <div className={css.tabs__panelItemTitle}>{data}</div>
                        <div className={css.tabs__panelItemContent}>
                          {renderText(tableData[colIndex + 1][index + 1])}
                        </div>
                      </div>
                    );
                  })}
              </TabPanel>
            );
          })}
        </Tabs>
      </div>
    </Fragment>
  );
};

export default Table;
