Martin Michálek Martin Michálek  – 3. 1. 2019

„Neumí to Explorer“ je, když to přeženeme, na prvních devíti místech z 10 důvodů, proč lidé ještě v roce 2021 CSS grid nepoužívají.

V realitě to ale zase tak moc velký problém není, protože u většiny projektů už nejspíš není MSIE nutné používat. Je-li toto i váš případ, tuto podkapitolu račte vynechat.

A pokud Explorer podporovat musíte, vězte, že nějakou (a ne úplně malou) podporu gridu má. To je jedna věc.

Druhá věc je, že tu podporu Exploreru můžete rozšířit pomocí chytrého hacku. V tomto textu se totiž budeme zabývat automatizovaným řešením pro zlepšení podpory gridu pomocí nástroje Autoprefixer.

Podívejte se na video „CSS grid v Internet Exploreru“.

YouTube: youtu.be/JjmXOB01Yq0

Pojďme tedy dát kombinaci gridu s MSIE novou šanci.

Které vlastnosti gridu Internet Explorer podporuje?

Jisté rozdíly mezi IE a moderními prohlížeči zde jsou. Z těch důležitých například uveďme, že Internet Explorer nativně neumí následující:

  • Automatické umísťování prvků do mřížky („auto-placement“).
  • Pojmenovávání oblastí mřížky (vlastnosti jako grid-template-areas).
  • Mezery mezi buňkami mřížky (vlastnost gap).

Velká část uvedeného pro vás ale přečtením tohodle dlouhého textu přestane platit.

Naopak se málo ví, že stařičký IE nativně podporuje následující:

  • Implicitní (nepředdefinovanou) mřížku.
  • Funkci repeat(), jen jinak. repeat(12, 1fr 20px) zapisuje jako (1fr 20px)[12].
  • Funkci minmax().
  • Klíčová slova min-contentmax-content.

To myslím není zlé.

Jen připomínám, že rozdíly nevznikly v nějakém microsoftím „týmu pro vytáčení webařů“.

Jejich příčinou je rychlá implementace gridu v rané fázi specifikace týmem v Microsoftu. Specifikace se bohužel časem změnila, grid ale v Exploreru zůstal v původní variantě, protože se tento prohlížeč ve své době aktualizoval jen velmi pomalu.

Třísloupcové demo aneb „Jak to kurnikšopa funguje?“

Podívejme se na jednoduchý layout, u kterého si ukážeme jak přesně Autoprefixer zařídí fungování gridu v MSIE.

Jde o rozvržení definované následujícím způsobem:

.container {
  display: grid;
  grid-template-columns: 1fr 3fr 1fr;
  grid-template-areas: "a b c";
  column-gap: 0.5em;  
}

Pro zájemce vše vysvětlím polopaticky:

  • display:grid asi vysvětlovat nemusím. Definujeme prostě kontejner mřížky.
  • grid-template-columns:1fr 3fr 1fr specifikuje samotnou mřížku. O jednotce fr píšu v jiném textu.
  • grid-template-areas je šablona pojmenování oblastí pro následné využití v CSS.
  • column-gap:0.5em je zápis pro mezeru mezi sloupci layoutu.

Teď to nejlepší. Tenhle kód nám Autoprefixer přeloží tak, aby v pohodě fungoval v Internet Exploreru 11. Včetně mezer (-gap) a pojmenovaných oblastí (-areas). Tedy vlastností, které tenhle pravěký prohlížeč neumí.

Než se k tomu dostaneme, musím zmínit jednu nevýhodu.

Proč layout zapisuji takhle složitě? Protože Autoprefixer

Vy znalejší jste si jistě všimli, že pro takto jednoduchý layout je zbytečné definovat šablonu pojmenování oblastí – grid-template-areas.

To je ale oběť na oltář podpory v Internet Exploreru, respektive vyžaduje to po nás Autoprefixer.

Dalším kódem ještě musíme umístít sloupečky do pojmenovaných oblastí:

.side-1 {
  grid-area: a;
}

.content {
  grid-area: b;
}

.side-2 {
  grid-area: c;
}

A šup! V další fázi se můžeme kochat kódem, který vypotí Autoprefixer.

Kód produkovaný Autoprefixerem

