bigbluebutton-Github/bigbluebutton-html5/imports/ui/components/poll/dragAndDrop/component.jsx

123 lines
3.1 KiB
React
Raw Normal View History

import React, { Component } from 'react';
import PropTypes from 'prop-types';
2021-11-04 19:30:49 +08:00
import Styled from './styles';
// src: https://medium.com/@650egor/simple-drag-and-drop-file-upload-in-react-2cb409d88929
class DragAndDrop extends Component {
static handleDrag(e) {
e.preventDefault();
e.stopPropagation();
}
constructor(props) {
super(props);
this.state = {
drag: false,
pollValueText: '',
};
this.dropRef = React.createRef();
}
componentDidMount() {
this.dragCounter = 0;
const div = this.dropRef.current;
div.addEventListener('dragenter', e => this.handleDragIn(e));
div.addEventListener('dragleave', e => this.handleDragOut(e));
2021-02-08 20:18:50 +08:00
div.addEventListener('dragover', e => DragAndDrop.handleDrag(e));
div.addEventListener('drop', e => this.handleDrop(e));
}
componentWillUnmount() {
const div = this.dropRef.current;
div.removeEventListener('dragenter', e => this.handleDragIn(e));
div.removeEventListener('dragleave', e => this.handleDragOut(e));
2021-02-08 20:18:50 +08:00
div.removeEventListener('dragover', e => DragAndDrop.handleDrag(e));
div.removeEventListener('drop', e => this.handleDrop(e));
}
setPollValues() {
const { pollValueText } = this.state;
const { handlePollValuesText } = this.props;
if (pollValueText) {
handlePollValuesText(pollValueText);
}
}
setPollValuesFromFile(file) {
const reader = new FileReader();
reader.onload = async (e) => {
const text = e.target.result;
this.setPollValueText(text);
this.setPollValues();
};
reader.readAsText(file);
}
setPollValueText(pollText) {
const { MAX_INPUT_CHARS } = this.props;
const arr = pollText.split('\n');
const text = arr.map(line => (line.length > MAX_INPUT_CHARS ? line.substring(0, MAX_INPUT_CHARS) : line)).join('\n');
this.setState({ pollValueText: text });
}
handleTextInput(e) {
this.setPollValueText(e.target.value);
}
handleDragIn(e) {
2021-02-08 20:18:50 +08:00
DragAndDrop.handleDrag(e);
this.dragCounter += 1;
if (e.dataTransfer.items && e.dataTransfer.items.length > 0) {
this.setState({ drag: true });
}
}
handleDragOut(e) {
2021-02-08 20:18:50 +08:00
DragAndDrop.handleDrag(e);
this.dragCounter -= 1;
if (this.dragCounter > 0) return;
this.setState({ drag: false });
}
handleDrop(e) {
2021-02-08 20:18:50 +08:00
DragAndDrop.handleDrag(e);
this.setState({ drag: false });
if (e.dataTransfer.files && e.dataTransfer.files.length > 0) {
this.setPollValuesFromFile(e.dataTransfer.files[0]);
this.dragCounter = 0;
}
}
getCleanProps() {
const props = Object.assign({}, this.props);
const propsToDelete = ['MAX_INPUT_CHARS', 'handlePollValuesText'];
propsToDelete.forEach((prop) => {
delete props[prop];
});
return props;
}
render() {
const { drag } = this.state;
return (
<Styled.DndTextArea
ref={this.dropRef}
active={drag}
{...this.getCleanProps()}
/>
);
}
}
DragAndDrop.propTypes = {
MAX_INPUT_CHARS: PropTypes.number.isRequired,
handlePollValuesText: PropTypes.func.isRequired,
};
export default DragAndDrop;