Уже задавал похожий вопрос, но понимания не пришло. Пишу калькулятор и возникает проблема с тем, что стейт обновляется с запозданием в шаг. Подскажите, в чем проблема. Вывожу все данные стейта в консоль, но при этом в консоли отображается все с запозданием в шаг.
function Button(props) {
return (
<button onClick={props.onClick}>
{props.value}
</button>
)
}
function Input(props) {
return (
<input type="text" value={props.value}/>
)
}
export default class App extends React.Component {
constructor() {
super();
this.state = {
valueInput: 0,
firstOperand: '',
secondOperand: '',
operator: '',
result: '',
}
this.renderButton = this.renderButton.bind(this);
this.refreshInput = this.refreshInput.bind(this);
}
refreshInput(event) {
const target = event.target.innerHTML;
// if result exists
if(this.state.result) {
let reset = '',
first = target;
this.setState({
valueInput:first,
firstOperand: first,
secondOperand: reset,
result: reset,
operator: reset,
})
}
//if you clicked a number
if(!isNaN(parseFloat(target)) && isFinite(target)) {
if(this.state.result) {
let first = target,
reset = '';
this.setState({
firstOperand: first,
secondOperand: reset,
operator: reset,
result: reset,
})
}
if(!this.state.secondOperand && !this.state.operator) {
let number = parseFloat(this.state.firstOperand + target);
this.setState({
firstOperand: number,
valueInput: number,
})
} else {
let number = parseFloat(this.state.secondOperand + target);
this.setState({
secondOperand: number,
valueInput: number,
})
}
}
//if you clicked a point
if(target === '.') {
if(!this.state.firstOperand) {
let number = '0.';
this.setState({
firstOperand: number,
valueInput: number
})
//is integer
} else if (this.state.firstOperand && (this.state.firstOperand ^ 0) === this.state.firstOperand) {
let result = this.state.firstOperand + '.';
this.setState({
firstOperand: result,
valueInput: result,
})
}
if (this.state.secondOperand && (this.state.secondOperand ^ 0) === this.state.secondOperand) {
let result = this.state.secondOperand + '.';
this.setState({
secondOperand: result,
valueInput: result,
})
}
}
//if you clicked an operator
if(target === '*' || target === '/' || target === '+' || target === '-') {
if(!this.state.firstOperand) {
alert('Please, state 1st operand');
} else {
let operatorType = target;
this.setState({
valueInput: operatorType,
operator: operatorType,
});
}
if(this.state.result) {
let first = this.state.result,
operator = target,
reset = '';
this.setState({
firstOperand: first,
operator: operator,
secondOperand: reset,
result: reset,
})
}
}
//if you clicked C button
if(target === 'C') {
if(!this.state.firstOperand && !this.state.secondOperand) {
const result = 0;
this.setState({
result: result,
valueInput: result,
})
} else if(this.state.firstOperand && !this.state.secondOperand) {
let first = this.state.firstOperand +'';
let result = first.substring(0, first.length-1);
this.setState({
firstOperand: result,
valueInput: result,
})
}
}
//if you clicked an equal
if(target === '=' && this.state.firstOperand && this.state.secondOperand) {
let mainResult = 0,
fixedResult;
switch(this.state.operator) {
case '*':
mainResult=parseFloat(this.state.firstOperand)*parseFloat(this.state.secondOperand);
break;
case '/':
mainResult=parseFloat(this.state.firstOperand)/parseFloat(this.state.secondOperand);
break;
case '+':
mainResult=parseFloat(this.state.firstOperand)+parseFloat(this.state.secondOperand);
break;
case '-':
mainResult=parseFloat(this.state.firstOperand)-parseFloat(this.state.secondOperand);
break;
default: alert('Unknown result');
}
fixedResult = mainResult.toFixed(2);
this.setState({
result: fixedResult,
valueInput: fixedResult,
})
}
console.log('result: '+this.state.result,
'first: ' + this.state.firstOperand,
'second: ' + this.state.secondOperand,
'operator: ' + this.state.operator);
}
renderButton(name) {
return (
<Button className='button_calculator'
value={name}
onClick={this.refreshInput}
/>
)
}
render() {
return (
<div className="calculator">
<div className="row">
<Input value={this.state.valueInput}/>
</div>
<div className="row">
{this.renderButton(1)}
{this.renderButton(2)}
{this.renderButton(3)}
{this.renderButton('*')}
</div>
<div className="row">
{this.renderButton(4)}
{this.renderButton(5)}
{this.renderButton(6)}
{this.renderButton('/')}
</div>
<div className="row">
{this.renderButton(7)}
{this.renderButton(8)}
{this.renderButton(9)}
{this.renderButton('+')}
</div>
<div className="row">
{this.renderButton('C')}
{this.renderButton(0)}
{this.renderButton('.')}
{this.renderButton('-')}
</div>
<div className="row">
{this.renderButton('=')}
</div>
</div>
)
}
}