import React, { useState } from 'react'
import {
  Animated,
  StyleProp,
  StyleSheet,
  Text,
  TextStyle,
  TouchableOpacity,
  View,
  ViewStyle,
} from 'react-native'

import { colors } from '../Colors'
import { NavigationProp } from '../Navigation'
import { TextStyles } from '../Styles'
import { OfflineToast } from '../components/OfflineToast'
import { ScreenNames } from '../constants/ScreenNames'
import { useIsFirstRouteInParent } from '../hooks/useIsFirstRouteInParent'
import { Strings } from '../i18n'
import BackArrow from '../icons/BackArrow'
import {
  TimeInterval,
  timeIntervals,
  timeIntervalStringLong,
} from '../types/TimeInterval'
import { useScreenName } from './CommonScreenContainer'
import { ContextMenuItem } from './ContextMenuModal'
import { Filter } from './Filter'
import { HeaderContextMenu } from './HeaderContextMenu'
import { InfoModalButton } from './InfoModalButton'
import { TimeIntervalSelectorModal } from './TimeIntervalSelectorModal'

const itemWidth = 40

const styles = StyleSheet.create({
  container: {
    position: 'relative',
    paddingVertical: 16,
    paddingHorizontal: 16,
    backgroundColor: colors.black,
  },
  topContainer: {
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'center',
    minHeight: 13,
  },
  horizontalContainer: {
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'space-between',
    height: 48,
  },
  title: {
    ...TextStyles.body,
    color: colors.midWhite,
    textAlign: 'center',
  },
  titleSecondary: {
    ...TextStyles.tinyCaps,
    textAlign: 'center',
  },
  leftContainer: {
    width: itemWidth * 2,
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'flex-start',
  },
  centerContainer: {
    flexShrink: 1,
    paddingHorizontal: 8,
  },
  rightContainer: {
    width: itemWidth * 2,
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'flex-end',
  },
  bottomContainer: {
    alignItems: 'center',
  },
})

export const HeaderNav: React.FC<{
  screenName?: string
  title?: string
  titleSecondary?: string | React.ReactNode
  titleInfoModal?: {
    title: string
    text: string
  }
  navigation: NavigationProp<ScreenNames>
  left?: React.ReactNode
  right?: React.ReactNode
  top?: React.ReactNode
  bottom?: React.ReactNode
  style?: StyleProp<ViewStyle>
  titleStyle?: StyleProp<TextStyle>
  titleOpacity?: Animated.Value | Animated.AnimatedInterpolation
  showToast: boolean
  showFeedback?: boolean
  timeInterval?: TimeInterval
  setTimeInterval?: (timeInterval: TimeInterval) => void
  contextMenuItems?: ContextMenuItem[]
}> = ({
  screenName,
  title,
  titleSecondary,
  titleInfoModal,
  navigation,
  left,
  right,
  top,
  bottom,
  style,
  titleStyle,
  titleOpacity,
  showToast,
  showFeedback = true,
  timeInterval,
  setTimeInterval,
  contextMenuItems,
}) => {
  const isFirstRouteInParent = useIsFirstRouteInParent()
  const [timeSelectorModalIsOpen, setTimeSelectorModalIsOpen] =
    useState<boolean>(false)
  const { screenName: providedScreenName } = useScreenName()

  return (
    <View style={[styles.container, style]}>
      <View style={styles.topContainer}>
        {top ??
          (timeInterval != null && setTimeInterval != null && (
            <>
              <Filter
                onPress={() => setTimeSelectorModalIsOpen(true)}
                label={timeIntervalStringLong[timeInterval]}
                accessibilityLabel={Strings.Shared.SelectTimeInterval}
              />
              <TimeIntervalSelectorModal
                isOpen={timeSelectorModalIsOpen}
                setIsOpen={setTimeSelectorModalIsOpen}
                timeInterval={timeInterval}
                setTimeInterval={setTimeInterval}
                timeIntervals={timeIntervals}
              />
            </>
          ))}
      </View>
      <View style={styles.horizontalContainer}>
        <View style={styles.leftContainer}>
          {left ??
            (!isFirstRouteInParent && (
              <TouchableOpacity
                onPress={(): void => navigation.goBack()}
                accessibilityLabel={Strings.Shared.Back}
              >
                <BackArrow />
              </TouchableOpacity>
            ))}
        </View>
        <View style={styles.centerContainer}>
          <View style={{ flexDirection: 'row', alignItems: 'center' }}>
            {title != null ? (
              <Animated.Text
                style={[
                  styles.title,
                  titleStyle,
                  titleOpacity != null ? { opacity: titleOpacity } : null,
                ]}
                ellipsizeMode="tail"
                numberOfLines={1}
              >
                {title}
              </Animated.Text>
            ) : null}
            {titleInfoModal != null ? (
              <InfoModalButton
                title={titleInfoModal.title}
                text={titleInfoModal.text}
                style={{}}
              />
            ) : null}
          </View>
          {titleSecondary &&
            (typeof titleSecondary === 'string' ? (
              <Text
                style={styles.titleSecondary}
                ellipsizeMode="tail"
                numberOfLines={1}
              >
                {titleSecondary}
              </Text>
            ) : (
              titleSecondary
            ))}
        </View>
        <View style={styles.rightContainer}>
          {right != null ? right : null}
          {showFeedback && (
            <HeaderContextMenu
              screenName={providedScreenName ?? screenName}
              contextMenuItems={contextMenuItems}
            />
          )}
        </View>
      </View>

      <View style={styles.bottomContainer}>{bottom}</View>
      <OfflineToast show={showToast} />
    </View>
  )
}
