vliv !doctype na vykreslování stránky
Skoro každý si všimnul, že spousta stránek vypadá v různých prohlížečích různě. Do značné míry za tu různost mohou vykreslovací režimy, kterým se také říká módy.
Jde o blokový model vykreslování, který se chová podle specifikace W3C. Používají je Mozilla (+ odvozeniny), Internet Explorer 6 a 7 (se striktním doctype) a Opera (se striktním doctype).
Začátek kódu stránky se striktním doctype vypadá třeba takto:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01">
<html>...
nebo
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
Také se tomu říká "režim zpětné kompatibility" nebo "kompatibilní režim". Používají ho všechny verze Internet Exploreru (kromě šestky a sedmičky se striktním doctype) a Opera bez striktního doctype.
Příklad začátku stránky vykreslovaný v Exploreru v quirk módu:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>...
nebo bez doctype:
<html>
...
V Exploreru 6 se do Quirk módu přepnou i dokumenty obsahující striktní doctype, pokud toto doctype není hned na první řádce (jde o velmi nepříjemnou chybu Exploreru).
Patrně jich bude víc, ale za podstatné považuji tři:
Říká se tomu také boxmodel. Specifikace říká (a standardní mód to respektuje), že do rozměrů prvků se nepočítá rámeček (border) a vnitřní okraj (padding):
Oproti tomu quirk mód (a zejména Internet Explorer) do šířky počítá border i padding:

