ظهر هذا الخطا
Restarted application in 1,014ms.

════════ Exception caught by rendering library ═════════════════════════════════
The following assertion was thrown during layout:
A RenderFlex overflowed by 24 pixels on the bottom.

The relevant error-causing widget was:
    Column Column:file:///E:/MicroPanel_flutter/micro_panel/lib/Login.dart:1657:14

: To inspect this widget in Flutter DevTools, visit: http://127.0.0.1:9100/#/inspector?uri=http%3A%2F%2F127.0.0.1%3A13257%2F1pjntnxjS7s%3D%2F&inspectorRef=inspector-0

The overflowing RenderFlex has an orientation of Axis.vertical.
The edge of the RenderFlex that is overflowing has been marked in the rendering with a yellow and black striped pattern. This is usually caused by the contents being too big for the RenderFlex.
Consider applying a flex factor (e.g. using an Expanded widget) to force the children of the RenderFlex to fit within the available space instead of being sized to their natural size.
This is considered an error condition because it indicates that there is content that cannot be seen. If the content is legitimately bigger than the available space, consider clipping it with a ClipRect widget before putting it in the flex, or using a scrollable container rather than a Flex, like a ListView.
The specific RenderFlex in question is: RenderFlex#3916a relayoutBoundary=up8 OVERFLOWING
    needs compositing
    parentData: offset=Offset(0.0, 0.0) (can use size)
    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=681.0)
    size: Size(494.5, 681.0)
    direction: vertical
    mainAxisAlignment: start
    mainAxisSize: max
    crossAxisAlignment: center
    verticalDirection: down
    spacing: 0.0
    child 1: RenderFlex#be239 relayoutBoundary=up9
        parentData: offset=Offset(147.3, 0.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(200.0, 150.0)
        direction: vertical
        mainAxisAlignment: start
        mainAxisSize: max
        crossAxisAlignment: center
        verticalDirection: down
        spacing: 0.0
        child 1: RenderConstrainedBox#db77c relayoutBoundary=up10
            parentData: offset=Offset(100.0, 0.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(0.0, 60.0)
            additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=60.0)
        child 2: RenderFlex#59837 relayoutBoundary=up10
            parentData: offset=Offset(0.0, 60.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(200.0, 60.0)
            direction: horizontal
            mainAxisAlignment: center
            mainAxisSize: min
            crossAxisAlignment: center
            textDirection: rtl
            verticalDirection: down
            spacing: 0.0
            child 1: RenderConstrainedBox#83884 relayoutBoundary=up11
                parentData: offset=Offset(140.0, 0.0); flex=null; fit=null (can use size)
                constraints: BoxConstraints(unconstrained)
                size: Size(60.0, 60.0)
                additionalConstraints: BoxConstraints(unconstrained)
                child: RenderOffstage#09f54 relayoutBoundary=up12
                    parentData: <none> (can use size)
                    constraints: BoxConstraints(unconstrained)
                    size: Size(60.0, 60.0)
                    offstage: false
            child 2: RenderConstrainedBox#e7713 relayoutBoundary=up11
                parentData: offset=Offset(130.0, 30.0); flex=null; fit=null (can use size)
                constraints: BoxConstraints(unconstrained)
                size: Size(10.0, 0.0)
                additionalConstraints: BoxConstraints(w=10.0, 0.0<=h<=Infinity)
            child 3: RenderFlex#b5e6a relayoutBoundary=up11
                parentData: offset=Offset(0.0, 4.0); flex=null; fit=null (can use size)
                constraints: BoxConstraints(unconstrained)
                size: Size(130.0, 52.0)
                direction: vertical
                mainAxisAlignment: start
                mainAxisSize: max
                crossAxisAlignment: start
                textDirection: rtl
                verticalDirection: down
                spacing: 0.0
                child 1: RenderParagraph#9c167 relayoutBoundary=up12
                    parentData: offset=Offset(0.0, 0.0); flex=null; fit=null (can use size)
                    constraints: BoxConstraints(unconstrained)
                    size: Size(130.0, 36.0)
                    textAlign: start
                    textDirection: rtl
                    softWrap: wrapping at box width
                    overflow: clip
                    locale: en_US
                    maxLines: unlimited
                child 2: RenderParagraph#f2132 relayoutBoundary=up12
                    parentData: offset=Offset(1.8, 36.0); flex=null; fit=null (can use size)
                    constraints: BoxConstraints(unconstrained)
                    size: Size(128.1, 16.0)
                    textAlign: start
                    textDirection: rtl
                    softWrap: wrapping at box width
                    overflow: clip
                    locale: en_US
                    maxLines: unlimited
        child 3: RenderConstrainedBox#7e38a relayoutBoundary=up10
            parentData: offset=Offset(100.0, 120.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(0.0, 30.0)
            additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=30.0)
    child 2: RenderConstrainedBox#7aa54 relayoutBoundary=up9
        parentData: offset=Offset(247.3, 150.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 20.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=20.0)
    child 3: RenderPadding#670de relayoutBoundary=up9
        parentData: offset=Offset(0.0, 170.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 92.0)
        padding: EdgeInsets(0.0, 0.0, 0.0, 10.0)
        textDirection: rtl
        child: RenderDecoratedBox#3cf1b relayoutBoundary=up10
            parentData: offset=Offset(0.0, 0.0) (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(494.5, 82.0)
            decoration: BoxDecoration
                color: Color(alpha: 0.0510, red: 1.0000, green: 1.0000, blue: 1.0000, colorSpace: ColorSpace.sRGB)
                borderRadius: BorderRadius.circular(12.0)
                boxShadow: BoxShadow(Color(alpha: 0.1020, red: 0.0000, green: 0.0000, blue: 0.0000, colorSpace: ColorSpace.sRGB), Offset(0.0, 2.0), 6.0, 0.0, BlurStyle.normal)
            configuration: ImageConfiguration(bundle: PlatformAssetBundle#e25e7(), devicePixelRatio: 1.0, locale: en_US, textDirection: TextDirection.rtl, platform: windows)
            child: RenderPadding#2feba relayoutBoundary=up11
                parentData: <none> (can use size)
                constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                size: Size(494.5, 82.0)
                padding: EdgeInsets.zero
                textDirection: rtl
                child: RenderPadding#0f716 relayoutBoundary=up12
                    parentData: offset=Offset(0.0, 0.0) (can use size)
                    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                    size: Size(494.5, 82.0)
                    padding: EdgeInsets.all(4.0)
                    textDirection: rtl
    child 4: RenderConstrainedBox#bde7e relayoutBoundary=up9
        parentData: offset=Offset(247.3, 262.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 5.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=5.0)
    child 5: RenderFlex#3b318 relayoutBoundary=up9
        needs compositing
        parentData: offset=Offset(0.0, 267.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 106.0)
        direction: vertical
        mainAxisAlignment: start
        mainAxisSize: max
        crossAxisAlignment: start
        textDirection: rtl
        verticalDirection: down
        spacing: 0.0
        child 1: RenderConstrainedBox#cca09 relayoutBoundary=up10
            parentData: offset=Offset(494.5, 0.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(0.0, 10.0)
            additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=10.0)
        child 2: RenderPadding#0fa9b relayoutBoundary=up10
            parentData: offset=Offset(437.8, 10.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(56.7, 28.0)
            padding: EdgeInsets(0.0, 0.0, 8.0, 8.0)
            textDirection: rtl
            child: RenderParagraph#dce07 relayoutBoundary=up11
                parentData: offset=Offset(0.0, 0.0) (can use size)
                constraints: BoxConstraints(0.0<=w<=486.5, 0.0<=h<=Infinity)
                size: Size(48.7, 20.0)
                textAlign: start
                textDirection: rtl
                softWrap: wrapping at box width
                overflow: clip
                locale: en_US
                maxLines: unlimited
                text: TextSpan
                    debugLabel: ((englishLike bodyMedium 2021).merge((blackRedmond bodyMedium).apply)).merge(unknown)
                    inherit: false
                    color: Color(alpha: 0.7020, red: 1.0000, green: 1.0000, blue: 1.0000, colorSpace: ColorSpace.sRGB)
                    family: Tajawal
                    size: 14.0
                    weight: 400
                    letterSpacing: 0.3
                    baseline: alphabetic
                    height: 1.4x
                    leadingDistribution: even
                    decoration: Color(alpha: 1.0000, red: 0.1137, green: 0.1059, blue: 0.1255, colorSpace: ColorSpace.sRGB) TextDecoration.none
                    "عنوان IP"
        child 3: RenderMouseRegion#91940 relayoutBoundary=up10
            needs compositing
            parentData: offset=Offset(0.0, 38.0); flex=null; fit=null (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(494.5, 68.0)
            behavior: opaque
            listeners: enter, exit
            cursor: SystemMouseCursor(text)
            child: RenderTapRegion#7f6ae relayoutBoundary=up11
                needs compositing
                parentData: <none> (can use size)
                constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                size: Size(494.5, 68.0)
                behavior: deferToChild
                groupId: EditableText
                child: RenderIgnorePointer#832fc relayoutBoundary=up12
                    needs compositing
                    parentData: <none> (can use size)
                    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                    size: Size(494.5, 68.0)
                    ignoring: false
                    ignoringSemantics: null
    child 6: RenderConstrainedBox#fb23b relayoutBoundary=up9
        parentData: offset=Offset(247.3, 373.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 12.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=12.0)
    child 7: RenderMouseRegion#db004 relayoutBoundary=up9
        needs compositing
        parentData: offset=Offset(0.0, 385.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 80.0)
        behavior: opaque
        listeners: enter, exit
        cursor: SystemMouseCursor(text)
        child: RenderTapRegion#89b84 relayoutBoundary=up10
            needs compositing
            parentData: <none> (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(494.5, 80.0)
            behavior: deferToChild
            groupId: EditableText
            child: RenderIgnorePointer#3c26e relayoutBoundary=up11
                needs compositing
                parentData: <none> (can use size)
                constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                size: Size(494.5, 80.0)
                ignoring: false
                ignoringSemantics: null
                child: RenderSemanticsAnnotations#05bd5 relayoutBoundary=up12
                    needs compositing
                    parentData: <none> (can use size)
                    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                    size: Size(494.5, 80.0)
    child 8: RenderConstrainedBox#3124b relayoutBoundary=up9
        parentData: offset=Offset(247.3, 465.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 12.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=12.0)
    child 9: RenderMouseRegion#d0249 relayoutBoundary=up9
        needs compositing
        parentData: offset=Offset(0.0, 477.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 80.0)
        behavior: opaque
        listeners: enter, exit
        cursor: SystemMouseCursor(text)
        child: RenderTapRegion#a3881 relayoutBoundary=up10
            needs compositing
            parentData: <none> (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(494.5, 80.0)
            behavior: deferToChild
            groupId: EditableText
            child: RenderIgnorePointer#f55f8 relayoutBoundary=up11
                needs compositing
                parentData: <none> (can use size)
                constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                size: Size(494.5, 80.0)
                ignoring: false
                ignoringSemantics: null
                child: RenderSemanticsAnnotations#36e69 relayoutBoundary=up12
                    needs compositing
                    parentData: <none> (can use size)
                    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                    size: Size(494.5, 80.0)
    child 10: RenderConstrainedBox#e3757 relayoutBoundary=up9
        parentData: offset=Offset(247.3, 557.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 12.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=12.0)
    child 11: RenderMouseRegion#61d27 relayoutBoundary=up9
        needs compositing
        parentData: offset=Offset(0.0, 569.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 48.0)
        behavior: opaque
        listeners: enter, exit
        cursor: SystemMouseCursor(text)
        child: RenderTapRegion#39f48 relayoutBoundary=up10
            needs compositing
            parentData: <none> (can use size)
            constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
            size: Size(494.5, 48.0)
            behavior: deferToChild
            groupId: EditableText
            child: RenderIgnorePointer#fd3d9 relayoutBoundary=up11
                needs compositing
                parentData: <none> (can use size)
                constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                size: Size(494.5, 48.0)
                ignoring: false
                ignoringSemantics: null
                child: RenderSemanticsAnnotations#de874 relayoutBoundary=up12
                    needs compositing
                    parentData: <none> (can use size)
                    constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
                    size: Size(494.5, 48.0)
    child 12: RenderConstrainedBox#dac08 relayoutBoundary=up9
        parentData: offset=Offset(247.3, 617.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 25.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=25.0)
    child 13: RenderConstrainedBox#beb0f relayoutBoundary=up9
        parentData: offset=Offset(0.0, 642.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(494.5, 48.0)
        additionalConstraints: BoxConstraints(w=Infinity, h=48.0)
        child: RenderSemanticsAnnotations#855e5
            parentData: <none> (can use size)
            constraints: BoxConstraints(w=494.5, h=48.0)
            semantic boundary
            size: Size(494.5, 48.0)
            child: _RenderInputPadding#381b0
                parentData: <none> (can use size)
                constraints: BoxConstraints(w=494.5, h=48.0)
                size: Size(494.5, 48.0)
                child: RenderConstrainedBox#4759c
                    parentData: offset=Offset(0.0, 0.0) (can use size)
                    constraints: BoxConstraints(w=494.5, h=48.0)
                    size: Size(494.5, 48.0)
                    additionalConstraints: BoxConstraints(56.0<=w<=Infinity, 32.0<=h<=Infinity)
    child 14: RenderConstrainedBox#1850b relayoutBoundary=up9
        parentData: offset=Offset(247.3, 690.0); flex=null; fit=null (can use size)
        constraints: BoxConstraints(0.0<=w<=494.5, 0.0<=h<=Infinity)
        size: Size(0.0, 15.0)
        additionalConstraints: BoxConstraints(0.0<=w<=Infinity, h=15.0)
◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤◢◤
════════════════════════════════════════════════════════════════════════════════
للعلم الكود
import 'dart:async';
import 'dart:convert';
import 'dart:io';
import 'dart:isolate';
import 'dart:math';
import 'dart:typed_data';
import 'package:encrypt/encrypt.dart' as encrypt;
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:http/http.dart' as http;
import 'package:micro_panel/HomePage.dart';
import 'package:micro_panel/SQLITE_HELPER/secure_storage_db.dart';
import 'package:micro_panel/main.dart';
import 'package:path_provider/path_provider.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:router_os_client/router_os_client.dart';
import 'package:smooth_page_indicator/smooth_page_indicator.dart';
import 'package:sqflite/sqflite.dart';
import 'package:flutter/foundation.dart' show kIsWeb;
import 'package:sqflite_common_ffi/sqflite_ffi.dart';

void main() async {
  // تهيئة binding قبل أي شيء آخر
  WidgetsFlutterBinding.ensureInitialized();

  if (!kIsWeb && (Platform.isWindows || Platform.isLinux || Platform.isMacOS)) {
    sqfliteFfiInit();
    databaseFactory = databaseFactoryFfi;
  }

  // الحصول على المسار هنا
  final maindirectory = await getApplicationDocumentsDirectory();
  final saveDirectory = Directory('${maindirectory.path}/MicropanelSecrt');
  if (!await saveDirectory.exists()) {
    await saveDirectory.create(recursive: true);
  }

  final appDocumentsPath = saveDirectory.path;
  runApp(MicroPanelApp(documentsPath: appDocumentsPath));
}

class MicroPanelApp extends StatelessWidget {
  final String documentsPath;
  const MicroPanelApp({super.key, required this.documentsPath});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      title: 'Micro Panel',
      theme: ThemeData(
        primarySwatch: Colors.blue,
        fontFamily: 'Tajawal',
        useMaterial3: true,
      ),
      home: const SplashScreen(),
    );
  }
}

class SplashScreen extends StatefulWidget {
  const SplashScreen({super.key});

  @override
  State<SplashScreen> createState() => _SplashScreenState();
}

class _SplashScreenState extends State<SplashScreen>
    with SingleTickerProviderStateMixin {
  late final AnimationController _controller;
  late final Animation<double> _scaleAnimation;
  late final Animation<double> _fadeAnimation;
  late final Animation<Offset> _slideAnimation;

  @override
  void initState() {
    super.initState();
    _initAnimations();
    _navigateToLogin();
  }

  void _initAnimations() {
    _controller = AnimationController(
      vsync: this,
      duration: const Duration(milliseconds: 800),
    );
    _scaleAnimation = Tween<double>(begin: 0.9, end: 1.0).animate(
      CurvedAnimation(parent: _controller, curve: Curves.easeInOutQuart),
    );
    _fadeAnimation = Tween<double>(
      begin: 0.0,
      end: 1.0,
    ).animate(CurvedAnimation(parent: _controller, curve: Curves.easeIn));
    _slideAnimation = Tween<Offset>(
      begin: const Offset(0.0, 0.3),
      end: Offset.zero,
    ).animate(CurvedAnimation(parent: _controller, curve: Curves.easeOutQuart));
    _controller.forward();
  }

  void _navigateToLogin() {
    Future.delayed(const Duration(seconds: 1), () {
      if (mounted) {
        Navigator.pushReplacement(
          context,
          PageRouteBuilder(
            pageBuilder: (_, __, ___) => const Login(),
            transitionsBuilder:
                (_, animation, __, child) =>
                    FadeTransition(opacity: animation, child: child),
            transitionDuration: const Duration(milliseconds: 500),
          ),
        );
      }
    });
  }

  @override
  void dispose() {
    _controller.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: const Color(0xFF0A192F),
      body: Stack(
        children: [_buildBackgroundCircles(), Center(child: _buildContent())],
      ),
    );
  }

  Widget _buildBackgroundCircles() {
    return Stack(
      children: [
        Positioned(
          top: -50,
          right: -50,
          child: Container(
            width: 200,
            height: 200,
            decoration: BoxDecoration(
              shape: BoxShape.circle,
              color: Color(0xFF1E3A8A).withOpacity(0.2),
            ),
          ),
        ),
        Positioned(
          bottom: -100,
          left: -100,
          child: Container(
            width: 300,
            height: 300,
            decoration: BoxDecoration(
              shape: BoxShape.circle,
              color: Color(0xFF1E3A8A).withOpacity(0.1),
            ),
          ),
        ),
      ],
    );
  }

  Widget _buildContent() {
    return Padding(
      padding: const EdgeInsets.all(20.0),
      child: Directionality(
        textDirection: TextDirection.rtl,
        child: ScaleTransition(
          scale: _scaleAnimation,
          child: FadeTransition(
            opacity: _fadeAnimation,
            child: SlideTransition(
              position: _slideAnimation,
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: [
                  _buildAppLogo(),
                  const SizedBox(height: 20),
                  _buildAppTitle(),
                  const SizedBox(height: 5),
                  _buildAppSubtitle(),
                  const SizedBox(height: 30),
                  _buildLoadingIndicator(),
                  const SizedBox(height: 15),
                  _buildLoadingText(),
                ],
              ),
            ),
          ),
        ),
      ),
    );
  }

  Widget _buildAppLogo() {
    return Hero(
      tag: 'app-logo',
      child: Container(
        height: 150,
        width: 150, // تأكد من أن العرض مساوٍ للارتفاع للحفاظ على الشكل الدائري
        padding: const EdgeInsets.all(5),
        decoration: BoxDecoration(
          color: Colors.white.withOpacity(0.1),
          shape: BoxShape.circle,
          border: Border.all(color: Colors.white.withOpacity(0.2), width: 1.5),
        ),
        child: ClipOval(
          child: Image.asset(
            'assets/img/MicroPanel.ico',
            fit: BoxFit.cover, // يجعل الصورة تملأ الحاوية بشكل متناسق
          ),
        ),
      ),
    );
  }

  Widget _buildAppTitle() {
    return const Text(
      'Micro Panel',
      style: TextStyle(
        fontFamily: 'Tajawal',
        fontSize: 30,
        fontWeight: FontWeight.bold,
        color: Colors.white,
        letterSpacing: 1.2,
      ),
    );
  }

  Widget _buildAppSubtitle() {
    return const Text(
      'نظام إدارة أجهزة الميكروتك',
      style: TextStyle(
        fontFamily: 'Tajawal',
        color: Colors.white70,
        fontSize: 14,
      ),
    );
  }

  Widget _buildLoadingIndicator() {
    return SizedBox(
      width: 180,
      child: ClipRRect(
        borderRadius: BorderRadius.circular(8),
        child: LinearProgressIndicator(
          valueColor: AlwaysStoppedAnimation<Color>(
            Colors.white.withOpacity(0.9),
          ),
          backgroundColor: Colors.white.withOpacity(0.2),
          minHeight: 5,
        ),
      ),
    );
  }

  Widget _buildLoadingText() {
    return const Text(
      'جاري التحميل...',
      style: TextStyle(
        fontFamily: 'Tajawal',
        color: Colors.white,
        fontSize: 14,
      ),
    );
  }
}

class MikroTikApi {
  Socket? _socket;
  final String host;
  final int port;
  final String user, pass;
  final _recvBuffer = <int>[];

  MikroTikApi({
    required this.host,
    this.port = 8728,
    required this.user,
    required this.pass,
  });

  Future<void> connect() async {
    _socket = await Socket.connect(host, port);
    _socket!.listen(_onData, onError: _onError, onDone: _onDone);
  }

  void _onData(Uint8List chunk) {
    _recvBuffer.addAll(chunk);
  }

  void _onError(e) => throw 'خطأ في الاتصال';
  void _onDone() => _socket = null;

  Uint8List _encodeWord(String s) {
    final b = utf8.encode(s);
    final len = b.length;
    final header = <int>[];
    if (len < 0x80)
      header.add(len);
    else if (len < 0x4000) {
      header.add((len >> 8) | 0x80);
      header.add(len & 0xFF);
    } else if (len < 0x200000) {
      header.add((len >> 16) | 0xC0);
      header.add((len >> 8) & 0xFF);
      header.add(len & 0xFF);
    } else {
      header.add((len >> 24) | 0xE0);
      header.add((len >> 16) & 0xFF);
      header.add((len >> 8) & 0xFF);
      header.add(len & 0xFF);
    }
    return Uint8List.fromList([...header, ...b]);
  }

  Future<Map<String, String>?> fetchLicenseData() async {
    await sendSentence(['/system/license/print']);
    final resp = await _readSentences();

    Map<String, String> licenseData = {};

    for (var sentence in resp) {
      if (sentence.isNotEmpty && sentence.first == '!re') {
        for (var token in sentence.skip(1)) {
          if (token.startsWith('=')) {
            final parts = token.substring(1).split('=');
            if (parts.length >= 2) {
              final key = parts[0];
              final value = parts.sublist(1).join('=');
              licenseData[key] = value;
            }
          }
        }
        break;
      }
    }

    if (licenseData.isEmpty) return null;
    return licenseData;
  }

  Future<bool> isLicenseDataStored() async {
    final storage = SecureStorageDB();

    final softwareId = await storage.read('license_software_id');
    // افعل نفس الشيء لمفاتيح أخرى إذا تريد

    return softwareId != null;
  }

  String encryptAES(String plainText, String keyString, String ivString) {
    final key = encrypt.Key.fromUtf8(keyString);
    final iv = encrypt.IV.fromUtf8(ivString);
    final encrypter = encrypt.Encrypter(
      encrypt.AES(key, mode: encrypt.AESMode.cbc),
    );

    final encrypted = encrypter.encrypt(plainText, iv: iv);
    return encrypted.base64;
  }

  Future<String> fetchRouterVersion(String appDocumentsPath) async {
    await sendSentence(['/system/resource/print']);
    final resp = await _readSentences();

    for (var sentence in resp) {
      if (sentence.isNotEmpty && sentence.first == '!re') {
        for (var token in sentence.skip(1)) {
          if (token.startsWith('=version=')) {
            final fullVersion = token.substring('=version='.length);
            final majorVersion = fullVersion.split('.').first;

            final data = {'router_version': majorVersion};
            final jsonString = jsonEncode(data);

            final filePath = '$appDocumentsPath/router_version.json';
            final file = File(filePath);

            await file.writeAsString(jsonString);
            print('تم حفظ إصدار الراوتر بنجاح في: $filePath');

            return majorVersion;
          }
        }
      }
    }

    throw Exception('لم يتم العثور على إصدار الراوتر في الاستجابة');
  }

  Future<List<Map<String, dynamic>>> fetchUserManagerUsers(
    String appDocumentsPath,
  ) async {
    // جلب إصدار الراوتر أولاً
    final versionString = await fetchRouterVersion(appDocumentsPath);
    final version = versionString.startsWith('7') ? 7 : 6;
    print('$version');

    // جلب بيانات المستخدمين الأساسية
    if (version == 7) {
      await sendSentence(['/user-manager/user/print']);
    } else {
      await sendSentence(['/tool/user-manager/user/print']);
    }

    final usersResp = await _readSentences();
    final users = <Map<String, dynamic>>[];

    // معالجة بيانات المستخدمين الأساسية
    for (var sentence in usersResp) {
      if (sentence.isNotEmpty && sentence.first == '!re') {
        final user = <String, dynamic>{};
        for (var token in sentence.skip(1)) {
          if (token.startsWith('=')) {
            final parts = token.split('=');
            if (parts.length >= 3) {
              user[parts[1]] = parts.sublist(2).join('=');
            }
          }
        }
        if (user.isNotEmpty) {
          final filteredUser =
              version == 7
                  ? {
                    '.id': user['.id'],
                    'name': user['name'],
                    'password': user['password'],
                    'otp-secret': user['otp-secret'],
                    'group': user['group'],
                    'shared-users': user['shared-users'],
                    'attributes': user['attributes'],
                    'disabled': user['disabled'],
                  }
                  : {
                    '.id': user['.id'],
                    'actual-profile': user['actual-profile'] ?? '',
                    'username': user['name'] ?? user['username'] ?? '',
                    'password': user['password'] ?? '',
                    'uptime-used': user['uptime-used'] ?? '',
                    'download-used': user['download-used'] ?? '',
                    'upload-used': user['upload-used'] ?? '',
                    'last-seen': user['last-seen'] ?? '',
                    'disabled':
                        user['disabled'] ??
                        (user['flags']?.contains('X') ?? false),
                    'active': user['flags']?.contains('A') ?? false,
                    'incomplete': user['flags']?.contains('I') ?? false,
                  };
          users.add(filteredUser);
        }
      }
    }

    if (version == 7) {
      await sendSentence(['/user-manager/user-profile/print']);
      final profilesResp = await _readSentences();
      final profiles = <Map<String, String>>[];

      for (var sentence in profilesResp) {
        if (sentence.isNotEmpty && sentence.first == '!re') {
          final profile = <String, String>{};
          for (var token in sentence.skip(1)) {
            if (token.startsWith('=')) {
              final parts = token.split('=');
              if (parts.length >= 3) {
                profile[parts[1]] = parts.sublist(2).join('=');
              }
            }
          }
          if (profile.isNotEmpty) {
            profiles.add(profile);
          }
        }
      }

      for (var user in users) {
        final userName = user['name'];
        if (userName != null) {
          final matchingProfile = profiles.firstWhere(
            (profile) => profile['user'] == userName,
            orElse: () => {},
          );

          if (matchingProfile.isNotEmpty) {
            user.addAll({
              'profile': matchingProfile['profile'] ?? '',
              'state': matchingProfile['state'] ?? '',
              'end-time': matchingProfile['end-time'] ?? '',
            });
          }
        }
      }
    }

    final file = File('$appDocumentsPath/user_manager_users.json');
    await file.writeAsString(jsonEncode(users));

    return users;
  }

  Future<void> sendSentence(List<String> words) async {
    final out = <int>[];
    for (var w in words) out.addAll(_encodeWord(w));
    out.add(0);
    _socket!.add(out);
    await _socket!.flush();
  }

  Future<List<List<String>>> _readSentences() async {
    final sentences = <List<String>>[];
    while (true) {
      await Future.delayed(Duration(milliseconds: 100));

      if (_recvBuffer.isEmpty) continue;

      final buf = List<int>.from(_recvBuffer);
      try {
        var i = 0;
        while (i < buf.length) {
          final sentence = <String>[];
          while (i < buf.length && buf[i] != 0) {
            int len = buf[i++];
            int bytesCount = 1;

            if (len & 0x80 != 0) {
              bytesCount =
                  (len & 0xC0) == 0x80
                      ? 2
                      : (len & 0xE0) == 0xC0
                      ? 3
                      : 4;
              len = ((len & 0x7F) << ((bytesCount - 1) * 8));

              for (int j = 0; j < bytesCount - 1 && i < buf.length; j++) {
                len |= buf[i++] << ((bytesCount - 2 - j) * 8);
              }
            }

            if (i + len > buf.length) {
              i -= bytesCount;
              break;
            }

            sentence.add(utf8.decode(buf.sublist(i, i + len)));
            i += len;
          }

          if (i < buf.length && buf[i] == 0) {
            i++; // تخطي حرف الإنهاء
            sentences.add(sentence);

            // إذا كانت الجملة تحتوي على !done، نخرج
            if (sentence.isNotEmpty && sentence.first == '!done') {
              _recvBuffer.removeRange(0, i);
              return sentences;
            }
          } else {
            break; // بيانات غير مكتملة
          }
        }

        _recvBuffer.removeRange(0, i);

        // إذا وجدنا جملة !done نعود بالنتيجة
        if (sentences.any((s) => s.isNotEmpty && s.first == '!done')) {
          return sentences;
        }
      } catch (e) {
        print('Error parsing sentences');
        break;
      }
    }
    return sentences;
  }

  Future<bool> login() async {
    await sendSentence(['/login', '=name=$user', '=password=$pass']);
    final resp = await _readSentences();
    return resp.any((s) => s.first == '!done');
  }

  Future<List<Map<String, String>>> fetchHotspotUsers() async {
    await sendSentence(['/ip/hotspot/user/print']);
    final resp = await _readSentences();
    return resp.where((s) => s.first == '!re').map((s) {
      final m = <String, String>{};
      for (var tok in s.skip(1)) {
        if (tok.startsWith('=')) {
          final idx = tok.indexOf('=', 1);
          if (idx != -1) {
            final key = tok.substring(1, idx);
            final value = tok.substring(idx + 1);
            m[key] = value;
          }
        }
      }

      return m;
    }).toList();
  }

  void close() => _socket?.destroy();
}

enum UserType { hotspot, userManager }

class Login extends StatefulWidget {
  const Login({super.key});

  @override
  State<Login> createState() => _LoginState();
}

class _LoginState extends State<Login> {
  final _formKey = GlobalKey<FormState>();
  final TextEditingController _ipController = TextEditingController();
  final FocusNode _ipFocusNode = FocusNode();
  final _usernameController = TextEditingController();
  final _passwordController = TextEditingController();
  final _portController = TextEditingController(text: '8728');
  bool _isLoading = false;
  bool _obscurePassword = true;
  bool _autoFetchEnabled = false;
  bool _hasSavedCredentials = false;
  bool _isActivated = false;

  Map<String, dynamic>? _savedCredentials;
  UserType _selectedUserType = UserType.hotspot;

  final PageController _pageController = PageController();
  int _currentPage = 0;

  bool _showText = false;

  final List<Map<String, dynamic>> _slides = [
    {
      'image': 'assets/img/1.png',
      'title': 'إدارة متكاملة',
      'description': 'تحكم كامل في جميع اصدارات الميكروتك من نظام واحد',
    },
    {
      'image': 'assets/img/2.png',
      'title': 'تقارير مفصلة',
      'description': 'احصل على تقارير أداء دقيقة لشبكتك',
    },
  ];

  final String firebaseUrl =
      'https://micropanel-b67e0-default-rtdb.firebaseio.com/information.json';

  // المفتاح (32 بايت = 256 بت)
  final String aesKey =
      'my32lengthsupersecretnooneknows1'; // يجب أن يكون 32 حرفًا
  final String aesIV = '8bytesiv12345678'; // يجب أن يكون 16 حرفًا

  String? phone;
  String? Urlapi;

  String decryptAES(String encryptedText, String keyString, String ivString) {
    try {
      final key = encrypt.Key.fromUtf8(keyString);
      final iv = encrypt.IV.fromUtf8(ivString);
      final encrypter = encrypt.Encrypter(
        encrypt.AES(key, mode: encrypt.AESMode.cbc),
      );

      // تنظيف النص المشفر من الأحرف غير الصالحة
      final cleanedEncryptedText = encryptedText
          .replaceAll('\n', '')
          .replaceAll('\r', '')
          .replaceAll(' ', '');

      final encrypted = encrypt.Encrypted.fromBase64(cleanedEncryptedText);
      final decrypted = encrypter.decrypt(encrypted, iv: iv);
      return decrypted;
    } catch (e) {
      print('Error decrypting AES: $e');
      rethrow;
    }
  }

  Future<void> fetchJsonFromFirebase() async {
    try {
      final response = await http.get(Uri.parse(firebaseUrl));

      if (response.statusCode == 200) {
        final Map<String, dynamic> data =
            jsonDecode(response.body) as Map<String, dynamic>;

        // التحقق من وجود البيانات قبل فك التشفير
        if (data['phone'] != null && data['Urlapi'] != null) {
          phone = decryptAES(data['phone'].toString(), aesKey, aesIV);
          Urlapi = decryptAES(data['Urlapi'].toString(), aesKey, aesIV);
          print('phone: $phone');
          print('Urlapi:$Urlapi');
        } else {
          throw Exception('بيانات التشفير غير موجودة في الاستجابة');
        }
      } else {
        throw http.ClientException(
          'حدث خطأ أثناء جلب البيانات: ${response.statusCode}',
        );
      }
    } catch (e, st) {
      print('Error fetching or decrypting config from Firebase: $e\n$st');
      throw Exception('فشل في جلب أو فك تشفير الإعدادات: $e');
    }
  }

  @override
  void initState() {
    super.initState();
    _requestFilePickerPermissions();
    _loadSavedCredentials();
    _startAutoSlide();
    Future.delayed(Duration(milliseconds: 150), () {
      fetchJsonFromFirebase();
    });
    checkActivation().then((isActivated) {
      if (mounted) {
        setState(() {
          _isActivated = isActivated;
        });
      }
    });

    Future.delayed(Duration(seconds: 1), () {
      if (!mounted) return;
      setState(() => _showText = true);

      Future.delayed(Duration(seconds: 4), () {
        if (!mounted) return;
        setState(() => _showText = false);
      });
    });
  }

  Future<void> _requestFilePickerPermissions() async {
    if (Platform.isAndroid) {
      if (Platform.version.contains("13") || Platform.version.contains("14")) {
        // لا تحتاج لإذن خاص على Android 13+ عند استخدام FilePicker
        return;
      }

      final permissions = [
        Permission.storage,
        if (Platform.isAndroid && Platform.version.contains("11"))
          Permission.manageExternalStorage,
      ];

      final statuses = await permissions.request();

      if (statuses[Permission.storage]?.isDenied ?? false) {
        // التخزين مرفوض
        print('تم رفض إذن التخزين');
      }

      if (statuses[Permission.manageExternalStorage]?.isDenied ?? false) {
        // إدارة التخزين مرفوضة
        print('تم رفض إذن إدارة التخزين');
      }

      if (statuses[Permission.manageExternalStorage]?.isPermanentlyDenied ??
          false) {
        // يجب توجيه المستخدم للإعدادات
        await openAppSettings();
      }
    }
  }

  Future<void> _loadSavedCredentials() async {
    try {
      final maindirectory = await getApplicationDocumentsDirectory();
      final saveDirectory = Directory('${maindirectory.path}/MicropanelSecrt');
      if (!await saveDirectory.exists()) {
        await saveDirectory.create(recursive: true);
      }
      final file = File('${saveDirectory.path}/login_credentials.json');
      if (await file.exists()) {
        final contents = await file.readAsString();
        final credentials = jsonDecode(contents);
        if (credentials != null && credentials is Map) {
          setState(() {
            _savedCredentials = Map<String, dynamic>.from(credentials);
            _hasSavedCredentials = true;
            _ipController.text = _savedCredentials?['ip'] ?? '';
            _usernameController.text = _savedCredentials?['username'] ?? '';
            _passwordController.text = _savedCredentials?['password'] ?? '';
            _portController.text = _savedCredentials?['port'] ?? '8728';

            // استرجاع قيمة TabBar المحفوظة
            int selectedTabIndex = _savedCredentials?['selectedTab'] ?? 0;
            _selectedUserType =
                selectedTabIndex == 0 ? UserType.hotspot : UserType.userManager;
          });
        }
      }
    } catch (e) {}
  }

  Future<void> _saveCredentials() async {
    try {
      final maindirectory = await getApplicationDocumentsDirectory();
      final saveDirectory = Directory('${maindirectory.path}/MicropanelSecrt');
      if (!await saveDirectory.exists()) {
        await saveDirectory.create(recursive: true);
      }
      final file = File('${saveDirectory.path}/login_credentials.json');
      final credentials = {
        'ip': _ipController.text,
        'username': _usernameController.text,
        'password': _passwordController.text,
        'port': _portController.text,
        'selectedTab': _selectedUserType == UserType.hotspot ? 0 : 1,
      };
      await file.writeAsString(jsonEncode(credentials));
      setState(() {
        _hasSavedCredentials = true;
        _savedCredentials = credentials;
      });
    } catch (e) {}
  }

  @override
  void dispose() {
    _ipController.dispose();
    _ipFocusNode.dispose();
    _usernameController.dispose();
    _passwordController.dispose();
    _portController.dispose();
    _pageController.dispose();
    super.dispose();
  }

  void _startAutoSlide() {
    Future.delayed(Duration(seconds: 5), () {
      if (_pageController.hasClients) {
        final nextPage =
            _currentPage < _slides.length - 1 ? _currentPage + 1 : 0;
        _pageController.animateToPage(
          nextPage,
          duration: Duration(milliseconds: 800),
          curve: Curves.easeInOutCubic,
        );
        _startAutoSlide();
      }
    });
  }

  @override
  Widget build(BuildContext context) {
    final size = MediaQuery.of(context).size;
    final isMobile = size.width < 600;
    return Directionality(
      textDirection: TextDirection.rtl,
      child: Scaffold(
        backgroundColor: const Color(0xFF0A192F),
        body: SafeArea(
          child: LayoutBuilder(
            builder: (context, constraints) {
              if (constraints.maxWidth > 800) {
                return Row(
                  children: [
                    Expanded(
                      flex: 5,
                      child: Stack(
                        children: [
                          Container(
                            padding: const EdgeInsets.symmetric(horizontal: 40),
                            color: const Color(0xFF0A192F),
                            child: Center(child: _buildLoginForm(isMobile)),
                          ),
                          Positioned(
                            top: 10,
                            right: 10,
                            child: InkWell(
                              onTap:
                                  _isActivated
                                      ? null
                                      : () => showSerialNumberDialog(context),
                              child: AnimatedContainer(
                                height: 40,
                                duration: Duration(milliseconds: 800),
                                curve: Curves.easeInOutQuad,
                                decoration: BoxDecoration(
                                  color:
                                      _isActivated
                                          ? Colors.blue.withOpacity(0.95)
                                          : Colors.amberAccent[400]!
                                              .withOpacity(0.95),
                                  borderRadius: BorderRadius.circular(25.0),
                                ),
                                padding: EdgeInsets.symmetric(horizontal: 10),
                                alignment: Alignment.center,
                                child: AnimatedSize(
                                  duration: Duration(milliseconds: 1000),
                                  curve: Curves.easeInOutBack,
                                  child: Row(
                                    mainAxisSize: MainAxisSize.min,
                                    children: [
                                      Icon(
                                        _isActivated
                                            ? Icons.verified
                                            : Icons.touch_app_outlined,
                                        color: Colors.white,
                                        size: 20,
                                      ),
                                      AnimatedSwitcher(
                                        duration: Duration(milliseconds: 800),
                                        switchInCurve: Curves.easeOutCubic,
                                        switchOutCurve: Curves.easeInCubic,
                                        transitionBuilder:
                                            (child, animation) =>
                                                ScaleTransition(
                                                  scale: animation,
                                                  child: FadeTransition(
                                                    opacity: animation,
                                                    child: child,
                                                  ),
                                                ),
                                        child:
                                            _showText || _isActivated
                                                ? Padding(
                                                  padding: EdgeInsets.only(
                                                    left: 8,
                                                  ),
                                                  key: ValueKey(
                                                    _isActivated
                                                        ? 'activated'
                                                        : 'text',
                                                  ),
                                                  child: Text(
                                                    _isActivated
                                                        ? '  تم التفعيل'
                                                        : '  طلب التفعيل',
                                                    style: TextStyle(
                                                      color: Colors.white,
                                                      fontFamily: 'Tajawal',
                                                      fontSize: 13,
                                                      fontWeight:
                                                          FontWeight.bold,
                                                      shadows: [
                                                        Shadow(
                                                          color: Colors.black
                                                              .withOpacity(0.2),
                                                          blurRadius: 2,
                                                          offset: Offset(1, 1),
                                                        ),
                                                      ],
                                                    ),
                                                  ),
                                                )
                                                : SizedBox.shrink(
                                                  key: ValueKey('empty'),
                                                ),
                                      ),
                                    ],
                                  ),
                                ),
                              ),
                            ),
                          ),
                        ],
                      ),
                    ),
                    Expanded(
                      flex: 6,
                      child: Container(
                        decoration: const BoxDecoration(
                          color: Color(0xFF0A192F),
                        ),
                        child: Stack(
                          children: [
                            // Image Slider
                            PageView.builder(
                              controller: _pageController,
                              itemCount: _slides.length,
                              onPageChanged: (index) {
                                setState(() {
                                  _currentPage = index;
                                });
                              },
                              itemBuilder: (context, index) {
                                return Container(
                                  decoration: BoxDecoration(
                                    image: DecorationImage(
                                      image: AssetImage(
                                        _slides[index]['image'],
                                      ),
                                      fit: BoxFit.contain,
                                    ),
                                  ),
                                  child: Container(
                                    decoration: BoxDecoration(
                                      gradient: LinearGradient(
                                        begin: Alignment.topCenter,
                                        end: Alignment.bottomCenter,
                                        colors: [
                                          Colors.transparent,
                                          Colors.black.withOpacity(0.7),
                                        ],
                                      ),
                                    ),
                                  ),
                                );
                              },
                            ),

                            // Content Overlay
                            Positioned(
                              bottom: 80,
                              left: 0,
                              right: 0,
                              child: AnimatedSwitcher(
                                duration: Duration(milliseconds: 500),
                                child: Container(
                                  key: ValueKey<int>(_currentPage),
                                  padding: EdgeInsets.symmetric(horizontal: 40),
                                  child: Column(
                                    children: [
                                      Text(
                                        _slides[_currentPage]['title'],
                                        style: TextStyle(
                                          fontFamily: 'Tajawal',
                                          color: Colors.white,
                                          fontSize: 28,
                                          fontWeight: FontWeight.bold,
                                        ),
                                      ),
                                      SizedBox(height: 15),
                                      Text(
                                        _slides[_currentPage]['description'],
                                        textAlign: TextAlign.center,
                                        style: TextStyle(
                                          fontFamily: 'Tajawal',
                                          color: Colors.white70,
                                          fontSize: 18,
                                        ),
                                      ),
                                    ],
                                  ),
                                ),
                              ),
                            ),

                            Positioned(
                              bottom: 40,
                              left: 0,
                              right: 0,
                              child: Center(
                                child: SmoothPageIndicator(
                                  controller: _pageController,
                                  count: _slides.length,
                                  effect: const ExpandingDotsEffect(
                                    dotHeight: 8,
                                    dotWidth: 8,
                                    activeDotColor: Color(0xFF64FFDA),
                                    dotColor: Colors.white54,
                                    spacing: 10,
                                  ),
                                ),
                              ),
                            ),
                          ],
                        ),
                      ),
                    ),
                  ],
                );
              } else {
                return CustomScrollView(
                  slivers: [
                    SliverFillRemaining(
                      hasScrollBody: false,
                      child: Stack(
                        children: [
                          Container(
                            padding: const EdgeInsets.symmetric(
                              horizontal: 20,
                              vertical: 40,
                            ),
                            child: _buildLoginForm(isMobile),
                          ),
                          Positioned(
                            top: 10,
                            right: 10,
                            child: InkWell(
                              onTap: () => showSerialNumberDialog(context),
                              child: AnimatedContainer(
                                height: 40,
                                duration: Duration(milliseconds: 800),
                                curve: Curves.easeInOutQuad,
                                decoration: BoxDecoration(
                                  color: Colors.amberAccent[400]!.withOpacity(
                                    0.95,
                                  ),
                                  borderRadius: BorderRadius.circular(25.0),
                                ),
                                padding: EdgeInsets.symmetric(horizontal: 10),
                                alignment: Alignment.center,
                                child: AnimatedSize(
                                  duration: Duration(milliseconds: 1000),
                                  curve: Curves.easeInOutBack,
                                  child: Row(
                                    mainAxisSize: MainAxisSize.min,
                                    children: [
                                      Icon(
                                        Icons.touch_app_outlined,
                                        color: Colors.white,
                                        size: 20,
                                      ),
                                      AnimatedSwitcher(
                                        duration: Duration(milliseconds: 800),
                                        switchInCurve: Curves.easeOutCubic,
                                        switchOutCurve: Curves.easeInCubic,
                                        transitionBuilder:
                                            (child, animation) =>
                                                ScaleTransition(
                                                  scale: animation,
                                                  child: FadeTransition(
                                                    opacity: animation,
                                                    child: child,
                                                  ),
                                                ),
                                        child:
                                            _showText
                                                ? Padding(
                                                  padding: EdgeInsets.only(
                                                    left: 8,
                                                  ),
                                                  key: ValueKey('text'),
                                                  child: Text(
                                                    'طلب التفعيل',
                                                    style: TextStyle(
                                                      color: Colors.white,
                                                      fontFamily: 'Tajawal',
                                                      fontSize: 13,
                                                      fontWeight:
                                                          FontWeight.bold,
                                                      shadows: [
                                                        Shadow(
                                                          color: Colors.black
                                                              .withOpacity(0.2),
                                                          blurRadius: 2,
                                                          offset: Offset(1, 1),
                                                        ),
                                                      ],
                                                    ),
                                                  ),
                                                )
                                                : SizedBox.shrink(
                                                  key: ValueKey('empty'),
                                                ),
                                      ),
                                    ],
                                  ),
                                ),
                              ),
                            ),
                          ),
                        ],
                      ),
                    ),
                  ],
                );
              }
            },
          ),
        ),
      ),
    );
  }

  void showSerialNumberDialog(BuildContext context) {
    final TextEditingController serial1Controller = TextEditingController();
    final TextEditingController serial2Controller = TextEditingController();
    final FocusNode serial1Focus = FocusNode();
    final FocusNode serial2Focus = FocusNode();

    showDialog(
      context: context,
      barrierDismissible: false,
      builder: (BuildContext context) {
        return Directionality(
          textDirection: TextDirection.rtl,
          child: Center(
            child: ConstrainedBox(
              constraints: BoxConstraints(maxWidth: 500, minWidth: 300),
              child: Dialog(
                backgroundColor: Colors.transparent,
                elevation: 0,
                child: SingleChildScrollView(
                  child: Container(
                    decoration: BoxDecoration(
                      color: Colors.white,
                      borderRadius: BorderRadius.circular(20),
                      boxShadow: [
                        BoxShadow(
                          color: Colors.black.withOpacity(0.15),
                          blurRadius: 24,
                          spreadRadius: 2,
                        ),
                      ],
                    ),
                    child: Column(
                      mainAxisSize: MainAxisSize.min,
                      children: [
                        _buildModernHeader(context),
                        Padding(
                          padding: const EdgeInsets.symmetric(
                            horizontal: 24,
                            vertical: 16,
                          ),
                          child: Column(
                            crossAxisAlignment: CrossAxisAlignment.stretch,
                            children: [
                              const Text(
                                'إدخال أرقام السيريال',
                                style: TextStyle(
                                  fontSize: 24,
                                  fontWeight: FontWeight.bold,
                                  color: Color(0xFF1A3052),
                                ),
                                textAlign: TextAlign.center,
                              ),
                              const SizedBox(height: 8),
                              Text(
                                'الرجاء إدخال رقمي السيريال الموجودين على المنتج',
                                textAlign: TextAlign.center,
                                style: TextStyle(
                                  color: Colors.grey[600],
                                  fontSize: 15,
                                  height: 1.4,
                                ),
                              ),
                              const SizedBox(height: 24),
                              _buildSerialField(
                                controller: serial1Controller,
                                focusNode: serial1Focus,
                                nextFocusNode: serial2Focus,
                                label: 'السيريال الأول',
                                icon: Icons.confirmation_number_outlined,
                                isFirstField: true,
                              ),
                              const SizedBox(height: 16),
                              _buildSerialField(
                                controller: serial2Controller,
                                focusNode: serial2Focus,
                                label: 'السيريال الثاني',
                                icon: Icons.confirmation_number_outlined,
                                isLastField: true,
                              ),
                              const SizedBox(height: 16),
                              Row(
                                children: [
                                  Text(
                                    'للطلب عبر الوتساب :',
                                    textAlign: TextAlign.center,
                                    style: TextStyle(
                                      color: Colors.grey[600],
                                      fontSize: 14,
                                    ),
                                  ),
                                  Text(
                                    '${phone ?? '+(967)xxxxxx '}',
                                    textDirection: TextDirection.ltr,
                                    style: TextStyle(
                                      color: Colors.grey[600],
                                      fontSize: 14,
                                    ),
                                  ),
                                ],
                              ),
                              const SizedBox(height: 24),
                              _buildModernActionButtons(
                                context: context,
                                serial1Controller: serial1Controller,
                                serial2Controller: serial2Controller,
                              ),
                              const SizedBox(height: 8),
                            ],
                          ),
                        ),
                      ],
                    ),
                  ),
                ),
              ),
            ),
          ),
        );
      },
    );
  }

  Widget _buildModernHeader(BuildContext context) {
    return Container(
      height: 120,
      decoration: BoxDecoration(
        color: const Color(0xFF1A3052),
        borderRadius: const BorderRadius.only(
          topLeft: Radius.circular(20),
          topRight: Radius.circular(20),
        ),
        boxShadow: [
          BoxShadow(
            color: Colors.black.withOpacity(0.1),
            blurRadius: 10,
            spreadRadius: 2,
          ),
        ],
      ),
      child: Stack(
        children: [
          Positioned(
            top: 0,
            right: 0,
            child: Container(
              width: 100,
              height: 100,
              decoration: BoxDecoration(
                color: const Color(0xFF2A5591).withOpacity(0.2),
                borderRadius: const BorderRadius.only(
                  bottomLeft: Radius.circular(100),
                ),
              ),
            ),
          ),
          Positioned(
            bottom: 0,
            left: 0,
            child: Container(
              width: 80,
              height: 80,
              decoration: BoxDecoration(
                color: const Color(0xFF2A5591).withOpacity(0.15),
                borderRadius: const BorderRadius.only(
                  topRight: Radius.circular(80),
                ),
              ),
            ),
          ),
          Positioned(
            top: 16,
            left: 16,
            child: IconButton(
              icon: const Icon(Icons.close, color: Colors.white, size: 28),
              onPressed: () => Navigator.pop(context),
            ),
          ),
          const Center(
            child: Column(
              mainAxisSize: MainAxisSize.min,
              children: [
                Icon(Icons.verified_outlined, color: Colors.white, size: 32),
                SizedBox(height: 8),
                Text(
                  'التفعيل',
                  style: TextStyle(
                    color: Colors.white,
                    fontSize: 18,
                    fontWeight: FontWeight.bold,
                  ),
                ),
              ],
            ),
          ),
        ],
      ),
    );
  }

  Widget _buildSerialField({
    required TextEditingController controller,
    required FocusNode focusNode,
    FocusNode? nextFocusNode,
    required String label,
    required IconData icon,
    bool isFirstField = false,
    bool isLastField = false,
  }) {
    return TextFormField(
      controller: controller,
      focusNode: focusNode,
      textInputAction:
          isLastField ? TextInputAction.done : TextInputAction.next,
      onFieldSubmitted: (_) {
        if (!isLastField && nextFocusNode != null) {
          FocusScope.of(focusNode.context!).requestFocus(nextFocusNode);
        }
      },
      textAlign: TextAlign.right,
      style: const TextStyle(color: Color(0xFF333333), fontSize: 16),
      decoration: InputDecoration(
        labelText: label,
        labelStyle: const TextStyle(color: Color(0xFF1A3052), fontSize: 15),
        prefixIcon: Container(
          margin: const EdgeInsets.only(right: 12),
          child: Icon(
            icon,
            color: const Color(0xFF1A3052).withOpacity(0.7),
            size: 22,
          ),
        ),
        filled: true,
        fillColor: Colors.grey[50],
        border: OutlineInputBorder(
          borderRadius: BorderRadius.circular(12),
          borderSide: BorderSide.none,
        ),
        enabledBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(12),
          borderSide: BorderSide(color: Colors.grey[300]!, width: 1),
        ),
        focusedBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(12),
          borderSide: const BorderSide(color: Color(0xFF1A3052), width: 1.5),
        ),
        contentPadding: const EdgeInsets.symmetric(
          horizontal: 16,
          vertical: 16,
        ),
        suffixIcon: IconButton(
          icon: Icon(
            Icons.paste,
            color: const Color(0xFF1A3052).withOpacity(0.6),
            size: 20,
          ),
          onPressed: () => _pasteFromClipboard(controller),
        ),
      ),
    );
  }

  Widget _buildModernActionButtons({
    required BuildContext context,
    required TextEditingController serial1Controller,
    required TextEditingController serial2Controller,
  }) {
    return Row(
      children: [
        Expanded(
          child: OutlinedButton(
            style: OutlinedButton.styleFrom(
              foregroundColor: const Color(0xFF1A3052),
              padding: const EdgeInsets.symmetric(vertical: 16),
              side: const BorderSide(color: Color(0xFF1A3052)),
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(12),
              ),
              backgroundColor: Colors.white,
            ),
            onPressed: () => Navigator.pop(context),
            child: const Text(
              'إلغاء',
              style: TextStyle(fontWeight: FontWeight.bold),
            ),
          ),
        ),
        const SizedBox(width: 16),
        Expanded(
          child: ElevatedButton(
            style: ElevatedButton.styleFrom(
              backgroundColor: const Color(0xFF1A3052),
              foregroundColor: Colors.white,
              padding: const EdgeInsets.symmetric(vertical: 16),
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(12),
              ),
              elevation: 2,
              shadowColor: const Color(0xFF1A3052).withOpacity(0.3),
            ),
            onPressed:
                () => _validateAndSubmit(
                  context: context,
                  serial1Controller: serial1Controller,
                  serial2Controller: serial2Controller,
                ),
            child: const Text(
              'تأكيد',
              style: TextStyle(fontWeight: FontWeight.bold),
            ),
          ),
        ),
      ],
    );
  }

  Future<bool> checkActivation() async {
    final storageDb = SecureStorageDB();
    final serial1 = await storageDb.read('serialPart1');
    final serial2 = await storageDb.read('serialPart2');
    return serial1 != null && serial2 != null;
  }

  Future<void> _validateAndSubmit({
    required BuildContext context,
    required TextEditingController serial1Controller,
    required TextEditingController serial2Controller,
  }) async {
    final serial1 = serial1Controller.text.trim();
    final serial2 = serial2Controller.text.trim();

    if (serial1.isEmpty || serial2.isEmpty) {
      _showValidationError(context, 'يجب إدخال كلا السيريالين');
      return;
    }

    try {
      showDialog(
        context: context,
        barrierDismissible: false,
        builder: (context) => const Center(child: CircularProgressIndicator()),
      );

      final response = await http.get(
        Uri.parse('$Urlapi/api/MicroSerial/by-parts/$serial1/$serial2'),
        headers: {'accept': '*/*'},
      );

      Navigator.pop(context);

      if (response.statusCode == 200) {
        final data = json.decode(response.body);
        if (data['serialPart1'] == serial1 && data['serialPart2'] == serial2) {
          // حفظ بيانات التفعيل بشكل آمن
          final storageDb = SecureStorageDB();
          await storageDb.write('serialPart1', serial1);
          await storageDb.write('serialPart2', serial2);
          Navigator.pop(context);
          _showSuccessDialog(context);
        } else {
          _showValidationError(
            context,
            'أرقام السيريال غير متطابقة مع السجلات',
          );
        }
      } else if (response.statusCode == 404) {
        _showValidationError(context, 'أرقام السيريال غير صحيحة');
      } else {
        _showValidationError(
          context,
          'حدث خطأ أثناء التحقق، يرجى المحاولة لاحقاً',
        );
      }
    } catch (e) {
      Navigator.pop(context);
      _showValidationError(
        context,
        'تعذر الاتصال بالخادم، يرجى التأكد من الاتصال بالإنترنت',
      );
      print('$e');
    }
  }

  void _showValidationError(BuildContext context, String message) {
    ScaffoldMessenger.of(context).showSnackBar(
      SnackBar(
        content: Row(
          children: [
            const Icon(Icons.error_outline, color: Colors.white),
            const SizedBox(width: 8),
            Text(message),
          ],
        ),
        backgroundColor: const Color(0xFFD32F2F),
        behavior: SnackBarBehavior.floating,
        shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)),
        margin: const EdgeInsets.all(16),
        duration: const Duration(seconds: 3),
      ),
    );
  }

  void _showSuccessDialog(BuildContext context) {
    showDialog(
      context: context,
      builder:
          (context) => Directionality(
            textDirection: TextDirection.rtl,
            child: Dialog(
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(20),
              ),
              child: Padding(
                padding: const EdgeInsets.all(24),
                child: Column(
                  mainAxisSize: MainAxisSize.min,
                  children: [
                    Container(
                      width: 80,
                      height: 80,
                      decoration: BoxDecoration(
                        color: const Color(0xFF4CAF50).withOpacity(0.2),
                        shape: BoxShape.circle,
                      ),
                      child: const Icon(
                        Icons.check_circle,
                        color: Color(0xFF4CAF50),
                        size: 60,
                      ),
                    ),
                    const SizedBox(height: 24),
                    const Text(
                      'تم التفعيل بنجاح',
                      style: TextStyle(
                        fontSize: 20,
                        fontWeight: FontWeight.bold,
                        color: Color(0xFF1A3052),
                      ),
                    ),
                    const SizedBox(height: 16),
                    const Text(
                      'تم تفعيل المنتج بنجاح، يمكنك الآن استخدام جميع الميزات',
                      textAlign: TextAlign.center,
                      style: TextStyle(color: Colors.grey, fontSize: 15),
                    ),
                    const SizedBox(height: 24),
                    SizedBox(
                      width: double.infinity,
                      child: ElevatedButton(
                        style: ElevatedButton.styleFrom(
                          backgroundColor: const Color(0xFF1A3052),
                          padding: const EdgeInsets.symmetric(vertical: 16),
                          shape: RoundedRectangleBorder(
                            borderRadius: BorderRadius.circular(12),
                          ),
                        ),
                        onPressed: () => Navigator.pop(context),
                        child: const Text(
                          'حسناً',
                          style: TextStyle(color: Colors.white),
                        ),
                      ),
                    ),
                  ],
                ),
              ),
            ),
          ),
    );
  }

  Future<void> _pasteFromClipboard(TextEditingController controller) async {
    final clipboardData = await Clipboard.getData('text/plain');
    if (clipboardData != null && clipboardData.text != null) {
      controller.text = clipboardData.text!;
    }
  }

  Widget _buildLoginForm(bool isMobile) {
    return Form(
      key: _formKey,
      child: Column(
        children: [
          _buildAppHeader(isMobile),
          const SizedBox(height: 20),
          _buildUserTypeSelection(),
          const SizedBox(height: 5),
          _buildIpFields(),
          const SizedBox(height: 12),
          _buildUsernameField(),
          const SizedBox(height: 12),
          _buildPasswordField(),
          const SizedBox(height: 12),
          _buildPortField(),
          const SizedBox(height: 25),
          _buildLoginButton(),
          const SizedBox(height: 15),
        ],
      ),
    );
  }

  Widget _buildAppHeader(bool isMobile) => Column(
    children: [
      SizedBox(height: MediaQuery.of(context).size.width > 768 ? 60 : 50),
      Row(
        mainAxisAlignment: MainAxisAlignment.center,
        mainAxisSize: MainAxisSize.min,
        children: [
          Hero(
            tag: 'app-icon',
            child: Icon(
              Icons.network_check,
              size: isMobile ? 55 : 60,
              color: Colors.white,
            ),
          ),

          const SizedBox(width: 10),
          Column(
            crossAxisAlignment: CrossAxisAlignment.start,
            children: [
              const Text(
                'Micro Panel',
                style: TextStyle(
                  fontFamily: 'Tajawal',
                  fontSize: 25,
                  fontWeight: FontWeight.bold,
                  color: Colors.white,
                ),
              ),
              const Text(
                'نظام إدارة أجهزة الميكروتك',
                style: TextStyle(
                  fontFamily: 'Tajawal',
                  color: Colors.white70,
                  fontSize: 11,
                ),
              ),
            ],
          ),
        ],
      ),
      SizedBox(height: MediaQuery.of(context).size.width > 768 ? 30 : 50),
    ],
  );

  Widget _buildIpFields() {
    return Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      children: [
        const SizedBox(height: 10),
        const Padding(
          padding: EdgeInsets.only(bottom: 8.0, right: 8.0),
          child: Text(
            'عنوان IP',
            style: TextStyle(fontFamily: 'Tajawal', color: Colors.white70),
          ),
        ),
        TextFormField(
          controller: _ipController,
          validator: (value) => _validateIpAddress(value),
          style: const TextStyle(fontFamily: 'Tajawal', color: Colors.white),
          decoration: InputDecoration(
            labelStyle: const TextStyle(
              fontFamily: 'Tajawal',
              color: Colors.white70,
            ),
            filled: true,
            fillColor: Colors.white.withOpacity(0.1),
            contentPadding: const EdgeInsets.symmetric(
              vertical: 14,
              horizontal: 16,
            ),
            enabledBorder: OutlineInputBorder(
              borderRadius: BorderRadius.circular(10),
              borderSide: BorderSide(color: Colors.white.withOpacity(0.2)),
            ),
            focusedBorder: OutlineInputBorder(
              borderRadius: BorderRadius.circular(10),
              borderSide: const BorderSide(color: Color(0xFF3B82F6)),
            ),
            hintText: 'مثال: 192.168.1.1',
            hintStyle: TextStyle(
              fontFamily: 'Tajawal',
              color: Colors.white.withOpacity(0.5),
            ),
          ),
          keyboardType: const TextInputType.numberWithOptions(decimal: true),
          textInputAction: TextInputAction.next,
          inputFormatters: [
            FilteringTextInputFormatter.allow(RegExp(r'[0-9.]')),
            LengthLimitingTextInputFormatter(15),
          ],
          focusNode: _ipFocusNode,
          onTap: () {
            // نقل المؤشر لنهاية النص
            final text = _ipController.text;
            _ipController.selection = TextSelection.fromPosition(
              TextPosition(offset: text.length),
            );
          },
          onChanged: (value) {
            // إزالة النقطة الثانية إذا أدخل المستخدم ".."
            if (value.endsWith('..')) {
              _ipController.text = value.substring(0, value.length - 1);
              _ipController.selection = TextSelection.fromPosition(
                TextPosition(offset: _ipController.text.length),
              );
            }
          },
        ),
      ],
    );
  }

  // دالة التحقق من صحة عنوان IP كامل
  String? _validateIpAddress(String? value) {
    if (value == null || value.isEmpty) return 'يرجى إدخال عنوان IP';

    final ipParts = value.split('.');
    if (ipParts.length != 4) return 'يجب أن يتكون عنوان IP من 4 أجزاء';

    for (int i = 0; i < ipParts.length; i++) {
      final part = ipParts[i];
      if (part.isEmpty) return 'جزء ${i + 1} من الـ IP فارغ';
      if (!RegExp(r'^\d+$').hasMatch(part))
        return 'يجب أن يحتوي جزء ${i + 1} على أرقام فقط';

      final num = int.tryParse(part) ?? 0;
      if (num < 0 || num > 255) return 'يجب أن يكون جزء ${i + 1} بين 0 و 255';
    }

    return null;
  }

  Widget _buildUsernameField() {
    return TextFormField(
      controller: _usernameController,
      validator: (value) => _validateEnglishOnly(value, 'اسم المستخدم'),
      style: const TextStyle(fontFamily: 'Tajawal', color: Colors.white),
      decoration: InputDecoration(
        labelText: 'اسم المستخدم',
        labelStyle: const TextStyle(
          fontFamily: 'Tajawal',
          color: Colors.white70,
        ),
        prefixIcon: const Icon(Icons.person_outline, color: Colors.white70),
        filled: true,
        fillColor: Colors.white.withOpacity(0.1),
        contentPadding: const EdgeInsets.symmetric(
          vertical: 14,
          horizontal: 16,
        ),
        enabledBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: BorderSide(color: Colors.white.withOpacity(0.2)),
        ),
        focusedBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: const BorderSide(color: Color(0xFF3B82F6)),
        ),
      ),
      textInputAction: TextInputAction.next,
      inputFormatters: [
        FilteringTextInputFormatter.allow(RegExp(r'[a-zA-Z0-9]')),
      ],
      onTap: () {
        // تأكد أن المؤشر في نهاية النص
        final text = _usernameController.text;
        _usernameController.selection = TextSelection.fromPosition(
          TextPosition(offset: text.length),
        );
      },
      onFieldSubmitted:
          (_) => FocusScope.of(
            context,
          ).requestFocus(_passwordController as FocusNode?),
    );
  }

  Widget _buildPasswordField() {
    return TextFormField(
      controller: _passwordController,
      obscureText: _obscurePassword,
      validator: _validatePassword,
      style: const TextStyle(fontFamily: 'Tajawal', color: Colors.white),
      decoration: InputDecoration(
        labelText: 'كلمة المرور',
        labelStyle: const TextStyle(
          fontFamily: 'Tajawal',
          color: Colors.white70,
        ),
        prefixIcon: const Icon(Icons.lock_outline, color: Colors.white70),
        suffixIcon: IconButton(
          icon: Icon(
            _obscurePassword ? Icons.visibility_off : Icons.visibility,
            color: Colors.white70,
          ),
          onPressed: () => setState(() => _obscurePassword = !_obscurePassword),
        ),
        filled: true,
        fillColor: Colors.white.withOpacity(0.1),
        contentPadding: const EdgeInsets.symmetric(
          vertical: 14,
          horizontal: 16,
        ),
        enabledBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: BorderSide(color: Colors.white.withOpacity(0.2)),
        ),
        focusedBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: const BorderSide(color: Color(0xFF3B82F6)),
        ),
      ),
      textInputAction: TextInputAction.next,
      inputFormatters: [
        FilteringTextInputFormatter.allow(
          RegExp(r'[a-zA-Z0-9!@#\$%^&*()_+\-=\[\]{};:"\\|,.<>\/?]'),
        ),
      ],
      onTap: () {
        // نقل المؤشر لنهاية النص
        final text = _passwordController.text;
        _passwordController.selection = TextSelection.fromPosition(
          TextPosition(offset: text.length),
        );
      },
      onFieldSubmitted: (_) => _connectToMikrotik(),
    );
  }

  String? _validatePassword(String? value) {
    if (value == null || value.isEmpty) {
      return 'يرجى إدخال كلمة المرور';
    }
    final passwordRegex = RegExp(
      r'^[a-zA-Z0-9!@#\$%^&*()_+\-=\[\]{};:"\\|,.<>\/?]+$',
    );
    if (!passwordRegex.hasMatch(value)) {
      return 'يمكن أن تحتوي كلمة المرور على أحرف وأرقام ورموز خاصة';
    }
    return null;
  }

  // أضف هذه الدالة في كلاس _LoginState
  String? _validateEnglishOnly(String? value, String fieldName) {
    if (value == null || value.isEmpty) {
      return 'يرجى إدخال $fieldName';
    }
    final englishRegex = RegExp(r'^[a-zA-Z0-9]+$');
    if (!englishRegex.hasMatch(value)) {
      return 'يجب أن يحتوي $fieldName على أحرف إنجليزية وأرقام فقط';
    }
    return null;
  }

  Widget _buildPortField() {
    return TextFormField(
      controller: _portController,
      validator: _validatePort,
      style: const TextStyle(fontFamily: 'Tajawal', color: Colors.white),
      decoration: InputDecoration(
        labelText: 'المنفذ',
        labelStyle: const TextStyle(
          fontFamily: 'Tajawal',
          color: Colors.white70,
        ),
        prefixIcon: const Icon(Icons.settings_ethernet, color: Colors.white70),
        filled: true,
        fillColor: Colors.white.withOpacity(0.1),
        contentPadding: const EdgeInsets.symmetric(
          vertical: 14,
          horizontal: 16,
        ),
        enabledBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: BorderSide(color: Colors.white.withOpacity(0.2)),
        ),
        focusedBorder: OutlineInputBorder(
          borderRadius: BorderRadius.circular(10),
          borderSide: const BorderSide(color: Color(0xFF3B82F6)),
        ),
      ),
      keyboardType: TextInputType.number,
      inputFormatters: [
        FilteringTextInputFormatter.digitsOnly,
        LengthLimitingTextInputFormatter(5),
      ],
      onTap: () {
        // نقل المؤشر لنهاية النص
        final text = _portController.text;
        _portController.selection = TextSelection.fromPosition(
          TextPosition(offset: text.length),
        );
      },
      onFieldSubmitted: (_) => _connectToMikrotik(),
    );
  }

  // يمكنك تحديث دالة التحقق إذا كنت تريد ضوابط إضافية
  String? _validatePort(String? value) {
    if (value == null || value.isEmpty) {
      return 'يرجى إدخال رقم المنفذ';
    }

    final port = int.tryParse(value);
    if (port == null) {
      return 'يجب أن يتكون المنفذ من أرقام فقط';
    }

    if (port <= 0 || port > 65535) {
      return 'يجب أن يكون المنفذ بين 1 و 65535';
    }

    return null;
  }

  Widget _buildUserTypeSelection() {
    return Padding(
      padding: const EdgeInsets.only(bottom: 10.0),
      child: DefaultTabController(
        length: 2,
        initialIndex: _selectedUserType == UserType.hotspot ? 0 : 1,
        child: Builder(
          // لإمكانية الوصول للسياق الصحيح للتاب
          builder: (context) {
            final tabController = DefaultTabController.of(context);
            if (tabController != null) {
              // مزامنة تغيير المتغير مع controller عند تغير القيمة
              tabController.addListener(() {
                if (!tabController.indexIsChanging) {
                  final idx = tabController.index;
                  final selectedType =
                      idx == 0 ? UserType.hotspot : UserType.userManager;
                  if (selectedType != _selectedUserType) {
                    setState(() {
                      _selectedUserType = selectedType;
                    });
                    _saveCredentials();
                  }
                }
              });
            }

            return Container(
              decoration: BoxDecoration(
                color: Colors.white.withOpacity(0.05),
                borderRadius: BorderRadius.circular(12),
                boxShadow: [
                  BoxShadow(
                    color: Colors.black.withOpacity(0.1),
                    blurRadius: 6,
                    offset: Offset(0, 2),
                  ),
                ],
              ),
              child: Padding(
                padding: const EdgeInsets.all(4.0),
                child: TabBar(
                  tabs: const [
                    Tab(
                      text: 'مستخدمي الهوتسبوت',
                      icon: Icon(Icons.wifi, size: 18),
                    ),
                    Tab(
                      text: 'مستخدمي اليوزر مانجر',
                      icon: Icon(Icons.people_alt, size: 18),
                    ),
                  ],
                  indicator: BoxDecoration(
                    borderRadius: BorderRadius.circular(8),
                    gradient: LinearGradient(
                      colors: [Color(0xFF3B82F6), Color(0xFF1D4ED8)],
                    ),
                  ),
                  labelColor: Colors.white,
                  unselectedLabelColor: Colors.white.withOpacity(0.7),
                  labelStyle: TextStyle(
                    fontSize: 14,
                    fontWeight: FontWeight.w500,
                    fontFamily: 'Tajawal',
                  ),
                  unselectedLabelStyle: TextStyle(
                    fontFamily: 'Tajawal',
                    fontSize: 13,
                    fontWeight: FontWeight.normal,
                  ),
                  indicatorSize: TabBarIndicatorSize.tab,
                  indicatorPadding: EdgeInsets.zero,
                ),
              ),
            );
          },
        ),
      ),
    );
  }

  Widget _buildLoginButton() {
    return SizedBox(
      width: double.infinity,
      height: 48,
      child: ElevatedButton(
        onPressed: _isLoading ? null : _connectToMikrotik,
        style: ElevatedButton.styleFrom(
          backgroundColor: _isLoading ? Colors.grey : const Color(0xFF3B82F6),
          shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.circular(10),
          ),
        ),
        child:
            _isLoading
                ? const SizedBox(
                  width: 20,
                  height: 20,
                  child: CircularProgressIndicator(
                    color: Colors.white,
                    strokeWidth: 3,
                  ),
                )
                : Row(
                  mainAxisAlignment: MainAxisAlignment.center,
                  children: const [
                    Icon(Icons.login, color: Colors.white, size: 20),
                    SizedBox(width: 8),
                    Text(
                      'تسجيل الدخول',
                      style: TextStyle(
                        fontFamily: 'Tajawal',
                        fontSize: 15,
                        color: Colors.white,
                      ),
                    ),
                  ],
                ),
      ),
    );
  }

  Future<void> _connectToMikrotik() async {
    if (!_formKey.currentState!.validate()) return;

    setState(() => _isLoading = true);

    final ip = _ipController.text;
    final port = int.tryParse(_portController.text) ?? 8728;

    // إعداد timeout لمحاولة الاتصال
    final timeoutDuration = Duration(seconds: 3);

    try {
      // استخدام Future.any للجمع بين عملية الاتصال و timeout
      final client = await Future.any([
        _attemptLogin(ip, port),
        Future.delayed(
          timeoutDuration,
          () => throw TimeoutException('تجاوز الوقت المحدد للاتصال'),
        ),
      ]);

      await _saveCredentials();
      if (mounted) {
        Navigator.pushReplacement(
          context,
          MaterialPageRoute(
            builder:
                (context) => DataLoadingScreen(
                  client: client,
                  host: ip,
                  port: port,
                  username: _usernameController.text,
                  password: _passwordController.text,
                  userType: _selectedUserType == UserType.hotspot ? 0 : 1,
                ),
          ),
        );
      }
    } on TimeoutException {
      _showErrorDialog(
        'تجاوز الوقت المحدد',
        'لم يتم الاتصال بالخادم خلال الوقت المحدد. يرجى التحقق من اتصال الشبكة وإعادة المحاولة.',
      );
    } on SocketException {
      _showErrorDialog(
        'خطأ في الاتصال',
        'تعذر الاتصال بالخادم. يرجى التحقق من عنوان IP والمنفذ وإعادة المحاولة.',
      );
    } on Exception catch (e) {
      _showErrorDialog('خطأ في تسجيل الدخول', e.toString());
    } finally {
      if (mounted) {
        setState(() => _isLoading = false);
      }
    }
  }

  Future<RouterOSClient> _attemptLogin(String ip, int port) async {
    final client = RouterOSClient(
      address: ip,
      port: port,
      user: _usernameController.text,
      password: _passwordController.text,
      useSsl: false,
      verbose: false,
    );

    final isLoggedIn = await client.login();
    if (!isLoggedIn) {
      throw Exception(
        "فشل تسجيل الدخول: اسم المستخدم أو كلمة المرور غير صحيحة",
      );
    }

    return client;
  }

  void _showErrorDialog(String title, String message) {
    if (!mounted) return;

    // تنظيف الرسالة من كلمة Exception إن وجدت
    String cleanedMessage = message.replaceAll('Exception:', '').trim();

    showDialog(
      context: context,
      builder:
          (context) => Directionality(
            textDirection: TextDirection.rtl,
            child: Dialog(
              backgroundColor: const Color(0xFF0A1A3A),
              shape: RoundedRectangleBorder(
                borderRadius: BorderRadius.circular(16.0),
              ),
              elevation: 10,
              child: Padding(
                padding: const EdgeInsets.symmetric(
                  horizontal: 24.0,
                  vertical: 20.0,
                ),
                child: Column(
                  mainAxisSize: MainAxisSize.min,
                  crossAxisAlignment: CrossAxisAlignment.stretch,
                  children: [
                    Align(
                      alignment: Alignment.centerRight,
                      child: Text(
                        title
                            .replaceAll('Exception:', '')
                            .trim(), // تنظيف العنوان أيضاً
                        textAlign: TextAlign.right,
                        style: const TextStyle(
                          fontFamily: 'Tajawal',
                          fontSize: 22,
                          fontWeight: FontWeight.bold,
                          color: Colors.white,
                          height: 1.5,
                        ),
                      ),
                    ),

                    const SizedBox(height: 12),

                    Text(
                      cleanedMessage, // استخدام الرسالة المنظفة
                      textAlign: TextAlign.right,
                      style: const TextStyle(
                        fontFamily: 'Tajawal',
                        fontSize: 16,
                        color: Colors.white70,
                        height: 1.6,
                      ),
                    ),

                    const SizedBox(height: 24),

                    Align(
                      alignment: Alignment.centerLeft,
                      child: Directionality(
                        textDirection: TextDirection.rtl,
                        child: TextButton(
                          onPressed: () => Navigator.pop(context),
                          style: TextButton.styleFrom(
                            backgroundColor: const Color(0xFF1A3A6E),
                            shape: RoundedRectangleBorder(
                              borderRadius: BorderRadius.circular(8.0),
                            ),
                            padding: const EdgeInsets.symmetric(
                              horizontal: 32,
                              vertical: 12,
                            ),
                          ),
                          child: Text(
                            'حسناً',
                            style: const TextStyle(
                              fontFamily: 'Tajawal',
                              fontSize: 16,
                              fontWeight: FontWeight.bold,
                              color: Colors.white,
                            ),
                          ),
                        ),
                      ),
                    ),
                  ],
                ),
              ),
            ),
          ),
    );
  }

  String? _validateRequired(String? value, String fieldName) {
    if (value == null || value.isEmpty) return 'يرجى إدخال $fieldName';
    final regex = RegExp(r'^[a-zA-Z0-9]+$');
    if (!regex.hasMatch(value))
      return 'يجب أن يحتوي $fieldName على أحرف إنجليزية وأرقام فقط';
    return null;
  }

  String? _validateIpPart(String? value, int part) {
    if (value == null || value.isEmpty) return 'يرجى إدخال جزء $part من الـ IP';
    if (!RegExp(r'^\d+$').hasMatch(value))
      return 'يجب أن يحتوي جزء $part على أرقام فقط';
    final num = int.tryParse(value) ?? 0;
    if (num < 0 || num > 255) return 'يجب أن يكون جزء $part بين 0 و 255';
    return null;
  }
}

