import 'package:flutter/widgets.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:go_router/go_router.dart';

import '../../core/contracts/library.dart';
import '../../core/contracts/tmdb.dart';
import '../../core/infra/emby_api/emby_headers.dart';
import '../../features/player/player_launcher.dart';
import '../../providers/di_providers.dart';
import '../../providers/session_provider.dart';
import '../../providers/tmdb_prefetch_provider.dart';
import 'platform_device_name.dart';


const _kContainerTypes = <String>{
  'BoxSet',
  'CollectionFolder',
  'Folder',
  'Playlist',
  'UserView',
};

void goMediaDetail(BuildContext context, EmbyRawItem item, {WidgetRef? ref}) {
  if (_kContainerTypes.contains(item.Type)) {
    context.push(
      Uri(
        path: '/library/${item.Id}',
        queryParameters: {
          'collection': '1',
          if (item.Name.isNotEmpty) 'title': item.Name,
        },
      ).toString(),
    );
    return;
  }
  if (ref != null) {
    ref.read(tmdbPrefetchProvider.notifier).prefetchItem(item, priority: true);
  }
  final isEpisode = item.Type == 'Episode';
  final seriesId = isEpisode && (item.SeriesId?.isNotEmpty ?? false)
      ? item.SeriesId
      : null;
  final seasonId = isEpisode && (item.SeasonId?.isNotEmpty ?? false)
      ? item.SeasonId
      : null;
  final query = <String, String>{
    if (seriesId != null) 'seriesId': seriesId,
    if (seasonId != null) 'seasonId': seasonId,
  };
  context.push(
    Uri(
      path: '/media/${item.Id}',
      queryParameters: query.isNotEmpty ? query : null,
    ).toString(),
    extra: item,
  );
}


Future<PlayerExitResult?> playFromTmdbOnServer(
  BuildContext context,
  WidgetRef ref, {
  required String serverId,
  required String itemId,
  String? mediaSourceId,
  int preferredSubtitleStreamIndex = -1,
  int? preferredAudioStreamIndex,
  bool fromStart = false,
  int? startPositionTicks,
  String? backdropUrl,
}) async {
  final active = ref.read(activeSessionProvider);
  if (active?.serverId != serverId) {
    await ref.read(sessionProvider.notifier).switchSession(serverId);
  }
  if (!context.mounted) return null;
  return PlayerLauncher.launch(
    context: context,
    itemId: itemId,
    serverId: serverId,
    mediaSourceId: mediaSourceId,
    preferredSubtitleStreamIndex: preferredSubtitleStreamIndex,
    preferredAudioStreamIndex: preferredAudioStreamIndex,
    startPositionTicks: startPositionTicks,
    fromStart: fromStart,
    backdropUrl: backdropUrl,
    ref: ref,
  );
}


void goTmdbDetail(
  BuildContext context, {
  required int tmdbId,
  required String mediaType,
  TmdbRecommendation? seed,
}) {
  if (mediaType != 'movie' && mediaType != 'tv') return;
  context.push('/tmdb/$mediaType/$tmdbId', extra: seed);
}


Future<void> goMediaDetailOnServer(
  BuildContext context,
  WidgetRef ref, {
  required String serverId,
  required EmbyRawItem item,
}) async {
  final activeId = ref.read(sessionProvider).value?.activeServerId;
  if (serverId != activeId) {
    await ref.read(sessionProvider.notifier).switchSession(serverId);
  }
  if (context.mounted) {
    goMediaDetail(context, item);
  }
}


Map<String, String> buildEmbyImageHeaders(
  WidgetRef ref, {
  required String token,
  required String userId,
}) {
  final deviceId = ref.read(deviceIdProvider).value ?? '';
  return EmbyRequestHeaders.image(
    deviceId: deviceId,
    deviceName: kEmbyDeviceName,
    token: token,
    userId: userId,
  );
}
