javascript - 如何在新的 Reactjs 函数中设置状态?
问题描述
我正在为没有类的函数尝试新的反应,并且我正在尝试使用 setstate 但它不起作用,如果我直接使用它就说未定义,或者如果我从中删除this.
它就说它不是一个函数。
这是我的代码
import './App.css';
import React, { useState } from 'react';
function App() {
var [sum1, setSum1] = useState(0);
var [sum2, setSum2] = useState(0);
function handleClick(props) {
let buttonText = props.target.value;
let inputText = document.getElementById('result').value;
console.log(inputText + buttonText);
// let sum1 =setState;
// let sum2 =setState;
let total = inputText + buttonText;
if (total.charAt(0) === "0") {
} else {
document.getElementById("result").value = total;
}
if (props.target.value === "clear") {
document.getElementById("result").value = "";
}
if (props.target.value === "+") {
sum1 =document.getElementById("result").value.slice(0, -1);
setSum1({sum1:parseFloat(sum1)});
// alert(sum1);
document.getElementById("result").value = "";
alert(sum1);
}
if (props.target.value === "=") {
sum2 =document.getElementById("result").value.slice(0, -1);
setSum2({sum2:parseFloat(sum2)});
alert(sum1+sum2);
document.getElementById("result").innerText = sum1+sum2;
}
return total;
}
// function handleClick2(props) {
// document.getElementById("ans").innerHTML = eval(document.getElementById("result").value);
// }
return (
<div className="App">
<div id="ans" className="answer">Ans = 0</div>
<input type="text" onChange={handleClick} readOnly placeholder="0" className="inputid" id="result"/>
<hr/>
{/* calculator buttons below */}
{/* button + */}
<button className="opbut" value="+" onClick={handleClick}>+</button>
{/* button - */}
<button className="opbut" value="-" onClick={handleClick}>-</button>
{/* button × */}
<button className="opbut" value="*" onClick={handleClick}>×</button>
{/* button ÷ */}
<button className="opbut" value="/" onClick={handleClick}>÷</button>
{/* button 0 */}
<button className="calbut" value={0} onClick={handleClick}>0</button>
{/* button 1 */}
<button className="calbut" value={1} onClick={handleClick}>1</button>
{/* button 2 */}
<button className="calbut" value={2} onClick={handleClick}>2</button>
{/* button 3 */}
<button className="calbut" value={3} onClick={handleClick}>3</button>
{/* button 4 */}
<button className="calbut" value={4} onClick={handleClick}>4</button>
{/* button 5 */}
<button className="calbut" value={5} onClick={handleClick}>5</button>
{/* button 6 */}
<button className="calbut" value={6} onClick={handleClick}>6</button>
{/* button 7 */}
<button className="calbut" value={7} onClick={handleClick}>7</button>
{/* button 8 */}
<button className="calbut" value={8} onClick={handleClick}>8</button>
{/* button 9 */}
<button className="calbut" value={9} onClick={handleClick}>9</button>
{/* button ( */}
<button className="opbut" value="clear" onClick={handleClick}>C</button>
{/* button ) */}
<button className="opbut" value="Del" onClick={handleClick}>Del</button>
{/* button % */}
<button className="opbut" value="%" onClick={handleClick}>%</button>
{/* button y^ */}
<button className="opbut" value="^" onClick={handleClick}>y^</button>
{/* button total = */}
<button className="ansbut" value="=" onClick={handleClick}>=</button>
<hr/>
<div className="appName">A Simple React Calculator - Jayflo</div>
</div>
);
}
export default App;
上面是代码....当我尝试选择一个按钮时,选择了 onclick 运算符,设置状态并删除文本字段,然后接受另一个输入并操作两个输入...
解决方案
React 有它自己的基于元素(值)状态更新 DOM 的特殊方式,所以你不能使用原生元素方法。
在这个例子中,我们使用了三个钩子:useState
、useEffect
和useRef
。
useState
维护输入元素的状态、更新的计算以及传递到结果 div 的最终评估。
useEffect
确保在结果完成后我们清除calc
状态。
useRef
是 React 识别元素的方式。在这种情况下,单击每个按钮后,输入元素会再次聚焦。
这是一个基于您的代码的工作示例。
const { useRef, useEffect, useState } = React;
function Example() {
const [ input, setInput ] = useState('');
const [ calc, setCalc ] = useState('');
const [ result, setResult ] = useState('');
const inputRef = useRef();
// Update the input state when the value is changed
function handleInput(e) {
const { value } = e.target;
setInput(value);
}
// When the input is no longer focused (we've clicked
// a button) update the `calc` state
function handleBlur(e) {
const { value } = e.target;
setCalc(prev => prev + value);
}
// When we click a button, either update the `calc` state,
// or if we click "=", update the `result` state
function handleClick(e) {
const { nodeName, value } = e.target;
if (nodeName === 'BUTTON') {
setInput('');
inputRef.current.focus();
switch(value) {
case '=': {
setResult(eval(calc));
break;
}
case 'clear': {
setCalc('');
break;
}
default: {
setCalc(prev => prev + value);
break;
}
}
}
}
// When the result is updated, clear the `calc` state
useEffect(() => setCalc(''), [result]);
return (
<div class="container">
<div>
<div>{`Result: ${result}`}</div>
<div>{`Calc: ${calc}`}</div>
<input autoFocus ref={inputRef} onBlur={handleBlur} onChange={handleInput} type="text" value={input} />
</div>
<div class="buttons" onClick={handleClick}>
<button value="+">+</button>
<button value="-">-</button>
<button value="*">×</button>
<button value="/">÷</button>
<button value="0">0</button>
<button value="1">1</button>
<button value="2" >2</button>
<button value="3">3</button>
<button value="4">4</button>
<button value="5">5</button>
<button value="6">6</button>
<button value="7">7</button>
<button value="8">8</button>
<button value="9">9</button>
<button value="clear">C</button>
<button value="Del">Del</button>
<button value="%">%</button>
<button value="^">y^</button>
<button value="=">=</button>
</div>
</div>
);
};
// Render it
ReactDOM.render(
<Example />,
document.getElementById("react")
);
.container { display: flex; width: 200px; height: 200px; }
.buttons {
padding: 10px;
display: grid;
grid-template-columns: 1fr 1fr 1fr 1fr;
grid-gap: 2px;
}
button {
background: rgba(0, 0, 0, 0.5);
border: 1px solid #111;
padding: 10px;
color: #EEE;
border-radius: 5px;
font-size: 12px;
cursor: pointer;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.1/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.1/umd/react-dom.production.min.js"></script>
<div id="react"></div>
减少状态数量并且不必使用的替代方法,useRef
因为现在没有输入。
const { useRef, useEffect, useState } = React;
function Example() {
const [ calc, setCalc ] = useState('');
const [ result, setResult ] = useState('');
// When we click a button, either update the `calc` state,
// or if we click "=", update the `result` state
function handleClick(e) {
const { nodeName, value } = e.target;
if (nodeName === 'BUTTON') {
switch(value) {
case '=': {
setResult(eval(calc));
break;
}
case 'clear': {
setCalc('');
break;
}
default: {
setCalc(prev => prev + value);
break;
}
}
}
}
// When the result is updated, clear the `calc` state
useEffect(() => setCalc(''), [result]);
return (
<div class="container">
<div class="results">
<div>{`Result: ${result}`}</div>
<br />
<div>{`Calc: ${calc}`}</div>
</div>
<div class="buttons" onClick={handleClick}>
<button value="+">+</button>
<button value="-">-</button>
<button value="*">×</button>
<button value="/">÷</button>
<button value="0">0</button>
<button value="1">1</button>
<button value="2" >2</button>
<button value="3">3</button>
<button value="4">4</button>
<button value="5">5</button>
<button value="6">6</button>
<button value="7">7</button>
<button value="8">8</button>
<button value="9">9</button>
<button value="clear">C</button>
<button value="Del">Del</button>
<button value="%">%</button>
<button value="^">y^</button>
<button value="=">=</button>
</div>
</div>
);
};
// Render it
ReactDOM.render(
<Example />,
document.getElementById("react")
);
.container { display: flex; }
.results { width: 40px; }
.buttons {
margin-left: 6em;
padding: 10px;
display: grid;
grid-template-columns: 1fr 1fr 1fr 1fr;
grid-gap: 2px;
}
button {
background: rgba(0, 0, 0, 0.5);
border: 1px solid #111;
padding: 10px;
color: #EEE;
border-radius: 5px;
font-size: 12px;
cursor: pointer;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.1/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.1/umd/react-dom.production.min.js"></script>
<div id="react"></div>
推荐阅读
- r - 如何在 R 中创建一个“情节”变量(在每个组中运行一个“for循环”?)
- php - 使用正则表达式在数组中搜索多个字符串
- c# - 这两种序列化对象的通用方法有什么区别?
- c++ - 如何使用 C++ 模板实现 int、string、float 和 date 对象的数组?
- mysql - 为什么“像'A%'='A%';” 'A' 的搜索结果为假?
- python - 为什么 docker-compose 在 `docker-compose up` 上构建一个新镜像?
- javascript - 如何使用来自后端服务器的图像?
- opencv - 使用opencv确定LED颜色的一些想法是什么?
- r - 将数字从 R 保存到 excel
- r - 在R中的外部迭代后开始嵌套for循环