import 'dart:math';

import 'package:collection/collection.dart';
import 'package:auto_route/auto_route.dart';
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:mnemo_cards/main.dart';
import 'package:mnemo_cards/utils/iterable_helper.dart';
import 'package:mnemo_cards/widgets/fade_in_widget.dart';
import 'package:mnemo_cards/widgets/feedback_builder.dart';
import 'package:mnemo_cards_common/mnemo_cards_common.dart';
import 'package:reorderables/reorderables.dart';
import 'package:yandex_mobileads/mobile_ads.dart';
import '../../domain/router/app_router.gr.dart';
import '../../features/analytics/analytics.dart';
import '../../features/yandex_ads/yandex_ads.dart';

import '../../di/locator.dart';
import '../../theme/themes.dart';
import '../horizontal_progress.dart';
import 'card_pack_header.dart';
import 'package:mnemo_cards/utils/string_helper.dart';

import 'cards_view.dart';
import 'cards_view_controller.dart';

final _mainScrollController = ScrollController();
final _reorderableTests = GlobalKey();

class AvailablePack extends StatelessWidget {
  final CardPackDto cardPack;
  late final CardsViewController _cardsViewController =
      CardsViewController(cardPack);

  AvailablePack(this.cardPack);

  @override
  Widget build(BuildContext context) {
    Analytics.availablePackOpened(cardPack);
    return Column(
      children: [
        CardPackHeader.fromDto(cardPack),
        Expanded(
          child: ListView(
            controller: _mainScrollController,
            children: [
              StatefulBuilder(builder: (context, setState) {
                return Column(
                  children: [
                    Container(
                      decoration: BoxDecoration(
                        color: cardPack.color?.asColor?.withOpacity(0.1),
                      ),
                      alignment: Alignment.center,
                      clipBehavior: Clip.antiAlias,
                      child: CardsView(_cardsViewController, cardPack),
                    ),
                    Container(
                      height: 1,
                      color: cardPack.color?.asColor ??
                          Colors.grey.withOpacity(0.5),
                    ),
                    SizedBox(
                      height: 10.h,
                    ),
                    Padding(
                      padding: EdgeInsets.symmetric(
                        horizontal: 10.w,
                      ),
                      child: Row(
                        mainAxisAlignment: MainAxisAlignment.spaceBetween,
                        children: [
                          StreamBuilder<bool>(
                              stream: _cardsViewController.asStream
                                  .map((s) => s.expanded),
                              builder: (context, snapshot) {
                                return _DownButton(
                                  !(snapshot.data ?? false),
                                  () async {
                                    if (snapshot.hasData) {
                                      _cardsViewController.setExpanded(
                                        !snapshot.requireData,
                                      );
                                    }
                                  },
                                  key: ValueKey('DownButton'),
                                );
                              }),
                          _Button('shuffle.png', () async {
                            final cards = _cardsViewController.state.packCards;
                            if (cards.isEmpty) return;
                            final index = (_cardsViewController.offsetCards +
                                    Random().nextInt(
                                      (cards.length / 2).ceil(),
                                    ) +
                                    3) %
                                cards.length;
                            await _cardsViewController.animateTo(index);
                            AutoRouter.of(context).push(
                              PageRouteInfo(
                                CardGamePage.name,
                                args: CardGamePageArgs(
                                  cards: cards,
                                  color: cardPack.color?.asColor,
                                  startCardId: cards[index].id,
                                  infinite: true,
                                  shuffle: true,
                                  // id: cardPack.dto.id.toString(),
                                ),
                              ),
                            );
                          }),
                          // _Button('chat.png', () {}),
                          StreamBuilder(
                              stream: _cardsViewController.asStream,
                              builder: (context, snapshot) {
                                return _Button(
                                    (snapshot.data?.favorite ?? false)
                                        ? 'heart_fill.png'
                                        : 'heart.png', () {
                                  if (snapshot.hasData) {
                                    _cardsViewController.setFavorite(
                                      !snapshot.requireData.favorite,
                                    );
                                  }
                                });
                              }),
                        ],
                      ),
                    ),
                  ],
                );
              }),
              _AdTile(),
              _TestsSection(cardPack.id.toString()),
              // _TestButton(
              //   title: 'Быстрый тест',
              //   subtitle: 'Лучший результат: 99 / 100',
              //   time: '3',
              //   timeSubtitle: 'мин',
              //   onTap: () {},
              // ),
              // _TestButton(
              //   title: 'Полный тест',
              //   subtitle: 'Лучший результат: 99 / 100',
              //   time: '10',
              //   timeSubtitle: 'мин',
              //   onTap: () {},
              // ),
            ],
          ),
        ),
        Hero(
          tag: 'bottom',
          child: SizedBox(
            height: 0,
            width: 300.w,
          ),
        ),
      ],
    );
  }
}

