import 'dart:io';

import 'package:device_info_plus/device_info_plus.dart';
import 'package:flutter/material.dart';
import 'package:flutter_svg/svg.dart';
import 'package:just_audio/just_audio.dart';
import 'package:path_provider/path_provider.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:record_mp3_plus/record_mp3_plus.dart';

import 'package:tangheem/classes/colors.dart';
import 'package:tangheem/classes/consts.dart';
import 'package:tangheem/classes/utils.dart';
import 'package:tangheem/extensions/string_extensions.dart';
import 'package:tangheem/extensions/widget_extensions.dart';
import 'package:shared_storage/shared_storage.dart' as saf;

class AyaRecordWidget extends StatefulWidget {
  AyaRecordWidget({Key key}) : super(key: key);

  @override
  _AyaRecordWidgetState createState() => _AyaRecordWidgetState();
}

class _AyaRecordWidgetState extends State<AyaRecordWidget> {
  bool _isRecording = false;
  AudioPlayer _audioPlayer;
  bool _isAudioHaveError = false;

  @override
  void initState() {
    super.initState();
    _audioPlayer = AudioPlayer();
  }

  @override
  void dispose() {
    _audioPlayer.dispose();
    if (recordFilePath != null && File(recordFilePath).existsSync()) {
      File(recordFilePath).deleteSync();
    }
    super.dispose();
  }

  Future<bool> checkPermission() async {
    if (!await Permission.microphone.isGranted) {
      PermissionStatus status = await Permission.microphone.request();
      if (status != PermissionStatus.granted) {
        return false;
      }
    }
    return true;
  }

  void startRecord() async {
    bool hasPermission = await checkPermission();
    if (hasPermission) {
      recordFilePath = await getFilePath();
      _isRecording = true;
      RecordMp3.instance.start(recordFilePath, (type) {
        _isRecording = false;
        setState(() {});
      });
    } else {
      Utils.showToast("يجب أن تمنح الإذن للتسجيل");
    }
    setState(() {});
  }

  void stopRecord() async {
    bool _isStop = RecordMp3.instance.stop();
    if (_isStop) {
      _isRecording = false;
      setState(() {});
    }
  }

  String recordFilePath;

  void play() async {
    if (recordFilePath != null && File(recordFilePath).existsSync()) {
      try {
        await _audioPlayer.setFilePath(recordFilePath);
        _audioPlayer.play();
      } catch (ex) {
        _isAudioHaveError = true;
      }
    } else {
      Utils.showToast("يجب عليك التسجيل أولا");
    }
  }

  Future<String> getFilePath() async {
    Directory storageDirectory = await getApplicationDocumentsDirectory();
    if (Platform.isIOS) {
      storageDirectory = await getTemporaryDirectory();
    }

    String sdPath = storageDirectory.path + "/record";
    var d = Directory(sdPath);
    if (!d.existsSync()) {
      d.createSync(recursive: true);
    }
    return sdPath + "/temp${DateTime.now().millisecondsSinceEpoch}.mp3";
  }

