立即响应 setState 并重新渲染



我是新手反应,只是尝试通过输入标签上传文件,因为文件可能很大,所以在上传时我想显示反馈,即系统当前正在 UI 中使用一些文本,例如"上传....."。为此,我正在做:

import PropTypes from 'prop-types';
import React from 'react';
import createReactClass from 'create-react-class';
import i18n from 'ar-i18n';
import _ from 'lodash';
const DragAndDropContainer = createReactClass({
propTypes: {
onDropFile: PropTypes.func.isRequired,
},
getInitialState () {
return { currentFile: null, uploadState: false };
},
render () {
const dragAndDropId = _.uniqueId('drag-and-drop-file-');
return (
<div className='drag-and-drop-container'>
{
this.state.currentFile && (
<p className='drag-and-drop-current-file'>
<strong>{ this.state.currentFile.name }</strong>
</p>
)
}
{
!this.state.currentFile && this.state.uploadState && (
<p className='drag-and-drop-current-file'>
<strong>{i18n.gettext('Uploading......')}</strong>
</p>
)
}
<div
className='drag-and-drop-area'
onDragEnter={e => e.preventDefault()}
onDrop={this.onDrop}
onDragOver={e => e.preventDefault()}
>
<img src={assetUrl('upload.png')} />
<input
id={dragAndDropId}
className='drag-and-drop-file'
name='files[]'
type='file'
onChange={this.onFileSelected}
/>
<p>
<label className='drag-and-drop-label' htmlFor={dragAndDropId}>
<strong>{i18n.gettext('Choose a file or drop it here')}</strong>
</label>
</p>
</div>
</div>
);
},
onDrop (e) {
this.onFileSelected(e);
e.preventDefault();
},
onFileSelected (e) {
this.setState({ uploadState: true }, function () {console.log('updated uplodastate---', this.state.uploadState)});
const file = e.dataTransfer ? e.dataTransfer.files[0] : e.currentTarget.files[0];
this.setState({ currentFile: file });
this.props.onDropFile(file);
// prevents control from "caching" files with same name in consecutive uploads
e.currentTarget.value = '';
},

});
export default DragAndDropContainer;

由于对setState的异步调用,条件!this.state.currentFile && this.state.uploadState永远不会为真。

如何在const file = e.dataTransfer ? e.dataTransfer.files[0] : e.currentTarget.files[0]之前设置this.state.uploadState; 以允许它调用 render。

可以将状态更新放在回调中currentFile以满足条件。

this.setState({
uploadState: true
}, ()=> {
console.log('updated uplodastate---', this.state.uploadState);
const file = e.dataTransfer ? e.dataTransfer.files[0] : e.currentTarget.files[0];
this.setState({
currentFile: file
});
});

您需要在 setState 之后设置const file = e.dataTransfer ? e.dataTransfer.files[0] : e.currentTarget.files[0],一旦状态更新,它将自动重新渲染组件。

这称为回调函数。

onFileSelected (e) {
this.setState({ uploadState: true }, function () {
const file = e.dataTransfer ? e.dataTransfer.files[0] : e.currentTarget.files[0];
this.setState({ currentFile: file });
});
this.props.onDropFile(file);
e.currentTarget.value = '';
}

最新更新