import 'dart:convert';

import 'package:farm_tpf/custom_model/SuppliesUsing.dart';
import 'package:farm_tpf/custom_model/action_form/ActionUIField.dart';
import 'package:farm_tpf/custom_model/action_form/ActionUIForm.dart';
import 'package:farm_tpf/custom_model/action_form/CommonData.dart';
import 'package:farm_tpf/custom_model/action_form/RequestActivity.dart';
import 'package:farm_tpf/data/api/app_exception.dart';
import 'package:farm_tpf/data/repository/repository.dart';
import 'package:farm_tpf/presentation/custom_widgets/app_bar_widget.dart';
import 'package:farm_tpf/presentation/custom_widgets/bloc/media_helper_bloc.dart';
import 'package:farm_tpf/presentation/custom_widgets/button_widget.dart';
import 'package:farm_tpf/presentation/custom_widgets/dropdown_supply_widget.dart';
import 'package:farm_tpf/presentation/custom_widgets/loading_list_page.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_action_field_date.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_field_time_picker.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_loading.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_media_picker.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_radio_button.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_text_field_area.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_text_form_field.dart';
import 'package:farm_tpf/presentation/custom_widgets/widget_utils.dart';
import 'package:farm_tpf/presentation/screens/actions/cubit/action_ui_cubit.dart';
import 'package:farm_tpf/utils/const_string.dart';
import 'package:farm_tpf/utils/pref.dart';
import 'package:farm_tpf/utils/validators.dart';
import 'package:flutter/material.dart';
import 'package:flutter/scheduler.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:get/get.dart';
import 'package:keyboard_dismisser/keyboard_dismisser.dart';
import 'package:farm_tpf/utils/formatter.dart';

import 'controller/ChangeFieldInForm.dart';
import 'controller/ChangeSupplyUsing.dart';
import 'controller/ChangeWorker.dart';
import 'dung/widget_dung_supply.dart';
import 'nursery/widget_worker.dart';
import 'plant/widget_plant_supply.dart';
import 'spraying/widget_spraying_supply.dart';
import 'state_management_helper/change_dropdown_controller.dart';
import 'state_management_helper/change_file_controller.dart';
import 'util_action.dart';

class ActionScreen extends StatefulWidget {
  final bool isEdit;
  final int cropId;
  final int idAction;
  final String activityType;
  final String title;
  final int activityId;
  ActionScreen({
    required this.isEdit,
    required this.cropId,
    required this.idAction,
    required this.title,
    required this.activityType,
    required this.activityId,
  });

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

class _ActionScreenState extends State<ActionScreen> {
  var _formKey = GlobalKey<FormState>();
  var pref = LocalPref();
  final _executeByController = TextEditingController();
  DateTime executeTime = DateTime.now();
  List<String> filePaths = <String>[];
  var controller = Get.put(ChangeDropdownController());
  var changeFileController = Get.put(ChangeFileController());
  Map<String, TextEditingController> textFieldControllers = {};
  Map<String, String> valueObjects = {};
  var _requestActivity = RequestActivity();
  final _repository = Repository();

  var _actionUIForm = ActionUIForm();
  var _nurseryDetails = <TbNurseryDetailsDTO>[];
  var _supplyUsings = <SuppliesUsing>[];

  var _previousGroupFieldName = '';
  var isValidated = false;

  Future<Null> getSharedPrefs() async {
    var currentFullName = await pref.getString(DATA_CONST.CURRENT_FULL_NAME);
    _executeByController.text = currentFullName ?? "";
  }

  @override
  void initState() {
    super.initState();
    getSharedPrefs();
    changeFileController.initValue();
  }