class _TestsSection extends StatelessWidget {
  final String packId;

  const _TestsSection(this.packId);

  @override
  Widget build(BuildContext context) {
    final order = (globalSharedPreferences
                .getString('tests_order_${packId}')
                ?.decodeList<String>() ??
            <String>[])
        .toList();

    void saveOrder() {
      globalSharedPreferences.setString(
        'tests_order_${packId}',
        order.encode(),
      );
    }

    return StreamBuilder(
      stream: locator.testManager.loadTestsStream(packId: packId),
      builder: (context, snapshot) {
        final tests = snapshot.data ?? [];
        if (tests.isEmpty) {
          return SizedBox.shrink();
        }

        if (order.isEmpty) {
          order.addAll(tests.map((t) => t.name));
          saveOrder();
        }
        return FadeInWidget(
          animationDuration: Duration(milliseconds: 400),
          child: StatefulBuilder(builder: (context, setState) {
            tests..sortInOrder(order, (t) => t.name);
            return ReorderableListView.builder(
              key: _reorderableTests,
              itemExtent: 130.h + 2 * 5.h,
              padding: EdgeInsets.symmetric(
                horizontal: 10.w,
                vertical: 5.h,
              ),
              shrinkWrap: true,
              scrollController: _mainScrollController,
              // physics: NeverScrollableScrollPhysics(),
              proxyDecorator: (_, index, animation) {
                final dto = tests[index];
                return Material(
                  elevation: 5,
                  borderRadius: BorderRadius.circular(16),
                  color: Colors.transparent,
                  child: _TestButton(
                    title: dto.name,
                    subtitle: null,
                    stats: dto.statistics,
                    color: dto.color?.asColor ?? borderGray,
                    time: dto.time,
                    timeSubtitle: dto.timeSubtitle,
                    onTap: () {},
                  ),
                );
              },
              onReorder: (int from, int to) {
                if (to - from > 1) {
                  to--;
                }
                order.move(from, to);
                saveOrder();
                setState(() {});
              },
              itemCount: tests.length,
              itemBuilder: (context, index) {
                final dto = tests[index];
                return Padding(
                  key: ValueKey(dto.id),
                  padding: EdgeInsets.symmetric(
                    vertical: 5.0.h,
                  ),
                  child: _TestButton(
                    title: dto.name,
                    subtitle: null,
                    stats: dto.statistics,
                    color: dto.color?.asColor ?? borderGray,
                    time: dto.time,
                    timeSubtitle: dto.timeSubtitle,
                    onTap: () {
                      AutoRouter.of(context).push(
                        PageRouteInfo(TestPage.name,
                            args: TestPageArgs(testId: dto.id!)),
                      );
                    },
                  ),
                );
              },
            );
          }),
        );
      },
    );
  }
}

class _AdTile extends StatelessWidget {
  const _AdTile();

  @override
  Widget build(BuildContext context) {
    return LayoutBuilder(builder: (context, constraints) {
      final banner = YandexAds.createBanner(
          BoxConstraints.tight(Size(constraints.maxWidth - 16, 80 - 8)));
      return FadeInWidget(
        future: banner.loadAd(),
        animationDuration: Duration(milliseconds: 1000),
        child: Container(
          height: 80,
          margin: const EdgeInsets.symmetric(vertical: 4.0, horizontal: 8.0),
          decoration: BoxDecoration(
            border: Border.all(
              color: Colors.white,
              width: 4.0,
            ),
            borderRadius: BorderRadius.circular(12.0),
          ),
          child: Center(
            child: AdWidget(bannerAd: banner),
          ),
        ),
      );
    });
  }
}

