I'm currently using the react-dropzone plugin and encountered a use case that's not exactly described in the documentations.
Basically, I have the following elements:
on click
on click
The problem I'm having right now is to stop the native file picker from showing up when the inner button is clicked.
To illustrate my example, you can paste this code into the View Code section.
import React from 'react';
import {useDropzone} from 'react-dropzone';
function Dropzone(props) {
const {getRootProps, getInputProps, open, acceptedFiles} = useDropzone({
// Disable click and keydown behavior
noKeyboard: true
});
const files = acceptedFiles.map(file => (
<li key={file.path}>
{file.path} - {file.size} bytes
</li>
));
return (
<div className="container">
<div {...getRootProps({className: 'dropzone'})}>
<input {...getInputProps()} />
<p>Drag 'n' drop some files here</p>
<InnerButton />
</div>
<aside>
<h4>Files</h4>
<ul>{files}</ul>
</aside>
</div>
);
}
function InnerButton(props) {
const { getRootProps } = useDropzone({ noClick: true }); // doesn't stop the parent's input file picker
return (
<button
{...getRootProps({
onClick: (event) => event.stopPropagation(), // this is bad for many reasons
})}
type="button">
This button should not open the file picker
</button>
);
}
<Dropzone />
I figured that using event.stopPropagation()
is one way but I've read that it should be avoided for many reasons (source 1, source 2). I tried using noClick: true
in the inner button but it doesn't work - most likely because it can't stop the parent's <input>
tag.
Is there another approach that I should try, other than using stopPropagation
?
I got an answer on GitHub, posting it here in case anyone else encounters the same question.
There's no way around it. You have to use
stopPropagation()
to stop the event from bubbling up the DOM. Your other option is to usenoClick
on the parent as well.
noClick
only disables opening the file selector when clicking on the dropzone node. It does not prevent the event from bubbling.The only thing we can do is to provide a
noClickBubbling
option that callsstopPropagation()
, but the user can already do that.