Tvorba internetových aplikací

Jakub Klinkovský

:: České vysoké učení technické v Praze
:: Fakulta jaderná a fyzikálně inženýrská
:: Katedra softwarového inženýrství

Akademický rok 2022-2023

Kaskádové styly

Cascading Style Sheets (CSS)

Motivace vzniku CSS

Jazyk HTML byl původně navržen pro popis struktury WWW dokumentu – nebyl zamýšlen jako jazyk pro popis vzhledu WWW stránek. Jenže s jeho rozšířením mimo akademickou oblast se objevily požadavky na definici grafického vzhledu WWW stránek. Tak byly do HTML přidány nové „užitečné“ značky (např. font) a atributy (např. align). Ale kód stránek se stal nepřehledným, navíc dodatečné změny vzhledu byly složité.

Koncem 20. století se proto objevuje snaha oddělit prezentaci (vzhled) od struktury WWW stránky. O změnu se postaralo W3C – do HTML 4.0 byly přidány styly. HTML5 se vrací k původní myšlence – definuje strukturu dokumentu a styly používá pro nastavení vzhledu webu.

CSS (Cascading Style Sheets)

CSS je jazyk („šablona stylů“), pomocí něhož autor přiřadí vzhled a formátování k dokumentu napsanému ve značkovacím jazyce HTML, resp. XHTML nebo XML. Pomocí CSS tedy může autor WWW stránky definovat, jak se mají určité části stránky zobrazovat v prohlížečích.

WWW dokument se potom skládá z vlastního kódu popisujícího jeho strukturu (pomocí značkovacího jazyka), a dále z definice stylů popisujících výsledný vzhled WWW stránky (přesněji: vzhled libovolného elementu použitého v kódu WWW stránky).

Proč používat CSS

Největší výhodou použití kaskádových stylů je oddělení prezentace od struktury WWW stránky, z čehož plyne:

  • přehlednější správa obsahu WWW stránky – kód je kratší a jednodušší (neobsahuje zbytečné „grafické“ značky a atributy),
  • snadná změna vzhledu WWW stránky (úpravou CSS, nikoli přepisováním částí kódu).

Další výhody přináší definice CSS v externím souboru:

  • jednotný vzhled stránek celého webu (sdílení CSS souborů pro všechny stránky),
  • možnost snadné změny vzhledu a rozložení všech stránek webu – stačí upravit definici vzhledu na jednom místě.

Vývoj CSS I

Již v roce 1994 se objevuje snaha oddělit strukturu stránek od jejich vzhledu, ale teprve s HTML 4.0 přichází řešení.

CSS1 (CSS level 1) – 1996-2018 (již nepodporováno)

CSS2 (CSS level 2) – specifikace 1998

  • CSS 2.1 (CSS level 2 revision 1) – specifikace 2011
  • CSS 2.2 (CSS level 2 revision 2) – neoficiální Working Draft z 2016

Vývoj CSS II

CSS3 (CSS level 3)

CSS aktuálně

  • CSS3, CSS4 atd. jsou „lidové“ pojmy, v praxi je vše „CSS bez čísla“
  • některé moduly mají čísla, např. CSS Color Level 5
  • podporu pro novější prvky CSS v prohlížečích je nutné ověřovat samostatně, např. pomocí https://caniuse.com/
    (případně referenční příručky W3Schools a MDN Web Docs obsahují sekce „Browser support“ resp. „Browser compatibility“ pro každou vlastnost CSS)
  • CSS lze použít pro různé značkovací jazyky: HTML, XML, XHTML, SVG, MathML3

Syntaxe CSS

Definice stylů neboli jednotlivá pravidla CSS obsahují vždy dvě části: selektor a seznam deklarací vzhledu uvnitř složených závorek:

selektor {
  deklarace1;
  deklarace2;
}
  • deklarace jsou ukončeny středníkem (pouze za poslední deklarací být nemusí)
  • každá deklarace se skládá z dvojice vlastnost : hodnota (property : value)
  • komentáře se zapisují mezi tokeny /* a */: např. /* komentář */
  • na umístění bílých znaků (mezera, konec řádku, atd.) nezáleží
    (pozor: mezera se používá pro kombinaci selektorů a hodnot pro určité vlastnosti)