class _Button extends StatelessWidget {
  final String asset;
  final VoidCallback onTap;

  _Button(this.asset, this.onTap, {super.key});

  @override
  Widget build(BuildContext context) {
    return InkWell(
      onTap: onTap,
      child: Container(
        width: 110.w,
        height: 60.h,
        decoration: BoxDecoration(
          color: Colors.white,
          border: Border.all(color: borderGray),
          borderRadius: BorderRadius.circular(16.0),
        ),
        alignment: Alignment.center,
        child: Image.asset(
          'icons/$asset',
          width: 29.w,
          // height: 29.h,
          fit: BoxFit.scaleDown,
        ),
      ),
    );
  }
}

class _DownButton extends StatelessWidget {
  final VoidCallback onTap;
  final bool isDown;

  _DownButton(bool this.isDown, this.onTap, {super.key});

  @override
  Widget build(BuildContext context) {
    return InkWell(
      onTap: onTap,
      child: Container(
        width: 110.w,
        height: 60.h,
        decoration: BoxDecoration(
          color: Colors.white,
          border: Border.all(color: borderGray),
          borderRadius: BorderRadius.circular(16.0),
        ),
        alignment: Alignment.center,
        child: AnimatedRotation(
          duration: Duration(milliseconds: 300),
          turns: isDown ? 0.0 : 0.5,
          child: Image.asset(
            'icons/down.png',
            width: 29.w,
            // height: 29.h,
            fit: BoxFit.scaleDown,
          ),
        ),
      ),
    );
  }
}

class _TestButton extends StatelessWidget {
  final VoidCallback onTap;
  final String title;
  final String? subtitle;
  final String? time;
  final String? timeSubtitle;
  final Color color;
  final TestStatisticsDto? stats;

  _TestButton({
    required this.title,
    required this.onTap,
    required this.color,
    this.subtitle,
    this.time,
    this.timeSubtitle,
    this.stats,
    super.key,
  });

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: onTap,
      child: Container(
        height: 130.h,
        alignment: Alignment.center,
        decoration: BoxDecoration(
          color: Colors.white,
          border: Border.all(color: borderGray),
          borderRadius: BorderRadius.circular(16.0),
        ),
        padding: EdgeInsets.only(
          top: 12.0.h,
          left: 10.0.w,
          right: 10.0.w,
          bottom: 20.h,
        ),
        child: Row(
          children: [
            Expanded(
              child: Column(
                crossAxisAlignment: CrossAxisAlignment.start,
                mainAxisAlignment: MainAxisAlignment.spaceBetween,
                children: [
                  Text(
                    title,
                    style: TextStyle(
                      fontSize: 25.sp,
                      fontWeight: FontWeight.w500,
                      height: 0.85,
                    ),
                  ),
                  if (subtitle != null)
                    Padding(
                      padding: const EdgeInsets.only(top: 8.0),
                      child: Text(
                        subtitle!,
                        style: TextStyle(
                          fontSize: 16.sp,
                          fontWeight: FontWeight.w300,
                          height: 0.85,
                        ),
                      ),
                    ),
                  Spacer(),
                  if (stats != null)
                    Padding(
                      padding: const EdgeInsets.only(right: 50.0),
                      child: Row(
                        children: [
                          Expanded(
                            child: HorizontalProgressWidget(
                              stats!.words.correct.round(),
                              stats!.words.total.round(),
                              color,
                              hasBorder: true,
                            ),
                          ),
                        ],
                      ),
                    ),
                ],
              ),
            ),
            Container(
              width: 75.w,
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: [
                  if (time != null)
                    Text(
                      time!,
                      style: TextStyle(
                          fontSize: 40.sp,
                          fontWeight: FontWeight.w400,
                          height: 0.85),
                    ),
                  if (timeSubtitle != null)
                    Text(
                      timeSubtitle!,
                      style: TextStyle(
                          fontSize: 24.sp,
                          fontWeight: FontWeight.w400,
                          height: 0.85),
                    ),
                ],
              ),
            ),
          ],
        ),
      ),
    );
  }
}
