Customiser le input file

Chaque navigateur possède son propre champ de type file, ce dernier n’est pratiquement pas modifiable en CSS. C’est fort dommage car d’une part, chaque navigateur possède son propre « design » de ce type de input, ce qui ne permet pas d’avoir une homogénéité entre les navigateurs, et d’autre part, cette impossibilité de le modifier via CSS, ne permet pas d’adapter ce dernier au design de notre site. Notre objectif est donc de palier à cette lacune, nous aurons recourt à CSS (quand même) et à jQuery.

Nous prendrons comme exemple Buzeo. Voici donc notre sélecteur avant opération :

input-file-uncustomed

Et le voici après :

input-file-customed

Vous l’aurez compris, l’opération consiste donc à substituer cet hideux champ input file par un joli bouton, qui au clic, se chargera d’ouvrir un navigateur de fichiers. Il n’y a à ma connaissance pas d’événement en JavaScript qui permette d’ouvrir un tel navigateur.

Une solution Full CSS

Avant que nous nous lancions dans la solution que je vais présenter ici, sachez qu’il existe une solution full CSS à ce petit problème. Cependant, il se trouve qu’elle n’est pas l’élue de mon cœur car elle présente un inconvénient que vous allez vite comprendre. La solution full CSS, consiste à rendre le input transparent, et à placer un bouton sous lui. Simplissime !! En croyant cliquer sur le bouton, l’internaute clique alors sur votre input et déclenche l’ouverture du navigateur de fichiers. L’inconvénient à cela ? Le input recouvrant le bouton, vous ne pourrez jamais avoir d’effet CSS de type :hover, ou :focus, donc pas de retour visuel au survol de la souris. C’est dommage, d’autant plus si tout le reste de votre site présente cet effet. Ne cherche-t-on pas là justement à procurer une certaine homogénéité à notre site ?

La solution jQuery

Je le disais juste au dessus, il n’existe pas d’événement qui permette de déclencher l’ouverture du navigateur de fichier, mais on peut toujours utiliser la méthode clic() de jQuery pour déclencher un événement. En l’occurrence, nous voulons déclencher un clic sur le input file lorsqu’on capte un clic sur notre bouton.

Le code voulez-vous ?

<div id="upload" class="whiteGlass">
    <h1 class="browse">Sélectionnez des vidéos à charger :</h1>
    <input type="file" name="film" id="file" class="browse" multiple>
    <span id="fileSelectButton" class="browse button black">Sélectionnez des fichiers</span>
    <p class="browse"><strong>Taille maximale :</strong> 2 GB.</p>
    <p class="browse"><strong>Formats supportés :</strong> avi, flv, mp4, m4v, mkv, mov, mpg, mpeg, ogg, ogv, wmv, 3gp, 3g2.</p>
</div>

Nous avons donc notre input file au dessus de notre bouton (oui mes boutons sont ©FULLCSS aussi. Vous trouverez pleins d’infos sur ce genre de petites merveilles à cette adresse [en]). Il va donc s’agir dans un premier temps de faire « disparaître » ce input. Attention toutefois, si je mets disparaître entre guillemets, c’est parce qu’on ne peut pas se permettre de le mettre en display: none;. En effet, pour des raisons de sécurité – la même raison d’ailleurs qui fait qu’on ne peut invoquer directement en JS explorateur de fichier du navigateur – il ne sera pas possible sur certains navigateurs de simuler un clic sur cet élément s’il est en display none.

On le mettra donc en absolut, pour qu’il sorte du flux, une taille ridicule, et un z-index négatif, le tout afin qu’il soit caché derrière notre bouton. Voici mon petit bout de CSS :

#upload .browse input[type='file']{
	position: absolute;
	margin-top: 3px;
	margin-left: 3px;
	height: 1px;
	width: 1px;
	z-index: -5;
}

Enfin, en ce qui concerne l’élément de jQuery, il n’y a rien de sorcier. Il consiste juste à capturer le clic sur le span d’id fileSelectButton et de déclencher un clic sur notre input. Le tout en quelques lignes grâce à jQuery :

$('#upload #fileSelectButton').click(function(){
	$('#upload input').click();
});

Je ne crois pas avoir besoin d’expliquer ce code là, niveau programmation, c’est pas trop ardu…

Déjà 4 réponses, rejoignez la discussion !

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *