import { EmailSelection } from '@/analyst/utilities'
import { useHideSidebarValue } from '@/clientsettings/vars/hidesidebar'
import ExitButton from '@/components/ExitButton'
import type { Section } from '@/components/Sidebar'
import Sidebar from '@/components/Sidebar'
import HideButton from '@/components/Sidebar/HideSidebarButton'
import Status from '@/components/Status'
import useMailToRef from '@/hooks/useMailToRef'
import { useNavigate } from '@/router'
import { cx } from '@emotion/css'
import { useLoopStatus } from '@inject/graphql/utils/useExerciseLoopStatusSubscription'
import CenteredSpinner from '@inject/shared/components/CenteredSpinner'
import type { FC, PropsWithChildren } from 'react'
import { Suspense } from 'react'
import { matchPath } from 'react-router-dom'
import TraineeEmailFormOverlay from '../../email/EmailFormOverlay/TraineeEmailFormOverlay'
import ChannelButton from '../ChannelButton'
import {
  contentClass,
  sidebarClass,
  sidebarClassCompact,
  viewClass,
} from '../classes'
import StopAnnounce from './StopAnnounce'
import useTraineeViewData from './useTraineeViewData'

interface TraineeViewProps extends PropsWithChildren {
  teamId?: string
  exerciseId: string
}

const TraineeView: FC<TraineeViewProps> = ({
  children,
  teamId,
  exerciseId,
}) => {
  const contentRef = useMailToRef()
  const hideLeftBar = useHideSidebarValue()
  const { running } = useLoopStatus()
  const nav = useNavigate()

  const { team, showExerciseTime, emailsEnabled, channels } =
    useTraineeViewData(exerciseId, teamId)

  const stickySections: Section[] = [
    {
      id: 'status',
      node: (
        <Status
          showTime={showExerciseTime}
          small={hideLeftBar}
          team={team}
          hideLabel={hideLeftBar}
        />
      ),
    },
  ]
  const sections: Section[] = [
    {
      id: 'options',
      name: 'Options',
      node: (
        <>
          <HideButton />
          <ExitButton hideLabel={hideLeftBar} />
        </>
      ),
    },
    ...(teamId
      ? [
          {
            id: 'channels',
            name: 'Channels',
            node: channels.map(channel => (
              <ChannelButton
                key={channel.id}
                channel={channel}
                exerciseId={exerciseId}
                linkTo='trainee'
                teamId={teamId}
                hideLabel={hideLeftBar}
              />
            )),
          },
        ]
      : []),
  ]

  return (
    <>
      {teamId && emailsEnabled && running && (
        <TraineeEmailFormOverlay
          teamId={teamId}
          exerciseId={exerciseId}
          onSuccess={threadId =>
            threadId &&
            !matchPath(
              {
                path: '/trainee/:exerciseId/:teamId/email',
                end: false,
              },
              window.location.pathname
            ) &&
            nav('/trainee/:exerciseId/:teamId/email/:tab/:threadId', {
              params: {
                exerciseId,
                tab: EmailSelection.RECEIVED,
                teamId,
                threadId,
              },
              state: {
                autoRedirect: true,
              },
            })
          }
        />
      )}

      <div className={viewClass}>
        <Sidebar
          className={cx({
            [sidebarClass]: !hideLeftBar,
            [sidebarClassCompact]: hideLeftBar,
          })}
          position='left'
          sections={sections}
          stickySections={teamId ? stickySections : undefined}
          hideNames={hideLeftBar}
          showLogo
        />

        <div style={{ position: 'relative', width: '100%' }}>
          <div className={contentClass} id='contentView' ref={contentRef}>
            <div style={{ position: 'sticky', top: '0', zIndex: '10' }}>
              <StopAnnounce />
            </div>
            <Suspense fallback={<CenteredSpinner />}>{children}</Suspense>
          </div>
        </div>

        <div id='toolPanel' />
        <div id='rightPanel' />
      </div>
    </>
  )
}

export default TraineeView
