import React, {useMemo} from 'react';
import {StyleSheet, View, TouchableOpacity} from 'react-native';
import {SwipeableListItemProps, SwipeableListItemSwipeActionsProps, SwipeAction} from './types';
import {SwipeableListItemContext} from './SwipeableListItemContext';
import {SwipeableListItemAvatar} from './SwipeableListItemAvatar';
import {SwipeableListItemContent} from './SwipeableListItemContent';
import {SwipeableListItemMetadata} from './SwipeableListItemMetadata';
import {
  SwipeableListItemSwipeActions,
  buildLeftSwipeActions,
  buildRightSwipeActions,
} from './SwipeableListItemSwipeActions';
import {SwipeableListItemSelection} from './SwipeableListItemSelection';
import {SwipeableListItemSelected} from './SwipeableListItemSelected';
import {SwipeableListItemUnselected} from './SwipeableListItemUnselected';
import {SwipeableListItemSwipeLeftActions} from './SwipeableListItemSwipeLeftActions';
import {SwipeableListItemSwipeRightActions} from './SwipeableListItemSwipeRightActions';
import {SwipeableListItemSwipeLeftAction} from './SwipeableListItemSwipeLeftAction';
import {SwipeableListItemSwipeRightAction} from './SwipeableListItemSwipeRightAction';
import {SwipeableListItemTitle} from './SwipeableListItemTitle';
import {SwipeableListItemSubTitle} from './SwipeableListItemSubTitle';
import {SwipeableListItemIcon} from './SwipeableListItemIcon';
import SwipeableComponent from '../Swipeable/Swipeable';
import {useTheme, ColorsScheme} from '../../theme/ThemeContext';

/**
 * SwipeableListItem - A flexible compound component for creating swipeable list items
 * 
 * @example
 * ```tsx
 * // New declarative swipe actions
 * <SwipeableListItem onPress={() => {}}>
 *   <SwipeableListItem.SwipeLeftActions>
 *     <SwipeableListItem.SwipeLeftAction backgroundColor="#007AFF" width={80} onPress={() => {}}>
 *       <View><Text>Read</Text></View>
 *     </SwipeableListItem.SwipeLeftAction>
 *   </SwipeableListItem.SwipeLeftActions>
 *   
 *   <SwipeableListItem.SwipeRightActions>
 *     <SwipeableListItem.SwipeRightAction backgroundColor="#FF3B30" width={80} onPress={() => {}}>
 *       <View><Text>Delete</Text></View>
 *     </SwipeableListItem.SwipeRightAction>
 *   </SwipeableListItem.SwipeRightActions>
 *   
 *   <SwipeableListItem.Avatar source={avatarUri} />
 *   <SwipeableListItem.Content>
 *     <SwipeableListItem.Title>John Doe</SwipeableListItem.Title>
 *     <SwipeableListItem.SubTitle>Hey there!</SwipeableListItem.SubTitle>
 *   </SwipeableListItem.Content>
 *   <SwipeableListItem.Metadata timestamp="2:30 PM">
 *     <SwipeableListItem.Icon><Text>📌</Text></SwipeableListItem.Icon>
 *   </SwipeableListItem.Metadata>
 * </SwipeableListItem>
 * ```
 */
type SwipeableListItemComponent = React.FC<SwipeableListItemProps> & {
  Avatar: typeof SwipeableListItemAvatar;
  Content: typeof SwipeableListItemContent;
  Metadata: typeof SwipeableListItemMetadata;
  // Legacy
  SwipeActions: typeof SwipeableListItemSwipeActions;
  // New declarative API
  SwipeLeftActions: typeof SwipeableListItemSwipeLeftActions;
  SwipeRightActions: typeof SwipeableListItemSwipeRightActions;
  SwipeLeftAction: typeof SwipeableListItemSwipeLeftAction;
  SwipeRightAction: typeof SwipeableListItemSwipeRightAction;
  // Content sub-components
  Title: typeof SwipeableListItemTitle;
  SubTitle: typeof SwipeableListItemSubTitle;
  // Metadata sub-components
  Icon: typeof SwipeableListItemIcon;
  // Selection compound component
  Selection: typeof SwipeableListItemSelection;
  Selected: typeof SwipeableListItemSelected;
  Unselected: typeof SwipeableListItemUnselected;
};