Nejprve se podíváme na kód generovaný tímto nástrojem pro rodiče layoutu:

.container {
  display: -ms-grid;
  -ms-grid-columns: 1fr 0.5em 3fr 0.5em 1fr;
}

Následuje samozřejmě výše uvedený kód pro moderní prohlížeče. Ten pro zjednodušení vynechávám. Opět ale oba řádky vysvětlím:

  • display: -ms-grid – prefixovaný zapínač gridu v Exploreru.
  • -ms-grid-columns: 1fr 0.5em 3fr 0.5em 1fr – magie. Autoprefixer spojil definici mřížky s definicí mezer (column-gap), abychom ty (sakramentsky návykové) díry v layoutu mohli využívat i v Exploreru, který žádnou z „gap vlastností“ nepodporuje.

Kód prvků layoutu, jež Autoprefixer vyrobí pro potřeby Exploreru, vypadá takhle:

.side-1 {
  -ms-grid-row: 1;
  -ms-grid-column: 1;
}

.content {
  -ms-grid-row: 1;
  -ms-grid-column: 3;
}

.side-2 {
  -ms-grid-row: 1;
  -ms-grid-column: 5;
}

IE totiž neumí ani žádnou z vlastností *-area. Autoprefixer tak automaticky spočítá umístění do patřičných sloupečků.

Pokud vám nesedí počty sloupců u vlastnosti -ms-grid-column, pak raději zopakuji, že Autoprefixer uměle přidává sloupečky, abychom mohli používat mezery -gap.

Demo jsme snad rozebrali do posledního kamínku. Tady je ještě v celé kráse: cdpn.io/e/BvJjdz.

Co Autoprefixer umí?

Následuje sumář aktuálně podporovaných a nepodporovaných vlastností gridu.

Dobrá zpráva zní, že těch druhých je poměrně málo.

Autoprefixer umí: Definování šablony mřížky

  • grid-template-columns se přeloží do -ms-grid-columns.
  • grid-template-rows se přeloží do -ms-grid-rows.
  • grid-template-areas slouží k tomu, aby Autoprefixer pochopil, jak vypadá váš layout. Žádný kód ale negeneruje.
  • grid-template je jen zkratka pro grid-template-columns, grid-template-rowsgrid-template-areas. Přeloží se tedy do nich.

Umí: Zarovnávání

Částečně umí: Umístění položky do mřížky

Překlad následujících vlastností funguje, ale nesmíte v nich použít záporná čísla:

  • grid-row-start se přeloží do -ms-grid-row. Pokud chcete použít span, musíte definovat grid-row-end.
  • grid-column-start se přeloží do -ms-grid-column. Pokud chcete použít span, musíte definovat grid-row-end.
  • grid-row-end. Musíte ale definovat grid-row-start.
  • grid-column-end. Musíte ale definovat grid-row-start.
  • grid-row se přeloží do -ms-grid-row.
  • grid-column se přeloží do -ms-grid-column.

Částečně umí: Definice pojmenovaných oblastí

Následující vlastnost funguje, ale každý potomek gridu musí mít unikátní jméno oblasti:

  • grid-area - Autoprefixer z oblastí udělá explicitní zápis pomocí grid-row-endgrid-column-end.

Částečně umí: Definice mezer

  • grid-gap a explicitní vlastnosti grid-row-gap nebo grid-column-gap.

Autoprefixer namísto -gap vygeneruje extra řádky nebo sloupečky. Fajn řešení, ne? Je ale důležité, abyste grid zapsali pomocí grid-template-areas a zároveň grid-template-columns.

Neumí vůbec: Vlastnost grid a automatické umístění

Tady máte zatím smůlu:

Automatické umísťování ale u jednodušších layoutů udělat jde, jak za chvíli uvidíte.

Au­to­ma­tic­ké umís­ťo­vá­ní do mříž­ky (autoplacement)

Autoplacement je další důležitá vlastnost gridu, Explorer ji neumí, ale i tady vám může částečně pomoci Explorer.

Pojďme tradičně na příklad. Chceme layout 2 × 2 prvky. HTML kód vypadá takto:

<div class="container">
  <p class="box">Box</p>
  <p class="box">Box</p>
  <p class="box">Box</p>
  <p class="box">Box</p>
</div>