Jednoduché příklady CSS

Pravidlo s jednou deklarací (pro značku p – odstavec):

p {
  text-align: center;
}

Pravidlo se dvěma deklaracemi (pro značku h1 – nadpis 1. úrovně):

h1 {
  font-size: 120%;
  color: blue;
}

Selektory I

Selektor (selector) zajišťuje vazbu na odpovídající element jazyka HTML (v podstatě určuje, na jaké elementy WWW stránky se deklarované vlastnosti budou aplikovat). Selektory lze různě spojovat (viz slide Spojování selektorů).

Základní selektory

  1. univerzální selektor: *
  2. typový selektor: E, kde E je jméno libovolné značky
  3. třídní selektor: .T, kde T je jméno nějaké třídy (hodnota atributu class v HTML)
  4. ID selektor: #I, kde I je nějaké ID použité v dokumentu (hodnota atributu id)
  5. atributový selektor: [A], [A⊗hodnota], [A⊗hodnota i], [A⊗hodnota s],
    kde A je jméno atributu, je nějaký operátor a hodnota je nějaká hodnota

Univerzální selektor

  • syntaxe: * (v jednoduchých případech lze vynechat, viz dále)
  • vztahuje se na všechny elementy

Příklad: nastavení červené barvy písma na celé stránce

* {
  color: red;
}

Typový selektor

  • syntaxe: E, kde E je jméno libovolné značky
  • např. selektor h3 ovlivní vzhled všech značek h3 (všechny nadpisy úrovně 3)
  • toto je nejčastěji používaný typ selektoru

Příklad: nastavení červené barvy písma pro všechny nadpisy úrovně 1

h1 {
  color: red;
}

Třídní selektor

  • syntaxe: .T, kde T je jméno nějaké třídy
  • vztahuje se na značky s danou hodnotou atributu class
  • používá se, když chceme daný typ elementu zobrazit v různých výskytech rozdílně

Příklad: nastavení červené barvy písma pro elementy ve třídě warning

.warning { color: red; }

Příklad dokumentu:

<p class="warning">Lorem ipsum dolor sit amet, ...</p>

Poznámka: kombinace s typovým selektorem: např. p.warning

ID selektor

  • syntaxe: #I, kde I je nějaké unikátní ID použité v dokumentu
  • stylovat jediný element má smysl pouze v případě, že se jedná o nějakou výjimku (jinak se připravujeme o možnost snadné editace vzhledu WWW stránky)

Příklad: nastavení červené barvy písma pro element s ID lorem-ipsum

#lorem-ipsum { color: red; }

Příklad dokumentu:

<p id="lorem-ipsum">Lorem ipsum dolor sit amet, ...</p>

