/*
 * Copyright (C) 2022 - Florindo Smilari (spherIC)
 */
package ch.spherIC.recurvebowsight.ui.configuration;

import android.app.AlertDialog;
import android.content.DialogInterface;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.ArrayAdapter;
import android.widget.AutoCompleteTextView;
import android.widget.Button;

import java.text.DecimalFormat;
import java.util.List;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.ViewModelProvider;
import ch.spherIC.recurvebowsight.R;
import ch.spherIC.recurvebowsight.database.dao.ArrowDao;
import ch.spherIC.recurvebowsight.databinding.ActivityArrowConfigurationBinding;
import ch.spherIC.recurvebowsight.model.IArrow;
import ch.spherIC.recurvebowsight.model.impl.Arrow;
import ch.spherIC.recurvebowsight.utilities.NoFilterArrayAdapter;
import ch.spherIC.recurvebowsight.utilities.PlatformUtils;

public class ArrowConfigurationActivity extends AppCompatActivity {

    private ActivityArrowConfigurationBinding binding;
    private ArrowConfigurationViewModel arrowConfigurationViewModel;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_arrow_configuration);
        getSupportActionBar().setDisplayHomeAsUpEnabled(true);
        getSupportActionBar().setTitle(R.string.title_activity_arrow_configuration);

        this.arrowConfigurationViewModel = new ViewModelProvider(this).get(ArrowConfigurationViewModel.class);
        this.binding = ActivityArrowConfigurationBinding.bind(findViewById(R.id.activity_arrow_configuration));

        addObservers();
        addArrowSpinnerListener();
        addButtonListeners();
        loadArrows();
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        MenuItem menuItemSettings = menu.findItem(R.id.action_settings);
        MenuItem menuItemHelp = menu.findItem(R.id.action_help);
        menuItemSettings.setEnabled(false);
        menuItemHelp.setEnabled(false);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(@NonNull MenuItem item) {
        switch (item.getItemId()) {
            case android.R.id.home:
                this.finish();
                return true;
            case R.id.action_help:
/*
                Intent userGuideArrowIntent = new Intent(this.binding.getRoot().getContext(), UserGuideArrowActivity.class);
                startActivity(userGuideArrowIntent);
*/
                return true;
        }
        return super.onOptionsItemSelected(item);
    }

    private void addObservers() {
        DecimalFormat dF = new DecimalFormat("#.#");
        this.arrowConfigurationViewModel.getManufacturer().observe(this, manufacturer -> this.binding.rcManufacturerTxt.setText(manufacturer));
        this.arrowConfigurationViewModel.getModel().observe(this, model -> this.binding.rcModelTxt.setText(model));
        this.arrowConfigurationViewModel.getDiameter().observe(this, diameter -> this.binding.acDiameterTxt.setText(diameter != null ? dF.format(diameter) : ""));
        this.arrowConfigurationViewModel.getCw().observe(this, cw -> this.binding.acCwTxt.setText(cw != null ? dF.format(cw) : ""));
        this.arrowConfigurationViewModel.getWeight().observe(this, weight -> this.binding.acWeigthTxt.setText(weight != null ? dF.format(weight) : ""));
        this.arrowConfigurationViewModel.getV0().observe(this, v0 -> this.binding.acV0Txt.setText(v0 != null ? dF.format(v0) : ""));
        this.arrowConfigurationViewModel.getColors().observe(this, colors -> this.binding.acColorsTxt.setText(colors));
    }

    private void addArrowSpinnerListener() {
        AutoCompleteTextView textView = findViewById(R.id.arrowSelectionTxt);
        textView.setOnItemClickListener((parent, view, position, id) -> {
            IArrow selectedArrow = (IArrow) textView.getAdapter().getItem(position);
            if (selectedArrow != null) {
                arrowConfigurationViewModel.setArrow(selectedArrow);
            }
        });
    }

    private void addButtonListeners() {
        Button newButton = findViewById(R.id.arrowcfg_button_new);
        newButton.setOnClickListener(v -> addNewArrow());

        Button deleteButton = findViewById(R.id.arrowcfg_button_delete);
        deleteButton.setOnClickListener(v -> deleteArrow());

        Button saveButton = findViewById(R.id.arrowcfg_button_save);
        saveButton.setOnClickListener(v -> saveArrowConfiguration());
    }


    private void loadArrows() {
        List<IArrow> arrows = ArrowDao.getInstance().loadAll();
        ArrayAdapter<IArrow> adapter = new NoFilterArrayAdapter<IArrow>(this, android.R.layout.simple_dropdown_item_1line, arrows);
        AutoCompleteTextView textView = this.binding.arrowSelectionTxt;
        textView.setAdapter(adapter);
        textView.invalidate();
    }

    private void addNewArrow() {
        IArrow newArrow = new Arrow(0, "", "", null, null, null, null, "");
        this.arrowConfigurationViewModel.setArrow(newArrow);
        String strMandatory = getString(R.string.caption_mandatory);
        this.binding.arrowSelectionTxt.setText(null, false);
        this.binding.rcManufacturerTxt.setError(strMandatory);
        this.binding.rcModelTxt.setError(strMandatory);
        this.binding.acDiameterTxt.setError(strMandatory);
        this.binding.acCwTxt.setError(strMandatory);
        this.binding.acWeigthTxt.setError(strMandatory);
        this.binding.acV0Txt.setError(strMandatory);
        this.binding.acColorsTxt.setError(strMandatory);
        AutoCompleteTextView textView = this.binding.arrowSelectionTxt;
        ((ArrayAdapter<IArrow>) textView.getAdapter()).insert(newArrow, 0);
        textView.setAdapter((ArrayAdapter<IArrow>) textView.getAdapter());
        textView.setSelection(0);
    }

    private void saveArrowConfiguration() {
        if (!validateInputs()) {
            return;
        }
        this.arrowConfigurationViewModel.setManufacturerText(this.binding.rcManufacturerTxt.getText().toString());
        this.arrowConfigurationViewModel.setModelText(this.binding.rcModelTxt.getText().toString());
        this.arrowConfigurationViewModel.setDiameter(PlatformUtils.parseDouble(this.binding.acDiameterTxt.getText().toString()));
        this.arrowConfigurationViewModel.setCW(PlatformUtils.parseDouble(this.binding.acCwTxt.getText().toString()));
        this.arrowConfigurationViewModel.setWeight(PlatformUtils.parseDouble(this.binding.acWeigthTxt.getText().toString()));
        this.arrowConfigurationViewModel.setV0(PlatformUtils.parseDouble(this.binding.acV0Txt.getText().toString()));
        this.arrowConfigurationViewModel.setColors(this.binding.acColorsTxt.getText().toString());

        IArrow lArrow = this.arrowConfigurationViewModel.getArrow().getValue();
        if (lArrow.getId() > 0) {
            ArrowDao.getInstance().update(lArrow);
            PlatformUtils.toast(ArrowConfigurationActivity.this, String.format(getString(R.string.caption_Cfg_UpdateSuccessful), lArrow)).show();
        } else {
            lArrow = ArrowDao.getInstance().insert(lArrow);
            loadArrows();
            AutoCompleteTextView textView = this.binding.arrowSelectionTxt;
            final int position = ((ArrayAdapter<IArrow>) textView.getAdapter()).getPosition(lArrow);
            textView.setListSelection(position);
            textView.setText(lArrow.toString(), false);
            ((ArrayAdapter<IArrow>) textView.getAdapter()).getFilter().filter(null);
            PlatformUtils.toast(ArrowConfigurationActivity.this, String.format(getString(R.string.caption_Cfg_SaveSuccessful), lArrow)).show();
        }
    }

    private boolean validateInputs() {
        int invalidFields = 0;
        if (this.binding.rcManufacturerTxt.getText().toString().isEmpty() || this.binding.rcManufacturerTxt.getText().toString().equals("*")) {
            invalidFields++;
        }
        if (this.binding.rcModelTxt.getText().toString().isEmpty() || this.binding.rcModelTxt.getText().toString().equals("*")) {
            invalidFields++;
        }
        if (this.binding.acDiameterTxt.getText() == null || this.binding.acDiameterTxt.getText().toString().equals("")) {
            invalidFields++;
        }
        if (this.binding.acCwTxt.getText() == null || this.binding.acCwTxt.getText().toString().equals("")) {
            invalidFields++;
        }
        if (this.binding.acWeigthTxt.getText() == null || this.binding.acWeigthTxt.getText().toString().equals("")) {
            invalidFields++;
        }
        if (this.binding.acV0Txt.getText() == null || this.binding.acV0Txt.getText().toString().equals("")) {
            invalidFields++;
        }
        if (this.binding.acColorsTxt.getText() == null || this.binding.acColorsTxt.getText().toString().equals("")) {
            invalidFields++;
        }
        if (invalidFields > 0) {
            PlatformUtils.toast(this, getResources().getString(R.string.caption_Cfg_FillAllMandatoryFields)).show();
            return false;
        }
        return true;
    }

    private void deleteArrow() {
        IArrow lArrow = this.arrowConfigurationViewModel.getArrow().getValue();

        if (lArrow != null) {
            AlertDialog dlg = PlatformUtils.getDeleteConfirmDialog(this, lArrow.toString(), new DialogInterface.OnClickListener() {
                @Override
                public void onClick(final DialogInterface dialog, final int which) {
                    String message = String.format(getString(R.string.caption_Cfg_DeleteSuccessful), lArrow);
                    try {
                        ArrowDao.getInstance().delete(lArrow);
                        loadArrows();
                        arrowConfigurationViewModel.setArrow(null);
                        binding.arrowSelectionTxt.setText(null, false);
                    } catch (Exception e) {
                        message = getString(R.string.caption_Cfg_DeleteNotPossible);
                    }
                    PlatformUtils.toast(ArrowConfigurationActivity.this, message).show();
                }
            });
            dlg.show();
        }
    }
}