import React, { useState, useEffect, useCallback, useRef } from 'react';
import { 
  View, 
  Text, 
  StyleSheet, 
  FlatList, 
  TouchableOpacity, 
  Dimensions,
  AppState,
  AppStateStatus
} from 'react-native';
import Animated, { FadeIn } from 'react-native-reanimated';
import { useNavigation } from '@react-navigation/native';
import { NavigationProp } from '@react-navigation/native';
import { RootStackParamList } from '../../navigation/AppNavigator';
import { StreamingContent, catalogService } from '../../services/catalogService';
import { LinearGradient } from 'expo-linear-gradient';
import { Image as ExpoImage } from 'expo-image';
import { useTheme } from '../../contexts/ThemeContext';
import { storageService } from '../../services/storageService';
import { logger } from '../../utils/logger';

// Define interface for continue watching items
interface ContinueWatchingItem extends StreamingContent {
  progress: number;
  lastUpdated: number;
  season?: number;
  episode?: number;
  episodeTitle?: string;
}

// Define the ref interface
interface ContinueWatchingRef {
  refresh: () => Promise<boolean>;
}

// Dynamic poster calculation based on screen width for Continue Watching section
const calculatePosterLayout = (screenWidth: number) => {
  const MIN_POSTER_WIDTH = 120; // Slightly larger for continue watching items
  const MAX_POSTER_WIDTH = 160; // Maximum poster width for this section
  const HORIZONTAL_PADDING = 40; // Total horizontal padding/margins
  
  // Calculate how many posters can fit (fewer items for continue watching)
  const availableWidth = screenWidth - HORIZONTAL_PADDING;
  const maxColumns = Math.floor(availableWidth / MIN_POSTER_WIDTH);
  
  // Limit to reasonable number of columns (2-5 for continue watching)
  const numColumns = Math.min(Math.max(maxColumns, 2), 5);
  
  // Calculate actual poster width
  const posterWidth = Math.min(availableWidth / numColumns, MAX_POSTER_WIDTH);
  
  return {
    numColumns,
    posterWidth,
    spacing: 12 // Space between posters
  };
};

const { width } = Dimensions.get('window');
const posterLayout = calculatePosterLayout(width);
const POSTER_WIDTH = posterLayout.posterWidth;

// Function to validate IMDB ID format
const isValidImdbId = (id: string): boolean => {
  // IMDB IDs should start with 'tt' followed by 7-10 digits
  const imdbPattern = /^tt\d{7,10}$/;
  return imdbPattern.test(id);
};

// Create a proper imperative handle with React.forwardRef and updated type
const ContinueWatchingSection = React.forwardRef<ContinueWatchingRef>((props, ref) => {
  const navigation = useNavigation<NavigationProp<RootStackParamList>>();
  const { currentTheme } = useTheme();
  const [continueWatchingItems, setContinueWatchingItems] = useState<ContinueWatchingItem[]>([]);
  const [loading, setLoading] = useState(true);
  const appState = useRef(AppState.currentState);
  const refreshTimerRef = useRef<NodeJS.Timeout | null>(null);

  // Use a state to track if a background refresh is in progress
  const [isRefreshing, setIsRefreshing] = useState(false);

  // Modified loadContinueWatching to be more efficient
  const loadContinueWatching = useCallback(async (isBackgroundRefresh = false) => {
    // Prevent multiple concurrent refreshes
    if (isRefreshing) return;

    if (!isBackgroundRefresh) {
      setLoading(true);
    }
    setIsRefreshing(true);

    try {
      const allProgress = await storageService.getAllWatchProgress();
      
      if (Object.keys(allProgress).length === 0) {
        setContinueWatchingItems([]);
        return;
      }

      const progressItems: ContinueWatchingItem[] = [];
      const latestEpisodes: Record<string, ContinueWatchingItem> = {};
      const contentPromises: Promise<void>[] = [];
      
      // Process each saved progress
      for (const key in allProgress) {
        // Parse the key to get type and id
        const keyParts = key.split(':');
        const [type, id, ...episodeIdParts] = keyParts;
        const episodeId = episodeIdParts.length > 0 ? episodeIdParts.join(':') : undefined;
        const progress = allProgress[key];
        
        // Skip items that are more than 85% complete (effectively finished)
        const progressPercent = (progress.currentTime / progress.duration) * 100;
        
        if (progressPercent >= 85) {
          continue;
        }
        
        const contentPromise = (async () => {
          try {
            // Validate IMDB ID format before attempting to fetch
            if (!isValidImdbId(id)) {
              return;
            }
            
            let content: StreamingContent | null = null;
            
            // Get basic content details using catalogService (no enhanced metadata needed for continue watching)
            content = await catalogService.getBasicContentDetails(type, id);
            
            if (content) {
              // Extract season and episode info from episodeId if available
              let season: number | undefined;
              let episode: number | undefined;
              let episodeTitle: string | undefined;
              
              if (episodeId && type === 'series') {
                // Try different episode ID formats
                let match = episodeId.match(/s(\d+)e(\d+)/i); // Format: s1e1
                if (match) {
                  season = parseInt(match[1], 10);
                  episode = parseInt(match[2], 10);
                  episodeTitle = `Episode ${episode}`;
                } else {
                  // Try format: seriesId:season:episode (e.g., tt0108778:4:6)
                  const parts = episodeId.split(':');
                  if (parts.length >= 3) {
                    const seasonPart = parts[parts.length - 2]; // Second to last part
                    const episodePart = parts[parts.length - 1]; // Last part
                    
                    const seasonNum = parseInt(seasonPart, 10);
                    const episodeNum = parseInt(episodePart, 10);
                    
                    if (!isNaN(seasonNum) && !isNaN(episodeNum)) {
                      season = seasonNum;
                      episode = episodeNum;
                      episodeTitle = `Episode ${episode}`;
                    }
                  }
                }
              }
              
              const continueWatchingItem: ContinueWatchingItem = {
                ...content,
                progress: progressPercent,
                lastUpdated: progress.lastUpdated,
                season,
                episode,
                episodeTitle
              };
              
              if (type === 'series') {
                // For series, keep only the latest watched episode for each show
                if (!latestEpisodes[id] || latestEpisodes[id].lastUpdated < progress.lastUpdated) {
                  latestEpisodes[id] = continueWatchingItem;
                }
              } else {
                // For movies, add to the list directly
                progressItems.push(continueWatchingItem);
              }
            }
          } catch (error) {
            logger.error(`Failed to get content details for ${type}:${id}`, error);
          }
        })();
        
        contentPromises.push(contentPromise);
      }
      
      // Wait for all content to be processed
      await Promise.all(contentPromises);
      
      // Add the latest episodes for each series to the items list
      progressItems.push(...Object.values(latestEpisodes));
      
      // Sort by last updated time (most recent first)
      progressItems.sort((a, b) => b.lastUpdated - a.lastUpdated);
      
      // Show all continue watching items (no limit)
      setContinueWatchingItems(progressItems);
    } catch (error) {
      logger.error('Failed to load continue watching items:', error);
    } finally {
      setLoading(false);
      setIsRefreshing(false);
    }
  }, [isRefreshing]);

  // Function to handle app state changes
  const handleAppStateChange = useCallback((nextAppState: AppStateStatus) => {
    if (
      appState.current.match(/inactive|background/) &&
      nextAppState === 'active'
    ) {
      // App has come to the foreground - trigger a background refresh
      loadContinueWatching(true);
    }
    appState.current = nextAppState;
  }, [loadContinueWatching]);

  // Set up storage event listener and app state listener
  useEffect(() => {
    // Add app state change listener
    const subscription = AppState.addEventListener('change', handleAppStateChange);

    // Add custom event listener for watch progress updates
    const watchProgressUpdateHandler = () => {
      // Debounce updates to avoid too frequent refreshes
      if (refreshTimerRef.current) {
        clearTimeout(refreshTimerRef.current);
      }
      refreshTimerRef.current = setTimeout(() => {
        // Trigger a background refresh
        loadContinueWatching(true);
      }, 500); // Increased debounce time slightly
    };

    // Try to set up a custom event listener or use a timer as fallback
    if (storageService.subscribeToWatchProgressUpdates) {
      const unsubscribe = storageService.subscribeToWatchProgressUpdates(watchProgressUpdateHandler);
      return () => {
        subscription.remove();
        unsubscribe();
        if (refreshTimerRef.current) {
          clearTimeout(refreshTimerRef.current);
        }
      };
    } else {
      // Fallback: poll for updates every 30 seconds
      const intervalId = setInterval(() => loadContinueWatching(true), 30000);
      return () => {
        subscription.remove();
        clearInterval(intervalId);
        if (refreshTimerRef.current) {
          clearTimeout(refreshTimerRef.current);
        }
      };
    }
  }, [loadContinueWatching, handleAppStateChange]);

  // Initial load
  useEffect(() => {
    loadContinueWatching();
  }, [loadContinueWatching]);

  // Expose the refresh function via the ref
  React.useImperativeHandle(ref, () => ({
    refresh: async () => {
      // Allow manual refresh to show loading indicator
      await loadContinueWatching(false);
      return true;
    }
  }));

  const handleContentPress = useCallback((id: string, type: string) => {
    navigation.navigate('Metadata', { id, type });
  }, [navigation]);

  // If no continue watching items, don't render anything
  if (continueWatchingItems.length === 0) {
    return null;
  }

  return (
    <Animated.View entering={FadeIn.duration(300).delay(150)} style={styles.container}>
      <View style={styles.header}>
        <View style={styles.titleContainer}>
          <Text style={[styles.title, { color: currentTheme.colors.text }]}>Continue Watching</Text>
          <View style={[styles.titleUnderline, { backgroundColor: currentTheme.colors.primary }]} />
        </View>
      </View>
      
      <FlatList
        data={continueWatchingItems}
        renderItem={({ item }) => (
          <TouchableOpacity
            style={[styles.wideContentItem, {
              backgroundColor: currentTheme.colors.elevation1,
              borderColor: currentTheme.colors.border,
              shadowColor: currentTheme.colors.black
            }]}
            activeOpacity={0.8}
            onPress={() => handleContentPress(item.id, item.type)}
          >
            {/* Poster Image */}
            <View style={styles.posterContainer}>
              <ExpoImage
                source={{ uri: item.poster || 'https://via.placeholder.com/300x450' }}
                style={styles.continueWatchingPoster}
                contentFit="cover"
                cachePolicy="memory"
                transition={200}
                placeholder={{ uri: 'https://via.placeholder.com/300x450' }}
                placeholderContentFit="cover"
                recyclingKey={item.id}
              />
            </View>

            {/* Content Details */}
            <View style={styles.contentDetails}>
              <View style={styles.titleRow}>
                <Text 
                  style={[styles.contentTitle, { color: currentTheme.colors.highEmphasis }]}
                  numberOfLines={1}
                >
                  {item.name}
                </Text>
                <View style={[styles.progressBadge, { backgroundColor: currentTheme.colors.primary }]}>
                  <Text style={styles.progressText}>{Math.round(item.progress)}%</Text>
                </View>
              </View>

              {/* Episode Info or Year */}
              {(() => {
                if (item.type === 'series' && item.season && item.episode) {
                  return (
                    <View style={styles.episodeRow}>
                      <Text style={[styles.episodeText, { color: currentTheme.colors.mediumEmphasis }]}>
                        Season {item.season}
                      </Text>
                      {item.episodeTitle && (
                        <Text 
                          style={[styles.episodeTitle, { color: currentTheme.colors.mediumEmphasis }]}
                          numberOfLines={1}
                        >
                          {item.episodeTitle}
                        </Text>
                      )}
                    </View>
                  );
                } else {
                  return (
                    <Text style={[styles.yearText, { color: currentTheme.colors.mediumEmphasis }]}>
                      {item.year} • {item.type === 'movie' ? 'Movie' : 'Series'}
                    </Text>
                  );
                }
              })()}

              {/* Progress Bar */}
              <View style={styles.wideProgressContainer}>
                <View style={styles.wideProgressTrack}>
                <View 
                  style={[
                      styles.wideProgressBar, 
                      { 
                        width: `${item.progress}%`, 
                        backgroundColor: currentTheme.colors.primary 
                      }
                  ]} 
                />
                </View>
                <Text style={[styles.progressLabel, { color: currentTheme.colors.textMuted }]}>
                  {Math.round(item.progress)}% watched
                </Text>
              </View>
            </View>
          </TouchableOpacity>
        )}
        keyExtractor={(item) => `continue-${item.id}-${item.type}`}
        horizontal
        showsHorizontalScrollIndicator={false}
        contentContainerStyle={styles.wideList}
        snapToInterval={280 + 16} // Card width + margin
        decelerationRate="fast"
        snapToAlignment="start"
        ItemSeparatorComponent={() => <View style={{ width: 16 }} />}
      />
    </Animated.View>
  );
});