  @override
  Widget build(BuildContext context) {
    bool isPortrait = MediaQuery.of(context).orientation == Orientation.portrait;

    return Column(
      children: [
        Container(
            height: 38,
            width: double.infinity,
            alignment: Alignment.center,
            decoration: BoxDecoration(
              color: ColorConsts.brownB1CColor,
              borderRadius: BorderRadius.only(
                topRight: Radius.circular(20.0),
                topLeft: Radius.circular(20.0),
              ),
            ),
            child: "سجل الآية بصوتك".toText(16)),
        Stack(
          alignment: Alignment.bottomCenter,
          children: [
            Container(
              margin: EdgeInsets.only(bottom: 35),
              padding: EdgeInsets.only(bottom: 14, top: 14, left: 16, right: 16),
              width: double.infinity,
              decoration: BoxDecoration(
                color: Colors.transparent,
                border: Border.all(width: 1, color: ColorConsts.greyE0Color),
                borderRadius: BorderRadius.only(
                  bottomLeft: Radius.circular(20),
                  bottomRight: Radius.circular(20),
                ),
              ),
              child: Column(
                crossAxisAlignment: CrossAxisAlignment.end,
                children: [
                  // if (!(recordFilePath != null && File(recordFilePath).existsSync())) SizedBox(height: 16),
                  if (recordFilePath != null && File(recordFilePath).existsSync())
                    Container(
                      height: 50,
                      margin: EdgeInsets.only(bottom: 14),
                      padding: EdgeInsets.only(left: 12, right: 12),
                      decoration: BoxDecoration(
                        color: Colors.white,
                        borderRadius: BorderRadius.circular(30),
                      ),
                      child: Row(
                        children: [
                          Expanded(
                            child: StreamBuilder<Duration>(
                              stream: _audioPlayer.positionStream,
                              builder: (context, snapshot) {
                                final state = snapshot.data;
                                return SliderTheme(
                                  data: SliderTheme.of(context).copyWith(
                                    inactiveTrackColor: ColorConsts.sliderBackground,
                                    activeTrackColor: ColorConsts.secondaryOrange,
                                    trackHeight: 3.0,
                                    thumbColor: ColorConsts.primaryBlack,
                                    thumbShape: RoundSliderThumbShape(enabledThumbRadius: 6.0),
                                    overlayColor: ColorConsts.primaryBlack.withAlpha(32),
                                    overlayShape: RoundSliderOverlayShape(overlayRadius: 6.0),
                                  ),
                                  child: Directionality(
                                    textDirection: TextDirection.ltr,
                                    child: Slider(
                                      value: (state?.inSeconds ?? 0) + 0.0,
                                      min: 0,
                                      max: (_audioPlayer?.duration?.inSeconds ?? 0) + 0.0,
                                      onChanged: (value) {},
                                    ),
                                  ),
                                );
                              },
                            ),
                          ),
                          SizedBox(width: 8),
                          StreamBuilder<Duration>(
                            stream: _audioPlayer.positionStream,
                            builder: (context, snapshot) {
                              final state = snapshot.data;
                              return Text(
                                _durationTime(state) ?? "",
                                style: TextStyle(color: ColorConsts.textGrey1, height: 1.1, fontFamily: "Roboto", fontSize: 16),
                              );
                            },
                          ),
                          SizedBox(width: 8),
                          StreamBuilder<PlayerState>(
                            stream: _audioPlayer.playerStateStream,
                            builder: (context, snapshot) {
                              final state = snapshot.data?.playing ?? false;
                              if (state) {
                                if (_audioPlayer?.duration?.inSeconds == _audioPlayer?.position?.inSeconds) {
                                  _audioPlayer.pause();
                                  _audioPlayer.seek(Duration.zero);
                                }
                              }
                              return IconButton(
                                  highlightColor: Colors.transparent,
                                  splashColor: Colors.transparent,
                                  constraints: BoxConstraints(),
                                  padding: EdgeInsets.only(right: 0),
                                  icon: SvgPicture.asset(state ? "assets/icons/pause.svg" : "assets/icons/play_aya.svg", height: 16, width: 16),
                                  onPressed: () {
                                    state
                                        ? _audioPlayer.pause()
                                        : _isAudioHaveError
                                            ? Utils.showToast("خطأ في تحميل ملف الصوت")
                                            : play();
                                  });
                            },
                          ),
                        ],
                      ),
                    ),
                  InkWell(
                    borderRadius: BorderRadius.circular(20),
                    onTap: () async {
                      if (Platform.isAndroid && (await DeviceInfoPlugin().androidInfo).version.sdkInt > 29) {
                        if (recordFilePath != null && File(recordFilePath).existsSync()) {
                          saveAudioToAboveAndroid32(recordFilePath, "Tangheem${DateTime.now().millisecondsSinceEpoch}.mp3", "audio/mpeg");
                        } else {
                          Utils.showToast("يجب عليك تسجيل صوتك أولا");
                        }
                      } else if (await _requestStoragePermission()) {
                        if (recordFilePath != null && File(recordFilePath).existsSync()) {
                          saveToPhoneStorage(recordFilePath);
                        } else {
                          Utils.showToast("يجب عليك تسجيل صوتك أولا");
                        }
                      } else {
                        Utils.showToast("يجب أن تمنح الإذن لتنزيل التسجيل");
                      }
                    },
                    child: Container(
                      height: 31,
                      width: 135,
                      padding: EdgeInsets.only(left: 12, right: 12),
                      alignment: Alignment.center,
                      decoration: BoxDecoration(
                        borderRadius: BorderRadius.circular(20),
                        color: ColorConsts.greenLightColor,
                      ),
                      child: "تحميل التسجيل".toText(14),
                    ),
                  ),
                ],
              ),
            ),
            Positioned(
              right: 24,
              child: Container(
                height: 80,
                width: 80,
                padding: EdgeInsets.all(16),
                decoration: BoxDecoration(
                  shape: BoxShape.circle,
                  color: _isRecording ? Color(0xffe5ced3) : Color(0xffD3E5CE),
                  border: Border.all(
                    width: 1,
                    color: _isRecording ? Color(0xffc6b0ae) : Color(0xffAEC6B5),
                  ),
                ),
                child: SvgPicture.asset("assets/icons/new/mic.svg", color: Colors.white),
              ).onPress(
                () {
                  if (_isRecording) {
                    stopRecord();
                  } else {
                    startRecord();
                  }
                },
              ),
            ),
          ],
        ),
      ],
    );
  }