Díky automatickému umístění bude v moderních prohlížečích stačit definovat mřížku v CSS:

.container {
  display: grid;
  grid-template-columns: 1fr 1fr;
  grid-template-rows: auto auto;
}

Prvky se nám pěkně rozmístí. Jenže smůla, tohle nebude fungovat v Internet Exploreru.

Pro MSIE 10 a 11, ve kterých nějaká verze CSS gridu funguje, nám zde Autoprefixer přidá pseudotřídy:

.container > *:nth-child(1) {
  -ms-grid-row: 1;
  -ms-grid-column: 1;
}

.container > *:nth-child(2) {
  -ms-grid-row: 1;
  -ms-grid-column: 2;
}

…a tak dále.

Chcete autoplacement? Pozor na výjimky

Autoplacement rozhodně nefunguje ve všech použitích mřížky. Následuje seznam možných problémů, ale bude jich více.

  • Nefunguje pro neznámý počet položek
    Je možné tedy automatizace použít jen pro explicitní mřížky definované pomocí grid-template-* vlastností, nikoliv grid-auto-*.
  • Pozor na zpětné nasazení na starých projektech
    Doporučení zní: Nechte grid vypnutý a pomocí CSS komentářů jej zapínejte pouze pro nové deklarace.
  • Neumí to repeat() v kombinaci a auto-fill, auto-fit
    I když IE funkci repeat() zvládá, klíčová slova auto-fillauto-fit bohužel ne.
  • Vyberte si: Buď autoplacement nebo manuální umístění v gridu
    V moderních prohlížečích lze obojí kombinovat, v IE bohužel ne. Buď tedy budete všechny prvky gridu umísťovat ručně (použijte vlastnost grid-template-areas v definici gridu) nebo automaticky (bez *-areas).
  • Pozor na pseudoelementy
    ::before::after uvnitř gridu vám v IE rozbijí mřížku, to se vsaďte.
  • V Media Queries nelze změnit jen grid-gap
    Namísto toho je Autoprefixeru potřeba znovu deklarovat explicitní mřížku pomocí vlastností grid-template-*.

Neřeší to všechno, ale máme tady o jeden silný důvod navíc použít.

Co potřebujete pro překlad gridu pro IE pomocí Autoprefixeru?

Potřebujete tyto suroviny:

  • Automatizaci
    Gulp, Grunt, skripty v NPM nebo podobné nástroje, které umí využít Autoprefixer.
  • Zapnout podporu IE11
    V Browserslist, seznamu podporovaných prohlížečů, je nutné specifikovat také IE 11, případně i desátou verzi – např. takto > 1%, IE 11, IE 10.
  • Zapnout grid a auto-umístění
    Zavolat Autoprefixer s parametrem grid: 'autoplace', který zařídí podporu právě pro automatické umístění. Alternativa jsou řídící komentáře přímo v CSS: /* autoprefixer grid: autoplace */.

Takto může vypadat konfigurace v automatizačním nástroji Gulpu:

gulp.task('autoprefixer', () =>
  {
    return gulp.src('src/css/*.css')
      .pipe(autoprefixer({
        grid: autoplace
      }))
      .pipe(gulp.dest('dist/css'));
  }
);

V samotném CSS kódu se pak držte těchto pravidel:

  • Definujte grid vždy kromě sloupců (grid-template-columns) nebo řádků také pojmenované oblasti: grid-template-areas.
  • Používejte vlastnost grid-template, nikoliv zkratku grid.
  • Vyhněte se pojmenovávání jmen řádků gridu.

Pokud na něco z toho zapomenete, Autoprefixer vás asi řádně potrápí, protože žádné prefixy nepřidá.

Možná vám to celé připadá dost složité. Nedivil bych se vám.

Na závěr ale chci akcentovat dva důležité fakty. Za prvé – jednodušší layouty nejsou pro Autoprefixer problematické a výše uvedené detailní znalosti pravděpodobně nebudete potřebovat.

Za druhé – v době vydání knihy velmi pravděpodobně nebudete muset podporovat Internet Explorer a tuto podkapitolu jste tedy mohli přeskočit. Z toho vyplývá, že bych vám v tomto odstavci klidně mohl nadávat a vy byste si dále žili klidný život. Bez mých nadávek a Exploreru.