/* eslint-disable @typescript-eslint/indent */
/**
 * @format
 */

import {
  Box,
  Button,
  Flex,
  Heading,
  Spacer,
  Text
} from '@chakra-ui/react'
import React, {FC} from 'react'
import {Legend} from 'recharts'
import {ActionsDropDown} from '../ActionDropDown/ActionDropDown'
import {ButtonWithIconProps} from '../UIcomponents'
import moment from 'moment'
import {TimePeriods} from '../../types/types'

export const ChartLegend: FC<any> = () => (
  <Box>
    <Legend iconType={'circle'} />
  </Box>
)

export interface ITooltipListElement {
  propertyNames: Array<string>
  propertyKeyNames: Array<string>
  color: string
  rightColumnKey?: string
}

export type CustomTooltipProps = {
  payload?: any
  headingKeyName: string
  headingType: 'date' | 'string'
  elements: Array<ITooltipListElement>
  style?: any
}

export const CustomTooltip: FC<CustomTooltipProps> = ({
  payload,
  headingKeyName,
  headingType,
  elements,
  style
}) => (
  <>
    {payload && payload.length && (
      <Box
        boxShadow="lg"
        borderRadius={4}
        borderWidth="1px"
        borderColor="grey.400"
        bgColor="white"
        minWidth="150px"
        style={style}>
        <Heading
          variant="size12"
          bgColor="grey.100"
          color="grey.500"
          px="12px"
          py="8px"
          borderBottomWidth={1}
          borderBottomColor={'grey.500'}
          borderTopRadius={4}
        >
          {headingType === 'date'
            ? moment(payload[0].payload[headingKeyName]).format('MMM, YY')
            : payload[0].payload[headingKeyName]}
        </Heading>
        <Box fontSize={'10px'} padding="8px" minH={'50px'} color={'grey.500'}>
          {Array.isArray(elements)
            ? elements.map((item, index) => (
              <React.Fragment key={index}>
                <Flex>
                  <Box
                    borderRadius={'4px'}
                    display={'inline-block'}
                    bgColor={item.color}
                    width={'8px'}
                    height={'8px'}
                    mt={2}
                    mr={1}
                  />
                  <Box>
                    {item.propertyNames.map((prop, index) => (
                      <Box key={index} display={'flex'} flexDir={'column'}>
                        {prop.length > 0 && (
                          <Text color={'grey.500'} variant="bold">
                            {prop}
                          </Text>
                        )}

                        {item.propertyKeyNames[index] === 'price' ? (
                          <Text
                            color={'grey.500'}
                            mb={-2}
                            fontSize={'10px'}
                            fontWeight={'bold'}>
                              RM{' '}
                            {payload[0].payload[item.propertyKeyNames[index]]}
                          </Text>
                        ) : (
                          <Text color={'grey.500'} mb={-2} fontSize={'10px'}>
                            {payload[0].payload[item.propertyKeyNames[index]]}
                          </Text>
                        )}
                      </Box>
                    ))}
                  </Box>
                </Flex>
              </React.Fragment>
            ))
            : elements}
        </Box>
      </Box>
    )}
  </>
)

export type TimeFilterButtonsProps = {
  buttons: Array<ButtonWithIconProps>
}

export const TimeFilterButtons = ({buttons}: {buttons: Array<any>}) => (
  <>
    <Box>
      {buttons.map((item, index) => (
        <Button
          _hover={{bg: 'grey.900', color: 'white'}}
          _active={{bg: 'grey.900', color: 'white'}}
          width={'100% / 3'}
          key={index}
          bg={item.isActive && 'grey.900'}
          color={item.isActive && 'white'}
          onClick={(e: any) => item.clickHandler(e, index)}
          variant={
            index === 0
              ? 'roundedGroupLeft'
              : index === buttons.length - 1
                ? 'roundedGroupRight'
                : 'squared'
          }>
          {item.children}
        </Button>
      ))}
    </Box>
  </>
)

export const ChartWrapper = ({
  heading,
  timeFilterButtons,
  dropDownActions,
  children,
  showTimePeriodFilters,
  showActionButtons
}: {
  heading: string
  timeFilterButtons: any
  dropDownActions: any
  children?: any
  showTimePeriodFilters: boolean
  showActionButtons: boolean
}) => (
  <Box>
    <Box>
      <Flex>
        <Heading variant={'size18'}>{heading}</Heading>
        <Spacer />
        {showActionButtons && <ActionsDropDown actions={dropDownActions} />}
      </Flex>
    </Box>
    <Box mt={2}>
      <Flex justifyContent={'flex-end'}>
        {showTimePeriodFilters && (
          <TimeFilterButtons buttons={timeFilterButtons} />
        )}
      </Flex>
    </Box>
    <Box>{children}</Box>
    <></>
  </Box>
)

export const CustomLabel = (props: any) => {
  const {
    x,
    y,
    index,
    activeLegends,
    dataArray,
    currentTimePeriod,
    tooltipType
  } = props
  const itemData = dataArray[index]
  const tobeDisplayed = activeLegends.find(
    (item: any) => item.id === itemData.id
  )

  if (tobeDisplayed) {
    if (tooltipType === 'double') {

      return (
        <g transform={`translate(${x},${y - 100})`}>
          <foreignObject x={0} y={0} width={155} height={500}>
            {<CustomTooltipDouble
              headingType={
                currentTimePeriod === TimePeriods.Montly ? 'date' : 'string'
              }
              payload={[{payload: tobeDisplayed}]}
              headingKeyName="date"
              elements={[
                {
                  propertyNames: ['', '75th', 'Median', '25th'],
                  propertyKeyNames: ['address', '75', 'price', '25'],
                  color: '#111928',
                  rightColumnKey: 'numOfTransactions'
                }
              ]}
              style={{zIndex: 999999}}
            />}
          </foreignObject>
        </g>
      )
    } else {
      return (
        <g transform={`translate(${x},${y})`}>
          <foreignObject x={0} y={0} width={155} height={100}>
            {
              <CustomTooltip
                payload={[{payload: tobeDisplayed}]}
                headingType={
                  currentTimePeriod === TimePeriods.Montly ? 'date' : 'string'
                }
                headingKeyName="date"
                elements={[
                  {
                    propertyNames: ['', ''],
                    propertyKeyNames: ['address', 'price'],
                    color: '#111928'
                  }
                ]}
              />
            }
          </foreignObject>
        </g>
      )
    }
  } else {
    return null
  }
}

type CustomTooltipDoubleProps = {
  payload?: any
  headingKeyName: string
  headingType: 'date' | 'string'
  elements: Array<ITooltipListElement>
  style?: any
}

export const CustomTooltipDouble: FC<CustomTooltipDoubleProps> = ({
  payload,
  headingKeyName,
  headingType,
  elements,
  style
}) => (
  <>
    {payload && payload.length && (
      <Box
        boxShadow="lg"
        borderRadius={4}
        borderWidth="1px"
        borderColor="grey.400"
        bgColor="white"
        minWidth="155px"
        style={style}>
        <Heading
          variant="size12"
          bgColor="grey.100"
          color="grey.500"
          px="12px"
          py="8px"
          borderBottomWidth={1}
          borderBottomColor={'grey.500'}
          borderTopRadius={4}>
          {headingType === 'date'
            ? moment(payload[0].payload[headingKeyName]).format('MMM, YY')
            : payload[0].payload[headingKeyName]}
        </Heading>
        <Box fontSize={'10px'} color={'grey.500'} padding="8px" minH={'50px'}>
          <Text
            fontSize={'10px'}
            p={0}
            mt={-2}
            mb={-1}
            textAlign={'right'}
            color={'grey.500'}>
              #
          </Text>
          {payload[0].payload &&

              Object.values(Object.keys(payload[0].payload)
              .filter(key => key !== 'id' && key !== 'date')
              .reduce((obj, key) => Object.assign(obj, {
                    [key]: payload[0].payload[key]
                  }), {}))
                .map((point: any, index: any) =>
                  elements.map((item, index) => (
                    <React.Fragment key={index}>
                      <Flex alignContent={'flex-end'}>
                        <Box
                          borderRadius={'4px'}
                          display={'inline-block'}
                          bgColor={item.color}
                          width={'8px'}
                          height={'8px'}
                          mt={2}
                          mr={1}
                        />
                        <Box>
                          {item.propertyNames.map((prop, index) => (
                            <Box key={index} mb={1}>
                              <Text
                                mb={-2}
                                fontSize={'10px'}
                                color={'grey.500'}>
                                {prop.length > 0 && <b>{prop}: </b>}
                                {item.propertyKeyNames[index] === 'price'
                                  ? ` RM ${point[item.propertyKeyNames[index]]}`
                                  : ` ${point[item.propertyKeyNames[index]]}`}
                              </Text>
                            </Box>
                          ))}

                        </Box>
                        <Box mt={0.5}>
                          <Text
                            textAlign={'right'}
                            mr={-8}
                            mt={-1}
                            fontSize={'10px'}
                            color={'grey.500'}>
                            {index === 0 && item.rightColumnKey && (
                              <span style={{float: 'right'}}>
                                {point[item.rightColumnKey]}
                              </span>
                            )}
                          </Text>
                        </Box>
                      </Flex>
                    </React.Fragment>
                  ))
                )}
        </Box>
      </Box>
    )}
  </>
)
