import React from 'react'; import { View, Text, FlatList, TouchableOpacity, Image, Dimensions, StyleSheet, } from 'react-native'; import { useTheme } from '../services/ThemeContext'; const { width } = Dimensions.get('window'); const GRID_GAP = 2; const PhotoGrid = ({ data, onItemPress, columns = 3, refreshControl, ListHeaderComponent, ListEmptyComponent, ListFooterComponent, onEndReached, }) => { const { theme } = useTheme(); const itemSize = (width - GRID_GAP * (columns + 1)) / columns; const getServiceIcon = (type) => ({ DEVICE: '📱', GOOGLE_PHOTOS: '📷', ICLOUD_PHOTOS: '🍎', NAS: '💾' }[type] || '📱'); const renderSourceBadges = (item) => { const sources = item.sources && item.sources.length > 0 ? item.sources : [item.source_service]; if (sources.length === 1) { // Single source — simple badge return ( {getServiceIcon(sources[0])} ); } // Multiple sources — show all icons with a subtle indicator return ( {sources.map((src, i) => ( {getServiceIcon(src)} ))} ); }; const renderItem = ({ item }) => ( onItemPress?.(item)} activeOpacity={0.8} > {item.local_path ? ( console.warn(`Image load failed [${item.source_service}]: ${item.local_path?.substring(0, 80)}`, e.nativeEvent?.error)} /> ) : ( 📷 )} {item.media_type === 'video' && ( ▶ )} {renderSourceBadges(item)} ); return ( item.id?.toString() || item.source_id || i.toString()} numColumns={columns} contentContainerStyle={styles.gridContent} refreshControl={refreshControl} ListHeaderComponent={ListHeaderComponent} ListEmptyComponent={ListEmptyComponent} ListFooterComponent={ListFooterComponent} onEndReached={onEndReached} onEndReachedThreshold={0.5} /> ); }; const styles = StyleSheet.create({ gridContent: { paddingBottom: 20 }, gridItem: { margin: GRID_GAP / 2, position: 'relative', }, gridImage: { width: '100%', height: '100%' }, placeholder: { width: '100%', height: '100%', justifyContent: 'center', alignItems: 'center', }, videoOverlay: { position: 'absolute', top: 0, left: 0, right: 0, bottom: 0, backgroundColor: 'rgba(0,0,0,0.25)', justifyContent: 'center', alignItems: 'center', }, sourceBadge: { position: 'absolute', bottom: 4, right: 4, backgroundColor: 'rgba(0,0,0,0.5)', borderRadius: 8, paddingHorizontal: 4, paddingVertical: 2, }, multiSourceBadge: { position: 'absolute', bottom: 4, right: 4, backgroundColor: 'rgba(0,0,0,0.6)', borderRadius: 8, paddingHorizontal: 4, paddingVertical: 2, flexDirection: 'row', gap: 2, }, }); export default PhotoGrid;