const SwipeableListItem: SwipeableListItemComponent = ({
  children,
  containerStyle,
  backgroundColor,
  selected,
  onSelectChange,
  isSelection,
  onPress,
  onLongPress,
  ...touchableProps // Capture all remaining TouchableOpacity props
}) => {
  const {colors} = useTheme();
  const styles = themedStyle(colors);

  // Extract new declarative swipe actions from children
  const {leftActions, rightActions, swipeConfig} = useMemo(() => {
    let config: SwipeableListItemSwipeActionsProps | undefined;
    const extractedLeftActions: SwipeAction[] = [];
    const extractedRightActions: SwipeAction[] = [];
    
    React.Children.forEach(children, child => {
      if (!React.isValidElement(child)) return;
      
      // Legacy SwipeActions component
      if (child.type === SwipeableListItemSwipeActions) {
        config = child.props as SwipeableListItemSwipeActionsProps;
      }
      
      // New declarative SwipeLeftActions
      if (child.type === SwipeableListItemSwipeLeftActions) {
        const props = child.props as any;
        if (props.children) {
          React.Children.forEach(props.children, actionChild => {
            if (React.isValidElement(actionChild) && actionChild.type === SwipeableListItemSwipeLeftAction) {
              const actionProps = actionChild.props as any;
              // Extract children and TouchableOpacity props
              const {children: actionChildren, backgroundColor, width, onPress, style, ...touchableProps} = actionProps;
              extractedLeftActions.push({
                comp: actionChildren,
                color: backgroundColor,
                width: width || 80,
                onPress,
                touchableProps, // Pass through all TouchableOpacity props
              });
            }
          });
        }
      }
      
      // New declarative SwipeRightActions
      if (child.type === SwipeableListItemSwipeRightActions) {
        const props = child.props as any;
        if (props.children) {
          React.Children.forEach(props.children, actionChild => {
            if (React.isValidElement(actionChild) && actionChild.type === SwipeableListItemSwipeRightAction) {
              const actionProps = actionChild.props as any;
              // Extract children and TouchableOpacity props
              const {children: actionChildren, backgroundColor, width, onPress, style, ...touchableProps} = actionProps;
              extractedRightActions.push({
                comp: actionChildren,
                color: backgroundColor,
                width: width || 80,
                onPress,
                touchableProps, // Pass through all TouchableOpacity props
              });
            }
          });
        }
      }
    });
    
    // Use extracted declarative actions if provided
    // Otherwise, fallback to legacy config (only if config exists)
    const finalLeftActions = extractedLeftActions.length > 0 
      ? extractedLeftActions 
      : (config ? buildLeftSwipeActions(config, colors) : []);
      
    const finalRightActions = extractedRightActions.length > 0
      ? extractedRightActions
      : (config ? buildRightSwipeActions(config, colors) : []);
    
    return {
      leftActions: finalLeftActions,
      rightActions: finalRightActions,
      swipeConfig: config,
    };
  }, [children, colors]);

  // Context value for child components
  const contextValue = useMemo(
    () => ({
      backgroundColor,
      onPress,
      onLongPress,
      selected,
      onSelectChange,
      isSelection,
      swipeConfig,
    }),
    [backgroundColor, onPress, onLongPress, selected, onSelectChange, isSelection, swipeConfig]
  );

  // Determine if swipe is enabled (disabled in selection mode)
  const leftSwipeEnabled = !isSelection && leftActions.length > 0;
  const rightSwipeEnabled = !isSelection && rightActions.length > 0;

  // Filter out configuration-only components from render
  const renderChildren = React.Children.toArray(children).filter(
    child => !React.isValidElement(child) || (
      child.type !== SwipeableListItemSwipeActions &&
      child.type !== SwipeableListItemSwipeLeftActions &&
      child.type !== SwipeableListItemSwipeRightActions
    )
  );

  // Render content
  const renderContent = () => (
    <TouchableOpacity
      style={[
        styles.container,
        {backgroundColor: backgroundColor ?? colors.background_primary},
        containerStyle,
      ]}
      activeOpacity={0.8}
      onLongPress={onLongPress}
      onPress={onPress}
      {...touchableProps}>
      {renderChildren}
      <View style={styles.bottomSeparator} />
    </TouchableOpacity>
  );

  // Wrap with swipeable if actions are configured
  if (leftSwipeEnabled || rightSwipeEnabled) {
    return (
      <SwipeableListItemContext.Provider value={contextValue}>
        <SwipeableComponent
          leftSwipeEnabled={leftSwipeEnabled}
          rightSwipeEnabled={rightSwipeEnabled}
          leftActions={leftActions}
          rightActions={rightActions}>
          {renderContent()}
        </SwipeableComponent>
      </SwipeableListItemContext.Provider>
    );
  }

  return (
    <SwipeableListItemContext.Provider value={contextValue}>
      {renderContent()}
    </SwipeableListItemContext.Provider>
  );
};

// Attach sub-components
SwipeableListItem.Avatar = SwipeableListItemAvatar;
SwipeableListItem.Content = SwipeableListItemContent;
SwipeableListItem.Metadata = SwipeableListItemMetadata;
// Legacy swipe actions
SwipeableListItem.SwipeActions = SwipeableListItemSwipeActions;
// New declarative swipe actions API
SwipeableListItem.SwipeLeftActions = SwipeableListItemSwipeLeftActions;
SwipeableListItem.SwipeRightActions = SwipeableListItemSwipeRightActions;
SwipeableListItem.SwipeLeftAction = SwipeableListItemSwipeLeftAction;
SwipeableListItem.SwipeRightAction = SwipeableListItemSwipeRightAction;
// Content sub-components
SwipeableListItem.Title = SwipeableListItemTitle;
SwipeableListItem.SubTitle = SwipeableListItemSubTitle;
// Metadata sub-components
SwipeableListItem.Icon = SwipeableListItemIcon;
// Selection compound component
SwipeableListItem.Selection = SwipeableListItemSelection;
SwipeableListItem.Selected = SwipeableListItemSelected;
SwipeableListItem.Unselected = SwipeableListItemUnselected;

const themedStyle = (colors: ColorsScheme) =>
  StyleSheet.create({
    container: {
      backgroundColor: colors.background_primary,
      flexDirection: 'row',
      alignItems: 'flex-start',
      paddingLeft: 16,
      paddingTop: 10,
      height: 77.33,
      paddingRight: 31,
      width: '100%',
    },
    bottomSeparator: {
      position: 'absolute',
      bottom: 0.1,
      right: 0,
      width: '88%',
      justifyContent: 'center',
      borderBottomWidth: 0.3,
      borderBottomColor: colors.separator_non_opaque,
    },
  });

export default SwipeableListItem;