  _submitForm() async {
    switch (widget.activityType) {
      case 'ACTIVE_TYPE_NURSERY':
        if (Get.find<ChangeFieldFormSupply>().isChanged ?? false) {
          Utils.showDialog(
              title: 'Thông tin người thực hiện chưa cập nhật',
              message: 'Bạn có muốn cập nhật',
              textConfirm: 'Tiếp tục',
              textCancel: 'Xem lại',
              onConfirm: () {
                Get.back();
                _validateInputs();
              });
        } else {
          _validateInputs();
        }
        break;
      case 'ACTIVE_TYPE_PLANTING':
      case 'ACTIVE_TYPE_FERTILIZE':
      case 'ACTIVE_TYPE_SPRAYING_PESTICIDES':
        if (Get.find<ChangeFieldFormSupply>().isChanged ?? false) {
          Utils.showDialogConfirmSupply(onConfirm: () {
            Get.back();
            _validateInputs();
          });
        } else {
          _validateInputs();
        }
        break;
      default:
        _validateInputs();
        break;
    }
  }

  _validateInputs() async {
    if (_formKey.currentState!.validate()) {
      _formKey.currentState!.save();

      try {
        LoadingDialog.showLoadingDialog(context);
        filePaths = Get.find<ChangeFileController>().newFiles ?? [];
        //Create request general model
        _requestActivity
          ..tbActivityTypeId = widget.idAction
          ..tbCropId = widget.cropId;
        if ((_actionUIForm.activityExtendTypeDTOList ?? []).isNotEmpty) {
          _requestActivity..externalTable = _actionUIForm?.activityExtendTypeDTOList?.first?.externalTable ?? '';
        }

        filePaths = Get.find<ChangeFileController>().newFiles ?? [];
        textFieldControllers.forEach((key, value) {
          valueObjects[key] = textFieldControllers[key]?.text ?? '';
        });
        //tbObjectUpdateDTOList
        var _objectPrameters = <TbObjectUpdateDTO>[];
        if (widget.isEdit) {
          // Edit
          if (_requestActivity.tbObjectUpdateDTOList != null) {
            _requestActivity.tbObjectUpdateDTOList?.forEach((element) {
              print(valueObjects[element.tbObjectParameterId.toString()]);
              var updateValue = '';
              if (Validators.stringNotNullOrEmpty(valueObjects[element.tbObjectParameterId.toString()] ?? '')) {
                updateValue = valueObjects[element.tbObjectParameterId.toString()] ?? '';
              } else {
                updateValue = element.index ?? '';
              }
              var objectUpdate = TbObjectUpdateDTO()
                ..id = element.id
                ..tbObjectParameterId = element.tbObjectParameterId
                ..index = updateValue;
              _objectPrameters.add(objectUpdate);
            });
            _requestActivity.tbObjectUpdateDTOList = _objectPrameters;
          }
        } else {
          //Add new

          valueObjects.forEach((key, value) {
            var objectUpdate = TbObjectUpdateDTO()
              ..tbObjectParameterId = int.tryParse(key)
              ..index = value;
            _objectPrameters.add(objectUpdate);
          });
          _requestActivity.tbObjectUpdateDTOList = _objectPrameters;
        }

        //CHECK NURSERY
        if (widget.activityType == 'ACTIVE_TYPE_NURSERY') {
          _requestActivity.tbNurseryDetailsDTOList = _nurseryDetails;
        } else if (widget.activityType == 'ACTIVE_TYPE_PLANTING' ||
            widget.activityType == 'ACTIVE_TYPE_FERTILIZE' ||
            widget.activityType == 'ACTIVE_TYPE_SPRAYING_PESTICIDES') {
          _requestActivity.tbSuppliesUsingDetailsDTOs = _supplyUsings;
        }
        //delete images
        _requestActivity.deletedImages = Get.find<ChangeFileController>().deleteFiles;
        //convert data to json
        var activityCommonData = jsonEncode(_requestActivity.toJson()).toString();
        print(activityCommonData);

        if (widget.activityId < 0) {
          //ADD New
          _repository.createActionCommon((data) {
            LoadingDialog.hideLoadingDialog(context);
            Get.back(result: 'ok');
            Utils.showSnackBarSuccess(message: label_add_success);
          }, (error) {
            LoadingDialog.hideLoadingDialog(context);
            Utils.showSnackBarError(message: AppException.handleError(error));
          }, activityType: widget.activityType, activityData: activityCommonData, filePaths: filePaths);
        } else {
          //UPDATE
          _repository.updateActionCommon((data) {
            LoadingDialog.hideLoadingDialog(context);
            Get.back(result: 'ok');
            Utils.showSnackBarSuccess(message: label_update_success);
          }, (error) {
            LoadingDialog.hideLoadingDialog(context);
            Utils.showSnackBarError(message: AppException.handleError(error));
          }, activityType: widget.activityType, activityData: activityCommonData, filePaths: filePaths);
        }

        //ADD NEW
        //Update
      } catch (e) {
        LoadingDialog.hideLoadingDialog(context);
        print(e.toString());
      }
    } else {
      //
      setState(() {
        isValidated = true;
      });
    }
  }