const styles = StyleSheet.create({
  container: {
    marginBottom: 28,
    paddingTop: 0,
    marginTop: 12,
  },
  header: {
    flexDirection: 'row',
    justifyContent: 'space-between',
    alignItems: 'center',
    paddingHorizontal: 16,
    marginBottom: 16,
  },
  titleContainer: {
    position: 'relative',
  },
  title: {
    fontSize: 24,
    fontWeight: '800',
    letterSpacing: 0.5,
    marginBottom: 4,
  },
  titleUnderline: {
    position: 'absolute',
    bottom: -2,
    left: 0,
    width: 40,
    height: 3,
    borderRadius: 2,
    opacity: 0.8,
  },
  wideList: {
    paddingHorizontal: 16,
    paddingBottom: 8,
    paddingTop: 4,
  },
  wideContentItem: {
    width: 280,
    height: 120,
    flexDirection: 'row',
    borderRadius: 12,
    overflow: 'hidden',
    elevation: 6,
    shadowOffset: { width: 0, height: 3 },
    shadowOpacity: 0.2,
    shadowRadius: 6,
    borderWidth: 1,
  },
  posterContainer: {
    width: 80,
    height: '100%',
  },
  continueWatchingPoster: {
    width: '100%',
    height: '100%',
    borderTopLeftRadius: 12,
    borderBottomLeftRadius: 12,
  },
  contentDetails: {
    flex: 1,
    padding: 12,
    justifyContent: 'space-between',
  },
  titleRow: {
    flexDirection: 'row',
    justifyContent: 'space-between',
    alignItems: 'flex-start',
    marginBottom: 4,
  },
  contentTitle: {
    fontSize: 16,
    fontWeight: '700',
    flex: 1,
    marginRight: 8,
  },
  progressBadge: {
    paddingHorizontal: 8,
    paddingVertical: 3,
    borderRadius: 12,
    minWidth: 44,
    alignItems: 'center',
  },
  progressText: {
    fontSize: 12,
    fontWeight: '700',
    color: '#FFFFFF',
  },
  episodeRow: {
    marginBottom: 8,
  },
  episodeText: {
    fontSize: 13,
    fontWeight: '600',
    marginBottom: 2,
  },
  episodeTitle: {
    fontSize: 12,
  },
  yearText: {
    fontSize: 13,
    fontWeight: '500',
    marginBottom: 8,
  },
  wideProgressContainer: {
    marginTop: 'auto',
  },
  wideProgressTrack: {
    height: 4,
    backgroundColor: 'rgba(255,255,255,0.1)',
    borderRadius: 2,
    marginBottom: 4,
  },
  wideProgressBar: {
    height: '100%',
    borderRadius: 2,
  },
  progressLabel: {
    fontSize: 11,
    fontWeight: '500',
  },
  // Keep old styles for backward compatibility
  list: {
    paddingHorizontal: 16,
    paddingBottom: 8,
    paddingTop: 4,
  },
  contentItem: {
    width: POSTER_WIDTH,
    aspectRatio: 2/3,
    margin: 0,
    borderRadius: 8,
    overflow: 'hidden',
    position: 'relative',
    elevation: 8,
    shadowOffset: { width: 0, height: 4 },
    shadowOpacity: 0.3,
    shadowRadius: 8,
    borderWidth: 1,
  },
  contentItemContainer: {
    width: '100%',
    height: '100%',
    borderRadius: 8,
    overflow: 'hidden',
    position: 'relative',
  },
  poster: {
    width: '100%',
    height: '100%',
    borderRadius: 8,
  },
  episodeInfoContainer: {
    position: 'absolute',
    bottom: 3,
    left: 0,
    right: 0,
    padding: 4,
    paddingHorizontal: 8,
  },
  episodeInfo: {
    fontSize: 12,
    fontWeight: 'bold',
  },
  progressBarContainer: {
    position: 'absolute',
    bottom: 0,
    left: 0,
    right: 0,
    height: 3,
    backgroundColor: 'rgba(0,0,0,0.5)',
  },
  progressBar: {
    height: '100%',
  },
});

export default React.memo(ContinueWatchingSection); 