summaryrefslogtreecommitdiff
path: root/packages/demobank-ui/src
diff options
context:
space:
mode:
authorSebastian <sebasjm@gmail.com>2022-12-09 12:07:01 -0300
committerSebastian <sebasjm@gmail.com>2022-12-09 12:07:01 -0300
commit6b6f80466ee07f591203c28a724ce4e7128af85d (patch)
tree4460721b74245625fe70443d466da677362abf1d /packages/demobank-ui/src
parentf2b319921c53010446e05ac4f24eef9995f65836 (diff)
downloadwallet-core-6b6f80466ee07f591203c28a724ce4e7128af85d.tar.gz
wallet-core-6b6f80466ee07f591203c28a724ce4e7128af85d.tar.bz2
wallet-core-6b6f80466ee07f591203c28a724ce4e7128af85d.zip
remove unused
Diffstat (limited to 'packages/demobank-ui/src')
-rw-r--r--packages/demobank-ui/src/.babelrc3
-rw-r--r--packages/demobank-ui/src/components/AsyncButton.tsx60
-rw-r--r--packages/demobank-ui/src/components/FileButton.tsx71
-rw-r--r--packages/demobank-ui/src/components/Notifications.tsx74
-rw-r--r--packages/demobank-ui/src/components/fields/DateInput.tsx102
-rw-r--r--packages/demobank-ui/src/components/fields/EmailInput.tsx69
-rw-r--r--packages/demobank-ui/src/components/fields/FileInput.tsx102
-rw-r--r--packages/demobank-ui/src/components/fields/ImageInput.tsx86
-rw-r--r--packages/demobank-ui/src/components/fields/NumberInput.tsx68
-rw-r--r--packages/demobank-ui/src/components/fields/TextInput.tsx80
-rw-r--r--packages/demobank-ui/src/components/menu/NavigationBar.tsx51
-rw-r--r--packages/demobank-ui/src/components/menu/SideBar.tsx74
-rw-r--r--packages/demobank-ui/src/components/menu/index.tsx135
-rw-r--r--packages/demobank-ui/src/components/picker/DatePicker.tsx347
-rw-r--r--packages/demobank-ui/src/components/picker/DurationPicker.stories.tsx55
-rw-r--r--packages/demobank-ui/src/components/picker/DurationPicker.tsx210
-rw-r--r--packages/demobank-ui/src/index.tsx4
-rw-r--r--packages/demobank-ui/src/pages/home/QrCodeSection.tsx2
-rw-r--r--packages/demobank-ui/src/style/index.css0
19 files changed, 3 insertions, 1590 deletions
diff --git a/packages/demobank-ui/src/.babelrc b/packages/demobank-ui/src/.babelrc
deleted file mode 100644
index 05f4dcc81..000000000
--- a/packages/demobank-ui/src/.babelrc
+++ /dev/null
@@ -1,3 +0,0 @@
-{
- "presets": ["preact-cli/babel"]
-}
diff --git a/packages/demobank-ui/src/components/AsyncButton.tsx b/packages/demobank-ui/src/components/AsyncButton.tsx
deleted file mode 100644
index 0e1391109..000000000
--- a/packages/demobank-ui/src/components/AsyncButton.tsx
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { ComponentChildren, h, VNode } from "preact";
-import { useLayoutEffect, useRef } from "preact/hooks";
-import { useAsync } from "../hooks/async.js";
-
-type Props = {
- children: ComponentChildren;
- disabled?: boolean;
- onClick?: () => Promise<void>;
- grabFocus?: boolean;
- [rest: string]: any;
-};
-
-export function AsyncButton({
- onClick,
- grabFocus,
- disabled,
- children,
- ...rest
-}: Props): VNode {
- const { isLoading, request } = useAsync(onClick);
-
- const buttonRef = useRef<HTMLButtonElement>(null);
- useLayoutEffect(() => {
- if (grabFocus) buttonRef.current?.focus();
- }, [grabFocus]);
-
- // if (isSlow) {
- // return <LoadingModal onCancel={cancel} />;
- // }
- if (isLoading) return <button class="button">Loading...</button>;
-
- return (
- <span data-tooltip={rest["data-tooltip"]} style={{ marginLeft: 5 }}>
- <button {...rest} ref={buttonRef} onClick={request} disabled={disabled}>
- {children}
- </button>
- </span>
- );
-}
diff --git a/packages/demobank-ui/src/components/FileButton.tsx b/packages/demobank-ui/src/components/FileButton.tsx
deleted file mode 100644
index d7ed52f5d..000000000
--- a/packages/demobank-ui/src/components/FileButton.tsx
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { h, VNode } from "preact";
-import { useRef, useState } from "preact/hooks";
-
-const MAX_IMAGE_UPLOAD_SIZE = 1024 * 1024;
-
-export interface FileTypeContent {
- content: string;
- type: string;
- name: string;
-}
-
-interface Props {
- label: string;
- onChange: (v: FileTypeContent | undefined) => void;
-}
-export function FileButton(props: Props): VNode {
- const fileInputRef = useRef<HTMLInputElement>(null);
- const [sizeError, setSizeError] = useState(false);
- return (
- <div>
- <button class="button" onClick={(e) => fileInputRef.current?.click()}>
- <span>{props.label}</span>
- </button>
- <input
- ref={fileInputRef}
- style={{ display: "none" }}
- type="file"
- onChange={(e) => {
- const f: FileList | null = e.currentTarget.files;
- if (!f || f.length != 1) return props.onChange(undefined);
-
- if (f[0].size > MAX_IMAGE_UPLOAD_SIZE) {
- setSizeError(true);
- return props.onChange(undefined);
- }
- setSizeError(false);
- return f[0].arrayBuffer().then((b) => {
- const content = new Uint8Array(b).reduce(
- (data, byte) => data + String.fromCharCode(byte),
- "",
- );
- return props.onChange({
- content,
- name: f[0].name,
- type: f[0].type,
- });
- });
- }}
- />
- {sizeError && (
- <p class="help is-danger">File should be smaller than 1 MB</p>
- )}
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/Notifications.tsx b/packages/demobank-ui/src/components/Notifications.tsx
deleted file mode 100644
index 6dd3a2d50..000000000
--- a/packages/demobank-ui/src/components/Notifications.tsx
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, VNode } from "preact";
-
-export interface Notification {
- message: string;
- description?: string | VNode;
- type: MessageType;
-}
-
-export type MessageType = "INFO" | "WARN" | "ERROR" | "SUCCESS";
-
-interface Props {
- notifications: Notification[];
- removeNotification?: (n: Notification) => void;
-}
-
-function messageStyle(type: MessageType): string {
- switch (type) {
- case "INFO":
- return "message is-info";
- case "WARN":
- return "message is-warning";
- case "ERROR":
- return "message is-danger";
- case "SUCCESS":
- return "message is-success";
- default:
- return "message";
- }
-}
-
-export function Notifications({
- notifications,
- removeNotification,
-}: Props): VNode {
- return (
- <div class="block">
- {notifications.map((n, i) => (
- <article key={i} class={messageStyle(n.type)}>
- <div class="message-header">
- <p>{n.message}</p>
- {removeNotification && (
- <button
- class="delete"
- onClick={() => removeNotification && removeNotification(n)}
- />
- )}
- </div>
- {n.description && <div class="message-body">{n.description}</div>}
- </article>
- ))}
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/DateInput.tsx b/packages/demobank-ui/src/components/fields/DateInput.tsx
deleted file mode 100644
index 0eeb1b2fd..000000000
--- a/packages/demobank-ui/src/components/fields/DateInput.tsx
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { format, subYears } from "date-fns";
-import { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-import { DatePicker } from "../picker/DatePicker.js";
-
-export interface DateInputProps {
- label: string;
- grabFocus?: boolean;
- tooltip?: string;
- error?: string;
- years?: Array<number>;
- onConfirm?: () => void;
- bind: [string, (x: string) => void];
-}
-
-export function DateInput(props: DateInputProps): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (props.grabFocus) inputRef.current?.focus();
- }, [props.grabFocus]);
- const [opened, setOpened] = useState(false);
-
- const value = props.bind[0] || "";
- const [dirty, setDirty] = useState(false);
- const showError = dirty && props.error;
-
- const calendar = subYears(new Date(), 30);
-
- return (
- <div class="field">
- <label class="label">
- {props.label}
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control">
- <div class="field has-addons">
- <p class="control">
- <input
- type="text"
- class={showError ? "input is-danger" : "input"}
- value={value}
- onKeyPress={(e) => {
- if (e.key === "Enter" && props.onConfirm) props.onConfirm();
- }}
- onInput={(e) => {
- const text = e.currentTarget.value;
- setDirty(true);
- props.bind[1](text);
- }}
- ref={inputRef}
- />
- </p>
- <p class="control">
- <a
- class="button"
- onClick={() => {
- setOpened(true);
- }}
- >
- <span class="icon">
- <i class="mdi mdi-calendar" />
- </span>
- </a>
- </p>
- </div>
- </div>
- <p class="help">Using the format yyyy-mm-dd</p>
- {showError && <p class="help is-danger">{props.error}</p>}
- <DatePicker
- opened={opened}
- initialDate={calendar}
- years={props.years}
- closeFunction={() => setOpened(false)}
- dateReceiver={(d) => {
- setDirty(true);
- const v = format(d, "yyyy-MM-dd");
- props.bind[1](v);
- }}
- />
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/EmailInput.tsx b/packages/demobank-ui/src/components/fields/EmailInput.tsx
deleted file mode 100644
index 9f6624aa5..000000000
--- a/packages/demobank-ui/src/components/fields/EmailInput.tsx
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-
-export interface TextInputProps {
- label: string;
- grabFocus?: boolean;
- error?: string;
- placeholder?: string;
- tooltip?: string;
- onConfirm?: () => void;
- bind: [string, (x: string) => void];
-}
-
-export function EmailInput(props: TextInputProps): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (props.grabFocus) inputRef.current?.focus();
- }, [props.grabFocus]);
- const value = props.bind[0];
- const [dirty, setDirty] = useState(false);
- const showError = dirty && props.error;
- return (
- <div class="field">
- <label class="label">
- {props.label}
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control has-icons-right">
- <input
- value={value}
- required
- placeholder={props.placeholder}
- type="email"
- class={showError ? "input is-danger" : "input"}
- onKeyPress={(e) => {
- if (e.key === "Enter" && props.onConfirm) props.onConfirm();
- }}
- onInput={(e) => {
- setDirty(true);
- props.bind[1]((e.target as HTMLInputElement).value);
- }}
- ref={inputRef}
- style={{ display: "block" }}
- />
- </div>
- {showError && <p class="help is-danger">{props.error}</p>}
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/FileInput.tsx b/packages/demobank-ui/src/components/fields/FileInput.tsx
deleted file mode 100644
index cc49a632d..000000000
--- a/packages/demobank-ui/src/components/fields/FileInput.tsx
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-import { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-
-const MAX_IMAGE_UPLOAD_SIZE = 1024 * 1024;
-
-export interface FileTypeContent {
- content: string;
- type: string;
- name: string;
-}
-
-export interface FileInputProps {
- label: string;
- grabFocus?: boolean;
- disabled?: boolean;
- error?: string;
- placeholder?: string;
- tooltip?: string;
- onChange: (v: FileTypeContent | undefined) => void;
-}
-
-export function FileInput(props: FileInputProps): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (props.grabFocus) inputRef.current?.focus();
- }, [props.grabFocus]);
-
- const fileInputRef = useRef<HTMLInputElement>(null);
- const [sizeError, setSizeError] = useState(false);
- return (
- <div class="field">
- <label class="label">
- <a class="button" onClick={(e) => fileInputRef.current?.click()}>
- <div class="icon is-small ">
- <i class="mdi mdi-folder" />
- </div>
- <span>{props.label}</span>
- </a>
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control">
- <input
- ref={fileInputRef}
- style={{ display: "none" }}
- type="file"
- // name={String(name)}
- onChange={(e) => {
- const f: FileList | null = e.currentTarget.files;
- if (!f || f.length != 1) return props.onChange(undefined);
-
- if (f[0].size > MAX_IMAGE_UPLOAD_SIZE) {
- setSizeError(true);
- return props.onChange(undefined);
- }
- setSizeError(false);
- return f[0].arrayBuffer().then((b) => {
- const b64 = btoa(
- new Uint8Array(b).reduce(
- (data, byte) => data + String.fromCharCode(byte),
- "",
- ),
- );
- return props.onChange({
- content: `data:${f[0].type};base64,${b64}`,
- name: f[0].name,
- type: f[0].type,
- });
- });
- }}
- />
- {props.error && <p class="help is-danger">{props.error}</p>}
- {sizeError && (
- <p class="help is-danger">File should be smaller than 1 MB</p>
- )}
- </div>
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/ImageInput.tsx b/packages/demobank-ui/src/components/fields/ImageInput.tsx
deleted file mode 100644
index 15b25f1c2..000000000
--- a/packages/demobank-ui/src/components/fields/ImageInput.tsx
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-import emptyImage from "../../assets/empty.png";
-import { TextInputProps } from "./TextInput.js";
-
-const MAX_IMAGE_UPLOAD_SIZE = 1024 * 1024;
-
-export function ImageInput(props: TextInputProps): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (props.grabFocus) inputRef.current?.focus();
- }, [props.grabFocus]);
-
- const value = props.bind[0];
- // const [dirty, setDirty] = useState(false)
- const image = useRef<HTMLInputElement>(null);
- const [sizeError, setSizeError] = useState(false);
- function onChange(v: string): void {
- // setDirty(true);
- props.bind[1](v);
- }
- return (
- <div class="field">
- <label class="label">
- {props.label}
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control">
- <img
- src={!value ? emptyImage : value}
- style={{ width: 200, height: 200 }}
- onClick={() => image.current?.click()}
- />
- <input
- ref={image}
- style={{ display: "none" }}
- type="file"
- name={String(name)}
- onChange={(e) => {
- const f: FileList | null = e.currentTarget.files;
- if (!f || f.length != 1) return onChange(emptyImage);
-
- if (f[0].size > MAX_IMAGE_UPLOAD_SIZE) {
- setSizeError(true);
- return onChange(emptyImage);
- }
- setSizeError(false);
- return f[0].arrayBuffer().then((b) => {
- const b64 = btoa(
- new Uint8Array(b).reduce(
- (data, byte) => data + String.fromCharCode(byte),
- "",
- ),
- );
- return onChange(`data:${f[0].type};base64,${b64}` as any);
- });
- }}
- />
- {props.error && <p class="help is-danger">{props.error}</p>}
- {sizeError && (
- <p class="help is-danger">Image should be smaller than 1 MB</p>
- )}
- </div>
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/NumberInput.tsx b/packages/demobank-ui/src/components/fields/NumberInput.tsx
deleted file mode 100644
index 69af18c77..000000000
--- a/packages/demobank-ui/src/components/fields/NumberInput.tsx
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-
-export interface TextInputProps {
- label: string;
- grabFocus?: boolean;
- error?: string;
- placeholder?: string;
- tooltip?: string;
- onConfirm?: () => void;
- bind: [string, (x: string) => void];
-}
-
-export function PhoneNumberInput(props: TextInputProps): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (props.grabFocus) inputRef.current?.focus();
- }, [props.grabFocus]);
- const value = props.bind[0];
- const [dirty, setDirty] = useState(false);
- const showError = dirty && props.error;
- return (
- <div class="field">
- <label class="label">
- {props.label}
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control has-icons-right">
- <input
- value={value}
- type="tel"
- placeholder={props.placeholder}
- class={showError ? "input is-danger" : "input"}
- onKeyPress={(e) => {
- if (e.key === "Enter" && props.onConfirm) props.onConfirm();
- }}
- onInput={(e) => {
- setDirty(true);
- props.bind[1]((e.target as HTMLInputElement).value);
- }}
- ref={inputRef}
- style={{ display: "block" }}
- />
- </div>
- {showError && <p class="help is-danger">{props.error}</p>}
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/fields/TextInput.tsx b/packages/demobank-ui/src/components/fields/TextInput.tsx
deleted file mode 100644
index 5c6fe3157..000000000
--- a/packages/demobank-ui/src/components/fields/TextInput.tsx
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { h, VNode } from "preact";
-import { useLayoutEffect, useRef, useState } from "preact/hooks";
-
-export interface TextInputProps {
- inputType?: "text" | "number" | "multiline" | "password";
- label: string;
- grabFocus?: boolean;
- disabled?: boolean;
- error?: string;
- placeholder?: string;
- tooltip?: string;
- onConfirm?: () => void;
- bind: [string, (x: string) => void];
-}
-
-const TextInputType = function ({ inputType, grabFocus, ...rest }: any): VNode {
- const inputRef = useRef<HTMLInputElement>(null);
- useLayoutEffect(() => {
- if (grabFocus) inputRef.current?.focus();
- }, [grabFocus]);
-
- return inputType === "multiline" ? (
- <textarea {...rest} rows={5} ref={inputRef} style={{ height: "unset" }} />
- ) : (
- <input {...rest} type={inputType} ref={inputRef} />
- );
-};
-
-export function TextInput(props: TextInputProps): VNode {
- const value = props.bind[0];
- const [dirty, setDirty] = useState(false);
- const showError = dirty && props.error;
- return (
- <div class="field">
- <label class="label">
- {props.label}
- {props.tooltip && (
- <span class="icon has-tooltip-right" data-tooltip={props.tooltip}>
- <i class="mdi mdi-information" />
- </span>
- )}
- </label>
- <div class="control has-icons-right">
- <TextInputType
- inputType={props.inputType}
- value={value}
- grabFocus={props.grabFocus}
- disabled={props.disabled}
- placeholder={props.placeholder}
- class={showError ? "input is-danger" : "input"}
- onKeyPress={(e: any) => {
- if (e.key === "Enter" && props.onConfirm) props.onConfirm();
- }}
- onInput={(e: any) => {
- setDirty(true);
- props.bind[1]((e.target as HTMLInputElement).value);
- }}
- style={{ display: "block" }}
- />
- </div>
- {showError && <p class="help is-danger">{props.error}</p>}
- </div>
- );
-}
diff --git a/packages/demobank-ui/src/components/menu/NavigationBar.tsx b/packages/demobank-ui/src/components/menu/NavigationBar.tsx
deleted file mode 100644
index 5c57d2c95..000000000
--- a/packages/demobank-ui/src/components/menu/NavigationBar.tsx
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, VNode } from "preact";
-
-interface Props {
- onMobileMenu: () => void;
- title: string;
-}
-
-export function NavigationBar({ onMobileMenu, title }: Props): VNode {
- return (
- <nav
- class="navbar is-fixed-top"
- role="navigation"
- aria-label="main navigation"
- >
- <div class="navbar-brand">
- <span class="navbar-item" style={{ fontSize: 24, fontWeight: 900 }}>
- {title}
- </span>
- </div>
-
- <div class="navbar-menu ">
- <div class="navbar-end">
- <div class="navbar-item" style={{ paddingTop: 4, paddingBottom: 4 }}>
- {/* <LangSelector /> */}
- </div>
- </div>
- </div>
- </nav>
- );
-}
diff --git a/packages/demobank-ui/src/components/menu/SideBar.tsx b/packages/demobank-ui/src/components/menu/SideBar.tsx
deleted file mode 100644
index 32fe216ab..000000000
--- a/packages/demobank-ui/src/components/menu/SideBar.tsx
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, VNode } from "preact";
-import { useTranslationContext } from "@gnu-taler/web-util/lib/index.browser";
-
-interface Props {
- mobile?: boolean;
-}
-
-export function Sidebar({ mobile }: Props): VNode {
- // const config = useConfigContext();
- const config = { version: "none" };
- // FIXME: add replacement for __VERSION__ with the current version
- const process = { env: { __VERSION__: "0.0.0" } };
- const { i18n } = useTranslationContext();
-
- return (
- <aside class="aside is-placed-left is-expanded">
- <div class="aside-tools">
- <div class="aside-tools-label">
- <div>
- <b>euFin bank</b>
- </div>
- <div
- class="is-size-7 has-text-right"
- style={{ lineHeight: 0, marginTop: -10 }}
- >
- Version {process.env.__VERSION__} ({config.version})
- </div>
- </div>
- </div>
- <div class="menu is-menu-main">
- <p class="menu-label">
- <i18n.Translate>Bank menu</i18n.Translate>
- </p>
- <ul class="menu-list">
- <li>
- <div class="ml-4">
- <span class="menu-item-label">
- <i18n.Translate>Select option1</i18n.Translate>
- </span>
- </div>
- </li>
- <li>
- <div class="ml-4">
- <span class="menu-item-label">
- <i18n.Translate>Select option2</i18n.Translate>
- </span>
- </div>
- </li>
- </ul>
- </div>
- </aside>
- );
-}
diff --git a/packages/demobank-ui/src/components/menu/index.tsx b/packages/demobank-ui/src/components/menu/index.tsx
deleted file mode 100644
index c0a845a62..000000000
--- a/packages/demobank-ui/src/components/menu/index.tsx
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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 { ComponentChildren, Fragment, h, VNode } from "preact";
-import Match from "preact-router/match";
-import { useEffect, useState } from "preact/hooks";
-import { NavigationBar } from "./NavigationBar.js";
-import { Sidebar } from "./SideBar.js";
-
-interface MenuProps {
- title: string;
-}
-
-function WithTitle({
- title,
- children,
-}: {
- title: string;
- children: ComponentChildren;
-}): VNode {
- useEffect(() => {
- document.title = `${title}`;
- }, [title]);
- return <Fragment>{children}</Fragment>;
-}
-
-export function Menu({ title }: MenuProps): VNode {
- const [mobileOpen, setMobileOpen] = useState(false);
-
- return (
- <Match>
- {({ path }: { path: string }) => {
- const titleWithSubtitle = title; // title ? title : (!admin ? getInstanceTitle(path, instance) : getAdminTitle(path, instance))
- return (
- <WithTitle title={titleWithSubtitle}>
- <div
- class={mobileOpen ? "has-aside-mobile-expanded" : ""}
- onClick={() => setMobileOpen(false)}
- >
- <NavigationBar
- onMobileMenu={() => setMobileOpen(!mobileOpen)}
- title={titleWithSubtitle}
- />
-
- <Sidebar mobile={mobileOpen} />
- </div>
- </WithTitle>
- );
- }}
- </Match>
- );
-}
-
-interface NotYetReadyAppMenuProps {
- title: string;
- onLogout?: () => void;
-}
-
-interface NotifProps {
- notification?: Notification;
-}
-export function NotificationCard({
- notification: n,
-}: NotifProps): VNode | null {
- if (!n) return null;
- return (
- <div class="notification">
- <div class="columns is-vcentered">
- <div class="column is-12">
- <article
- class={
- n.type === "ERROR"
- ? "message is-danger"
- : n.type === "WARN"
- ? "message is-warning"
- : "message is-info"
- }
- >
- <div class="message-header">
- <p>{n.message}</p>
- </div>
- {n.description && <div class="message-body">{n.description}</div>}
- </article>
- </div>
- </div>
- </div>
- );
-}
-
-export function NotYetReadyAppMenu({
- onLogout,
- title,
-}: NotYetReadyAppMenuProps): VNode {
- const [mobileOpen, setMobileOpen] = useState(false);
-
- useEffect(() => {
- document.title = `Taler Backoffice: ${title}`;
- }, [title]);
-
- return (
- <div
- class="has-aside-mobile-expanded"
- // class={mobileOpen ? "has-aside-mobile-expanded" : ""}
- onClick={() => setMobileOpen(false)}
- >
- <NavigationBar
- onMobileMenu={() => setMobileOpen(!mobileOpen)}
- title={title}
- />
- {onLogout && <Sidebar mobile={mobileOpen} />}
- </div>
- );
-}
-
-export interface Notification {
- message: string;
- description?: string | VNode;
- type: MessageType;
-}
-
-export type ValueOrFunction<T> = T | ((p: T) => T);
-export type MessageType = "INFO" | "WARN" | "ERROR" | "SUCCESS";
diff --git a/packages/demobank-ui/src/components/picker/DatePicker.tsx b/packages/demobank-ui/src/components/picker/DatePicker.tsx
deleted file mode 100644
index 0a93144ec..000000000
--- a/packages/demobank-ui/src/components/picker/DatePicker.tsx
+++ /dev/null
@@ -1,347 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, Component } from "preact";
-
-interface Props {
- closeFunction?: () => void;
- dateReceiver?: (d: Date) => void;
- initialDate?: Date;
- years?: Array<number>;
- opened?: boolean;
-}
-interface State {
- displayedMonth: number;
- displayedYear: number;
- selectYearMode: boolean;
- currentDate: Date;
-}
-const now = new Date();
-
-const monthArrShortFull = [
- "January",
- "February",
- "March",
- "April",
- "May",
- "June",
- "July",
- "August",
- "September",
- "October",
- "November",
- "December",
-];
-
-const monthArrShort = [
- "Jan",
- "Feb",
- "Mar",
- "Apr",
- "May",
- "Jun",
- "Jul",
- "Aug",
- "Sep",
- "Oct",
- "Nov",
- "Dec",
-];
-
-const dayArr = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
-
-const yearArr: number[] = [];
-
-// inspired by https://codepen.io/m4r1vs/pen/MOOxyE
-export class DatePicker extends Component<Props, State> {
- closeDatePicker() {
- this.props.closeFunction && this.props.closeFunction(); // Function gets passed by parent
- }
-
- /**
- * Gets fired when a day gets clicked.
- * @param {object} e The event thrown by the <span /> element clicked
- */
- dayClicked(e: any) {
- const element = e.target; // the actual element clicked
-
- if (element.innerHTML === "") return false; // don't continue if <span /> empty
-
- // get date from clicked element (gets attached when rendered)
- const date = new Date(element.getAttribute("data-value"));
-
- // update the state
- this.setState({ currentDate: date });
- this.passDateToParent(date);
- }
-
- /**
- * returns days in month as array
- * @param {number} month the month to display
- * @param {number} year the year to display
- */
- getDaysByMonth(month: number, year: number) {
- const calendar = [];
-
- const date = new Date(year, month, 1); // month to display
-
- const firstDay = new Date(year, month, 1).getDay(); // first weekday of month
- const lastDate = new Date(year, month + 1, 0).getDate(); // last date of month
-
- let day: number | null = 0;
-
- // the calendar is 7*6 fields big, so 42 loops
- for (let i = 0; i < 42; i++) {
- if (i >= firstDay && day !== null) day = day + 1;
- if (day !== null && day > lastDate) day = null;
-
- // append the calendar Array
- calendar.push({
- day: day === 0 || day === null ? null : day, // null or number
- date: day === 0 || day === null ? null : new Date(year, month, day), // null or Date()
- today:
- day === now.getDate() &&
- month === now.getMonth() &&
- year === now.getFullYear(), // boolean
- });
- }
-
- return calendar;
- }
-
- /**
- * Display previous month by updating state
- */
- displayPrevMonth() {
- if (this.state.displayedMonth <= 0)
- this.setState({
- displayedMonth: 11,
- displayedYear: this.state.displayedYear - 1,
- });
- else
- this.setState({
- displayedMonth: this.state.displayedMonth - 1,
- });
- }
-
- /**
- * Display next month by updating state
- */
- displayNextMonth() {
- if (this.state.displayedMonth >= 11)
- this.setState({
- displayedMonth: 0,
- displayedYear: this.state.displayedYear + 1,
- });
- else
- this.setState({
- displayedMonth: this.state.displayedMonth + 1,
- });
- }
-
- /**
- * Display the selected month (gets fired when clicking on the date string)
- */
- displaySelectedMonth() {
- if (this.state.selectYearMode) this.toggleYearSelector();
- else {
- if (!this.state.currentDate) return false;
- this.setState({
- displayedMonth: this.state.currentDate.getMonth(),
- displayedYear: this.state.currentDate.getFullYear(),
- });
- }
- }
-
- toggleYearSelector() {
- this.setState({ selectYearMode: !this.state.selectYearMode });
- }
-
- changeDisplayedYear(e: any) {
- const element = e.target;
- this.toggleYearSelector();
- this.setState({
- displayedYear: parseInt(element.innerHTML, 10),
- displayedMonth: 0,
- });
- }
-
- /**
- * Pass the selected date to parent when 'OK' is clicked
- */
- passSavedDateDateToParent() {
- this.passDateToParent(this.state.currentDate);
- }
- passDateToParent(date: Date) {
- if (typeof this.props.dateReceiver === "function")
- this.props.dateReceiver(date);
- this.closeDatePicker();
- }
-
- componentDidUpdate() {
- // if (this.state.selectYearMode) {
- // document.getElementsByClassName('selected')[0].scrollIntoView(); // works in every browser incl. IE, replace with scrollIntoViewIfNeeded when browsers support it
- // }
- }
-
- constructor(props: any) {
- super(props);
-
- this.closeDatePicker = this.closeDatePicker.bind(this);
- this.dayClicked = this.dayClicked.bind(this);
- this.displayNextMonth = this.displayNextMonth.bind(this);
- this.displayPrevMonth = this.displayPrevMonth.bind(this);
- this.getDaysByMonth = this.getDaysByMonth.bind(this);
- this.changeDisplayedYear = this.changeDisplayedYear.bind(this);
- this.passDateToParent = this.passDateToParent.bind(this);
- this.toggleYearSelector = this.toggleYearSelector.bind(this);
- this.displaySelectedMonth = this.displaySelectedMonth.bind(this);
-
- const initial = props.initialDate || now;
-
- this.state = {
- currentDate: initial,
- displayedMonth: initial.getMonth(),
- displayedYear: initial.getFullYear(),
- selectYearMode: false,
- };
- }
-
- render() {
- const { currentDate, displayedMonth, displayedYear, selectYearMode } =
- this.state;
-
- return (
- <div>
- <div class={`datePicker ${this.props.opened && "datePicker--opened"}`}>
- <div class="datePicker--titles">
- <h3
- style={{
- color: selectYearMode
- ? "rgba(255,255,255,.87)"
- : "rgba(255,255,255,.57)",
- }}
- onClick={this.toggleYearSelector}
- >
- {currentDate.getFullYear()}
- </h3>
- <h2
- style={{
- color: !selectYearMode
- ? "rgba(255,255,255,.87)"
- : "rgba(255,255,255,.57)",
- }}
- onClick={this.displaySelectedMonth}
- >
- {dayArr[currentDate.getDay()]},{" "}
- {monthArrShort[currentDate.getMonth()]} {currentDate.getDate()}
- </h2>
- </div>
-
- {!selectYearMode && (
- <nav>
- <span onClick={this.displayPrevMonth} class="icon">
- <i
- style={{ transform: "rotate(180deg)" }}
- class="mdi mdi-forward"
- />
- </span>
- <h4>
- {monthArrShortFull[displayedMonth]} {displayedYear}
- </h4>
- <span onClick={this.displayNextMonth} class="icon">
- <i class="mdi mdi-forward" />
- </span>
- </nav>
- )}
-
- <div class="datePicker--scroll">
- {!selectYearMode && (
- <div class="datePicker--calendar">
- <div class="datePicker--dayNames">
- {["S", "M", "T", "W", "T", "F", "S"].map((day, i) => (
- <span key={i}>{day}</span>
- ))}
- </div>
-
- <div onClick={this.dayClicked} class="datePicker--days">
- {/*
- Loop through the calendar object returned by getDaysByMonth().
- */}
-
- {this.getDaysByMonth(
- this.state.displayedMonth,
- this.state.displayedYear,
- ).map((day) => {
- let selected = false;
-
- if (currentDate && day.date)
- selected =
- currentDate.toLocaleDateString() ===
- day.date.toLocaleDateString();
-
- return (
- <span
- key={day.day}
- class={
- (day.today ? "datePicker--today " : "") +
- (selected ? "datePicker--selected" : "")
- }
- disabled={!day.date}
- data-value={day.date}
- >
- {day.day}
- </span>
- );
- })}
- </div>
- </div>
- )}
-
- {selectYearMode && (
- <div class="datePicker--selectYear">
- {(this.props.years || yearArr).map((year) => (
- <span
- key={year}
- class={year === displayedYear ? "selected" : ""}
- onClick={this.changeDisplayedYear}
- >
- {year}
- </span>
- ))}
- </div>
- )}
- </div>
- </div>
-
- <div
- class="datePicker--background"
- onClick={this.closeDatePicker}
- style={{
- display: this.props.opened ? "block" : "none",
- }}
- />
- </div>
- );
- }
-}
-
-for (let i = 2010; i <= now.getFullYear() + 10; i++) yearArr.push(i);
diff --git a/packages/demobank-ui/src/components/picker/DurationPicker.stories.tsx b/packages/demobank-ui/src/components/picker/DurationPicker.stories.tsx
deleted file mode 100644
index db417b949..000000000
--- a/packages/demobank-ui/src/components/picker/DurationPicker.stories.tsx
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, FunctionalComponent } from "preact";
-import { useState } from "preact/hooks";
-import { DurationPicker as TestedComponent } from "./DurationPicker.js";
-
-export default {
- title: "Components/Picker/Duration",
- component: TestedComponent,
- argTypes: {
- onCreate: { action: "onCreate" },
- goBack: { action: "goBack" },
- },
-};
-
-function createExample<Props>(
- Component: FunctionalComponent<Props>,
- props: Partial<Props>,
-) {
- const r = (args: any) => <Component {...args} />;
- r.args = props;
- return r;
-}
-
-export const Example = createExample(TestedComponent, {
- days: true,
- minutes: true,
- hours: true,
- seconds: true,
- value: 10000000,
-});
-
-export const WithState = () => {
- const [v, s] = useState<number>(1000000);
- return <TestedComponent value={v} onChange={s} days minutes hours seconds />;
-};
diff --git a/packages/demobank-ui/src/components/picker/DurationPicker.tsx b/packages/demobank-ui/src/components/picker/DurationPicker.tsx
deleted file mode 100644
index 973f2f507..000000000
--- a/packages/demobank-ui/src/components/picker/DurationPicker.tsx
+++ /dev/null
@@ -1,210 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2022 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/>
- */
-
-/**
- *
- * @author Sebastian Javier Marchano (sebasjm)
- */
-
-import { h, VNode } from "preact";
-import { useState } from "preact/hooks";
-import { useTranslationContext } from "@gnu-taler/web-util/lib/index.browser";
-import "../../scss/DurationPicker.scss";
-
-export interface Props {
- hours?: boolean;
- minutes?: boolean;
- seconds?: boolean;
- days?: boolean;
- onChange: (value: number) => void;
- value: number;
-}
-
-// inspiration taken from https://github.com/flurmbo/react-duration-picker
-export function DurationPicker({
- days,
- hours,
- minutes,
- seconds,
- onChange,
- value,
-}: Props): VNode {
- const ss = 1000;
- const ms = ss * 60;
- const hs = ms * 60;
- const ds = hs * 24;
- const { i18n } = useTranslationContext();
-
- return (
- <div class="rdp-picker">
- {days && (
- <DurationColumn
- unit={i18n.str`days`}
- max={99}
- value={Math.floor(value / ds)}
- onDecrease={value >= ds ? () => onChange(value - ds) : undefined}
- onIncrease={value < 99 * ds ? () => onChange(value + ds) : undefined}
- onChange={(diff) => onChange(value + diff * ds)}
- />
- )}
- {hours && (
- <DurationColumn
- unit={i18n.str`hours`}
- max={23}
- min={1}
- value={Math.floor(value / hs) % 24}
- onDecrease={value >= hs ? () => onChange(value - hs) : undefined}
- onIncrease={value < 99 * ds ? () => onChange(value + hs) : undefined}
- onChange={(diff) => onChange(value + diff * hs)}
- />
- )}
- {minutes && (
- <DurationColumn
- unit={i18n.str`minutes`}
- max={59}
- min={1}
- value={Math.floor(value / ms) % 60}
- onDecrease={value >= ms ? () => onChange(value - ms) : undefined}
- onIncrease={value < 99 * ds ? () => onChange(value + ms) : undefined}
- onChange={(diff) => onChange(value + diff * ms)}
- />
- )}
- {seconds && (
- <DurationColumn
- unit={i18n.str`seconds`}
- max={59}
- value={Math.floor(value / ss) % 60}
- onDecrease={value >= ss ? () => onChange(value - ss) : undefined}
- onIncrease={value < 99 * ds ? () => onChange(value + ss) : undefined}
- onChange={(diff) => onChange(value + diff * ss)}
- />
- )}
- </div>
- );
-}
-
-interface ColProps {
- unit: string;
- min?: number;
- max: number;
- value: number;
- onIncrease?: () => void;
- onDecrease?: () => void;
- onChange?: (diff: number) => void;
-}
-
-function InputNumber({
- initial,
- onChange,
-}: {
- initial: number;
- onChange: (n: number) => void;
-}) {
- const [value, handler] = useState<{ v: string }>({
- v: toTwoDigitString(initial),
- });
-
- return (
- <input
- value={value.v}
- onBlur={(e) => onChange(parseInt(value.v, 10))}
- onInput={(e) => {
- e.preventDefault();
- const n = Number.parseInt(e.currentTarget.value, 10);
- if (isNaN(n)) return handler({ v: toTwoDigitString(initial) });
- return handler({ v: toTwoDigitString(n) });
- }}
- style={{
- width: 50,
- border: "none",
- fontSize: "inherit",
- background: "inherit",
- }}
- />
- );
-}
-
-function DurationColumn({
- unit,
- min = 0,
- max,
- value,
- onIncrease,
- onDecrease,
- onChange,
-}: ColProps): VNode {
- const cellHeight = 35;
- return (
- <div class="rdp-column-container">
- <div class="rdp-masked-div">
- <hr class="rdp-reticule" style={{ top: cellHeight * 2 - 1 }} />
- <hr class="rdp-reticule" style={{ top: cellHeight * 3 - 1 }} />
-
- <div class="rdp-column" style={{ top: 0 }}>
- <div class="rdp-cell" key={value - 2}>
- {onDecrease && (
- <button
- style={{ width: "100%", textAlign: "center", margin: 5 }}
- onClick={onDecrease}
- >
- <span class="icon">
- <i class="mdi mdi-chevron-up" />
- </span>
- </button>
- )}
- </div>
- <div class="rdp-cell" key={value - 1}>
- {value > min ? toTwoDigitString(value - 1) : ""}
- </div>
- <div class="rdp-cell rdp-center" key={value}>
- {onChange ? (
- <InputNumber
- initial={value}
- onChange={(n) => onChange(n - value)}
- />
- ) : (
- toTwoDigitString(value)
- )}
- <div>{unit}</div>
- </div>
-
- <div class="rdp-cell" key={value + 1}>
- {value < max ? toTwoDigitString(value + 1) : ""}
- </div>
-
- <div class="rdp-cell" key={value + 2}>
- {onIncrease && (
- <button
- style={{ width: "100%", textAlign: "center", margin: 5 }}
- onClick={onIncrease}
- >
- <span class="icon">
- <i class="mdi mdi-chevron-down" />
- </span>
- </button>
- )}
- </div>
- </div>
- </div>
- </div>
- );
-}
-
-function toTwoDigitString(n: number) {
- if (n < 10) return `0${n}`;
-
- return `${n}`;
-}
diff --git a/packages/demobank-ui/src/index.tsx b/packages/demobank-ui/src/index.tsx
index 97f68f18f..a0ce8cb59 100644
--- a/packages/demobank-ui/src/index.tsx
+++ b/packages/demobank-ui/src/index.tsx
@@ -15,8 +15,8 @@
*/
import App from "./components/app.js";
-export default App;
-import { render, h } from "preact";
+
+import { h, render } from "preact";
import "./scss/main.scss";
const app = document.getElementById("app");
diff --git a/packages/demobank-ui/src/pages/home/QrCodeSection.tsx b/packages/demobank-ui/src/pages/home/QrCodeSection.tsx
index 531df75bc..7e89cd516 100644
--- a/packages/demobank-ui/src/pages/home/QrCodeSection.tsx
+++ b/packages/demobank-ui/src/pages/home/QrCodeSection.tsx
@@ -42,7 +42,7 @@ export function QrCodeSection({
<article>
<div class="qr-div">
<p>{i18n.str`Use this QR code to withdraw to your mobile wallet:`}</p>
- {QR({ text: talerWithdrawUri })}
+ <QR text={talerWithdrawUri} />
<p>
<i18n.Translate>
Click{" "}
diff --git a/packages/demobank-ui/src/style/index.css b/packages/demobank-ui/src/style/index.css
deleted file mode 100644
index e69de29bb..000000000
--- a/packages/demobank-ui/src/style/index.css
+++ /dev/null