Photo by Pawel Czerwinski on Unsplash
How to Create a Custom File Upload Button in React with TypeScript
Table of contents
Creating a custom file upload button in React allows for more control over styling and user experience compared to the default file input. However, styling the default file input is often a hassle. No worries, though! This tutorial will guide you through creating a custom file upload button that easily integrates with a hidden file input element.
To access the full source code for this tutorial, visit the sandbox here. This article was originally posted here.
Customizing the Input
First, we need to set up our hidden file input and create a button to trigger it. By using React's useRef
hook, we can programmatically access and interact with the hidden input element. Here's how you can do it.
import { useRef, useState } from "react";
import "./styles.css";
export default function App() {
const inputRef = useRef<HTMLInputElement>(null);
function handleFileUpload(e: React.ChangeEvent<HTMLInputElement>) {
const files = e.target.files;
if (!files) return;
const file = files[0];
// use the file
console.log(file.name);
}
function handleButtonClick(e: React.MouseEvent<HTMLButtonElement>) {
e.preventDefault();
if (!inputRef || !inputRef.current) return;
inputRef.current.click();
}
return (
<form>
<button onClick={handleButtonClick}>Upload File</button>
<input ref={inputRef} type="file" hidden onChange={handleFileUpload} />
</form>
);
}
Instead of displaying the default file input, this approach hides the input element and uses a button to trigger the file selection dialog.
Let’s breakdown of how this works:
Hidden File Input and Custom Button
The input element of type
file
is hidden using thehidden
attribute.A button element is provided for the user to click, which will trigger the file selection dialog.
The ref (
inputRef
) is created usinguseRef
and attached to the hidden input element. This allows us to programmatically interact with the input element.
Handling Button Click.
The
handleButtonClick
function is triggered when the button is clicked.e.preventDefault()
is called to prevent the form from submitting, which would otherwise cause a page reload.The function then checks if the
inputRef
exists. If so, it programmatically clicks the input element by callinginputRef.current.click
()
. This action opens the file selection dialog.
Handling File Selection:
When the user selects a file, the
handleFileUpload
function is triggered by theonChange
event of the input element.Inside
handleFileUpload
, we check if any files were selected by the user. If so, we access the first file from thefiles
list (files[0]
).
Typically, within handleFileUpload
, additional logic would be implemented to handle the selected file. This could include storing the file in state, uploading it to a server, or displaying it in the UI.
Styling the Button
To further improve the UI, we can style the button. You can add these styles to a styles.css
file and then import it in your component as shown in the earlier snippet.
button {
background-color: rgb(223, 223, 223);
border: none;
border-radius: 50px;
padding: 10px 15px;
font-weight: 600;
cursor: pointer;
}
Okay, that’s it. 🚀 By leveraging React's useRef
hook and event handling, we can trigger a file upload dialog with a styled button instead of the default file input.