# Copyright (c) 2020-2022 Jan-Michael Brummer <jan.brummer@tabos.org>
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.

"""
Transfer dialog
"""

from gi.repository import Adw, Gtk
from schwifty import IBAN


@Gtk.Template(resource_path="/org/tabos/saldo/ui/transfer.ui")
class Transfer(Adw.Dialog):
    __gtype_name__ = "Transfer"

    _name_row = Gtk.Template.Child()
    _iban_row = Gtk.Template.Child()
    _amount_row = Gtk.Template.Child()
    _reason_row = Gtk.Template.Child()
    send_button = Gtk.Template.Child()
    _account_stringlist = Gtk.Template.Child()
    _bank_label = Gtk.Template.Child()
    _account_comborow = Gtk.Template.Child()

    def __init__(self, backend, **kwargs):
        super().__init__(**kwargs)

        self._backend = backend

        self._name_row.connect("changed", self._on_name_changed)
        self._amount_row.connect("changed", self._on_amount_value_changed)
        self._iban_row.connect("changed", self._on_iban_changed)
        self.send_button.connect("activate", self._on_send_button_clicked)

        self.__name_valid = False
        self.__iban_valid = False
        self.__amount_valid = False
        self.send_button.add_css_class("suggested-action")

        for account in self._backend.accounts:
            iban = IBAN(account.iban, allow_invalid=True)
            self._account_stringlist.append(iban.formatted)

        self.__validate()

    def _on_iban_changed(self, entry):
        text = entry.get_text()
        iban = IBAN(text, allow_invalid=True)

        institute = None
        self.__iban_valid = iban.is_valid

        if iban.is_valid:
            institute = self._backend.find_institute(iban.bank_code)

        if institute:
            self._bank_label.set_subtitle(institute["institute"])
        else:
            self._bank_label.set_subtitle("")

        self.__validate()

    def _on_name_changed(self, entry):
        self.__name_valid = len(entry.get_text()) != 0
        self.__validate()

    def _on_amount_value_changed(self, entry):
        try:
            value = float(entry.get_text())

            self.__amount_valid = value != 0
            self.__validate()
        except ValueError as err:
            print("Warning: Invalid amount specified: " + str(err))
            self.__amount_valid = False

        self.__validate()

    def __validate(self):
        if self.__iban_valid:
            self._iban_row.remove_css_class("error")
        else:
            self._iban_row.add_css_class("error")

        if self.__name_valid:
            self._name_row.remove_css_class("error")
        else:
            self._name_row.add_css_class("error")

        if self.__amount_valid:
            self._amount_row.remove_css_class("error")
        else:
            self._amount_row.add_css_class("error")

        valid = self.__iban_valid and self.__name_valid and self.__amount_valid
        self.send_button.set_sensitive(valid)

    def _on_send_button_clicked(self, button):
        try:
            amount = float(self._amount_row.get_text())
        except ValueError as err:
            print("Invalid amount given: " + str(err))
            return

        selected_account = self._account_comborow.get_selected()
        account = self._backend.accounts[selected_account]

        iban = self._iban_row.get_text().replace(" ", "")
        reason = self._reason_row.get_text()
        recipient = self._name_row.get_text()
        account_name = account._account["owner_name"]

        print(
            f"Sending from '{account_name}' '{amount}' to '{recipient}'/'{iban}', Reason '{reason}'"
        )
        self.destroy()

        self._backend.sepa_transfer(
            account, account_name, recipient, iban, amount, reason
        )
