Last Updated: December 18, 2022
·
82.42K
· supershabam

styling html file input

<input type="file" class="custom-style" />

If you think making this input tag look pretty is simply a matter of some CSS, think again.

problem

The file input element is ugly and every browser displays it a little bit differently. Unfortunately, CSS can only style some things about this element, and I usually want more.

The best solution to achieve a custom style is to create a new element (a button perhaps) that when clicked triggers the click event on this input element.

That works in most every browser.

IE FTW

IE does not appreciate fake click events on file input elements. You will get a security error if the user did not actually click on the file input element.

Grrrr

solution

Invisibly hover the actual file input element over the pretty styled button.

<div class="file-input-wrapper">
  <button class="btn-file-input">Upload File</button>
  <input type="file" name="file" />
</div>
<style>
  .file-input-wrapper {
    width: 200px;
    height: 40px;
    overflow: hidden;
    position: relative;
  }
  .file-input-wrapper > input[type="file"] {
    font-size: 200px;
    position: absolute;
    top: 0;
    right: 0;
    opacity: 0;
  }
  .file-input-wrapper > .btn-file-input {
    display: inline-block;
    width: 200px;
    height: 40px;
  }

You can play with this setup on JSFiddle
http://jsfiddle.net/supershabam/b3WXe/

Key parts:

  • wrapper sets width and height
  • wrapper overflow hidden
  • file input has font-size set very high
  • file input positioned to the top right of the wrapper
  • file input is made invisible by setting opacity

5 Responses
Add your response

Thanks. Rebound using bootstrap:
http://jsfiddle.net/jmarizfiddle/FvPAE/3/

over 1 year ago ·

@jmarizgit good rebound adding bootstrap. The goal, after all, was to make something that looks good :P

over 1 year ago ·

Tried out a few solutions across the interwebs and this is definitely the best one. Thanks very much!

over 1 year ago ·

Very clearly written post, thanks!

You can do the same thing more simply by dropping the button. There is no semantic value of having it there, and would only be confusing to those using the page on less capable devices (such as screen readers).

<div class="btn-file-input"><input type="file" name="file" /></div>
<style>
  .btn-file-input {
    display: inline-block;
    width: 200px;
    height: 40px;
    overflow: hidden;
    position: relative;
  }
  .btn-file-input > input[type="file"] {
    font-size: 200px;
    position: absolute;
    top: 0;
    right: 0;
    opacity: 0;
  }
</style>
over 1 year ago ·

Thanks, that's a valid point about the semantic value. The button element is unnecessary and confusing. The semantic value of the (although invisible) file input tag is all the page needs.

over 1 year ago ·
  NODES
Community 1
iOS 2
Javascript 5
node.js 1
os 16
text 1
web 3