import '../../core/contracts/tmdb.dart';
import 'tmdb_image_url.dart';

class TmdbImageSelector {
  static TmdbImage? bestImage(
    List<TmdbImage> images, {
    bool preferNeutral = false,
  }) {
    if (images.isEmpty) return null;
    if (preferNeutral) {
      final neutrals = images
          .where((i) => i.filePath.isNotEmpty && i.isLanguageNeutral)
          .toList();
      if (neutrals.isNotEmpty) return _pickBest(neutrals);
    }
    return _pickBest(images);
  }

  static TmdbImage? _pickBest(List<TmdbImage> images) {
    TmdbImage? best;
    for (final image in images) {
      if (image.filePath.isEmpty) continue;
      if (best == null || _isBetter(image, best)) best = image;
    }
    return best;
  }

  static String? backdropUrl(
    TmdbImageSet? imageSet,
    String? imageBaseUrl, {
    String size = 'original',
  }) {
    if (imageBaseUrl == null || imageBaseUrl.isEmpty) return null;
    final image = bestImage(
      imageSet?.backdrops ?? const [],
      preferNeutral: true,
    );
    return TmdbImageUrl.backdrop(imageBaseUrl, image?.filePath, size: size);
  }

  static String? posterUrl(
    TmdbImageSet? imageSet,
    String? imageBaseUrl, {
    String size = 'w500',
  }) {
    if (imageBaseUrl == null || imageBaseUrl.isEmpty) return null;
    final image = bestImage(imageSet?.posters ?? const []);
    return TmdbImageUrl.poster(imageBaseUrl, image?.filePath, size: size);
  }


  static String? logoUrl(
    TmdbImageSet? imageSet,
    String? imageBaseUrl, {
    String? language,
    String size = 'w500',
  }) {
    if (imageBaseUrl == null || imageBaseUrl.isEmpty) return null;
    final logos = imageSet?.logos ?? const <TmdbImage>[];
    if (logos.isEmpty) return null;

    final lang = _iso639Of(language);
    final image =
        (lang != null ? _pickBest(_withLang(logos, lang)) : null) ??
        _pickBest(_withLang(logos, 'en')) ??
        _pickBest(logos.where((i) => i.isLanguageNeutral).toList()) ??
        _pickBest(logos);
    return TmdbImageUrl.logo(imageBaseUrl, image?.filePath, size: size);
  }

  static List<TmdbImage> _withLang(List<TmdbImage> images, String iso) =>
      images.where((i) => i.iso639 == iso).toList();


  static String? _iso639Of(String? language) {
    if (language == null || language.isEmpty) return null;
    final dash = language.indexOf('-');
    final code = dash >= 0 ? language.substring(0, dash) : language;
    return code.isEmpty ? null : code.toLowerCase();
  }

  static List<String> buildFallbackUrls({
    required String? primaryUrl,
    required Iterable<String?> candidates,
  }) {
    final urls = <String>[];
    for (final url in candidates) {
      if (url == null || url.isEmpty || url == primaryUrl) continue;
      if (!urls.contains(url)) urls.add(url);
    }
    return urls;
  }

  static bool _isBetter(TmdbImage candidate, TmdbImage current) {
    final voteCompare = (candidate.voteAverage ?? 0).compareTo(
      current.voteAverage ?? 0,
    );
    if (voteCompare != 0) return voteCompare > 0;
    final pixelsCompare = (candidate.width * candidate.height).compareTo(
      current.width * current.height,
    );
    if (pixelsCompare != 0) return pixelsCompare > 0;
    return candidate.filePath.compareTo(current.filePath) < 0;
  }
}