Poznámka: kombinace s typovým selektorem (např. section#lorem-ipsum) má smysl při sdílení CSS pro více dokumentů

Atributový selektor

  • syntaxe: [A], [A⊗hodnota], [A⊗hodnota i], [A⊗hodnota s],
    kde A je jméno atributu, je nějaký operátor a hodnota je nějaká hodnota
  • platné operátory: =, ~=, |=, ^=, $=, *=
  • znaky i a s před uzavírací závorkou modifikují chování při rozlišování velikosti písmen (case-insensitive resp. case-sensitive) – defaultně to závisí na použitém značkovacím jazyku

Příklad: selektor *[lang] resp. [lang] vybere všechny elementy, které mají nastavený atribut lang (např. <body lang="en"> i <p lang="cs">, ale ne <p>)

Příklad: selektor a[title] vybere všechny odkazy s atributem title

Atributový selektor – příklady operátorů I

Příklad:
selektor a[href="https://example.org"] vybere všechny odkazy, jejichž cíl se přesně rovná "https://example.org"

Příklad:
selektor a[href*="example"] vybere všechny odkazy, jejichž cíl obsahuje "example"

Příklad:
selektor a[href$=".org"] vybere všechny odkazy, jejichž cíl končí řetězcem ".org"

Příklad:
selektor a[href^="https://"] vybere všechny odkazy, jejichž cíl začíná "https://"

Atributový selektor – příklady operátorů II

Příklad: selektor a[href^="https://"][href$=".org"] vybere všechny odkazy, jejichž cíl začíná řetězcem "https://" a končí řetězcem ".org"

Příklad: selektor a[class~="logo"] vybere všechny odkazy, jejichž atribut class obsahuje slovo "logo"
Poznámka: operátor ~= předpokládá, že atribut obsahuje seznam slov oddělených mezerami

Příklad: selektor p[lang|="en"] vybere všechny odstavce, jejichž lang se přesně rovná "en", nebo začíná řetězcem "en-" (např. "en-US", "en-GB")

Spojování selektorů

Selektory lze spojovat několika způsoby:

  1. seskupení: A, B vybere elementy odpovídající selektoru A nebo B
    (viz slide Syntaxe CSS) – sjednocení množin elementů odpovídajícím A a B
    např. h1, h2, h3, h4, h5, h6 pro jednotné stylování všech nadpisů
  2. řetězení: AB – průnik množin elementů odpovídajícím A a B
    např. *.classname, body.classname, .class1.class2, .classname#idname, a[href^="https://"][href$=".org"]
  3. kombinování: A⊗B, kde ⊗ je nějaký operátor (combinator)

Kombinování selektorů – následující sourozenec

Příklad: jak nastylovat pouze první odstavec pod nadpisem?

<section>
  <h1>Nadpis</h1>
  <p>První odstavec...</p>
  <p>Druhý odstavec...</p>
  ...
</section>

Např. tímto pravidlem CSS:

h1 + p {
  color: red;
}

Kombinování selektorů – obecný sourozenec

Příklad: jak nastylovat všechny odstavce následující po nadpisu?

<section>
  <p>Tohle nebude červeně</p>
  <h1>Nadpis</h1>
  <p>Tohle bude červeně</p>
  <h2>Podnadpis</h2>
  <p>Tohle bude taky červeně</p>
</section>

Např. tímto pravidlem CSS:

h1 ~ p {
  color: red;
}

Kombinování selektorů – přímý potomek

Příklad: jak nastylovat všechny odstavce, které jsou dítětem nějaké sekce?

<section>
  <h1>Nadpis</h1>
  <p>Vybraný odstavec...</p>
  <article>
    <p>Nevybraný odstavec...</p>
  </article>
  ...
</section>

Např. tímto pravidlem CSS:

section > p {
  color: red;
}

Kombinování selektorů – obecný potomek

Příklad: jak nastylovat vnořené seznamy?

/* pravidlo pro odrážky první úrovně */
li {
  list-style-type: disc;
}

/* pravidlo pro odrážky druhé úrovně */
li li {
  list-style-type: circle;
}

Pseudo-třídy I

Pseudo-třídy jsou klíčová slova, která specifikují nějaký speciální stav vybraného elementu. Ukážeme si jen některé příklady, pro úplný seznam navštivte předchozí odkaz.

  • Pseudotřídy odkazů (používané u značky a):
    • :link – zatím nenavštívený odkaz
    • :visited – již navštívený odkaz
    • :active – aktivovaný odkaz, tj. uživatel nad ním právě drží zmáčknuté tlačítko myši
    • :hover – odkaz, nad nímž uživatel přejel myší
    • Pozor: při řetězení dodržujte toto pořadí: :link nebo :visited, dále :hover a nakonec :active

Pseudo-třídy II

  • Jazykové pseudotřídy
    • :lang() styluje elementy psané v daném jazyce
    • :dir() styluje elementy psané daným směrem (ltr nebo rtl)
  • Pseudotřídy pro práci s formuláři – umožňují stylovat stavy formulářových prvků
    • :enabled – prvky povolené v kódu HTML
    • :disabled – prvky zakázané v kódu HTML
    • :checked – uživatel právě „zaškrtnul“ prvek
      (týká se prvků checkbox a radio)
    • :focus – aktivuje (vybere) prvek, který má fokus
    • :required – styluje prvky, u kterých je uveden atribut required
    • :optional – styluje prvky, u kterých není uveden atribut required

Pseudo-třídy III

  • Pseudotřídy pro práci s formuláři (pokračovaní)
    • :in-range – prvky, jejichž hodnota je v zadaném rozsahu
    • :out-of-range – prvky, jejichž hodnota je mimo zadaný rozsah
    • :valid – prvky, jejichž hodnota je správná (validní)
    • :invalid – prvky, jejichž hodnota je chybná (nevalidní)
    • :read-only – styluje prvky, u kterých je uveden atribut readonly
    • :read-write – styluje prvky, u kterých není uveden atribut readonly
  • Negující pseudotřída :not(S) umožňuje stylovat elementy, které neodpovídají zadanému selektoru S

Pseudo-třídy IV

  • Pseudotřídy, které se řídí stromem dokumentu:
    • pseudotřída :root – kořenový element dokumentu (pro HTML je to <html>)
    • :empty – prázdný element dokumentu (nemá obsah ani potomky)
    • následující pseudotřídy vybírají element podle jejich pořadí ve skupině sourozenců:
      • :first-child (první), :last-child (poslední), :nth-child(n) (n-tý), :nth-last-child(n) (n-té od konce), :only-child (jediné dítě)
      • za n lze dosadit přirozené číslo, even (sudý), odd (lichý), nebo dokonce polynom ve tvaru an+b, kde a a b jsou celá čísla
      • využití: např. u tabulek a seznamů
    • náhradou slova child za of-type získáme pseudotřídy, které se týkají pořadí pouze mezi sourozenci stejného typu

Pseudo-elementy

Pseudo-elementy jsou klíčová slova, která umožňují stylovat části skutečných elementů. Pro odlišení od pseudo-tříd obsahují čtyřtečku (::).

Příklady pseudo-elementů:

  • ::first-line označuje první řádek blokového elementu (podle toho, jak se zobrazí v prohlížeči)
  • ::first-letter označuje první písmeno (tzv. iniciálu) vybraného elementu
  • ::before označuje místo před začátkem vybraného elementu
    (příklad využití: číslování nadpisů)
  • ::after označuje místo za koncem vybraného elementu

Další informace o selektorech

Deklarace I

Připomeňme si, že každá deklarace v CSS je složena z dvojice vlastnost:hodnota.

  • Deklarace je ukončena středníkem, pouze za poslední deklarací středník být nemusí (ale může).
  • Za dvojicí vlastnost:hodnota může následovat ještě !important (viz dále).

Povolené vlastnosti a jejich hodnoty:

Deklarace II

Při deklaraci stylu lze použít kteroukoli z povolených vlastností (a jejich hodnot) v závislosti na druhu použitého selektoru (elementu).

Rozdělení elementů

  • blokové (block): mají před a za sebou konec řádku, jde jim nastavit šířka a výška (např. p, div, h1, tabulky a seznamy; viz JakPsatWeb, bloky)
  • řádkové (inline): jsou součástí textu na řádce, nemají za sebou řádkový zlom (např. strong, span, cite; viz JakPsatWeb, text)
  • elementy nahrazované „cizím“ obsahem: prohlížeč vynechá potřebnou šířku a výšku, po jejich načtení si obsah doplní (např. img, object)

Číselné hodnoty

U mnoha vlastností lze využít číselnou hodnotu s odpovídající jednotkou (např. %, px, em, ex, in, cm, mm, ...). Pozor: mezi číslem a jednotkou nesmí být mezera!
čísla mohou být celá nebo desetinná (s desetinnou tečkou), s nebo bez znaménka.

Procentuální hodnoty (percentage)

Pozor: vždy se vztahují k jiné referenční hodnotě, podle které se vypočte skutečná velikost ⇒ uvědomte si, vzhledem k jaké hodnotě procenta zadáváte!

Příklad: výška řádku (line-height) se vztahuje k velikosti písma (font-size), takže při deklaraci line-height: 120% a velikosti písma 10px (pixelů) bude výška řádku 12px.

„Obecné“ hodnoty – rodiny písma

Obecné rodiny písma (generic font families) pro vlastnost font-family: vždy bychom kromě konkrétních rodin měli uvádět i jednu z pěti obecných rodin pro případ, že prohlížeč nebude mít k dispozici žádný z uvedených fontů. Fonty uvedené dříve mají přednost, tj. obecnou rodinu písma píšeme za konkrétní rodinu.

Hodnota Význam (příklad) Primární určení
sans-serif bezpatkové písmo (Arial, Helvetica) monitor
serif patkové písmo (Times) tisk na papír
monospace neproporcionální písmo (Courier) zdrojové kódy

Ukázky: CSS Web Safe Fonts nebo CSS: fonts

„Obecné“ hodnoty – velikosti písma I

Absolutní velikost (absolute size) pro vlastnost font-size:

hodnota násobek představa
xx-small 3/5 velikost h6
x-small 3/4
small 8/9 velikost h5
medium 1 velikost h4
large 6/5 velikost h3
x-large 3/2 velikost h2
xx-large 2 velikost h1

„Obecné“ hodnoty – velikosti písma II

Relativní velikost (relative size) pro vlastnost font-size:

hodnota význam
larger o stupeň větší
smaller o stupeň menší

Příklad: má-li rodičovský element velikost large a dítěti nastavíme smaller, pak dítě bude mít velikost medium.

Barvy I

Barvy (u vlastností obsahujících slovo color) se v CSS zadávají nejčastěji:

  • pomocí jména – viz další slide pro 16 základních barev, další viz MDN Web Docs
  • pomocí RGB zápisu (směs červené, zelené a modré)
zápis hodnoty r, g, b příklad (yellow)
#rgb 0,1,...,9,A,B,...,F #FF0
#rrggbb šestnáctkové (00-FF) #FFFF00
rgb(r,g,b) desítkové (0-255) rgb(255,255,0)
rgb(r%,g%,b%) procenta (0-100) rgb(100%,100%,0%)

Barvy II

Jména 16 základních barev:

Ukázky CSS

  • Referenční příručka na W3schools: každá stránka popisující určitou vlastnost obsahuje odkaz „Try it yourself“, kde dokonce můžete měnit zdrojový kód CSS a dívat se, jak se změní výsledné formátování stránky.
  • Další referenční příručka s příklady je na MDN Web Docs
  • interval.cz nabízí odkazy na „hotová řešení“ typických postupů
  • Spoustu příkladů lze najít na StackOverflow
  • JSFiddle umožňuje testovat vlastní HTML + CSS + JavaScript přímo v prohlížeči

Validátor CSS

W3C nabízí on-line validátor CSS: http://jigsaw.w3.org/css-validator/

Správnost CSS si tak můžete ověřit několika způsoby:

  • zadáním URL (pro samotný soubor CSS nebo pro HTML včetně CSS)
  • nahráním souboru CSS
  • zkopírováním CSS do formuláře

Lze zadat také další možnosti (především verzi CSS). Validátor CSS je v současnosti přeložen i do češtiny, takže jeho ovládání je snadné.

O typech chyb a jejich příčinách (z dob, kdy byl validátor pouze v angličtině) si můžete přečíst na http://www.webtvorba.cz/css/css-validator-w3c.html.

Další koncepty

Dědičnost

Většina vlastností (především u písma) se dědí od nadřazeného elementu. Pokud tedy nějaký element nemá nějakou vlastnost definovanou, tak ji zdědí od rodiče.

Tip: pokud chcete definovat nějakou vlastnost společnou všem elementům, definujte ji pro element body. Poté můžete nastavit výjimky.

Hodnoty initial a inherit

Hodnota initial představuje počáteční hodnotu dané vlastnosti před aplikací pravidel. Lze ji také explicitně vynutit („resetování“ vlastnosti).
Hodnota inherit deklaruje, že element danou vlastnost dědí od rodiče. Tuto hodnotu lze použít i pro vlastnosti, které normálně dědičné nejsou.

Příklad: h1 {font-size: inherit;}

Specifičnost

Specifičnost určuje, která deklarace z kaskády stylů je pro daný element nejvíce relevantní. Podle toho se aplikují hodnoty daných vlastností.

Každý WWW dokument může mít 3 zdroje stylů: od autora stránky (definice CSS), od uživatele (sám si nastaví formátování v prohlížeči) nebo od výrobce prohlížeče (defaultní nastavení). Nejvyšší váhu mají styly od autora, nejnižší pak od prohlížeče.

Dále záleží na typu selektoru (ID > class > type > universal). V případě rovnosti vah vítězí pozdější pravidlo.

Specifičnost deklarace lze zvýšit uvedením !important.
Příklad: h1 {color: blue !important}

Jak přidat CSS do WWW stránky?

Definice stylů mohou být k WWW dokumentu přidány třemi způsoby:

  1. připojením externího souboru (typicky s příponou .css) ke stránce (v HTML např. značkou link),
  2. přímým zápisem definic CSS do záhlaví dokumentu (párová značka style),
  3. přidáním atributu style k libovolné značce HTML.

Nejvýhodnější je první způsob (snadná údržba vzhledu celého webu, minimalizace přenosové kapacity, optimalizace pro vyhledávače, ...).

Příklad připojení CSS I

  1. Připojení externího souboru s definicí stylů (např. styl.css) k WWW stránce (uvnitř značky head):
    • pomocí značky link:

      <link href="styl.css" rel="stylesheet" type="text/css" >
      
    • uvnitř značky style:

      <style type="text/css" >
        @import "styl.css";
      </style>
      

      Poznámka: je-li CSS soubor umístěn na jiném serveru, tak lze použít zápis: @import url("http://www.xxx.cz/yyy.css");

Příklad připojení CSS II

  1. Zápis definice stylů do záhlaví dokumentu (párová značka style):

    <style type="text/css" >
      body {color: blue}
      h1 {color: navy}
    </style>
    
  2. Přiřazení stylu přímo k nějakému elementu (hodí se pouze pro výjimečné případy, jinak je to zbytečně pracné a neuniverzální!):

    <h1 style="color: green" >nadpis</h1>
    

Media queries I

Blok @media se používá k omezení platnosti CSS jen za určitých podmínek, typicky určité schopnosti zařízení – např. jak široký je průhled (viewport)? Dovnitř bloku se zapisují běžné selektory CSS. Za slovem @media se uvede typ zařízení a/nebo podmínky, při jejichž splnění se aplikují pravidla CSS uvedená uvnitř bloku.

Příklad:

body {
  background-color: pink;
}

@media screen and (min-width: 480px) {
  body {
    background-color: lightgreen;
  }
}

Typické využití bloku @media: responzivní vzhled (viz dále).

Media queries II

Druhy médií v CSS3 (media types):

  • all = všechna zařízení
  • print = tiskárny (tj. vzhled pro tisk)
  • screen = obrazovky (počítače, tabletu, smartphonu, ...)

Nejvyužívanější „schopnosti“ médií (media features):

  • max-width = maximální šířka průhledu (např. okna prohlížeče)
  • min-width = minimální šířka průhledu (např. okna prohlížeče)

Existují desítky „schopností“, viz např. MDN Web Docs.

Media queries III

Vyzkoušejte:

Další informace:

Responzivní vzhled webu I

Responzivní vzhled webu (responsive web design, RWD), se týká optimálního rozvržení webové stránky při jejím zobrazování na různých typech koncových zařízení. Nejčastěji se řeší šířka/umístění/skrytí menu nebo velikost obrázků (aby stránku nebylo potřeba „rolovat“). Využívá media queries.

Informace o RWD:

Responzivní vzhled webu II

Jak otestovat RWD:

  • Firefox, Google Chrome: Nástroje pro vývojáře (Ctrl+Shift+I), nahoře je ikonka pro zobrazení na mobilních zařízeních (Ctrl+Shift+M). Případně pravá myš na (označený) text webové stránky a „prozkoumat“ (inspect).
  • Am I Responsive?