` to `dropRef`.
@@ -743,79 +744,67 @@ Finally, bind the `ref` of the created `
` to `dropRef`.
```
```jsx
-class FileDrop extends React.Component {
- constructor(props) {
- super(props);
- this.dropRef = React.createRef();
- this.state = {
- drag: false,
- filename: ''
- }
- this.handleDrag = this.handleDrag.bind(this);
- this.handleDragIn = this.handleDragIn.bind(this);
- this.handleDragOut = this.handleDragOut.bind(this);
- this.handleDrop = this.handleDrop.bind(this);
- }
+function FileDrop(props) {
+ const [drag, setDrag] = React.useState(false);
+ const [filename, setFilename] = React.useState('');
+ let dropRef = React.createRef();
+ let dragCounter = 0;
- handleDrag(e) {
+ const handleDrag = e => {
e.preventDefault();
e.stopPropagation();
- }
+ };
- handleDragIn(e) {
+ const handleDragIn = e => {
e.preventDefault();
e.stopPropagation();
- this.dragCounter++;
- if (e.dataTransfer.items && e.dataTransfer.items.length > 0)
- this.setState({ drag: true });
- }
+ dragCounter++;
+ if (e.dataTransfer.items && e.dataTransfer.items.length > 0) setDrag(true);
+ };
- handleDragOut(e) {
+ const handleDragOut = e => {
e.preventDefault();
e.stopPropagation();
- this.dragCounter--;
- if (this.dragCounter === 0)
- this.setState({ drag: false });
- }
+ dragCounter--;
+ if (dragCounter === 0) setDrag(false);
+ };
- handleDrop(e) {
+ const handleDrop = e => {
e.preventDefault();
e.stopPropagation();
- this.setState({ drag: false });
+ setDrag(false);
if (e.dataTransfer.files && e.dataTransfer.files.length > 0) {
- this.props.handleDrop(e.dataTransfer.files[0]);
- this.setState({ filename : e.dataTransfer.files[0].name});
+ props.handleDrop(e.dataTransfer.files[0]);
+ setFilename(e.dataTransfer.files[0].name);
e.dataTransfer.clearData();
- this.dragCounter = 0;
+ dragCounter = 0;
}
- }
+ };
- componentDidMount() {
- let div = this.dropRef.current;
- div.addEventListener('dragenter', this.handleDragIn);
- div.addEventListener('dragleave', this.handleDragOut);
- div.addEventListener('dragover', this.handleDrag);
- div.addEventListener('drop', this.handleDrop);
- }
+ React.useEffect(() => {
+ let div = dropRef.current;
+ div.addEventListener("dragenter", handleDragIn);
+ div.addEventListener("dragleave", handleDragOut);
+ div.addEventListener("dragover", handleDrag);
+ div.addEventListener("drop", handleDrop);
+ return function cleanup() {
+ div.removeEventListener("dragenter", handleDragIn);
+ div.removeEventListener("dragleave", handleDragOut);
+ div.removeEventListener("dragover", handleDrag);
+ div.removeEventListener("drop", handleDrop);
+ };
+ });
- componentWillUnmount() {
- let div = this.dropRef.current;
- div.removeEventListener('dragenter', this.handleDragIn);
- div.removeEventListener('dragleave', this.handleDragOut);
- div.removeEventListener('dragover', this.handleDrag);
- div.removeEventListener('drop', this.handleDrop);
- }
-
- render() {
- return (
-
- {this.state.filename && !this.state.drag ?
-
{this.state.filename}
- :
Drop files here!
- }
-
- )
- }
+ return (
+
+ {filename && !drag ?
{filename}
:
Drop files here!
}
+
+ );
}
```
diff --git a/data/snippet_data.json b/data/snippet_data.json
index 42be599d0..fdc493f20 100644
--- a/data/snippet_data.json
+++ b/data/snippet_data.json
@@ -82,10 +82,10 @@
{
"name": "FileDrop.md",
"title": "FileDrop",
- "text": "Renders a file drag and drop component for a single file.\n\nCreate a ref called `dropRef` for this component.\nInitialize `state.drag` and `state.filename` to `false` and `''` respectively.\nThe variables `dragCounter` and `state.drag` are used to determine if a file is being dragged, while `state.filename` is used to store the dropped file's name.\nCreate the `handleDrag`, `handleDragIn`, `handleDragOut` and `handleDrop` methods to handle drag and drop functionality, bind them to the component's context.\nEach of the methods will handle a specific event, the listeners for which are created and removed in `componentDidMount` and `componentWillUnmount` respectively.\n`handleDrag` prevents the browser from opening the dragged file, `handleDragIn` and `handleDragOut` handle the dragged file entering and exiting the component, while `handleDrop` handles the file being dropped and passes it to `this.props.handleDrop`.\nIn the `render()` method, create an appropriately styled `
` and use `state.drag` and `state.filename` to determine its contents and style. \nFinally, bind the `ref` of the created `
` to `dropRef`.\n\n\n",
+ "text": "Renders a file drag and drop component for a single file.\n\nCreate a ref called `dropRef` for this component.\nUse the `React.useState()` hook to create the `drag` and `filename` variables, initialized to `false` and `''` respectively.\nThe variables `dragCounter` and `drag` are used to determine if a file is being dragged, while `filename` is used to store the dropped file's name.\n\nCreate the `handleDrag`, `handleDragIn`, `handleDragOut` and `handleDrop` methods to handle drag and drop functionality, bind them to the component's context.\nEach of the methods will handle a specific event, the listeners for which are created and removed in the `React.useEffect()` hook and its attached `cleanup()` method.\n`handleDrag` prevents the browser from opening the dragged file, `handleDragIn` and `handleDragOut` handle the dragged file entering and exiting the component, while `handleDrop` handles the file being dropped and passes it to `props.handleDrop`.\nReturn an appropriately styled `
` and use `drag` and `filename` to determine its contents and style. \nFinally, bind the `ref` of the created `
` to `dropRef`.\n\n\n",
"codeBlocks": [
"```css\n.filedrop {\n min-height: 120px;\n border: 3px solid #D3D3D3;\n text-align: center;\n font-size: 24px;\n padding: 32px;\n border-radius: 4px;\n}\n\n.filedrop.drag {\n border: 3px dashed #1E90FF;\n}\n\n.filedrop.ready {\n border: 3px solid #32CD32;\n}\n```",
- "```jsx\nclass FileDrop extends React.Component {\n constructor(props) {\n super(props);\n this.dropRef = React.createRef();\n this.state = {\n drag: false,\n filename: ''\n }\n this.handleDrag = this.handleDrag.bind(this);\n this.handleDragIn = this.handleDragIn.bind(this);\n this.handleDragOut = this.handleDragOut.bind(this);\n this.handleDrop = this.handleDrop.bind(this);\n }\n\n handleDrag(e) {\n e.preventDefault();\n e.stopPropagation();\n }\n\n handleDragIn(e) {\n e.preventDefault();\n e.stopPropagation();\n this.dragCounter++;\n if (e.dataTransfer.items && e.dataTransfer.items.length > 0) \n this.setState({ drag: true });\n }\n\n handleDragOut(e) {\n e.preventDefault();\n e.stopPropagation();\n this.dragCounter--;\n if (this.dragCounter === 0) \n this.setState({ drag: false });\n }\n\n handleDrop(e) {\n e.preventDefault();\n e.stopPropagation();\n this.setState({ drag: false });\n if (e.dataTransfer.files && e.dataTransfer.files.length > 0) {\n this.props.handleDrop(e.dataTransfer.files[0]);\n this.setState({ filename : e.dataTransfer.files[0].name});\n e.dataTransfer.clearData();\n this.dragCounter = 0;\n }\n }\n\n componentDidMount() {\n let div = this.dropRef.current;\n div.addEventListener('dragenter', this.handleDragIn);\n div.addEventListener('dragleave', this.handleDragOut);\n div.addEventListener('dragover', this.handleDrag);\n div.addEventListener('drop', this.handleDrop);\n }\n\n componentWillUnmount() {\n let div = this.dropRef.current;\n div.removeEventListener('dragenter', this.handleDragIn);\n div.removeEventListener('dragleave', this.handleDragOut);\n div.removeEventListener('dragover', this.handleDrag);\n div.removeEventListener('drop', this.handleDrop);\n }\n\n render() {\n return (\n
\n {this.state.filename && !this.state.drag ? \n
{this.state.filename}
\n :
Drop files here!
\n }\n
\n )\n }\n}\n```",
+ "```jsx\nfunction FileDrop(props) {\n const [drag, setDrag] = React.useState(false);\n const [filename, setFilename] = React.useState('');\n let dropRef = React.createRef();\n let dragCounter = 0;\n\n const handleDrag = e => {\n e.preventDefault();\n e.stopPropagation();\n };\n\n const handleDragIn = e => {\n e.preventDefault();\n e.stopPropagation();\n dragCounter++;\n if (e.dataTransfer.items && e.dataTransfer.items.length > 0) setDrag(true);\n };\n\n const handleDragOut = e => {\n e.preventDefault();\n e.stopPropagation();\n dragCounter--;\n if (dragCounter === 0) setDrag(false);\n };\n\n const handleDrop = e => {\n e.preventDefault();\n e.stopPropagation();\n setDrag(false);\n if (e.dataTransfer.files && e.dataTransfer.files.length > 0) {\n props.handleDrop(e.dataTransfer.files[0]);\n setFilename(e.dataTransfer.files[0].name);\n e.dataTransfer.clearData();\n dragCounter = 0;\n }\n };\n\n React.useEffect(() => {\n let div = dropRef.current;\n div.addEventListener(\"dragenter\", handleDragIn);\n div.addEventListener(\"dragleave\", handleDragOut);\n div.addEventListener(\"dragover\", handleDrag);\n div.addEventListener(\"drop\", handleDrop);\n return function cleanup() {\n div.removeEventListener(\"dragenter\", handleDragIn);\n div.removeEventListener(\"dragleave\", handleDragOut);\n div.removeEventListener(\"dragover\", handleDrag);\n div.removeEventListener(\"drop\", handleDrop);\n };\n });\n\n return (\n
\n {filename && !drag ?
{filename}
:
Drop files here!
}\n
\n );\n}\n```",
"```jsx\nReactDOM.render(
, document.getElementById('root'));\n```"
],
"expertise": 2,
diff --git a/snippets/FileDrop.md b/snippets/FileDrop.md
index c64075fee..7fefbb103 100644
--- a/snippets/FileDrop.md
+++ b/snippets/FileDrop.md
@@ -3,12 +3,13 @@
Renders a file drag and drop component for a single file.
Create a ref called `dropRef` for this component.
-Initialize `state.drag` and `state.filename` to `false` and `''` respectively.
-The variables `dragCounter` and `state.drag` are used to determine if a file is being dragged, while `state.filename` is used to store the dropped file's name.
+Use the `React.useState()` hook to create the `drag` and `filename` variables, initialized to `false` and `''` respectively.
+The variables `dragCounter` and `drag` are used to determine if a file is being dragged, while `filename` is used to store the dropped file's name.
+
Create the `handleDrag`, `handleDragIn`, `handleDragOut` and `handleDrop` methods to handle drag and drop functionality, bind them to the component's context.
-Each of the methods will handle a specific event, the listeners for which are created and removed in `componentDidMount` and `componentWillUnmount` respectively.
-`handleDrag` prevents the browser from opening the dragged file, `handleDragIn` and `handleDragOut` handle the dragged file entering and exiting the component, while `handleDrop` handles the file being dropped and passes it to `this.props.handleDrop`.
-In the `render()` method, create an appropriately styled `` and use `state.drag` and `state.filename` to determine its contents and style.
+Each of the methods will handle a specific event, the listeners for which are created and removed in the `React.useEffect()` hook and its attached `cleanup()` method.
+`handleDrag` prevents the browser from opening the dragged file, `handleDragIn` and `handleDragOut` handle the dragged file entering and exiting the component, while `handleDrop` handles the file being dropped and passes it to `props.handleDrop`.
+Return an appropriately styled `
` and use `drag` and `filename` to determine its contents and style.
Finally, bind the `ref` of the created `
` to `dropRef`.
@@ -32,79 +33,67 @@ Finally, bind the `ref` of the created `
` to `dropRef`.
```
```jsx
-class FileDrop extends React.Component {
- constructor(props) {
- super(props);
- this.dropRef = React.createRef();
- this.state = {
- drag: false,
- filename: ''
- }
- this.handleDrag = this.handleDrag.bind(this);
- this.handleDragIn = this.handleDragIn.bind(this);
- this.handleDragOut = this.handleDragOut.bind(this);
- this.handleDrop = this.handleDrop.bind(this);
- }
+function FileDrop(props) {
+ const [drag, setDrag] = React.useState(false);
+ const [filename, setFilename] = React.useState('');
+ let dropRef = React.createRef();
+ let dragCounter = 0;
- handleDrag(e) {
+ const handleDrag = e => {
e.preventDefault();
e.stopPropagation();
- }
+ };
- handleDragIn(e) {
+ const handleDragIn = e => {
e.preventDefault();
e.stopPropagation();
- this.dragCounter++;
- if (e.dataTransfer.items && e.dataTransfer.items.length > 0)
- this.setState({ drag: true });
- }
+ dragCounter++;
+ if (e.dataTransfer.items && e.dataTransfer.items.length > 0) setDrag(true);
+ };
- handleDragOut(e) {
+ const handleDragOut = e => {
e.preventDefault();
e.stopPropagation();
- this.dragCounter--;
- if (this.dragCounter === 0)
- this.setState({ drag: false });
- }
+ dragCounter--;
+ if (dragCounter === 0) setDrag(false);
+ };
- handleDrop(e) {
+ const handleDrop = e => {
e.preventDefault();
e.stopPropagation();
- this.setState({ drag: false });
+ setDrag(false);
if (e.dataTransfer.files && e.dataTransfer.files.length > 0) {
- this.props.handleDrop(e.dataTransfer.files[0]);
- this.setState({ filename : e.dataTransfer.files[0].name});
+ props.handleDrop(e.dataTransfer.files[0]);
+ setFilename(e.dataTransfer.files[0].name);
e.dataTransfer.clearData();
- this.dragCounter = 0;
+ dragCounter = 0;
}
- }
+ };
- componentDidMount() {
- let div = this.dropRef.current;
- div.addEventListener('dragenter', this.handleDragIn);
- div.addEventListener('dragleave', this.handleDragOut);
- div.addEventListener('dragover', this.handleDrag);
- div.addEventListener('drop', this.handleDrop);
- }
+ React.useEffect(() => {
+ let div = dropRef.current;
+ div.addEventListener("dragenter", handleDragIn);
+ div.addEventListener("dragleave", handleDragOut);
+ div.addEventListener("dragover", handleDrag);
+ div.addEventListener("drop", handleDrop);
+ return function cleanup() {
+ div.removeEventListener("dragenter", handleDragIn);
+ div.removeEventListener("dragleave", handleDragOut);
+ div.removeEventListener("dragover", handleDrag);
+ div.removeEventListener("drop", handleDrop);
+ };
+ });
- componentWillUnmount() {
- let div = this.dropRef.current;
- div.removeEventListener('dragenter', this.handleDragIn);
- div.removeEventListener('dragleave', this.handleDragOut);
- div.removeEventListener('dragover', this.handleDrag);
- div.removeEventListener('drop', this.handleDrop);
- }
-
- render() {
- return (
-
- {this.state.filename && !this.state.drag ?
-
{this.state.filename}
- :
Drop files here!
- }
-
- )
- }
+ return (
+
+ {filename && !drag ?
{filename}
:
Drop files here!
}
+
+ );
}
```