Untitled

 avatar
unknown
plain_text
a year ago
8.4 kB
5
Indexable
import 'package:family_tree/app/modules/session/controllers/session_controller.dart';
import 'package:family_tree/app/routes/app_pages.dart';
import 'package:family_tree/constant/shared_preference_key.dart';
import 'package:family_tree/lockscreen/password_screen_lock_dialog.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:shared_preferences/shared_preferences.dart';
import '../../constant/url.dart';
import '../../library/dio_client.dart';
import '../../models/response_model.dart';
import 'screen_lock_manager.dart';

class ScreenLockDialogController extends FullLifeCycleController
    with FullLifeCycleMixin {
  final dio = DioClient();

  late final _lockManager = ScreenLockManager(
    keyboardFocus: keyboardSetFocus,
    lockscreenOpen: lockScreenOpen,
  );

  final int pinLength = 6;
  final pin = List<int>.empty().obs;
  final keyboardTextController = TextEditingController();
  final keyboardFocus = FocusNode();
  final wrongPin = false.obs;
  bool canBackNavigation = false;
  String? goPage;
  Map<String, dynamic>? argument;
  String? lastType;

  final passwordFormKey = GlobalKey<FormState>(debugLabel: 'password_form');
  final passwordController = TextEditingController();
  final passwordFocus = FocusNode();
  late final _passwordDialog = PasswordScreenLockDialog(context: Get.context!);
  final loading = false.obs;
  final isForgotPassword = false.obs;
  final _session = Get.find<SessionController>();
  String? passwordErorr;
  final erorrValidate = false.obs;

  bool keyboardOpen = false;

  @override
  void onInit() async {
    await initPin();
    initKeyboard();
    super.onInit();
  }

  ///screenLock
  ///untuk mengunci aplikasi dengan pin
  ///can back = false maka pin tidak dapat di close
  ///fungsi action dijalankan ketika pin ditutup
  ///fungsi args untuk parameter
  ///route untuk pergi ke page
  Future locked({
    String? route,
    bool canBack = true,
    Map<String, dynamic>? args,
    VoidCallback? action,
  }) async {
    clearPin();
    clearPassword();
    await _lockManager.lockScreen(
      route: route,
      canBack: canBack,
      args: args,
      action: action,
    );
  }

  //ketika pin dialog menutup
  void lockScreenOpen() {
    isForgotPassword(false);
    clearPin();
  }

  void setParam({
    required bool canBack,
    String? route,
    Map<String, dynamic>? args,
  }) {
    canBackNavigation = canBack;
    goPage = route;
    argument = args;
  }

  Future initPin([String? pin]) async {
    _lockManager.setLock(false);
    if (pin == null) {
      final prefs = await SharedPreferences.getInstance();
      final havePin = prefs.getString(SharedPreferenceKey.pin);
      await _lockManager.setPin(havePin);
    } else {
      await _lockManager.setPin(pin);
    }
  }

  void initKeyboard() {
    keyboardTextController.addListener(() {
      keyboardChange();
    });
  }

  void keyboardSetFocus() {
    WidgetsBinding.instance.addPostFrameCallback((timeStamp) {
      FocusScope.of(Get.context!).requestFocus(keyboardFocus);
    });
  }

  void keyboardChange() async {
    pin.clear();

    //add pin
    for (var i = 0; i < keyboardTextController.text.length; i++) {
      int? number = int.tryParse(keyboardTextController.text[i]);
      if (number != null) pin.add(number);
    }

    //backspace
    resetWrongPin();

    //submit
    if (keyboardTextController.text.length == pinLength) {
      bool check = pinCheck();
      if (check) {
        await Future.delayed(const Duration(milliseconds: 100));
        submit();
      } else {
        await whenWrongPin();
      }
    }
    // submit();
  }

  void clearPin() {
    pin.clear();
    keyboardTextController.clear();
    resetWrongPin();
  }

  void resetWrongPin() {
    if (keyboardTextController.text.length < pinLength && wrongPin.value) {
      wrongPin(false);
    }
  }

  Future whenWrongPin() async {
    wrongPin(true);
    await Future.delayed(const Duration(milliseconds: 1000));
    clearPin();
  }

  bool pinCheck() {
    String pinInput = "";

    for (var i = 0; i < pin.length; i++) {
      pinInput += pin[i].toString();
    }

    int pinInputToNumber = int.parse(pinInput);

    if (!_lockManager.comparePin(pinInputToNumber)) return false;

    return true;
  }

  Future logoutPin() async {
    await _lockManager.clearPin();
  }

  void submit() {
    Get.back();
    if (goPage != null) Get.toNamed(goPage!, arguments: argument);
  }

  void clearPassword() {
    passwordController.clear();
  }

  void closeForgotPassword() {
    clearPassword();
    isForgotPassword(false);
  }

  void forgotPinOpenDialog() async {
    keyboardFocus.unfocus();
    await Future.delayed(const Duration(milliseconds: 350));
    _passwordDialog.open(closeForgotPassword);
  }

  void forgotPassword(bool val) async {
    passwordFocus.unfocus();
    await Future.delayed(const Duration(milliseconds: 350));
    isForgotPassword(val);
  }

  ///forgot password next button
  void nextButton() async {
    try {
      passwordFocus.unfocus();
      passwordErorr = null;

      if (passwordFormKey.currentState!.validate()) {
        if (passwordFocus.hasFocus) {
          await Future.delayed(const Duration(milliseconds: 350));
        }

        erorrValidate(false);
        loading(true);

        //do api
        final prefs = await SharedPreferences.getInstance();
        await prefs.reload();

        var token = prefs.getString(SharedPreferenceKey.token);
        dio.baseOptions.headers['Authorization'] = 'Bearer $token';

        Map<String, dynamic> payload = {
          'password': passwordController.text,
        };

        var checkPasswordPost = await dio.requestPost(
          checkPassword,
          payload,
        );

        if (checkPasswordPost == null) return null;

        final checkPasswordResponse = ResponseModel.fromJson(
          checkPasswordPost.data,
        );

        if (checkPasswordResponse.status.code == 200) {
          _lockManager.setForgotPassword(true);
          passwordFocus.unfocus();
          await Future.delayed(const Duration(milliseconds: 350));
          if (canBackNavigation) Get.back();
          Get.back();
          Get.toNamed(Routes.CREATE_PIN, arguments: {
            "option": "change",
            "forgot": true,
          });
        } else if (checkPasswordResponse.status.code == 401 ||
            checkPasswordResponse.status.code == 405) {
          await _session.logoutOffline();
        } else {
          passwordErorr = checkPasswordResponse.status.message;
          passwordFormKey.currentState!.validate();
        }

        loading(false);
      } else {
        erorrValidate(true);
      }
    } catch (e) {
      //catch
    }
  }

  ///lupa password
  void resetPassword() async {
    loading(true);
    //do api
    final prefs = await SharedPreferences.getInstance();
    await prefs.reload();

    var token = prefs.getString(SharedPreferenceKey.token);
    dio.baseOptions.headers['Authorization'] = 'Bearer $token';

    Map<String, dynamic> payload = {
      'email': _session.email,
    };

    var forgotPasswordPost = await dio.requestPost(
      forgotPasswordPath,
      payload,
    );

    if (forgotPasswordPost == null) return null;

    final forgotPasswordResponse = ResponseModel.fromJson(
      forgotPasswordPost.data,
    );

    if (forgotPasswordResponse.status.code == 200) {
      await _session.logout(forgotPassword: true);
    } else if (forgotPasswordResponse.status.code == 401 ||
        forgotPasswordResponse.status.code == 405) {
      await _session.logoutOffline(forgotPassword: true);
    }

    closeForgotPassword();
    loading(false);
  }

  @override
  void dispose() {
    keyboardTextController.dispose();
    keyboardFocus.dispose();
    passwordController.dispose();
    passwordFocus.dispose();
    super.dispose();
  }

  @override
  void onDetached() {
    print("screen lock detached");
  }

  @override
  void onInactive() {
    print("screen lock onInactive");
  }

  @override
  void onPaused() {
    _lockManager.appMinimize();
    print("screen lock onPaused");
  }

  @override
  void onResumed() async {
    print("screen lock onResumed");
    await _lockManager.appResume();
    ScreenLockManager.canShowPin();
  }

  @override
  void onHidden() {
    // TODO: implement onHidden
  }
}
Editor is loading...
Leave a Comment