gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[taler-wallet-core] branch master updated: fix #7731


From: gnunet
Subject: [taler-wallet-core] branch master updated: fix #7731
Date: Tue, 28 Feb 2023 11:42:02 +0100

This is an automated email from the git hooks/post-receive script.

sebasjm pushed a commit to branch master
in repository wallet-core.

The following commit(s) were added to refs/heads/master by this push:
     new 04eec324b fix #7731
04eec324b is described below

commit 04eec324bff7601a89a1669ea6edfc699d698595
Author: Sebastian <sebasjm@gmail.com>
AuthorDate: Tue Feb 28 07:41:51 2023 -0300

    fix #7731
---
 .../src/components/AmountField.stories.tsx         |  11 +-
 .../src/components/AmountField.tsx                 | 152 ++++++++++-----------
 2 files changed, 81 insertions(+), 82 deletions(-)

diff --git 
a/packages/taler-wallet-webextension/src/components/AmountField.stories.tsx 
b/packages/taler-wallet-webextension/src/components/AmountField.stories.tsx
index f253d1996..9ac17155c 100644
--- a/packages/taler-wallet-webextension/src/components/AmountField.stories.tsx
+++ b/packages/taler-wallet-webextension/src/components/AmountField.stories.tsx
@@ -31,7 +31,11 @@ export default {
 };
 
 function RenderAmount(): VNode {
-  const [value, setValue] = useState<AmountJson | undefined>(undefined);
+  const [value, setValue] = useState<AmountJson | undefined>({
+    currency: "USD",
+    value: 1,
+    fraction: 0,
+  });
 
   const error = value === undefined ? undefined : undefined;
 
@@ -53,7 +57,10 @@ function RenderAmount(): VNode {
         handler={handler}
       />
       <p>
-        <pre>{JSON.stringify(value, undefined, 2)}</pre>
+        <pre>
+          value : {value?.value} <br />
+          fraction : {value?.fraction}
+        </pre>
       </p>
     </Fragment>
   );
diff --git a/packages/taler-wallet-webextension/src/components/AmountField.tsx 
b/packages/taler-wallet-webextension/src/components/AmountField.tsx
index 786244433..88ac71dd8 100644
--- a/packages/taler-wallet-webextension/src/components/AmountField.tsx
+++ b/packages/taler-wallet-webextension/src/components/AmountField.tsx
@@ -25,6 +25,7 @@ import {
 } from "@gnu-taler/taler-util";
 import { Fragment, h, VNode } from "preact";
 import { useState } from "preact/hooks";
+import { useTranslationContext } from "../context/translation.js";
 import { AmountFieldHandler } from "../mui/handlers.js";
 import { TextField } from "../mui/TextField.js";
 
@@ -47,80 +48,49 @@ export function AmountField({
   required?: boolean;
   handler: AmountFieldHandler;
 }): VNode {
+  const { i18n } = useTranslationContext();
   const [unit, setUnit] = useState(1);
-  const [decimalPlaces, setDecimalPlaces] = useState<number | undefined>(
-    undefined,
-  );
-  const currency = handler.value.currency;
+  const [error, setError] = useState<string>("");
 
-  let hd = Math.floor(Math.log10(highestDenom || 1) / 3);
-  let ld = Math.ceil((-1 * Math.log10(lowestDenom || 1)) / 3);
+  const normal = normalize(handler.value, unit);
+  const previousValue = Amounts.stringifyValue(normal);
 
-  const currencyLabels: Array<{ name: string; unit: number }> = [
-    {
-      name: currency,
-      unit: 1,
-    },
-  ];
+  const [textValue, setTextValue] = useState<string>(previousValue);
 
-  while (hd > 0) {
-    currencyLabels.push({
-      name: `${HIGH_DENOM_SYMBOL[hd]}${currency}`,
-      unit: Math.pow(10, hd * 3),
-    });
-    hd--;
-  }
-  while (ld > 0) {
-    currencyLabels.push({
-      name: `${LOW_DENOM_SYMBOL[ld]}${currency}`,
-      unit: Math.pow(10, -1 * ld * 3),
-    });
-    ld--;
+  function updateUnit(newUnit: number) {
+    setUnit(newUnit);
+    const newNorm = normalize(handler.value, newUnit);
+    setTextValue(Amounts.stringifyValue(newNorm));
   }
 
-  const previousValue = Amounts.stringifyValue(handler.value, decimalPlaces);
-
-  const normal = normalize(handler.value, unit) ?? handler.value;
+  const currency = handler.value.currency;
 
-  let textValue = Amounts.stringifyValue(normal, decimalPlaces);
-  if (decimalPlaces === 0) {
-    textValue += ".";
-  }
+  const currencyLabels = buildLabelsForCurrency(
+    currency,
+    lowestDenom,
+    highestDenom,
+  );
 
   function positiveAmount(value: string): string {
-    // setDotAtTheEnd(value.endsWith("."));
-    // const dotAtTheEnd = value.endsWith(".");
     if (!value) {
       if (handler.onInput) {
         handler.onInput(Amounts.zeroOfCurrency(currency));
       }
-      return "";
-    }
-    try {
-      //remove all but last dot
-      const withoutDots = value.replace(/(\.)(?=.*\1)/g, "");
-      const parts = withoutDots.split(".");
-      setDecimalPlaces(parts.length === 1 ? undefined : parts[1].length);
-
-      //FIXME: should normalize before parsing
-      //parsing first add some restriction on the rage of the values
-      const parsed = parseValue(currency, withoutDots);
-
-      if (!parsed || parsed.value < 0) {
-        return previousValue;
-      }
+    } else
+      try {
+        const parsed = Amounts.parseOrThrow(`${currency}:${value.trim()}`);
 
-      const realValue = denormalize(parsed, unit);
+        const realValue = denormalize(parsed, unit);
 
-      // console.log(real, unit, normal);
-      if (realValue && handler.onInput) {
-        handler.onInput(realValue);
+        if (handler.onInput) {
+          handler.onInput(realValue);
+        }
+        setError("");
+      } catch (e) {
+        setError(i18n.str`Amount is not valid`);
       }
-      return withoutDots;
-    } catch (e) {
-      // do nothing
-    }
-    return previousValue;
+    setTextValue(value);
+    return value;
   }
 
   return (
@@ -149,7 +119,7 @@ export function AmountField({
               disabled={!handler.onInput}
               onChange={(e) => {
                 const unit = Number.parseFloat(e.currentTarget.value);
-                setUnit(unit);
+                updateUnit(unit);
               }}
               value={String(unit)}
               style={{
@@ -171,29 +141,11 @@ export function AmountField({
         disabled={!handler.onInput}
         onInput={positiveAmount}
       />
+      {error && <div style={{ color: "red" }}>{error}</div>}
     </Fragment>
   );
 }
 
-function parseValue(currency: string, s: string): AmountJson | undefined {
-  const [intPart, fractPart] = s.split(".");
-  const tailPart = !fractPart
-    ? "0"
-    : fractPart.substring(0, amountFractionalLength);
-
-  const value = Number.parseInt(intPart, 10);
-  const parsedTail = Number.parseFloat(`.${tailPart}`);
-  if (Number.isNaN(value) || Number.isNaN(parsedTail)) {
-    return undefined;
-  }
-  if (value > amountMaxValue) {
-    return undefined;
-  }
-
-  const fraction = Math.round(amountFractionalBase * parsedTail);
-  return { currency, fraction, value };
-}
-
 /**
  * Return the real value of a normalized unit
  * If the value is 20 and the unit is kilo == 1000 the returned value will be 
amount * 1000
@@ -201,7 +153,7 @@ function parseValue(currency: string, s: string): 
AmountJson | undefined {
  * @param unit
  * @returns
  */
-function denormalize(amount: AmountJson, unit: number): AmountJson | undefined 
{
+function denormalize(amount: AmountJson, unit: number): AmountJson {
   if (unit === 1 || Amounts.isZero(amount)) return amount;
   const result =
     unit < 1
@@ -218,7 +170,7 @@ function denormalize(amount: AmountJson, unit: number): 
AmountJson | undefined {
  * @param unit
  * @returns
  */
-function normalize(amount: AmountJson, unit: number): AmountJson | undefined {
+function normalize(amount: AmountJson, unit: number): AmountJson {
   if (unit === 1 || Amounts.isZero(amount)) return amount;
   const result =
     unit < 1
@@ -226,3 +178,43 @@ function normalize(amount: AmountJson, unit: number): 
AmountJson | undefined {
       : Amounts.divide(amount, unit);
   return result;
 }
+
+/**
+ * Take every label in HIGH_DENOM_SYMBOL and LOW_DENOM_SYMBOL and create
+ * which create the corresponding unit multiplier
+ * @param currency
+ * @param lowestDenom
+ * @param highestDenom
+ * @returns
+ */
+function buildLabelsForCurrency(
+  currency: string,
+  lowestDenom: number,
+  highestDenom: number,
+): Array<{ name: string; unit: number }> {
+  let hd = Math.floor(Math.log10(highestDenom || 1) / 3);
+  let ld = Math.ceil((-1 * Math.log10(lowestDenom || 1)) / 3);
+
+  const result: Array<{ name: string; unit: number }> = [
+    {
+      name: currency,
+      unit: 1,
+    },
+  ];
+
+  while (hd > 0) {
+    result.push({
+      name: `${HIGH_DENOM_SYMBOL[hd]}${currency}`,
+      unit: Math.pow(10, hd * 3),
+    });
+    hd--;
+  }
+  while (ld > 0) {
+    result.push({
+      name: `${LOW_DENOM_SYMBOL[ld]}${currency}`,
+      unit: Math.pow(10, -1 * ld * 3),
+    });
+    ld--;
+  }
+  return result;
+}

-- 
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]