import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:frontend_eccp_mobile/app/core/constants/constants.dart';
import 'package:pull_to_refresh_flutter3/pull_to_refresh_flutter3.dart';

typedef AppAsyncCallback = Future<void> Function();

class AppScreen extends StatelessWidget {
  const AppScreen({
    required this.body,
    super.key,
    this.isSliver = false,
    this.slivers,
    this.appBar,
    this.title,
    this.centerTitle = true,
    this.leading,
    this.actions,
    this.onBack,
    this.useWillPopScope = false,
    this.useShadowAppBar = true,
    this.scrollableBody = true,
    this.scrollController,
    this.physics,
    this.refreshController,
    this.enablePullDown = false,
    this.enablePullUp = false,
    this.onRefresh,
    this.onLoadMore,
    this.refreshHeader,
    this.refreshFooter,
    this.footers,
    this.footersPadding = AppPadding.p16,
    this.hasSafeArea = true,
    this.safeTop = true,
    this.safeBottom,
    this.safeLeft = true,
    this.safeRight = true,
    this.backgroundColor,
    this.backgroundWidgets,
    this.resizeToAvoidBottomInset,
    this.floatingActionButton,
    this.bottomNavigationBar,
    this.extendBody = false,
    this.extendBodyBehindAppBar = false,
    this.statusBarStyle,
    this.isLoading = false,
  });
  final bool isLoading;

  final Widget body;

  final bool isSliver;
  final List<Widget>? slivers;

  final PreferredSizeWidget? appBar;
  final bool useShadowAppBar;
  final String? title;
  final bool centerTitle;
  final Widget? leading;
  final List<Widget>? actions;
  final VoidCallback? onBack;
  final bool useWillPopScope;

  final bool scrollableBody;
  final ScrollController? scrollController;
  final ScrollPhysics? physics;

  final RefreshController? refreshController;
  final bool enablePullDown;
  final bool enablePullUp;
  final AppAsyncCallback? onRefresh;
  final AppAsyncCallback? onLoadMore;
  final Widget? refreshHeader;
  final Widget? refreshFooter;

  final List<Widget>? footers;
  final EdgeInsets footersPadding;

  final bool hasSafeArea;
  final bool safeTop;
  final bool? safeBottom;
  final bool safeLeft;
  final bool safeRight;

  final Color? backgroundColor;
  final List<Widget>? backgroundWidgets;
  final bool? resizeToAvoidBottomInset;
  final Widget? floatingActionButton;
  final Widget? bottomNavigationBar;
  final bool extendBody;
  final bool extendBodyBehindAppBar;

  final SystemUiOverlayStyle? statusBarStyle;

  Widget _wrapScrollbar(BuildContext context, Widget child) {
    return ScrollbarTheme(
      data: ScrollbarThemeData(
        thumbColor: MaterialStateProperty.all(AppColors.neutral400),
        thickness: MaterialStateProperty.all(3),
        radius: const Radius.circular(AppSizes.s24),
      ),
      child: Scrollbar(
        controller: scrollController,
        interactive: true,
        thumbVisibility:
            MediaQuery.of(context).size.width > AppSizes.maxContentWidth,
        child: child,
      ),
    );
  }

  Widget _buildBodyContent(BuildContext context) {
    Widget content;

    if (isSliver) {
      content = _wrapScrollbar(
        context,
        CustomScrollView(
          controller: scrollController,
          physics: physics,
          slivers: slivers!,
        ),
      );
    } else {
      content = body;

      if (scrollableBody) {
        content = _wrapScrollbar(
          context,
          SingleChildScrollView(
            controller: scrollController,
            physics: physics,
            child: content,
          ),
        );
      }
    }

    if (refreshController != null) {
      content = SmartRefresher(
        controller: refreshController!,
        enablePullDown: enablePullDown,
        enablePullUp: enablePullUp,
        onRefresh: onRefresh,
        onLoading: onLoadMore,
        header: refreshHeader,
        footer: refreshFooter,
        physics: physics,
        child: content,
      );
    }

    if (footers == null) return content;

    return Column(
      children: [
        Expanded(child: content),
        Padding(
          padding: footersPadding,
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.stretch,
            children: footers!,
          ),
        ),
      ],
    );
  }

  Widget _buildBody(BuildContext context) {
    final content = backgroundWidgets == null
        ? _buildBodyContent(context)
        : Stack(
            children: [
              ...backgroundWidgets!,
              _buildBodyContent(context),
            ],
          );

    final safeContent = hasSafeArea
        ? SafeArea(
            top: safeTop,
            left: safeLeft,
            right: safeRight,
            bottom:
                safeBottom ??
                (!kIsWeb && defaultTargetPlatform == TargetPlatform.android),
            child: content,
          )
        : content;

    return Stack(
      children: [
        safeContent,
        _buildLoadingOverlay(),
      ],
    );
  }

  Widget _buildLoadingOverlay() {
    return AnimatedOpacity(
      duration: const Duration(milliseconds: 200),
      opacity: isLoading ? 1 : 0,
      child: isLoading
          ? Positioned.fill(
              child: ColoredBox(
                color: Colors.black.withOpacity(0.1),
                child: Center(
                  child: Container(
                    width: 70,
                    height: 70,
                    padding: AppPadding.p16,
                    decoration: BoxDecoration(
                      color: AppColors.neutralWhite,
                      borderRadius: AppRadius.r10,
                    ),
                    child: CircularProgressIndicator(
                      color: AppColors.primary900,
                      strokeWidth: 3,
                      backgroundColor: Colors.transparent,
                    ),
                  ),
                ),
              ),
            )
          : const SizedBox(),
    );
  }

  PreferredSizeWidget? _buildAppBar(BuildContext context) {
    if (appBar != null) return appBar;
    if (title == null) return null;

    return AppBar(
      backgroundColor: AppColors.neutralWhite,
      surfaceTintColor: Colors.transparent,
      scrolledUnderElevation: useShadowAppBar ? 4 : 0,
      shadowColor: useShadowAppBar
          ? Colors.black.withOpacity(AppOpacity.opacity15)
          : Colors.transparent,
      title: Text(
        title!,
        style: AppTextStyles.h3,
      ),
      centerTitle: centerTitle,
      leading:
          leading ??
          (onBack != null
              ? IconButton(
                  icon: const Icon(Icons.arrow_back),
                  onPressed: onBack,
                )
              : null),
      actions: actions,
    );
  }

  @override
  Widget build(BuildContext context) {
    final Widget screen = AnnotatedRegion<SystemUiOverlayStyle>(
      value:
          statusBarStyle ??
          SystemUiOverlayStyle.dark.copyWith(
            statusBarColor: Colors.transparent,
          ),
      child: Scaffold(
        backgroundColor: backgroundColor,
        resizeToAvoidBottomInset: resizeToAvoidBottomInset,
        appBar: _buildAppBar(context),
        body: _buildBody(context),
        floatingActionButton: floatingActionButton,
        bottomNavigationBar: bottomNavigationBar,
        extendBody: extendBody,
        extendBodyBehindAppBar: extendBodyBehindAppBar,
      ),
    );

    if (!useWillPopScope) return screen;

    return WillPopScope(
      onWillPop: () async {
        onBack?.call();
        return false;
      },
      child: screen,
    );
  }
}
