/*
 This file is part of GNU Taler
 (C) 2021-2024 Taler Systems S.A.

 GNU Taler 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, or (at your option) any later version.

 GNU Taler 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
 GNU Taler; see the file COPYING.  If not, see <http://www.gnu.org/licenses/>
 */

import { AbsoluteTime, MerchantPersona } from "@gnu-taler/taler-util";
import {
  useCommonPreferences,
  useTranslationContext,
} from "@gnu-taler/web-util/browser";
import { format } from "date-fns";
import { h, VNode } from "preact";
import {
  FormErrors,
  FormProvider,
} from "../../components/form/FormProvider.js";
import { InputSelector } from "../../components/form/InputSelector.js";
import { NotificationCardBulma } from "@gnu-taler/web-util/browser";
import { LangSelector } from "../../components/menu/LangSelector.js";
import { useSessionContext } from "../../context/session.js";
import {
  dateFormatForPreferences,
  datetimeFormatForPreferences,
  Preferences,
  usePreference,
} from "../../hooks/preference.js";
import { InputBoolean } from "../../components/form/InputBoolean.js";
import { Tooltip } from "../../components/Tooltip.js";

const TALER_SCREEN_ID = 83;

type FormType = Preferences & { developer: boolean };
export function Settings({ onClose }: { onClose?: () => void }): VNode {
  const { i18n } = useTranslationContext();
  const { config } = useSessionContext();
  const [value, , updateValue] = usePreference();
  const [{ showDebugInfo }, updateCommonPref] = useCommonPreferences();
  const errors: FormErrors<FormType> = {};

  const formValue: FormType = {
    ...value,
    persona: value.persona ?? config.default_persona,
    developer: showDebugInfo,
  };

  function valueHandler(s: (d: Partial<FormType>) => Partial<FormType>): void {
    const next = s(formValue);
    const v: Preferences = {
      hideMissingAccountUntil:
        next.hideMissingAccountUntil ?? AbsoluteTime.never(),
      hideKycUntil: next.hideKycUntil ?? AbsoluteTime.never(),
      dateFormat: next.dateFormat ?? "ymd",
      persona: next.persona ?? config.default_persona,
    };

    const isDeveloper = next.developer === true;
    if (isDeveloper !== showDebugInfo) {
      updateCommonPref("showDebugInfo", isDeveloper);
    }

    updateValue(v);
  }
  const [preferences] = usePreference();

  return (
    <div>
      <section class="section is-main-section">
        <div class="columns">
          <div class="column" />
          <div class="column is-four-fifths">
            <div>
              <FormProvider<FormType>
                name="settings"
                errors={errors}
                object={formValue}
                valueHandler={valueHandler}
              >
                <div class="field is-horizontal">
                  <div class="field-label is-normal">
                    <label class="label">
                      <i18n.Translate>Language</i18n.Translate>
                      <Tooltip
                        text={i18n.str`Force language setting instance of taking the browser`}
                      >
                        <i class="icon mdi mdi-information" />
                      </Tooltip>
                    </label>
                  </div>
                  <div class="field field-body has-addons is-flex-grow-3">
                    <LangSelector />
                  </div>
                </div>
                <InputSelector<Preferences>
                  name="dateFormat"
                  label={i18n.str`Date format`}
                  expand={true}
                  help={
                    <p>
                      {format(
                        new Date(),
                        dateFormatForPreferences(preferences),
                      )}
                      <br />
                      {format(
                        new Date(),
                        datetimeFormatForPreferences(preferences),
                      )}
                      <br />
                    </p>
                  }
                  toStr={(e) => {
                    if (e === "ymd") return "year month day";
                    if (e === "mdy") return "month day year";
                    if (e === "dmy") return "day month year";
                    return "choose one";
                  }}
                  values={["ymd", "mdy", "dmy"]}
                  tooltip={i18n.str`How the date is going to be displayed`}
                />
                <InputSelector<FormType>
                  label={i18n.str`Merchant type`}
                  tooltip={i18n.str`Simplify the UI based on use case.`}
                  name="persona"
                  values={
                    [
                      "digital-publishing",
                      "e-commerce",
                      "offline-vending-machine",
                      "point-of-sale",
                      "expert",
                      "tester",
                    ] as MerchantPersona[]
                  }
                  toStr={(e: MerchantPersona) => {
                    switch (e) {
                      case "tester":
                        return i18n.str`Beta tester`;
                      case "expert":
                        return i18n.str`Expert user`;
                      case "offline-vending-machine":
                        return i18n.str`Unattended in-person offline vending`;
                      case "point-of-sale":
                        return i18n.str`In-person online point-of-sale with inventory`;
                      case "digital-publishing":
                        return i18n.str`Digital publishing`;
                      case "e-commerce":
                        return i18n.str`E-commerce site`;
                    }
                  }}
                />
                <InputBoolean
                  label={i18n.str`Developer tools`}
                  tooltip={i18n.str`Enable UI tools for troubleshooting.`}
                  name="developer"
                />
              </FormProvider>
            </div>
            {value.persona === "tester" ? (
              <NotificationCardBulma
                notification={{
                  message: i18n.str`Testing features`,
                  description: i18n.str`Only use beta-tester mode if you know how the application works. Features enabled in this mode requires more work.`,
                  type: "WARN",
                }}
              />
            ) : undefined}
            {formValue.developer === true ? (
              <NotificationCardBulma
                notification={{
                  message: i18n.str`Developer mode`,
                  description: i18n.str`Only use developer mode if you know what you are doing. Tools enabled in this mode are intended to fix problems or get more information about the runtime. YOU MAY LOSE DATA.`,
                  type: "ERROR",
                }}
              />
            ) : undefined}
          </div>
          <div class="column" />
        </div>
      </section>
      {onClose && (
        <section class="section is-main-section">
          <button type="button" class="button" onClick={onClose}>
            <i18n.Translate>Close</i18n.Translate>
          </button>
        </section>
      )}
    </div>
  );
}