Protože Internet Explorer byl prvním prohlížečem se slušnou podporou CSS, používání nestandardního boxmodelu mezi autory hodně rozšířilo. To je i důvod, proč je hodně starších webů hnusných v Mozille a proč konzervativní kodéři mají rádi tabulky -- nepochopili rozdíly boxmodelů a nenaučili se je hackovat.
V různých režimech jsou jinak chápána klíčová slova pro velikost písma middle, large, small apod. Zjednodušeně lze říci, že Internet Explorer v nestandardním módu kreslí všechno o jeden stupeň větší.
Standardní mód nedovoluje (zcela logicky) zadávat řádkovým prvkům rozměry (např. odkazům, tagu span apod.), občas mi to chybí. Nestandardní mód to dovoluje a občas to vede k podivným efektům. Částečná řešení nabízím níže.
Ve standardním vykreslovacím módu se do šířky a výšky nezapočítává border (rámeček) a padding (vnitřní okraj). V nestandardním módu se do šířky a výšky border i padding počítá. Aby bylo zaručeno stejné (nebo alespoň podobné) vykreslení stránky v Internet Exploreru 5 (vždy quirk mód) a v Mozille (standardní mód), musí se kód ohackovat. Stejné hacky se dají použít i pro velikost písma (font-size).
Můj oblíbený (ale nevalidní) hack spočívá v použití uvozovek kolem quirk hodnot:
.prvek {padding-left: 20px; width: 300px; width: "320px";}
první hodnota 300px je pro standardní režim, druhá hodnota v uvozovkách je pro nestandardní quirk režim. Internet Explorer 6 ve standardním módu hodnotu v uvozovkách nevidí.
Používá se stejně jako uvozovkový hack na odlišení standardních a nestandardních módů určitých prohlížečů.
prvek {padding-left: 20px; width: 320px; w\idth: 300px;}
Zpětné lomítko před nějakým vnitřním písmenkem zápisu vlastnosti způsobí, že standardní módy (Mozilla, Explorer 6 se standardním doctype, Opera se standardním doctype) vlastnost vidí a některé nestandardní módy (starší Explorery, Explorer 6 bez standardního doctype) takto zapsanou vlastnost nevidí (podporou si nejsem zcela jist, nutno vyzkoušet).
Pozor, zpětné lomítko nesmí být před písmenky a b c d e f, potom to nefunguje.
Pokud se před jménem css vlastnosti uvede podtržítko (např. _height), Internet Explorer ho nevidí a vlastnost interpretuje, jako by byla zapsána bez podtržítka. Jiné prohlížeče (správně) interpretují vlastnost jako neznámou (pozor, včetně Opery). Zápis hacku by pak vypadal takto:
.prvek {padding-left: 20px; width: 300px; _width: 320px;}
Narozdíl od hacku s uvozovkami jde pravděpodobně o validní zápis. Internet Explorer ve standardním módu vlastnost _width vidí, a proto je tento hack použitelný spíše jenom v tom případě, kdy stránka bude v nestandardním (quirk) módu.
Výška 18 pixelů pro standardní mód a 24px pro nestandardní mód se dá udělat takhle:
.prvek {height:18px !important; height /**/:24px;}
totéž funguje pro šířku a všechny ostatní vlastnosti. Je to validní zápis a z validních zápisů je asi nejjednodušší.
Pokud máte starý design odladěný pro quirk mód Internet Exploreru, je nerychlejší řešení optimalizace pro Mozillu nastavit
* {-moz-box-sizing: border-box}
Více o -moz-box-sizing.
Matroška hack vyžaduje trochu ukecanější html kód, ale přijde mi na hackování rozměrů nejspolehlivejší. Zakládá se na tom, že se vůbec nepoužívá padding. Pokud nějakému prvku chcete přidat padding, uděláte to tak, že celý obsah prvku obalíte ještě jedním divem a tomu nastavíte margin. Margin se v obou režimech interpretuje stejně, takže nevznikají žádné odlišnosti. Příklad když chci mít prvek široký 300 pixelů včetně paddingu (jako by to odpovídalo quirk módu),
tak namísto
<div style="padding: 5px; backgound-color:
yellow; width: 300px;">
obsah prvku
</div>
stačí napsat
<div style="backgound-color: yellow; width: 300px;">
<div style="margin:
5px;">
obsah prvku
</div>
</div>
Hacků na boxmodel existují desítky, ale připadají mi většinou málo použitelné.
Je potřeba je převést na blokové prvky. Možná je to divná odpověď, ale je to tak. Pokud chcete mít i v Mozille stejný vzhled stránek, nejde se tomu vyhnout.
Typickým případem, kdy je třeba nastavit rozměry řádkovým prvkům, jsou odkazy v menu, vykreslované pod sebou.
Jedním řešením je obalit každý odkaz třeba do odstavce nebo do divu -- prostě do jiného blokového prvku. Potom ostylovat ten vnější blokový prvek a přidat mu rozměry, například přes class:
<div class="polozkamenu">
<a href="druha-stranka">odkaz</a>
</div>
Aby se třeba hover efekt (změna při přejetí myší) projevil hezky i v Internet Exploreru, je třeba od tohoto řešení upustit. Pokud hover efekt nevyžadujete nebo vám stačí v jiných prohlížečích, jde o dobré řešení.
Když potřebuji třeba mít odkazy s určitými rozměry, nastavím odkazům blokové zobrazování:
<style>
a {display: block;}
</style>
V tu chvíli půjdou odkazům nastavovat rozměry, ale objeví se nepříjemnnost -- před a za každým odkazem se zalomí řádek. To většinou nejde akceptovat. Proto se dělá to, že se odkazům, které mají mít rozměr, přiřadí nějaká třída, třeba "rozmerovane":
<a href="jina-stranka.html" class="rozmerovane">odkaz</a>
a potom se ve stylu vyznačí, že takové prvky opravdu mají být na samostatném řádku a že mají mít rozměry:
a.rozmerovane {display: block; width: 12em; height: 1em;}
Taková věc se hodí zejména v nějakém menu, kde nevadí, že jsou odkazy pod sebou, ale na druhou stranu je potřeba, aby měly opticky stejné rozměry.
Jedná se o obměnu předchozího postupu používané u různých menu horizontálních (proužkových). Tam se používá stejný trik s class, pouze se nastaví float, takže prvky budou vedle sebe:
a.rozmerovane {float: left; width: 12em; height: 1em;}
v tom případě se samozřejmě musí použít víc podobných odkazů za sebou a nesmí se to kombinovat s textem (úplně by někam uletěl). Dříve se takováto horizontální menu dělala pomocí obrázků v tabulkách, což je i dnes v některých případech nejspolehlivější způsob.
Stačí na začátku html souboru napsat doctype s určitou syntaxí. Popíšu způsob, který používám pro přepínání módů v Internet Exploreru. Když dám dokument bez doctype nebo s chybným doctype, tak je v quirk módu. Stejně tak je v quirk módu je dokument s následujícím doctype:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
Takže to je quirk. A teď doctype, při němž Internet Explorer 6 přepne do standardního módu:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN">
Určitě vidíte, že rozdíl je tam v tom "Transitional". Doctypů se standardním vykreslováním je víc. Výše zmíněné přepínání funguje i pro Operu.
Další zajímavost Internet Exploreru 6 je ta, že když doctype není zcela na začátku dokumentu (třeba je před ní xml deklarace), tak přepínání módů nefunguje. Teď rychle si nevzpomínám, jak se to řeší.
Jak psát web píše Yuhů, Dušan Janovský. Kontakt. Poslední aktualizace 26. srpna 2010.