  Widget _btnExecuteTimePicker() {
    return WidgetFieldDateTimePicker(
        initDateTime: executeTime,
        onUpdateDateTime: (selectedDate) {
          _requestActivity.executeDate = selectedDate.convertLocalDateTimeToStringUtcDateTime();
        });
  }

  Widget _executeByField() {
    return TextFormField(
      keyboardType: TextInputType.text,
      decoration: InputDecoration(labelText: "Người thực hiện"),
      enabled: false,
      controller: _executeByController,
      onSaved: (newValue) {},
    );
  }

  //
  // GENERATE DYNAMIC FORM
  //
  Widget groupName(String name) {
    if (_previousGroupFieldName == name || !Validators.stringNotNullOrEmpty(name)) {
      return SizedBox();
    } else {
      _previousGroupFieldName = name ?? '';
      return Container(
        child: Row(
          children: [
            Container(
              width: 24,
              height: 0.5,
              color: Colors.green,
            ),
            Text(' ${name ?? ''} '),
            Expanded(
              child: Container(
                width: 5,
                height: 0.5,
                color: Colors.green,
              ),
            ),
          ],
        ),
      );
    }
  }

  Widget generateField(List<ActionUIField> fields) {
    return Wrap(
      children: [
        ListView.separated(
            shrinkWrap: true,
            physics: NeverScrollableScrollPhysics(),
            itemCount: fields.length,
            separatorBuilder: (context, index) {
              return SizedBox(
                height: 8,
              );
            },
            itemBuilder: (context, index) {
              var field = fields[index];
              if (field.tbControlTypeName == 'text') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    TextFormField(
                      keyboardType: TextInputType.text,
                      decoration: InputDecoration(
                          labelText: ((field.isMandatory ?? false) ?? false) ? '${field.description} *' : '${field.description}',
                          hintText: field.description),
                      controller: textFieldControllers[field.id.toString()],
                      onSaved: (newValue) {},
                      validator: ((field.isMandatory ?? false) ?? false)
                          ? (String? value) {
                              return Validators.validateNotNullOrEmpty(
                                value ?? '',
                                'Vui lòng nhập ${field.description}',
                              );
                            }
                          : null,
                    ),
                  ],
                );
              } else if (field.tbControlTypeName == 'number') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    WidgetTextFormFieldNumber(
                      hintValue: field.description ?? '',
                      labelText: ((field.isMandatory ?? false) ?? false) ? '${field.description} *' : '${field.description}',
                      textController: textFieldControllers[field.id.toString()] ?? TextEditingController(),
                      onSaved: (newValue) {},
                      validator: ((field.isMandatory ?? false) ?? false)
                          ? (String? value) {
                              return Validators.validNumberOrEmpty(
                                value ?? '',
                                'Vui lòng nhập ${field.description}',
                              );
                            }
                          : null,
                    ),
                  ],
                );
              } else if (field.tbControlTypeName == 'textarea') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    TextFieldAreaWidget(
                      hint: field.description ?? '',
                      labelText: (field.isMandatory ?? false) ? '${field.description} *' : '${field.description}',
                      controller: textFieldControllers[field.id.toString()] ?? TextEditingController(),
                      onSaved: (newValue) {},
                      validator: (field.isMandatory ?? false)
                          ? (String? value) {
                              return Validators.validateNotNullOrEmpty(
                                value ?? '',
                                'Vui lòng nhập ${field.description}',
                              );
                            }
                          : null,
                    ),
                  ],
                );
              } else if (field.tbControlTypeName == 'dropdown') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    DropdownSupplyWidget(
                      titleName: field.description ?? '',
                      tbSupply: field.tbActivityExtendTypeExternalTable ?? '',
                      tag: field.name ?? '',
                      value: field.description,
                      hint: '${field.description} ${(field.isMandatory ?? false) ? '*' : ''}',
                      condition: field.tbActivityExtendTypeCondition ?? '',
                      invalidMessage: '',
                      onPressed: (commonData) {
                        valueObjects[field.id.toString()] = commonData.id.toString();
                      },
                    ),
                  ],
                );
              } else if (field.tbControlTypeName == 'radiobutton') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    RadioButtonWidget(
                      tag: field.name ?? '',
                      condition: field.tbActivityExtendTypeCondition ?? '',
                      supply: field.tbActivityExtendTypeExternalTable ?? '',
                      onPressed: (commonData) {
                        valueObjects[field.id.toString()] = commonData.id.toString();
                      },
                    ),
                  ],
                );
              } else if (field.tbControlTypeName == 'date') {
                return Column(
                  children: [
                    groupName(field.groupName ?? ''),
                    FieldDateWidget(
                      tag: field.name ?? '',
                      isValidated: isValidated,
                      value: field.description,
                      hint: '${field.description} ${(field.isMandatory ?? false) ? '*' : ''}',
                      onPressed: (selectedDate) {
                        valueObjects[field.id.toString()] = selectedDate.convertLocalDateTimeToStringUtcDateTime();
                      },
                      validator: (field.isMandatory ?? false)
                          ? (String? value) {
                              return Validators.validateNotNullOrEmpty(value ?? '', 'Vui lòng nhập ${field.description}');
                            }
                          : null,
                    ),
                  ],
                );
              } else {
                return Container();
              }
            })
      ],
    );
  }

  //
  // GENERATE SUPPLY
  //

  Widget generateSupply(String activityType) {
    switch (activityType) {
      case 'ACTIVE_TYPE_NURSERY':
        return WidgetWorker(onChangeWorkers: (nurseryDetails) {
          _nurseryDetails = nurseryDetails;
        });
        break;
      case 'ACTIVE_TYPE_PLANTING':
        return Column(
          children: [
            Container(
              width: double.infinity,
              height: 16,
              color: Colors.grey[200],
            ),
            WidgetPlantSupply(
                currentItems: [],
                onChangeSupplies: (value) {
                  _supplyUsings = value;
                }),
          ],
        );
        break;
      case 'ACTIVE_TYPE_FERTILIZE':
        return Column(
          children: [
            Container(
              width: double.infinity,
              height: 16,
              color: Colors.grey[200],
            ),
            WidgetDungSupply(
                currentItems: [],
                onChangeSupplies: (value) {
                  _supplyUsings = value;
                }),
          ],
        );
        break;
      case 'ACTIVE_TYPE_SPRAYING_PESTICIDES':
        return Column(
          children: [
            Container(
              width: double.infinity,
              height: 16,
              color: Colors.grey[200],
            ),
            WidgetSprayingSupply(
                currentItems: [],
                onChangeSupplies: (value) {
                  _supplyUsings = value;
                }),
          ],
        );
        break;
      default:
        return Container();
        break;
    }
  }

  void showDataWhenEdit(BuildContext context) {
    //Show media
    try {
      if (Validators.stringNotNullOrEmpty(_requestActivity.media ?? '')) {
        BlocProvider.of<MediaHelperBloc>(context).add(
          ChangeListMedia(
            items: UtilAction.convertFilePathToMedia(
              _requestActivity.media ?? '',
            ),
          ),
        );
      }
    } catch (e) {
      print(e);
    }

    SchedulerBinding.instance.addPostFrameCallback((_) {
      if (widget.activityType == 'ACTIVE_TYPE_PLANTING' ||
          widget.activityType == 'ACTIVE_TYPE_FERTILIZE' ||
          widget.activityType == 'ACTIVE_TYPE_SPRAYING_PESTICIDES') {
        //list supply
        Get.find<ChangeSupplyUsing>().changeInitList(_requestActivity.tbSuppliesUsingDetailsDTOs ?? []);
      } else if (widget.activityType == 'ACTIVE_TYPE_NURSERY') {
        //list nursery
        Get.find<ChangeWorker>().changeInitList(_requestActivity.tbNurseryDetailsDTOList ?? []);
      }
    });

    //Show value textfield
    if (_requestActivity.tbObjectUpdateDTOList != null) {
      print(textFieldControllers.keys.toList());
      _requestActivity.tbObjectUpdateDTOList?.forEach((element) {
        if (element.tbObjectParameterDTO?.tbControlTypeName == 'text' || element.tbObjectParameterDTO?.tbControlTypeName == 'textarea') {
          SchedulerBinding.instance.addPostFrameCallback((_) {
            textFieldControllers[element.tbObjectParameterId.toString()]?.text = element.index ?? '';
          });
        } else if (element.tbObjectParameterDTO?.tbControlTypeName == 'number') {
          SchedulerBinding.instance.addPostFrameCallback((_) {
            textFieldControllers[element.tbObjectParameterId.toString()]?.text = element.index?.formatStringToStringDecimal() ?? '';
          });
        } else {
          SchedulerBinding.instance.addPostFrameCallback((_) {
            if (element.tbObjectParameterDTO?.tbControlTypeName == 'dropdown' ||
                element.tbObjectParameterDTO?.tbControlTypeName?.toLowerCase() == 'radiobutton') {
              var dropdownValueName = '';
              if ((element.tbObjectParameterDTO?.tbActivityExtendTypeDropDownDTOList ?? []).isNotEmpty ||
                  element.tbObjectParameterDTO?.tbActivityExtendTypeDropDownDTOList != null) {
                element.tbObjectParameterDTO?.tbActivityExtendTypeDropDownDTOList?.forEach((dropdownData) {
                  if (dropdownData.id == int.tryParse(element.index ?? '-1')) {
                    dropdownValueName = dropdownData.name ?? '';
                  }
                });
              }
              var commonData = CommonData()
                ..id = int.tryParse(element.index ?? '-1')
                ..name = dropdownValueName;
              Get.find<ChangeDropdownController>(tag: element.tbObjectParameterDTO?.name).change(commonData);
            } else if (element.tbObjectParameterDTO?.tbControlTypeName == 'date') {
              Get.find<ChangeDateTimePicker>(tag: element.tbObjectParameterDTO?.name).change(
                element.index?.convertStringServerDateTimeToLocalDateTime() ?? DateTime.now(),
              );
            }
          });
        }
      });
    } else {
//
    }
  }

  @override
  Widget build(BuildContext context) => KeyboardDismisser(
          gestures: [
            GestureType.onTap,
            GestureType.onPanUpdateDownDirection,
          ],
          child: Scaffold(
              backgroundColor: Colors.white,
              appBar: AppBarWidget(
                isBack: true,
                action: InkWell(
                  child: Text(
                    'Lưu',
                    style: TextStyle(color: Colors.red, fontWeight: FontWeight.normal),
                  ),
                  onTap: () {
                    FocusScopeNode currentFocus = FocusScope.of(context);
                    if (!currentFocus.hasPrimaryFocus) {
                      currentFocus.unfocus();
                    }
                    _submitForm();
                  },
                ),
              ),
              body: MultiBlocProvider(
                providers: [
                  BlocProvider<ActionUiCubit>(
                      create: (context) => ActionUiCubit(repository: Repository())
                        ..getActionUIForm(
                            actionId: widget.idAction, actionType: widget.activityType, isEdit: widget.isEdit, activityId: widget.activityId)),
                  BlocProvider<MediaHelperBloc>(
                    create: (context) => MediaHelperBloc()..add(ChangeListMedia(items: [])),
                  )
                ],
                child: Form(
                    key: _formKey,
                    child: SafeArea(
                      child: BlocBuilder<ActionUiCubit, ActionUiState>(
                        builder: (context, state) {
                          if (state is ActionUiLoading) {
                            print('loading...');
                            return Center(
                              child: LoadingListPage(),
                            );
                          } else if (state is ActionUiSuccess) {
                            _actionUIForm = state.actionUIForm ?? ActionUIForm();
                            _requestActivity = state.activityDetail ?? RequestActivity();

                            //CREATE UI
                            _actionUIForm.objectParameterDTOList?.forEach((element) {
                              //generate controller
                              if (element.tbControlTypeName == 'text' ||
                                  element.tbControlTypeName == 'number' ||
                                  element.tbControlTypeName == 'textarea') {
                                var textEditingController = new TextEditingController();
                                textFieldControllers.putIfAbsent(element.id.toString(), () => textEditingController);
                              }
                              // generate value each parameter
                              valueObjects.putIfAbsent(element.id.toString(), () => '');
                            });
                            //SHOW EDIT DATA
                            if (widget.isEdit) {
                              showDataWhenEdit(context);
                            }

                            return SingleChildScrollView(
                              child: Column(
                                children: [
                                  Padding(
                                    padding: const EdgeInsets.all(8.0),
                                    child: Column(
                                      children: <Widget>[
                                        Container(
                                          width: double.infinity,
                                          child: Text(
                                            "Ngày thực hiện *",
                                            style: TextStyle(color: Colors.black54, fontSize: 13.0),
                                          ),
                                        ),
                                        _btnExecuteTimePicker(),
                                        SizedBox(
                                          height: 8.0,
                                        ),
                                        generateField(_actionUIForm.objectParameterDTOList ?? []),
                                        _executeByField(),
                                        SizedBox(
                                          height: 8.0,
                                        ),
                                      ],
                                    ),
                                  ),
                                  generateSupply(widget.activityType),
                                  Container(
                                    width: double.infinity,
                                    height: 16,
                                    color: Colors.grey[200],
                                  ),
                                  BlocBuilder<MediaHelperBloc, MediaHelperState>(builder: (context, state) {
                                    if (state is MediaHelperSuccess) {
                                      return WidgetMediaPicker(
                                          currentItems: state.items,
                                          onChangeFiles: (newPathFiles, deletePathFiles) async {
                                            Get.find<ChangeFileController>().change(newPathFiles, deletePathFiles);
                                          });
                                    } else {
                                      return Center(child: CircularProgressIndicator());
                                    }
                                  }),
                                  Padding(
                                    padding: const EdgeInsets.all(8.0),
                                    child: ButtonWidget(
                                        title: 'CẬP NHẬT',
                                        onPressed: () {
                                          FocusScopeNode currentFocus = FocusScope.of(context);
                                          if (!currentFocus.hasPrimaryFocus) {
                                            currentFocus.unfocus();
                                          }
                                          _submitForm();
                                        }),
                                  ),
                                ],
                              ),
                            );
                          } else if (state is ActionUiFailure) {
                            return Center(child: Text(state.errorString));
                          }
                          return Container();
                        },
                      ),
                    )),
              )));
  @override
  void dispose() {
    _executeByController.dispose();
    textFieldControllers.forEach((key, value) {
      textFieldControllers[key]?.dispose();
    });
    super.dispose();
  }
}
