在我的React组件中,我有一个按钮,用于在单击时通过AJAX发送一些数据。我只需要第一次发生,即在第一次使用后禁用按钮。
我是如何尝试这样做的:
var UploadArea = React.createClass({
getInitialState() {
return {
showUploadButton: true
};
},
disableUploadButton(callback) {
this.setState({ showUploadButton: false }, callback);
},
// This was simpler before I started trying everything I could think of
onClickUploadFile() {
if (!this.state.showUploadButton) {
return;
}
this.disableUploadButton(function() {
$.ajax({
[...]
});
});
},
render() {
var uploadButton;
if (this.state.showUploadButton) {
uploadButton = (
<button onClick={this.onClickUploadFile}>Send</button>
);
}
return (
<div>
{uploadButton}
</div>
);
}
});
我认为发生的是状态变量showUploadButton
没有立即更新,React文档说的是预期的。
我如何强制按钮被禁用或在点击它的瞬间全部消失?
答案 0 :(得分:28)
您可以执行的操作是在单击按钮后将其禁用并将其保留在页面中(不是可单击的元素)。
要实现这一点,您必须为按钮元素添加引用
<button ref="btn" onClick={this.onClickUploadFile}>Send</button>
然后在onClickUploadFile函数上禁用按钮
this.refs.btn.setAttribute("disabled", "disabled");
然后,您可以相应地设置禁用按钮的样式,以便通过
向用户提供一些反馈.btn:disabled{ /* styles go here */}
如果需要,请务必使用
重新启用它this.refs.btn.removeAttribute("disabled");
更新:在React中处理引用的首选方法是使用函数而不是字符串。
<button
ref={btn => { this.btn = btn; }}
onClick={this.onClickUploadFile}
>Send</button>
this.btn.setAttribute("disabled", "disabled");
this.btn.removeAttribute("disabled");
这是使用您提供的代码的一个小例子 https://jsfiddle.net/69z2wepo/30824/
答案 1 :(得分:19)
解决方案是在进入处理程序后立即检查状态。 React保证在浏览器事件边界刷新交互事件(例如click)中的setState。参考:https://github.com/facebook/react/issues/11171#issuecomment-357945371
// In constructor
this.state = {
disabled : false
};
// Handler for on click
handleClick = (event) => {
if (this.state.disabled) {
return;
}
this.setState({disabled: true});
// Send
}
// In render
<button onClick={this.handleClick} disabled={this.state.disabled} ...>
{this.state.disabled ? 'Sending...' : 'Send'}
<button>
答案 2 :(得分:14)
经过测试:http://codepen.io/zvona/pen/KVbVPQ
class UploadArea extends React.Component {
constructor(props) {
super(props)
this.state = {
isButtonDisabled: false
}
}
uploadFile() {
// first set the isButtonDisabled to true
this.setState({
isButtonDisabled: true
});
// then do your thing
}
render() {
return (
<button
type='submit'
onClick={() => this.uploadFile()}
disabled={this.state.isButtonDisabled}>
Upload
</button>
)
}
}
ReactDOM.render(<UploadArea />, document.body);
答案 3 :(得分:2)
您可以尝试使用React Hooks来设置Component State。
import React, { setState } from 'react';
const Button = () => {
const [double, setDouble] = setState(false);
return (
<button
disabled={double}
onClick={() => {
// doSomething();
setDouble(true);
}}
/>
);
};
export default Button;
确保使用^16.7.0-alpha.x
和react
的{{1}}版。
希望这对您有帮助!
答案 4 :(得分:0)
如果需要,只需阻止提交即可。
如何使用lodash.js debounce
将突发事件(如击键)分组为一个事件。
https://lodash.com/docs/4.17.11#debounce
<Button accessible={true}
onPress={_.debounce(async () => {
await this.props._selectUserTickets(this.props._accountId)
}, 1000)}
></Button>
答案 5 :(得分:0)
const once = (f, g) => {
let done = false;
return (...args) => {
if (!done) {
done = true;
f(...args);
} else {
g(...args);
}
};
};
const exampleMethod = () => console.log("exampleMethod executed for the first time");
const errorMethod = () => console.log("exampleMethod can be executed only once")
let onlyOnce = once(exampleMethod, errorMethod);
onlyOnce();
onlyOnce();
输出
exampleMethod executed for the first time
exampleMethod can be executed only once
答案 6 :(得分:0)
使用event.target
可以禁用单击的按钮。
创建并调用函数onClick
时,请使用箭头函数。不要忘记在参数中传递事件。
看到我的codePen
代码如下:
class Buttons extends React.Component{
constructor(props){
super(props)
this.buttons = ['A','B','C','D']
}
disableOnclick = (e) =>{
e.target.disabled = true
}
render(){
return(
<div>
{this.buttons.map((btn,index) => (
<button type='button'
key={index}
onClick={(e)=>this.disableOnclick(e)}
>{btn}</button>
))}
</div>
)}
}
ReactDOM.render(<Buttons />, document.body);
答案 7 :(得分:0)
您可以在onClick回调和setAttribute
中获得元素引用,例如:
<Button
onClick={(e) => {
e.target.setAttribute("disabled", true);
this.handler();
}}
>
Submit
</Button>
答案 8 :(得分:0)
保持简单和内联:
<button type="submit"
onClick={event => event.currentTarget.disabled = true}>
save
</button>
但是!当表单校准失败时,这也将禁用该按钮!所以您将无法重新提交。
在这种情况下,setter 更好。
此修复此设置禁用 onSubmit
形式:
// state variable if the form is currently submitting
const [submitting, setSubmitting] = useState(false);
// ...
return (
<form onSubmit={e => {
setSubmitting(true); // create a method to modify the element
}}>
<SubmitButton showLoading={submitting}>save</SubmitButton>
</form>
);
按钮看起来像这样:
import {ReactComponent as IconCog} from '../../img/icon/cog.svg';
import {useEffect, useRef} from "react";
export const SubmitButton = ({children, showLoading}) => {
const submitButton = useRef();
useEffect(() => {
if (showLoading) {
submitButton.current.disabled = true;
} else {
submitButton.current.removeAttribute("disabled");
}
}, [showLoading]);
return (
<button type="submit"
ref={submitButton}>
<main>
<span>{children}</span>
</main>
</button>
);
};