Skip to main content

PNG trasparenti su Internet Explorer

Il problema che voglio affrontare in questo articolo è l’errata gestione delle PNG trasparenti su Internet Explorer 6. Su questo browser. infatti, le aree trasparenti nelle immagini PNG vengono rese con un colore grigio che impedisce la visualizzazione di quello che sta sotto l’immagine, ad esempio un altro elemento o lo sfondo.

Essendo un bug riferito al browser più diffuso (anche se a breve verrà scalzato da Internet Explorer 7), in rete si può trovare una elevata quantità di informazioni e possibili soluzioni, alcune delle quali usano i CSS, alcune JavaScript, altre perfino PHP.

Io ho scelto di adottarne una basata sui CSS. Si tratta sostanzialmente di utilizzare una proprieta’ CSS chiamata filter. La proprieta’ filter è compatibile solo con Internet Explorer. Se volete mantenere ordine nei vostri CSS ed evitare segnalazioni di errore, potreste fare come me, che uso CSS separati per IE grazie ai commenti condizionali.

Veniamo al codice. La pagina html recita cosi’:

<div id="header">
...
</div>

Questa div usa come sfondo un immagine “sfondo_header.png” che ha un’area trasparente. Lo stile di base – che funziona perfettamente in Firefox – e’ il seguente:

#header {
	position: relative;
	height: 260px;
	background: transparent url("/images/sfondo_header.png") no-repeat;
	z-index: 20;
}

Nota: lo “z-index” mi serve per sovrappore l’header alla colonna sinistra, che grazie a un posizionamento relativo si estende fino in cima alla pagina.

Per Internet Explorer ho dovuto applicare questo stile:

#header {
	background: none;
	width: 100%;
	filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(
	 src='images/sfondo_header.png', sizingMethod='crop'
	);
	/* la riga viene spezzata solo per una migliore visualizzazione */
}

Esaminiamo le (poche) regole necessarie.

Prima il background viene annullato. Poi viene impostata una dimensione, che è fondamentale per far sì che il filtro funzioni (lo stesso si può ottenere impostando ad esempio l’altezza, ma “width: 100%” in questo caso va più che bene). Poi viene applicato il filtro vero e proprio, che come potete intuire e’ un filtro proprietario Microsoft.

Nella definizione del filtro ci sono due parametri

  • src indica il percorso dell’immagine (relativo al percorso della pagina html, non del foglio di stile)
  • sizingMethod indica come comportarsi in caso l’elemento e l’immagine di sfondo non abbiano la stessa dimensione:
    • con il valore scale l’immagine viene adattata al contenuto, riducendola o allargandola se necessario
    • con il valore image (default) l’elemento viene ingrandito fino alla dimensione dell’immagine
    • con il valore crop, l’immagine viene tagliata alla grandezza dell’elemento

L’ultimo caso è quello che fa per me.

Tutto a posto?

Quasi.

Succede che gli elementi interattivi (link e input, per esempio) non funzionano più se posizionati sopra l’immagine applicata tramite filtro. Vengono visualizzati, ma è come se l’immagine filtrata introducesse una pellicola sopra che ci impedisce di usare quello che c’è sotto. Particolare ironico, questo non succede se si è sull’area trasparente dell’immagine, che quindi adesso è quella che funziona bene.

Ho trovato una soluzione anche per questo. Si tratta di creare un elemento aggiuntivo all’interno della div, e applicare a quello il filtro. Così gli elementi esterni non vengono influenzati e il tutto torna a funzionare. Quindi il codice HTML diventa:

<div id="header">
	<div id="ieheader">
	...
	</div>
</div>

Lo stile per Internet Explorer quindi va modificato cosi’:

#header {
	background: none
}
#ieheader {
	width: 100%;
	filter:progid:DXImageTransform.Microsoft.AlphaImageLoader(
	 src='images/sfondo_header.png', sizingMethod='crop'
	);
	/* riga spezzata per soli motivi di visualizzazione */
}

Per completare l’opera, ho deciso che fosse piu’ giusto racchiudere la div aggiuntiva in un commento condizionale, cosi’ che venisse visualizzata solo da Internet Explorer:

<div id="header">
	<!--[if IE]>
	<div id="ieheader">
	<![endif]-->
	...
	<!--[if IE]>
	</div>
	<![endif]-->
</div>

Ora il mio sito è bello anche su Internet Explorer.