import React from 'react'
import Accordion from '@mui/material/Accordion/index.js'
import AccordionSummary from '@mui/material/AccordionSummary/index.js'
import AccordionDetails from '@mui/material/AccordionDetails/index.js'
import { object } from 'prop-types'
import Divider from '@mui/material/Divider/index.js'

import FarmhandContext from '../Farmhand/Farmhand.context.js'
import ProgressBar from '../ProgressBar/index.js'
import Achievement from '../Achievement/index.js'
import achievements from '../../data/achievements.js'
import { memoize } from '../../utils/memoize.js'
import { Div } from '../Elements/index.js'

const partitionAchievements = memoize(
  (completedAchievements: Partial<Record<string, boolean>>) =>
    achievements.reduce(
      (acc, achievement) => {
        acc[
          completedAchievements[achievement.id] ? 'complete' : 'incomplete'
        ].push(achievement)

        return acc
      },
      {
        complete: [] as typeof achievements[number][],
        incomplete: [] as typeof achievements[number][],
      }
    )
)

const AchievementsList = ({
  unpartitionedAchievements,
}: {
  unpartitionedAchievements: farmhand.achievement[]
}) => (
  <AccordionDetails>
    <ul className="card-list">
      {unpartitionedAchievements.map((achievement: farmhand.achievement) => (
        <li {...{ key: achievement.id }}>
          <Achievement {...{ achievement }} />
        </li>
      ))}
    </ul>
  </AccordionDetails>
)

const AchievementsView = ({
  completedAchievements,
  partitionedAchievements: { complete, incomplete } = partitionAchievements(
    completedAchievements
  ),
}: {
  completedAchievements: Partial<Record<string, boolean>>
  partitionedAchievements?: ReturnType<typeof partitionAchievements>
}) => (
  <Div
    className="AchievementsView"
    sx={{
      '& h3': { margin: 0 },
      '& .ProgressBar': { maxWidth: 500 },
    }}
  >
    <ProgressBar
      {...{ percent: (complete.length / achievements.length) * 100 }}
    />
    {complete.length ? (
      <>
        <Accordion {...{ defaultExpanded: true }}>
          <AccordionSummary>
            <h3>Completed</h3>
          </AccordionSummary>
          <AchievementsList {...{ unpartitionedAchievements: complete }} />
        </Accordion>
        <Divider />
      </>
    ) : null}
    <Accordion {...{ defaultExpanded: true }}>
      <AccordionSummary>
        <h3>Not Completed</h3>
      </AccordionSummary>
      <AchievementsList {...{ unpartitionedAchievements: incomplete }} />
    </Accordion>
  </Div>
)

AchievementsView.propTypes = {
  completedAchievements: object.isRequired,
}

export default function Consumer(
  props: Partial<Parameters<typeof AchievementsView>[0]>
) {
  return (
    <FarmhandContext.Consumer>
      {({ gameState, handlers }) => (
        <AchievementsView
          {...({
            ...gameState,
            ...handlers,
            ...props,
          } as Parameters<typeof AchievementsView>[0])}
        />
      )}
    </FarmhandContext.Consumer>
  )
}