  Future<bool> _requestStoragePermission() async {
    Map<Permission, PermissionStatus> statuses = await [Permission.storage].request();
    return statuses[Permission.storage].isGranted;
  }

  String _durationTime(Duration duration) {
    if (duration == null) {
      return "00:00";
    }
    String twoDigits(int n) => n.toString().padLeft(2, "0");
    String twoDigitMinutes = twoDigits(duration.inMinutes.remainder(60));
    String twoDigitSeconds = twoDigits(duration.inSeconds.remainder(60));
    return "$twoDigitMinutes:$twoDigitSeconds";
  }

  void saveToPhoneStorage(String filePath) async {
    File file = File(filePath);
    Directory storageDirectory;
    if (Platform.isAndroid) {
      storageDirectory = await getExternalStorageDirectory();
    } else if (Platform.isIOS) {
      storageDirectory = await getApplicationDocumentsDirectory();
    } else {
      return;
    }

    String storagePath = storageDirectory.path;
    if (storagePath.contains("/Android/data")) {
      storagePath = storagePath.substring(0, storagePath.indexOf("/Android/data"));
    }

    if (Platform.isAndroid) {
      storagePath += "/Download/Tangheem/";
    } else {
      storagePath += "/Recording/";
    }

    var d = Directory(storagePath);
    if (!d.existsSync()) {
      d.createSync(recursive: true);
    }
    storagePath += "Tangheem${DateTime.now().millisecondsSinceEpoch}.mp3";
    print("storagePath:$storagePath");
    await file.copy(storagePath);
    Utils.showToast("تم التنزيل");
  }

  void saveAudioToAboveAndroid32(String pathUrl, String fileName, String fileType) async {
    List<saf.UriPermission> _persistedPermissionUris = await saf.persistedUriPermissions();
    if (_persistedPermissionUris.isNotEmpty) {
      saf.UriPermission permissionUri = _persistedPermissionUris.first;
      startFileAboveAndroid32(pathUrl, fileName, permissionUri.uri, fileType);
    } else {
      Uri selectedDocumentUris = await saf.openDocumentTree();
      if (selectedDocumentUris == null) return;
      saveAudioToAboveAndroid32(pathUrl, fileName, fileType);
    }
  }

  void startFileAboveAndroid32(String filePath, String fileName, Uri persistentUri, String fileType) async {
    try {
      File file = File(filePath);
      final documentFile = await persistentUri.toDocumentFile();
      final child = await documentFile?.child(fileName);
      if (child == null) {
        documentFile?.createFileAsBytes(
          mimeType: fileType,
          bytes: file.readAsBytesSync(),
          displayName: fileName,
        );
      } else {
        documentFile?.writeToFileAsBytes(
          bytes: file.readAsBytesSync(),
          mode: FileMode.write,
        );
      }

      Utils.showToast("تم حفظ الملف بنجاح");
    } catch (ex) {
      print(ex);
      Utils.hideLoading(context);
    }
  }
}