class DataLoadingScreen extends StatefulWidget {
  final MikroTikApi? api; // يمكن إزالته لاحقًا إذا لم تعد تحتاج إليه
  final String host;
  final int port;
  final String username;
  final String password;
  final RouterOSClient client;
  final int userType;

  const DataLoadingScreen({
    super.key,
    required this.client,
    required this.host,
    required this.port,
    required this.username,
    required this.password,
    required this.userType,
    this.api,
  });

  @override
  State<DataLoadingScreen> createState() => _DataLoadingScreenState();
}

class _DataLoadingScreenState extends State<DataLoadingScreen>
    with SingleTickerProviderStateMixin {
  bool _loading = true;
  int _userCount = 0;
  int _currentProgress = 0;
  bool _hasError = false;
  String _errorMessage = '';
  late final StreamController<int> _progressController;
  late final Stream<int> _progressStream;
  Isolate? _isolate;
  ReceivePort? _receivePort;
  int _totalUsers = 0;
  int _batchSize = 500;
  Timer? _simulationTimer;
  Random _random = Random();
  bool _realDataStarted = false;

  @override
  void initState() {
    super.initState();
    _progressController = StreamController<int>();
    _progressStream = _progressController.stream;
    _initDataLoading();
  }

  Future<void> _initDataLoading() async {
    try {
      await _startIsolate();
    } catch (e) {
      _handleError('فشل في بدء عملية الجلب');
    }
  }

  Future<void> _startIsolate() async {
    _receivePort = ReceivePort();
    final maindirectory = await getApplicationDocumentsDirectory();
    final saveDirectory = Directory('${maindirectory.path}/MicropanelSecrt');
    if (!await saveDirectory.exists()) {
      await saveDirectory.create(recursive: true);
    }
    await Isolate.spawn(
      _fetchUsersInBackground,
      _IsolateData(
        host: widget.host,
        port: widget.port,
        username: widget.username,
        password: widget.password,
        sendPort: _receivePort!.sendPort,
        userType: widget.userType,
        appDocumentsPath: saveDirectory.path,
      ),
      onError: _receivePort!.sendPort,
      onExit: _receivePort!.sendPort,
    );
    _receivePort!.listen(_handleIsolateMessage);
  }

  void _handleIsolateMessage(dynamic message) {
    try {
      if (message is _ProgressUpdate) {
        if (!_realDataStarted) {
          _startSimulation(message.total);
          if (!mounted) return;
          setState(() => _realDataStarted = true);
        }
        _updateProgress(message.current, message.total);
      } else if (message is Map) {
        if (message.containsKey('type') && message.containsKey('users')) {
          final users = List<Map<String, dynamic>>.from(message['users']);
          // تمرير كافة البيانات المستقبلة إلى دالة _handleSuccess
          _handleSuccess(
            users,
            additionalData: {
              'type': message['type'],
              if (message.containsKey('version')) 'version': message['version'],
              if (message.containsKey('timestamp'))
                'timestamp': message['timestamp'],
            },
          );
        } else {
          _handleError('صيغة البيانات غير صحيحة');
        }
      } else if (message is String) {
        _handleError(message);
      } else if (message is List) {
        if (message.isNotEmpty && message.first is Map) {
          _handleSuccess(message.cast<Map<String, dynamic>>());
        }
      } else {
        _handleError('استلم رسالة غير معروفة من النوع: ${message.runtimeType}');
      }
    } catch (e, stack) {
      _handleError('حدث خطأ أثناء معالجة الرسالة:  \n$stack');
    }
  }

  void _startSimulation(int totalUsers) {
    _simulationTimer?.cancel();
    _totalUsers = totalUsers;
    _currentProgress = 0;
    _simulationTimer = Timer.periodic(Duration(milliseconds: 300), (timer) {
      if (_currentProgress < _totalUsers) {
        _currentProgress += 1 + _random.nextInt(40);
        if (_currentProgress > _totalUsers) {
          _currentProgress = _totalUsers;
        }
        _progressController.add(_currentProgress);
      } else {
        timer.cancel();
      }
    });
  }

  void _updateProgress(int current, int total) {
    if (!mounted) return;
    setState(() {
      _currentProgress = current;
      _totalUsers = total;
    });
    _progressController.add(current);
  }

  void _handleError(String message) {
    if (!mounted) return;
    _simulationTimer?.cancel();
    setState(() {
      _hasError = true;
      _errorMessage = message;
      _loading = false;
    });
    _cleanUpResources();
  }

  void _cleanUpResources() {
    _simulationTimer?.cancel();
    _progressController.close();
    _isolate?.kill(priority: Isolate.immediate);
    _receivePort?.close();
  }

  static Future<void> _fetchUsersInBackground(_IsolateData isolateData) async {
    if (!kIsWeb &&
        (Platform.isWindows || Platform.isLinux || Platform.isMacOS)) {
      sqfliteFfiInit();
      databaseFactory = databaseFactoryFfi;
    }
    final sendPort = isolateData.sendPort;
    try {
      final api = MikroTikApi(
        host: isolateData.host,
        port: isolateData.port,
        user: isolateData.username,
        pass: isolateData.password,
      );

      await api.connect();
      bool loggedIn = await api.login();

      if (!loggedIn) {
        sendPort.send("فشل تسجيل الدخول إلى جهاز الميكروتك");
        return;
      }

      // --- البروتوكول الجديد: جلب الترخيص وتخزينه مشفر (مرة واحدة فقط) ---
      final storageDb = SecureStorageDB();
      String? existingSoftwareId = await storageDb.read('license_software_id');
      if (existingSoftwareId == null) {
        // لم يتم التخزين مسبقًا
        final licenseData = await api.fetchLicenseData();

        if (licenseData != null && licenseData.isNotEmpty) {
          final aesKey = 'my32lengthsupersecretnooneknows1';
          final aesIV = '8bytesiv12345678';

          String encryptAES(String plainText) {
            final key = encrypt.Key.fromUtf8(aesKey);
            final iv = encrypt.IV.fromUtf8(aesIV);
            final encrypter = encrypt.Encrypter(
              encrypt.AES(key, mode: encrypt.AESMode.cbc),
            );
            return encrypter.encrypt(plainText, iv: iv).base64;
          }

          await storageDb.write(
            'license_software_id',
            encryptAES(licenseData['software-id'] ?? ''),
          );
          await storageDb.write(
            'license_nlevel',
            encryptAES(licenseData['nlevel'] ?? ''),
          );

          print("تم تخزين بيانات الترخيص المشفرة في قاعدة البيانات");
        }
      }

      final versionString = await api.fetchRouterVersion(
        isolateData.appDocumentsPath,
      );

      final version = versionString.startsWith('7') ? 7 : 6;

      if (isolateData.userType == UserType.hotspot.index) {
        final hotspotUsers = await api.fetchHotspotUsers();
        sendPort.send(
          _ProgressUpdate(hotspotUsers.length, hotspotUsers.length),
        );
        sendPort.send({
          'type': 'hotspot',
          'users': hotspotUsers,
          'timestamp': DateTime.now().toIso8601String(),
        });
      } else {
        final userManagerUsers = await api.fetchUserManagerUsers(
          isolateData.appDocumentsPath,
        );
        sendPort.send(
          _ProgressUpdate(userManagerUsers.length, userManagerUsers.length),
        );
        sendPort.send({
          'type': 'user_manager',
          'users': userManagerUsers,
          'version': version,
          'timestamp': DateTime.now().toIso8601String(),
        });
      }
    } catch (e, stackTrace) {
      sendPort.send('حدث خطأ أثناء جلب البيانات:\n \n$stackTrace');
      print('$e');
    }
  }

  Future<void> _handleSuccess(
    List<Map<String, dynamic>> users, {
    Map<String, dynamic>? additionalData,
  }) async {
    try {
      final maindirectory = await getApplicationDocumentsDirectory();
      final saveDirectory = Directory('${maindirectory.path}/MicropanelSecrt');
      if (!await saveDirectory.exists()) {
        await saveDirectory.create(recursive: true);
      }
      final fileName =
          widget.userType == UserType.hotspot.index
              ? 'hotspot_users.json'
              : 'user_manager_users.json';
      final file = File('${saveDirectory.path}/$fileName');

      // تحضير البيانات الأساسية للحفظ
      final encoder = JsonEncoder.withIndent('  ');
      final formattedJson = encoder.convert(users);
      await file.writeAsString(formattedJson);

      if (mounted) {
        setState(() {
          _userCount = users.length;
          _loading = false;
        });
        Navigator.pushReplacement(
          context,
          MaterialPageRoute(
            builder: (context) => RouterDetailsPage(client: widget.client),
          ),
        );
      }
    } catch (e) {
      _handleError('فشل في حفظ البيانات');
    }
  }

  @override
  void dispose() {
    _cleanUpResources();
    _receivePort?.close();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: const Color(0xFF0A192F),
      body: Center(
        child: Padding(
          padding: const EdgeInsets.all(16.0),
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: [
              if (_hasError)
                _buildErrorWidget()
              else if (_loading)
                _buildLoadingWidget()
              else
                _buildSuccessWidget(),
            ],
          ),
        ),
      ),
    );
  }

  Widget _buildErrorWidget() {
    return Column(
      children: [
        const Icon(Icons.error_outline, color: Colors.red, size: 40),
        const SizedBox(height: 16),
        Text(
          _errorMessage,
          style: const TextStyle(
            fontFamily: 'Tajawal',
            color: Colors.white,
            fontSize: 15,
          ),
          textAlign: TextAlign.center,
        ),
        const SizedBox(height: 20),
        ElevatedButton(
          onPressed: () => Navigator.pop(context),
          style: ElevatedButton.styleFrom(
            backgroundColor: const Color(0xFF3B82F6),
            padding: const EdgeInsets.symmetric(horizontal: 24, vertical: 10),
          ),
          child: const Text(
            'العودة',
            style: TextStyle(fontFamily: 'Tajawal', fontSize: 15),
          ),
        ),
      ],
    );
  }

  Widget _buildLoadingWidget() {
    int displayedProgress = 0;
    int displayedTotal = _totalUsers;
    double displayedPercentage = 0.0;

    void updateDisplayedValues() {
      final progressDiff = _currentProgress - displayedProgress;
      final totalDiff = _totalUsers - displayedTotal;
      if (progressDiff > 0) {
        displayedProgress += (progressDiff / 5).ceil();
        if (displayedProgress > _currentProgress) {
          displayedProgress = _currentProgress;
        }
      }
      if (totalDiff > 0) {
        displayedTotal += (totalDiff / 3).ceil();
        if (displayedTotal > _totalUsers) {
          displayedTotal = _totalUsers;
        }
      }
      if (displayedTotal > 0) {
        displayedPercentage = (displayedProgress / displayedTotal * 100);
      }
    }

    return Column(
      children: [
        const SizedBox(
          width: 30,
          height: 30,
          child: CircularProgressIndicator(color: Colors.white, strokeWidth: 3),
        ),
        const SizedBox(height: 16),
        Text(
          _realDataStarted
              ? 'جاري جلب بيانات المستخدمين...'
              : 'جاري تهيئة عملية الجلب...',
          style: const TextStyle(
            fontFamily: 'Tajawal',
            color: Colors.white,
            fontSize: 16,
          ),
        ),
        const SizedBox(height: 8),
        StreamBuilder<int>(
          stream: _progressStream,
          builder: (context, snapshot) {
            updateDisplayedValues();
            return Column(
              children: [
                Text(
                  '$displayedProgress من $displayedTotal (${displayedPercentage.toStringAsFixed(1)}%)',
                  style: const TextStyle(
                    fontFamily: 'Tajawal',
                    color: Colors.white70,
                    fontSize: 13,
                  ),
                ),
                const SizedBox(height: 16),
                ClipRRect(
                  borderRadius: BorderRadius.circular(12),
                  child: LinearProgressIndicator(
                    value:
                        displayedTotal > 0
                            ? displayedProgress / displayedTotal
                            : 0,
                    backgroundColor: Colors.white.withOpacity(0.1),
                    valueColor: const AlwaysStoppedAnimation<Color>(
                      Colors.blueAccent,
                    ),
                    minHeight: 10,
                  ),
                ),
              ],
            );
          },
        ),
      ],
    );
  }

  Widget _buildSuccessWidget() {
    return Column(
      children: [
        const Icon(Icons.check_circle_outline, color: Colors.green, size: 40),
        const SizedBox(height: 16),
        Text(
          'تم جلب $_userCount مستخدم بنجاح',
          style: const TextStyle(
            fontFamily: 'Tajawal',
            color: Colors.white,
            fontSize: 16,
          ),
        ),
        const SizedBox(height: 8),
        const SizedBox(
          width: 20,
          height: 20,
          child: CircularProgressIndicator(
            color: Colors.white70,
            strokeWidth: 2,
          ),
        ),
        const SizedBox(height: 8),
        const Text(
          'جاري التوجيه إلى لوحة التحكم...',
          style: TextStyle(
            fontFamily: 'Tajawal',
            color: Colors.white70,
            fontSize: 13,
          ),
        ),
      ],
    );
  }
}

class _IsolateData {
  final String host;
  final int port;
  final String username;
  final String password;
  final SendPort sendPort;
  final int userType;
  final String appDocumentsPath;

  _IsolateData({
    required this.host,
    required this.port,
    required this.username,
    required this.password,
    required this.sendPort,
    required this.userType,
    required this.appDocumentsPath,
  });
}

class _ProgressUpdate {
  final int current;
  final int total;

  _ProgressUpdate(this.current, this.total);
}

// Custom clipper for the curved header
class _DialogHeaderClipper extends CustomClipper<Path> {
  @override
  Path getClip(Size size) {
    final path = Path();
    path.lineTo(0, size.height - 30);
    path.quadraticBezierTo(
      size.width / 4,
      size.height,
      size.width / 2,
      size.height - 20,
    );
    path.quadraticBezierTo(
      3 / 4 * size.width,
      size.height - 40,
      size.width,
      size.height - 30,
    );
    path.lineTo(size.width, 0);
    path.close();
    return path;
  }

  @override
  bool shouldReclip(CustomClipper<Path> oldClipper) => false;
}


ملاحظة اعطيني الجزء السابق والجزء المراد استبدالة بة