当我们在文本框中输入一些值并在 fromCurrency
下拉字段中输入货币并在 toCurrency
下拉字段中选择适当的货币时,我们如何在 toCurrency
中显示基于那个选择?
https://codesandbox.io/s/rough-http-jc35u?file=/src/App.js
import React, { useState, useEffect } from "react";
import "./styles.css";
const axios = require("axios");
function App() {
const [sourceCurrency, setSourceCurrency] = useState("");
const [targetCurrency, setTargetCurrency] = useState("");
const [ratesList, setRatesList] = useState([]);
const [selectFromCurrency, setFromSourceCurrency] = useState("");
const [selectToCurrency, setSelectToCurrency] = useState("");
const getSourceCurrency = (source) => {
setSourceCurrency(source);
};
const getTargetCurrency = (target) => {
setTargetCurrency(target);
};
useEffect(() => {
const fetchData = async () => {
try {
const data = await axios.get("https://api.exchangeratesapi.io/latest");
setRatesList(data);
console.log(data);
} catch (e) {
console.log(e);
}
};
fetchData();
}, []);
const selectSourceCurrency = (sourceCurr) => {
setFromSourceCurrency(sourceCurr);
};
const selectTargetCurrency = (targetCurr) => {
setSelectToCurrency(targetCurr);
};
const convertRate = () => {
const rateCalc = sourceCurrency * targetCurrency;
console.log("print rate: " + rateCalc);
// how can we the rates list here and based on the selection ?
};
return (
<div className="App">
<div className="globalCurrencyConverter">
<h2>Currency Converter</h2>
<div className="container box">
<label>
<input
name="sourceCurrency"
type="text"
placeholder="fromCurrency"
onChange={(event) => getSourceCurrency(event.target.value)}
/>
<select
className="fromCurrency"
defaultValue={"DEFAULT"}
onChange={(event) => selectSourceCurrency(event.target.value)}
>
<option>USD</option>
<option value="DEFAULT">AUD</option>
<option>NZD</option>
<option>INR</option>
<option>UAE Dirham</option>
</select>
</label>
<label>
<input
name="targetCurrency"
type="text"
placeholder="toCurrency"
onChange={(event) => getTargetCurrency(event.target.value)}
/>
<select
className="toCurrency"
onChange={(event) => selectTargetCurrency(event.target.value)}
>
<option>USD</option>
<option>AUD</option>
<option>NZD</option>
<option>INR</option>
<option>UAE Dirham</option>
</select>
</label>
<div className="recordBtn">
<button name="convert" onClick={(event) => convertRate()}>
Convert
</button>
</div>
</div>
</div>
</div>
);
}
export default App;
答案 0 :(得分:3)
我假设您可以自己处理这些带有货币的选定字段的数量,而是向您展示如何解决实际的转换问题。因此,我们将保留这些选择选项硬编码在您的代码中。例如(美元、新西兰元、澳元等)
所以我们实际上甚至不需要在这个测试中使用 useEffect,因为我们只是简单地对货币进行了硬编码。就我个人而言,我喜欢用尽可能少的重新渲染来解决我的 React 问题。所以我解决这个特定问题的方法是创建对所有 4 个字段的引用。它将允许我们随时访问它们的值。查看useRef()
。
然后,当有人输入所有信息并单击“转换”按钮时,我会调用您的 API 并将所选货币作为基础货币传递给它。像这样
https://api.exchangeratesapi.io/latest?base=USD
一旦 axios 获取其上的数据,它只是一些基本匹配和将正确值分配给“To Currency”字段的问题。所以这里有一个工作示例和一个 Sandbox:
import React, { useState, useEffect, useRef } from "react";
import "./styles.css";
const axios = require("axios");
function App() {
const from_select = useRef(),
to_select = useRef(),
from_input = useRef(),
to_input = useRef();
useEffect(() => {
const fetchData = async () => {
try {
const data = await axios.get("https://api.exchangeratesapi.io/latest");
//setRatesList(data);
console.log(data);
} catch (e) {
console.log(e);
}
};
fetchData();
}, []);
const convertRate = () => {
const from_cur = from_select.current.value;
const to_cur = to_select.current.value;
const from_amount = from_input.current.value;
console.log(from_cur);
axios
.get("https://api.exchangeratesapi.io/latest?base=" + from_cur)
.then((result) => {
const rate = result.data.rates[to_cur];
const converted_amount = rate * from_amount;
to_input.current.value = converted_amount;
});
};
return (
<div className="App">
<div className="globalCurrencyConverter">
<h2>Currency Converter</h2>
<div className="container box">
<label>
<input
ref={from_input}
name="sourceCurrency"
type="text"
placeholder="fromCurrency"
/>
<select
ref={from_select}
className="fromCurrency"
defaultValue={"USD"}
>
<option value="USD">USD</option>
<option value="AUD">AUD</option>
<option value="NZD">NZD</option>
</select>
</label>
{" -> "}
<label>
<input
ref={to_input}
name="targetCurrency"
type="text"
placeholder="toCurrency"
/>
<select ref={to_select} className="toCurrency" defaultValue="AUD">
<option value="USD">USD</option>
<option value="AUD">AUD</option>
<option value="NZD">NZD</option>
<option value="RUB">RUB</option>
<option value="EUR">EUR</option>
</select>
</label>
<div className="recordBtn">
<button name="convert" onClick={convertRate}>
Convert
</button>
</div>
</div>
</div>
</div>
);
}
export default App;
答案 1 :(得分:1)
您的 ratesList
将是从 data.data.rates
中提取的对象,其国家键和费率值在初始 useEffect
设置为:
useEffect(() => {
const fetchData = async () => {
try {
const data = await axios.get("https://api.exchangeratesapi.io/latest");
setRatesList(data.data.rates);
} catch (e) {
console.log(e);
}
};
fetchData();
}, []);
您的 convertRate
首先验证 sourceCurrency
是否为数字且是否存在 ratesList
。要计算转化率,您需要将金额值乘以比率 (toCurrency/FromCurrency)
:
const convertRate = () => {
if (isNaN(sourceCurrency) || !ratesList) return;
setTargetCurrency(
(ratesList[selectToCurrency] / ratesList[selectFromCurrency]) *
sourceCurrency
);
};
设置货币的初始值:
const [selectFromCurrency, setFromSourceCurrency] = useState("USD");
const [selectToCurrency, setSelectToCurrency] = useState("NZD");
并删除选择和输入值的默认值。而是传递状态值以获得受控输入,例如:
<select
className="fromCurrency"
value={selectFromCurrency}
onChange={(event) => selectSourceCurrency(event.target.value)}
>
<option>USD</option>
<option>AUD</option>
<option>NZD</option>
<option>INR</option>
<option>PLN</option>
</select>
对于您的 toCurrency
输入,将其设为禁用字段,因为您无需用户在其上键入值:
<input
name="targetCurrency"
value={targetCurrency}
disabled
type="text"
placeholder="toCurrency"
/>
工作演示:
注意:阿联酋迪拉姆与 API 响应不匹配,因此更改为 PLN