import React, { useRef, useEffect, useCallback } from 'react';
import { Animated } from 'react-native';
import { SPlaceholder } from '../s-components/s-placeholder';
import { getPlaceholderHeight } from '../transducers';
import { inputFocus$ } from './input';
import { SPlaceholderAnimated } from '../s-components/s-placeholder-animated';

const duration = 250;

type TProps = {
  variant: string;
  baseWidth: number;
  baseHeight: number;
  marginBottom?: number;
  withAnimation?: boolean;
};

export const Placeholder: React.FC<TProps> = props => {
  const { variant, baseWidth, baseHeight, marginBottom, withAnimation } = props;
  const ref = useRef<React.RefObject<any>>();

  const opacityValue = useRef(new Animated.Value(1));

  const show = () => {
    //@ts-ignore
    ref.current!.setNativeProps({
      style: [{ height: 0 }],
    });
    Animated.timing(opacityValue.current, {
      toValue: 0,
      duration,
      useNativeDriver: true,
    }).start();
  };

  const hide = useCallback(() => {
    //@ts-ignore
    ref.current!.setNativeProps({
      style: [
        {
          height: getPlaceholderHeight(baseWidth, baseHeight),
        },
      ],
    });
    setTimeout(() => {
      Animated.timing(opacityValue.current, {
        toValue: 1,
        duration,
        useNativeDriver: true,
      }).start();
    }, 200);
  }, [baseWidth, baseHeight]);

  useEffect(() => {
    const focusSub = inputFocus$.subscribe(isFocus => {
      if (!ref.current) return null;
      if (isFocus) {
        show();
      } else hide();
    });

    return () => {
      focusSub.unsubscribe();

      opacityValue.current.stopAnimation();
    };
  }, []);

  let uri;

  /* eslint-disable global-require */
  switch (variant) {
    case 'no-starred':
      uri = require('../../../assets/placeholders/no-starred-tracks.png');
      break;
    case 'no-charts':
      uri = require('../../../assets/placeholders/all-caught-up.png');
      break;
    case 'profile-paused':
      uri = require('../../../assets/profile-paused.png');
      break;
    case 'load-failed':
    case 'load-failed-graph':
      uri = require('../../../assets/placeholders/failed-to-load-the-page.png');
      break;
    case 'load-failed-light':
      uri = require('../../../assets/placeholders/failed-to-load-the-page-light.png');
      break;
    case 'no-search':
      uri = require('../../../assets/placeholders/no-tracks-to-show-dark.png');
      break;
    case 'no-search-white':
      uri = require('../../../assets/placeholders/no-tracks-to-show.png');
      break;
    case 'no-search-light':
      uri = require('../../../assets/placeholders/no-tracks-to-show-light.png');
      break;
    case 'network-failed':
      uri = require('../../../assets/placeholders/connection-is-lost.png');
      break;
    case 'network-failed-white':
      uri = require('../../../assets/placeholders/connection-is-lost-white.png');
      break;
    case 'network-failed-light':
      uri = require('../../../assets/placeholders/connection-is-lost-light.png');
      break;
    case 'empty-search':
      uri = require('../../../assets/placeholders/start-typing.png');
      break;
    case 'no-notifications':
      uri = require('../../../assets/placeholders/all-caught-up.png');
      break;
    case 'no-tracks-in-chart':
      uri = require('../../../assets/placeholders/no-tracks-in-chart.png');
      break;
    case 'no-playlists':
      uri = require('../../../assets/placeholders/no-playlists.png');
      break;
    case 'no-apple':
      uri = require('../../../assets/placeholders/no-apple.png');
      break;
    case 'no-spotify':
      uri = require('../../../assets/placeholders/no-spotify.png');
      break;
    case 'no-amazon':
      uri = require('../../../assets/placeholders/no-amazon.png');
      break;
    case 'no-any-charts':
      uri = require('../../../assets/placeholders/no-any-charts.png');
      break;
    case 'not-available-in-market':
      uri = require('../../../assets/placeholders/not-available-in-market.png');
      break;
    case 'no-streams':
      uri = require('../../../assets/placeholders/no-streams.png');
      break;
    case 'no-listeners':
      uri = require('../../../assets/placeholders/no-listeners.png');
      break;
    case 'no-followers':
      uri = require('../../../assets/placeholders/no-followers.png');
      break;
    case 'no-track-entered':
      uri = require('../../../assets/placeholders/no-tracks-entered.png');
      break;
    case 'no-track-exited':
      uri = require('../../../assets/placeholders/no-tracks-exited.png');
      break;
    case 'no-major-moves':
      uri = require('../../../assets/placeholders/no-major-moves.png');
      break;
    case 'global':
      uri = require('../../../assets/placeholders/global.png');
      break;
    case 'notifications-disabled':
      uri = require('../../../assets/placeholders/notifications-disabled.png');
      break;
    case 'no-markets':
      uri = require('../../../assets/placeholders/no-markets.png');
      break;
    default:
      break;
  }

  const placeholder = (
    <SPlaceholder
      maxWidth={baseWidth}
      height={getPlaceholderHeight(baseWidth, baseHeight)}
      source={uri}
      marginBottom={marginBottom}
    />
  );

  const animatedPlaceholder = (
    <SPlaceholderAnimated
      source={uri}
      marginBottom={marginBottom}
      ref={ref}
      style={{
        opacity: opacityValue.current,
        maxWidth: baseWidth,
        height: getPlaceholderHeight(baseWidth, baseHeight),
      }}
    />
  );

  if (withAnimation) {
    return animatedPlaceholder;
  }
  return placeholder;
};

Placeholder.defaultProps = {
  withAnimation: false,
};
