Werking van de submenu's op de site - uitleg
Laatst aangepast: .

Korte omschrijving
Links naar achterliggende pagina's zijn verborgen onder een kleine schermafdruk van die pagina. In grotere vensters kan in een pop-up een grotere schermafdruk worden getoond.
BELANGRIJK
Deze uitleg hoort bij het voorbeeld dat in de download zit. Het voorbeeld uit de download verschilt iets van het voorbeeld hier op de site. In de download ontbreekt bijvoorbeeld de navigatie voor de site. Ook in de kopregels zit vaak wat verschil. Daarnaast kunnen er nog andere (meestal kleine) verschillen zijn.
Als je deze uitleg leest naast de broncode van het voorbeeld op de site, kan het dus bijvoorbeeld zijn dat 'n <h1> uit de css bij 'n <h2> uit de html hoort. Maar het gaat niet om hele grote, fundamentele afwijkingen.
Als je dit lastig vindt, kun je bovenaan de pagina de hele handel downloaden. In de download zit 'n voorbeeld dat wel naadloos aansluit op de uitleg in de download.
Alles op deze site kan vrij worden gebruikt, met twee beperkingen:
* Je gebruikt het materiaal op deze site volledig op eigen risico. Het kan prima zijn dat er fouten in de hier verstrekte info zitten. Voor eventuele schade die door gebruik van materiaal van deze site ontstaat, in welke vorm dan ook, zijn www.css-voorbeelden.nl en medewerkers daarvan op geen enkele manier verantwoordelijk.
* Deze uitleg wordt regelmatig bijgewerkt. Het is daarom niet toegestaan deze uitleg op welke manier dan ook te verspreiden, zonder daarbij duidelijk te vermelden dat de uitleg afkomstig is van www.css-voorbeelden.nl en dat daar altijd de nieuwste versie is te vinden. Dit is om te voorkomen dat er verouderde versies worden verspreid.
Een link naar www.css-voorbeelden.nl wordt trouwens altijd op prijs gesteld.
Alle code is geschreven in een afwijkende
lettersoort en -kleur. De code die te maken heeft met de basis van dit voorbeeld (essentiële code), is in de hele uitleg onderstippeld blauw
. Alle niet-essentiële code is bruin
. (In de inhoudsopgave staat alles vanwege de leesbaarheid in een gewone letter.)
Opmerkingen
- De foto's zijn gemaakt in het Vondelpark in Amsterdam op Koninginnedag 2009. Als je jezelf herkent en de originele foto wilt hebben, stuur dan even 'n mailtje naar info@css-voorbeelden.nl.
-
Hoewel de code behoorlijk is aangepast, lijkt dit voorbeeld toch nog redelijk veel op wat er op de site gebeurt. En eh, hm, tja, eh, nou ja... Bij het maken van dit voorbeeld zijn er enkele tientallen (heel) kleine foutjes op de site aan het licht gekomen. Goed, praten we niet meer over.
(Maar simpelweg door het gedetailleerd beschrijven van wat er gebeurt, word je dus gedwongen heel kritisch te kijken. En dat werkt prima. Een fout ter grootte van een olifant zie je zo wel. Het vangen van een fout ter grootte van een springende vlo, daar helpt het schrijven van zo'n gedetailleerde uitleg prima bij.)
-
Als je in een desktopbrowser met behulp van zoomen het beeld vergroot, heeft dit hetzelfde effect, als wanneer de pagina in een kleiner browservenster wordt getoond. Je kunt hiermee dus kleinere apparaten zoals een tablet of een smartphone simuleren. Maar het blijft natuurlijk wel een simulatie: het is nooit hetzelfde als testen op een écht apparaat. Zo kun je bijvoorbeeld aanrakingen alleen echt testen op een echt touchscreen.
Inmiddels hebben veel browsers mogelijkheden voor het simuleren van weergave op een kleiner scherm in de ontwikkelgereedschappen ingebouwd. Ook dit blijft een simulatie, maar geeft vaak wel een beter beeld dan zoomen.
- Op de site zit boven de pagina's met submenu's een menubalk voor navigatie binnen de site. Die ontbreekt (uiteraard) in het voorbeeld. Om een enigszins gelijksoortige pagina te krijgen, zit daarom boven de knoppen een <h1>, die – net als op de site – niet meescrolt.
- De css voor de hulppagina's achter de knoppen zit in een aparte stylesheet ('menu-019-hulp-dl.css' in de map '019-css-dl'). Deze is dermate simpel, dat die hier verder niet wordt besproken. Normaal genomen zou deze css worden samengevoegd met de css voor het voorbeeld zelf, maar om verwarring te voorkomen staat het hier in een aparte stylesheet.
-
In tegenstelling tot wat elders in dit artikel wordt beweerd, zijn de thumbnails op de knoppen en de afbeeldingen in de pop-ups geen schermafdrukken van de pagina's achter die knoppen. Dat zou weinig opwindend zijn, want op die pagina's staan alleen teksten als 'Dit is de pagina achter de derde knop: drummen.' Als iemand wel opgewonden raakt van zo'n tekst, zou ik haar of hem ernstig aanraden toch 'ns gewoon 'n kroeg in te lopen en daar een gesprek te beginnen over maakt-niet-uit-wat, als het maar niet over websites gaat.
Voor alle mensen die niet opgewonden raken, zijn in plaats van schermafdrukken foto's van kinderen gebruikt.
- Belangrijke informatie moet nooit alleen in een pop-up of zoiets worden gezet. Als om een of andere reden die pop-ups niet (kunnen) worden geopend, is de informatie volstrekt onzichtbaar. In dit voorbeeld staan alleen grotere versies van de thumbnails en een korte omschrijving daarvan in de pop-up. Als dat wordt gemist, vallen er niet direct doden door.
- Als een pagina achter een knop is bezocht, staat – in bredere browservensters – een vinkje naast het vraagteken. Om dat vinkje weer weg te krijgen, moet je de geschiedenis van de browser verwijderen (de bezochte pagina's). In (vrijwel) elke browser is via het menu ergens een instelling te vinden, waarmee dit kan.
Links in deze uitleg, vooral links naar andere sites, kunnen verouderd zijn. Op de pagina met links vind je steeds de meest recente links.
Alles op deze site is gemaakt op een systeem met Linux (Kubuntu). Daarbij is vooral gebruik gemaakt van Komodo Edit, GIMP en Firefox met extensies. De pdf-bestanden zijn gemaakt met LibreOffice.
Vragen of opmerkingen? Fout gevonden? Ga naar het forum.
Achterliggend idee
Toen ik met deze site begon, bestonden touchscreens nog nauwelijks. En van een tablet of smartphone had niemand nog ooit gehoord.
Op de oorspronkelijke site kon je op 'n knop klikken, waarna de bijbehorende pagina werd geopend. Als je met de muis over de knop hoverde, verscheen een pop-up met een schermafdruk van de pagina achter de knop.
In grote lijnen ziet het er nog steeds zo uit, maar de achterliggende code is volledig veranderd. Dat gebeurde op de site eerst met het betere plakband en paperclipwerk. Op touchscreens werkte het niet, dus werd er aan elke pagina een compleet menu toegevoegd speciaal voor touchscreens. Vervolgens bleek dat mensen zelfs zo'n uitleg op een smartphone gaan zitten lezen (lijkt me gruwelijk, maar goed). Dus 'n schuifmenu voor smartphones erbij. Microsoft ontdekte het touchscreen en maakte 'n geheel eigen bewerking van hoveren. Niet eens zo gek, maar helaas veranderde dat in de volgende versie van Internet Explorer weer geheel. En over Apple wil ik het niet hebben, want die grossiert in eigenaardigheden (Applefans: gelieve hier 'verbeteringen' te lezen).
Oftewel: de code had inmiddels meer weg van een afgekoeld en daardoor niet meer te eten bord spaghetti, dan van ordentelijke html en css.
Een tijd geleden zijn daarom de pagina's met menu's en dergelijke van de grond af volledig herschreven. (Een groot deel van de voorbeelden zelf moet nog worden herschreven voor touchscreens en dergelijke.)
Daarbij was er een aantal voorwaarden, en die voorwaarden gelden dus ook voor dit voorbeeld:
* De pagina moet werken op elke breedte, van heel smal tot heel breed.
* Menu's en dergelijke moeten er maar één keer in staan. De code moet niet drie keer worden herhaald voor drie verschillende menu's.
* De toelichtende tekst boven de pop-ups moet in elk browservenster te zien zijn, ook in hele smalle vensters waarin geen ruimte is voor een pop-up.
* De pop-ups moeten ook voor gebruikers van de Tab-toets te openen zijn.
* De toelichtende tekst boven de pop-ups moet ook door schermlezers voorgelezen kunnen worden.
* De pop-ups moeten geopend kunnen worden door middel van aanraken en hoveren.
* Bij een andere lettergrootte en bij zoomen moet alles redelijk blijven werken.
* Omdat deze site nou eenmaal over css (en html) gaat, moet het niet afhankelijk zijn van JavaScript, of in ieder geval moet JavaScript niet essentieel zijn voor de werking.
* De tekst in het midden van de pagina (in smalle browservensters onderaan de pagina) moet in alle vensters volledig te lezen zijn, ook op touchscreens.
* Bovenaan de pagina moet een menubalk voor navigatie binnen de site staan, en die moet altijd in beeld blijven, ook als er wordt gescrold. (In het voorbeeld is die vervangen door een <h1>, die altijd in beeld blijft.)
* Het moet ook acceptabel zijn in browsers die dingen als calc()
niet kennen. Internet Explorer 8 ondersteun ik niet meer, maar in iets nieuwere browsers moet alles redelijk werken.
Ik geloof dat bovenstaande lijstje redelijk is gelukt.
De tekst in het midden staat eigenlijk helemaal los van de rest van de pagina. Het is 'n simpele kolom, waarvan breedte en hoogte worden aangepast aan breedte en hoogte van het browservenster. Rondom deze kolom met tekst staan de knoppen van het menu. (In browservensters smaller dan 763 px óf lager dan 543 px staat de kolom met tekst niet tussen, maar onder de knoppen. Dat is kleiner dan 1024 x 768 px, een veel voorkomende maat voor tablets.)
In vensters met een hoogte tussen 543 en 712 px is geen ruimte voor vier knoppen links en rechts van de kolom met tekst. In die vensters staan links en rechts twee knoppen, en de resterende vier knoppen staan onder de kolom met tekst. Door scrollen van de tekst kan de tekst toch volledig worden gelezen. Omdat het mogelijk onduidelijk is dat de tekst onderaan nog doorloopt, staat in deze vensters onderaan de tekst een doorzichtige gradiënt over de tekst heen.
De acht knoppen met bijbehorende teksten, pop-up, enz. staan elk in een eigen lijst-item <li>. Door ze elk in een eigen, volledig op zichzelf staande, <li> te zetten, is het relatief makkelijk de knoppen op de juiste plaatsen neer te zetten. Relatief, want er zat een complete kudde beren op de weg. (Heet 'n groep beren wel 'n kudde???)

In kleinere browservensters is geen ruimte voor een grote pop-up met een voorbeeld van de onder de knop zittende pagina. Voor kleinere vensters is daardoor veel minder html en css nodig. De rest van de code, die voornamelijk voor de pop-up is, wordt voor deze vensters gewoon verborgen.
In elke <li> zit een thumbnail: een kleine afbeelding van de pagina achter de link in de knop.
Als alle tussenliggende <span>'s en dergelijke worden weggelaten – die zijn alleen nodig voor de pop-ups en dergelijke –, volgt daarop een <span> met een omschrijving van de afbeelding. In smallere browservensters staat deze niet in de pop-up, maar gelijk naast de thumbnail. De thumbnails zelf worden iets verkleind weergegeven. Daar worden geen aparte afbeeldingen voor gebruikt, want dat levert nauwelijks kleinere bestanden op. Ze worden niet echt veel verkleind.
Ten slotte is er dan nog een gewone link, een <a>, die naar de pagina leidt. Deze wordt over de thumbnail gezet, waardoor de thumbnail als link naar de achterliggende pagina werkt.
Als je dan nog wat schaduw, lijntjes, ronde hoekjes en dergelijke toevoegt, ziet het geheel eruit als op bovenstaande afbeelding.

In browservensters met een minimale breedte van 763 px én een minimale hoogte van 543 px is ruimte om, links en rechts van de kolom met tekst, vier thumbnails onder elkaar te zetten. De thumbnails worden nu niet meer verkleind, maar op ware grootte weergegeven.
Omdat de tekst in de middelste kolom tot de onderkant van het venster doorloopt, is duidelijk dat er onder het venster nog meer tekst staat. Ook wanneer, zoals op veel touchscreens het geval is, een scrollbalk ontbreekt.
Bij openen van de pagina moet je eerst in de tekst klikken, voordat het scrollwieltje van de muis, pijltjestoetsen, en dergelijke werken. Om dat te voorkomen is bovenaan de kolom met tekst een <input> met het attribuut autofocus
neergezet.
Hierdoor werken scrollwieltje, pijltjestoetsen, en dergelijke zonder dat eerst in de tekst geklikt moet worden. Dit verandert wel de volgorde van de tabindex: bij gebruik van de Tab-toets wordt eerst door de kolom met tekst gelopen, en daarna volgen de knoppen links en rechts.
Veel maakt dat volgens mij in dit geval niet uit, want er is iets te zeggen voor het eerst door de tekst lopen, en er is iets te zeggen voor het eerst door de knoppen lopen. Verwarring zal hier niet door ontstaan. Overigens is dit vrij simpel te voorkomen door in de html de kolom met tekst boven de lijst met knoppen te zetten. Als de tekst bovenaan staat, werkt het scrollwieltje ook gelijk zonder klikken.
Op de site kan de volgorde niet worden veranderd, omdat er nog veel meer links in die lijst staan. Daarom heb ik de volgorde in het voorbeeld ook niet veranderd, want dat zou weer 'n extra verandering ten opzichte van de site zijn. Bovendien maakt het in dit geval niets uit.

In browservensters met een minimale breedte van 763 px is genoeg ruimte voor een thumbnail links en rechts van de kolom met tekst. Maar alleen bij een minimale hoogte van 712 px passen er vier thumbnails onder elkaar. Daarom worden bij een minimale breedte van 763 px én een hoogte tussen 543 px en 712 px links en rechts van de tekst slechts twee knoppen neergezet. De andere vier knoppen komen onderaan te staan.
(Als je je inmiddels afvraagt hoe ik aan die krankzinnige grenzen kom: dat is gewoon een kwestie van uitproberen. Kijken wat het beste uitkomt in verschillende vensters. Bij een andere breedte van bijvoorbeeld de pop-ups zul je de waarden van de grenzen moeten aanpassen.)
Op de afbeelding is het browservenster 967 px breed en 661 px hoog. De knoppen worden verticaal en horizontaal zo goed mogelijk verdeeld over het venster. In browsers die calc()
niet kennen, staan de middelste knoppen (van boven naar beneden gezien) gelijk onder de bovenste twee knoppen. Minder netjes, maar het werkt allemaal wel.
Onderaan de tekst is over de tekst een doorzichtige gradiënt neergezet, zodat ook in vensters zonder scrollbalk duidelijk is dat de tekst nog doorloopt. Door het gebruik van pointer-events: none;
kan tekst onder deze gradiënt op de normale manier worden geselecteerd, gekopieerd, en dergelijke.
Anders dan in browservensters smaller dan763 px of lager dan 543 px is de toelichting bij de thumbnails hier verdwenen. Hierdoor is er ruimte om alle acht de thumbnails gelijktijdig in het venster van de browser te tonen. De toelichting, en een grotere schermafdruk, kunnen worden getoond door een pop-up te openen. Ook deze pop-up werkt volledig met css.
Elke thumbnail met bijbehorende pop-up, link, enz. staat in een eigen lijst-item <li>. Onder de thumbnail, een gewone <img>, staat een radioknop. (De <input>'s met id="open-1", id="open-2", enz.) Deze radioknoppen zijn verborgen.
Onder elke radioknop staat een bijbehorend <label>. (De <label>'s met class="open".) Dat <label> zorgt voor het doorzichtige witte vierkantje met het vraagteken. Het vraagteken zelf zit in een <span> met class="vraagteken" binnen de <label>. Door op de <label> te klikken of dit aan te raken, wordt de bijbehorende radioknop geselecteerd. Omdat alle acht de radioknoppen in dezelfde groep zitten, kan er steeds slechts één worden geopend. Zodra je via de <label> een andere radioknop selecteert, wordt een eventuele andere radioknop gedeselecteerd. En zal een eventueel daarbij horende pop-up daardoor worden gesloten.
Binnen de <label> staat, in een aparte <span> met class="pop-up-tekst", de toelichtende tekst bij de thumbnail. Deze tekst is normaal genomen niet te zien. Pas als de bijbehorende radioknop is geselecteerd, wordt de in de <label> zittende tekst in een pop-up getoond.
In de <label> zit ook nog een <span> met class="pop-up". Zodra een radioknop is geselecteerd, krijgt deze <span> een achtergrond-afbeelding: een grotere uitvoering van de thumbnail. Omdat deze pas wordt getoond als de radioknop is geselecteerd, wordt deze grotere afbeelding pas gedownload, als deze daadwerkelijk wordt bekeken.
De <label> is ook gevoelig is voor hoveren. Hierdoor openen toelichting en grotere afbeelding ook, als over het witte blokje met het vraagteken wordt gehoverd.
De plaats van de pop-up is afhankelijk van de plaats van de thumbnail.
In de link naar de achterliggende pagina zit nog een <span> met class="naam". Hierin zit de naam van de pagina. Deze wordt zichtbaar gemaakt, zodra over het witte vlakje met het vraagteken wordt gehoverd, of zodra dit wordt aangeklikt of aangeraakt.
Er zit nog een negende radioknop in de groep radioknoppen. Deze staat helemaal bovenaan de pagina en hoort niet specifiek bij een bepaalde thumbnail.
Binnen elke <li> zit onderaan nog een <label> met class="sluit". Deze <label>'s horen bij deze negende radioknop. Zodra een van de acht bij een knop horende radioknoppen is geselecteerd, zorgt dit label.sluit
voor het tonen van een rood sluitkruis. Dit is een gewone letter 'x', die wat is opgeleukt. Door hierop te klikken of dit aan te raken, wordt de negende radioknop geselecteerd. Waardoor een geopende pop-up weer verdwijnt, want de bij de pop-up horende radioknop is nu niet meer geselecteerd.
De diverse witte vlakjes, vraagtekens, sluitkruizen, en dergelijke worden met behulp van nogal wat berekeningen steeds op de juiste plaats ten opzichte van de bijbehorende knop gezet.

In browservensters met een maximale hoogte van 712 px staan vier van de thumbnails onderaan het venster. In vensters met een breedte tussen 763 en 1073 px levert dit een probleem op: als de zesde of zevende pop-up wordt geopend, valt deze net buiten het venster. Op de afbeelding is het venster 787 px breed en 712 px hoog. De zesde pop-up valt hier voor een groot deel buiten het venster.
Daarom worden in deze vensters de zesde en zevende pop-up met behulp van transform
verkleind. Dat is verreweg de makkelijkste manier om dit op te lossen. Uiteraard moet dan ook weer de positie worden aangepast. En dan blijken de letters te klein te worden, dus die worden weer vergroot. En zo houd ik mezelf aardig van de straat en voorkom dat ik een hangoudere word.

Als een pagina is bezocht, verschijnt een klein vinkje naast het vraagteken. Dit vinkje bestaat uit twee borders, die wat worden gedraaid en zo. Ze zitten in een pseudo-element dat met behulp van ::after
aan span.naam
, een <span> met de naam van de pagina, wordt toegevoegd.
Feitelijk is dit vinkje altijd aanwezig, ook als de pagina nog niet is bezocht. Maar het wordt pas zichtbaar, als de pagina is bezocht. Dat kan door in de css te controleren op a:visited
: is de link bezocht?
Tot 'n paar jaar geleden kon je met behulp van :visited
de wildste dingen doen. Omdat het kinderlijk eenvoudig bleek met behulp van wat JavaScript uit te lezen, welke sites waren bezocht, kun je :visited
nog slechts voor een beperkt aantal dingen gebruiken. Dat geldt ook voor dit pseudo-element, want span.naam
zit in de <a> en is dus onderdeel van de link.
Eén van de dingen die nog kan worden veranderd, is de kleur. Het vinkje is altijd aanwezig, maar als de link nog niet is bezocht, heeft het (vrijwel) dezelfde achtergrondkleur als het witte vlakje met het vraagteken. Als de link is bezocht, wordt de kleur van het vinkje veranderd, waardoor het zichtbaar wordt.
Sommige mensen kunnen of willen geen muis gebruiken om een link aan te klikken, een pop-up te openen, een <input> te bezoeken, of wat dan ook. Je kunt ook links, <input>'s, enz. bezoeken door de Tab-toets in te drukken. (Over hoe dit precies werkt, is meer te vinden bij Tabindex.)
In elke <li> zit een link. Als die met behulp van de Tab-toets wordt bezocht, focus heeft, wordt die link gevolgd door het indrukken van Enter. Door in de css te checken op a:focus
zou je de op de link volgende pop-up kunnen openen, als de link focus heeft. Maar helaas zit de pop-up vóór de link in de html, dat kan niet anders. Dus dat werkt hier niet. Dat zou betekenen dat gebruikers van de Tab-toets wel de link kunnen volgen, maar de pop-up niet zien.
Je zou ook een pop-up kunnen openen als de radioknop voor de pop-up focus heeft. Maar ook dat werkt niet, want als een radioknop focus heeft, kunnen andere radioknoppen uit diezelfde groep geen focus meer krijgen. (Je selecteert een radioknop in een bepaalde groep door te bewegen met de pijltjes.)
Daarom is in elke <li> aan het begin een <span> met class="focus-open" toegevoegd. Een <span> wordt normaal genomen niet bezocht door de Tab-toets, maar wel als je tabindex="0"
aan de <span> toevoegt. Door de selector span.focus-open:focus
te gebruiken, kan de pop-up worden geopend zodra de<span> focus heeft.
Bij de volgende tab gaat de focus van de <span> naar de daarop volgende <a> en kan de link worden gevolgd. Dit wordt nog wat verduidelijkt door wat kleurtjes en zo.
De <span> voor de Tab-toets wordt volledig verborgen, waardoor hij geen enkele invloed heeft op touchscreens. Als de <span> aangeraakt zou kunnen worden, zou hij problemen opleveren op iOS, omdat op dat systeem de pop-up geopend zou blijven, tot een ander element focus zou krijgt. Een van de verbeteringen van Apple waar je hartstikke gek van wordt.
Je zou de pop-up ook kunnen openen, als de <label> met het vraagteken focus krijgt. Maar dat werkt om dezelfde reden niet op iOS: pas als een ander element focus zou krijgen, zou de pop-up weer sluiten. Los van of de radioknop die bij de <label> hoort, is geselecteerd of niet.
Als je 'n nieuwe pop-up opent, sluit de vorige, want de nieuwe pop-up heeft dan focus. Maar de laatste pop-up blijft altijd geopend, tot een ander element focus krijgt. Dat is uiterst verwarrend, vandaar de volledig aparte <span> voor gebruikers van de Tab-toets.
Meer over de Tab-toets, tabindex, en dergelijke kun je vinden bij Tabindex. Meer over focus bij focus.
Als dit zo zou worden gebruikt, met al die <input>'s, <label>'s en andere ongein, zouden gebruikers van een schermlezer massaal de weg kwijtraken. Die hebben daar helemaal niets aan. De schermlezer moet gewoon de links en de toelichting voorlezen, en dat is het.
Daarom worden veel elementen verborgen voor schermlezers met behulp van de WAI-ARIA-code aria-hidden="true"
. Dat kan niet met de <label> waarbinnen de toelichting staat, want dan wordt ook de toelichting genegeerd. Die <label> is veranderd in een element zonder betekenis met behulp van role="presentation"
. Wat betreft schermlezers is de <label> hiermee hetzelfde geworden als een gewone <span> of zoiets.
Meer over WAI-ARIA-codes is te vinden bij Semantische elementen en WAI-ARIA.
De voorvoegsels -moz-, -ms- en -webkit-
Voordat een nieuwe css-eigenschap wordt ingevoerd, is er in de regel een experimentele fase. Browsers passen het dan al toe, maar met een aangepaste naam. Tijdens deze fase kunnen problemen worden opgelost en worden veldslagen uitgevochten, over hoe de standaard precies moet worden toegepast.
Als iedereen het overal over eens is en alle problemen zijn opgelost, wordt de officiële naam uit de standaard gebruikt.
De belangrijkste browsers hebben elk een eigen voorvoegsel:
Firefox: -moz-
, naar de maker: Mozilla.
Op webkit gebaseerde browsers, zoals Google Chrome, Opera, Safari en Android browser: -webkit-
.
(Google Chrome is van webkit overgestapt op een eigen weergave-machine: Blink. Blink gaat geen voorvoegsels gebruiken. Het is echter een aftakking van webkit, dus het zal nog wel even duren voor -webkit-
hier helemaal uit is verdwenen. Ook Opera gebruikt Blink.)
Internet Explorer: -ms-
, naar de maker: Microsoft.
In dit voorbeeld worden hyphens
, linear-gradient
, transform
, @-webkit-keyframes
, -webkit-animation
en -webkit-overflow-scrolling
gebruikt.
Zodra de experimentele fase voorbij is, wordt het voorvoegsel weggelaten. Omdat dat moment niet bij alle browsers hetzelfde is, zet je nu ook al de officiële naam erbij. Deze wordt als laatste opgegeven. Bijvoorbeeld Android browser herkent -webkit-linear-gradient
. Zodra Android browser linear-gradient
gaat herkennen, zal dit -webkit-linear-gradient
overrulen, omdat het er later in staat. Dat ze er beide in staan, is dus geen enkel probleem.
-webkit-animation en @-webkit-keyframes
Deze twee eigenschappen worden alleen maar gebruikt om een bug in sommige oudere op webkit gebaseerde browsers te repareren. Daarom hoeft alleen maar op browsers gelet te worden, die op webkit zijn gebaseerd. In dit geval is daarom het volgende voldoende:
{-webkit-animation: ...;}
Hetzelfde geldt voor @keyframes
:
@-webkit-keyframes{...}
In nieuwere browsers is deze bug niet meer aanwezig, dus de versie zonder voorvoegsel hoeft in dit geval helemaal niet gebruikt te worden.
(In het algemeen is het een bijzonder slechte gewoonte om van een eigenschap alleen één bepaalde versie te gebruiken. Dit gebeurt nogal eens voor iOS, waarmee Apple actief wordt geholpen om sites en dergelijke ontoegankelijk te maken voor andere browsers dan Safari. Ontwikkelaars die dit doen, werken mee aan de totstandkoming van eenzelfde wantoestand als in het verleden met het monopolie van Internet Explorer 6 heeft bestaan.
Maar in dit geval maakt het niet uit, omdat het alleen om een bug gaat. Andere browsers hebben deze css helemaal niet nodig.)
-webkit-overflow-scrolling
Als op iOS niet de hele pagina, maar binnen een element wordt gescrold, zoals hier bij de tekst binnen <main> gebeurt, gaat dat scrollen om een of andere duistere reden ongelooflijk schokkerig. Met deze eigenschap kan voor vloeiend scrollen worden gezorgd.
Omdat dit alleen voor iOS nodig is, wordt van deze eigenschap ook alleen de -webkit-
versie gebruikt: buiten iOS is hij niet nodig (en werkt ook niet).
hyphens
Op dit moment moet je nog het volgende schrijven:
{-moz-hyphens: ...; -ms-hyphens: ...; -webkit-hyphens: ...; hyphens: ...;}
In de toekomst kun je volstaan met:
{hyphens: ...;}
In de laatste twee versies van Firefox is het voorvoegsel -moz-
niet meer nodig. Maar omdat dat pas sinds heel kort zo is, gebruik ik het op dit moment nog.
linear-gradient
Op dit moment moet je nog het volgende schrijven:
{-webkit-linear-gradient(...); linear-gradient();}
In de toekomst kun je volstaan met:
{linear-gradient(...);}
transform
Op dit moment moet je nog het volgende schrijven:
{-ms-transform: ...; -webkit-transform: ...; transform: ...;}
In de toekomst kun je volstaan met:
{transform: ...;}
Inmiddels is de algemene mening dat 'vendor prefixes', zoals deze voorvoegsels in het Engels heten, geen groot succes zijn. Eén van de grootste problemen: veel sitemakers gebruiken alleen de -webkit-
variant. Daar kwamen ze in het verleden nog mee weg, omdat Apple op mobiel zo'n beetje 'n monopolie had. Inmiddels is dat niet meer zo, maar deze gewoonte bestaat nog steeds. Waardoor 'n site alleen in op webkit georiënteerde browsers goed is te bekijken.
Dit is zo'n groot probleem dat andere browsers soms de variant met -webkit-
ook maar zijn gaan implementeren, naast de standaard. Want als 'n site het niet goed doet in 'n bepaalde browser, krijgt in de regel niet de site maar de browser de schuld.
Voorlopig zijn we echter nog niet van deze voorvoegsels af. Als je ze gebruikt, gebruik dan álle varianten, en eindig met de variant zonder voorvoegsel, zoals die uiteindelijk ooit gebruikt gaat worden. Als je alleen de -webkit-
variant gebruikt, ben je in feite 'n onbetaalde reclamemaker voor Apple.
Semantische elementen en WAI-ARIA
Deze twee onderwerpen zijn samengevoegd, omdat ze veel met elkaar te maken hebben.
Semantische elementen
De meeste elementen die in html worden gebruikt, hebben een semantische betekenis. Dat wil zeggen dat je aan de gebruikte tag al (enigszins) kunt zien, wat voor soort inhoud er in het element staat. In een <h1> staat een belangrijke kop. In een <h2> staat een iets minder belangrijke kop. In een <p> staat een alinea. In een <table> staat een tabel (en geen lay-out, als het goed is!). Enz.
Door het op de goede manier gebruiken van semantische elementen, kunnen zoekmachines, schermlezers, enz. de structuur van een pagina begrijpen. De spider van een zoekmachine is redelijk te vergelijken met een blinde. Het is dus ook in je eigen belang, om semantische elementen zo goed mogelijk te gebruiken. Een site die toegankelijk is voor mensen met een handicap, is in de regel ook goed te verwerken door een zoekmachine en maakt dus een grotere kans gevonden en bezocht te worden.
Als het goed is, wordt het uiterlijk van de pagina bepaald met behulp van css. Het uiterlijk staat hierdoor (vrijwel) los van de semantische inhoud van de pagina. Met behulp van css kun je een <h1> heel klein weergeven en een <h6> heel groot, terwijl schermlezers, zoekmachines, en dergelijke nog steeds weten dat de <h1> een belangrijke kop is.
Slechts enkele elementen, zoals <div> en <span>, hebben geen semantische betekenis. Daardoor zijn deze elementen uitstekend geschikt, om met behulp van css het uiterlijk van de pagina aan te passen: de semantische betekenis verandert niet, maar het uiterlijk wel. Voor een schermlezer of zoekmachine verandert er (vrijwel) niets, voor de gemiddelde bezoeker krijgt het door de css een heel ander uiterlijk.
(De derde laag, naast html voor de inhoud en css voor het uiterlijk, is JavaScript. Die zorgt voor de interactie tussen site en bezoeker. De min of meer strikte scheiding tussen css en html aan de ene kant en JavaScript aan de andere kant is met de komst van css3 en html5 veel vager geworden. Je kunt nu bijvoorbeeld ook met css dingen langzaam verplaatsen en met html deels de invoer in formulieren controleren.)
Html5 heeft een aantal nieuwe elementen, die speciaal zijn bedoeld om de opbouw van een pagina aan te geven. In dit voorbeeld worden van deze nieuwe semantische elementen <main>, <nav> en <header> gebruikt. <main> voor de belangrijkste inhoud: de kolom met tekst; <nav> voor het navigatiedeel met de links en <header> voor de kop van de pagina.
(De kolom met tekst is hier natuurlijk niet het belangrijkste, omdat het in dit voorbeeld om de navigatie gaat. Maar normaal genomen zou de tekst waarschijnlijk wel het belangrijkste onderdeel van de pagina zijn.
Met behulp van dit soort nieuwe semantische elementen kan bijvoorbeeld een schermlezer in één keer een heel menu passeren en gelijk naar de echte inhoud gaan. Alleen hadden deze nieuwe elementen tot voor kort één probleem: ze hadden in de praktijk nog weinig nut, omdat schermlezers en dergelijke ze nog niet herkenden. Daarom werd een zogenaamde WAI-ARIA-code toegevoegd aan de <main>. Dat is een al veel langer bestaande code, die schermlezers en dergelijke wel herkennen. Voor een <main> ziet dat er zo uit:
<main role="main">
Inmiddels is dit behoorlijk veranderd. Het advies is nu, om deze speciale toevoeging niet meer te gebruiken, omdat de meeste schermlezers en dergelijke een <main> inmiddels herkennen.
WAI-ARIA-codes
WAI-ARIA wordt vaak ingekort tot ARIA. Voluit betekent het Web Accessibility Initiative – Accessible Rich Internet Applications.
Er worden in dit voorbeeld twee WAI-ARIA-codes gebruikt: aria-hidden
en role="presentation"
.
aria-hidden
Met behulp van aria-hidden="true"
kan een deel van de code worden verborgen voor schermlezers en dergelijke, zodat dit niet wordt voorgelezen. Op de normale weergave op het scherm heeft dit verder geen enkele invloed.
In dit voorbeeld kunnen de <input>'s en <label>'s voor schermlezers uiterst verwarrend zijn, terwijl ze voor schermlezers geen enkel nut hebben. Daarom is het beter ze te verbergen voor schermlezers.
Bij input, .vraagteken, .sluit worden alle <input>'s verborgen met behulp van display: none;
. Dit verbergt ze ook voor schermlezers, dus hier is verder geen extra code voor nodig.
De <label> die wordt gebruikt om de pop-up te sluiten, kan niet op deze manier worden verborgen. Deze moet in grotere browservensters getoond worden, als een pop-up is geopend door klikken of aanraken. In bepaalde situaties kan een schermlezer dit element aankondigen als 'label', wat erg verwarrend kan zijn. Bovendien zit in de <label> de letter 'x', die braaf wordt voorgelezen door de schermlezer.
Om deze <label> voor schermlezers te verbergen, is aan deze <label> aria-hidden="true"
toegevoegd:
<label class="sluit" for="sluit-x" aria-hidden="true">x</label>
Aan het begin van de tekst in de middelste kolom is een <input> neergezet:
<input id="checkbox-voor-focus" type="checkbox" aria-hidden="true" autofocus>
Deze <input> heeft geen enkele zichtbare werking. Maar door het gebruik van het attribuut autofocus
wordt de focus op de tekst gezet. Als dat niet zou gebeuren, moet eerst in de tekst worden geklikt, voordat de tekst kan worden gescrold met behulp van scrollwieltje of pijltjes. Meer hierover is te vinden bij checkbox-voor-focus.
Voor schermlezers kan deze <input> verwarrend zijn. Bovendien heeft hij daar geen enkel nut. Daarom wordt deze <input> met behulp van aria-hidden="true"
voor schermlezers verborgen.
Bij elke thumbnail zit ook nog een <span> met daarin een vraagteken:
<span class="vraagteken" aria-hidden="true" title="Klik om pop-up open te houden">?</span>
Ook dit vraagteken heeft geen enkel nut voor schermlezers. Maar het wordt wel voorgelezen. Daarom wordt ook deze <span> voor schermlezers verborgen.
role="presentation"
De <label> die bij de <inpu>t's voor het openen van de pop-ups hoort, kan niet zonder meer volledig voor schermlezers worden verborgen. Want in deze <label> zit ook de beschrijving van de thumbnails, en die moet wel worden voorgelezen.
Daarom wordt deze <label> niet verborgen, maar voor schermlezers met behulp van het attribuut role="presentation"
veranderd in een element zonder enige semantische betekenis. Een soort <span> of <div>:
<label class="open" for="open-2" role="presentation">
Nu wordt de omschrijving van de thumbnails gewoon voorgelezen, zonder dat de <label> een eventueel storende werking heeft voor gebruikers van een schermlezer.
Tabindex
Links, invoervelden in formulieren, en dergelijke kunnen met behulp van de Tab-toets (of een soortgelijke toets) één voor één worden bezocht, in de volgorde waarin ze in de html voorkomen. Shift+Tab-toets keert de volgorde van de Tab-toets om. Dit is een belangrijk hulpmiddel voor mensen die om een of andere reden de muis niet kunnen of willen gebruiken. (En het is vaak ook veel sneller dan de muis, vooral in formulieren.)
In sommige browsers en/of besturingssystemen is dit vreemd genoeg standaard uitgeschakeld en is een zoektocht in de instellingen nodig om dit aan te zetten. Maar gebruikers van de Tab-toets zullen dit al hebben gedaan.
Als je met behulp van de Tab-toets een element hebt bereikt, heeft dit 'focus': als het een link is en je drukt op Enter, wordt de link gevolgd. Bij een tekstveld kun je tekst gaan invoeren. Enz.
De Tab-toets volgt normaal genomen de volgorde van de elementen in de html. Het maakt niet uit, in welke volgorde ze op het scherm staan. Als je met behulp van css de elementen van plaats verwisselt op het scherm, wordt toch gewoon de volgorde in de html gevolgd.
De volgorde van de Tab-toets kan worden veranderd met behulp van het tabindex
-attribuut: <div tabindex="3">
. Deze <div> zal nu als derde worden bezocht, ook al krijgt een simpele <div> normaal genomen nooit bezoek van de Tab-toets.
Normaal genomen is het gebruik van een tabindex niet nodig. Het is zeker niet bedoeld om de bezoeker als een kangoeroe op een hindernisbaan van onder via links over rechts naar boven te laten springen. Maar soms kan het handig zijn voor kleinere correcties, als de normale volgorde in de html niet optimaal is. Of om een element bereikbaar te maken voor de Tab-toets, zoals de hierboven genoemde <div>.
Schermlezers blijven altijd de volgorde van de html volgen, dus als de tabindex sterk afwijkt van de volgorde in de html, kan dat behoorlijk verwarrend zijn.
De tabindex kan drie verschillende waarden hebben: -1, 0 of een positief getal.
In principe is de volgorde bij gebruik van de Tab-toets als volgt: eerst worden alle positieve getallen in volgorde afgewerkt. Als twee tabindexen dezelfde waarde hebben, wordt de volgorde in de html aangehouden. Een waarde van '0' wordt, afhankelijk van browser en besturingssysteem, verschillend behandeld, waarover iets hieronder bij Tabindex="0" meer.
Bovenaan de pagina staat een <input>, en bij elke thumbnail staat ook een <input>. Normaal genomen worden die ook bezocht door de Tab-toets. Maar omdat deze met display: none;
zijn verborgen, worden ze genegeerd door de Tab-toets. Precies de bedoeling, want voor gebruikers van de Tab-toets hebben deze <input>'s in dit geval geen enkel nut.
tabindex="-1"
Een negatieve waarde van -1 zorgt ervoor dat het element volledig wordt genegeerd door de Tab-toets. Zelfs een link met een negatieve tabindex wordt volledig genegeerd. Normaal genomen heeft een tabindex="-1"
maar één nut: je kunt dan met behulp van JavaScript toch focus aan het element geven, zonder dat gebruikers van de Tab-toets erdoor worden gehinderd.
In dit voorbeeld wordt tabindex="-1"
niet gebruikt.
tabindex="0"
Volgens de specificatie van html 4.01 moest een tabindex="0"
pas worden bezocht, nadat tabindexen met een positief nummer waren bezocht. Sommige browsers hielden zich hier echter niet aan: een tabindex="0"
werd gewoon tussen de positieve tabindexen gezet.
In html5 is de situatie nog fijner. Nu staat er alleen dat, wat betreft de volgorde, de gewoonte van het platform wordt gevolgd. Oftewel: doe maar raak. Maar hoe dan ook: als je tabindex="0"
gebruikt, kan een element focus krijgen met behulp van de Tab-toets. Ook als dat element normaal genomen geen focus kan krijgen.
Deze waarde wordt in dit voorbeeld gebruikt bij de <span>'s bovenin elke <li>:
<span class="focus-open" tabindex="0"></span>
Door de toevoeging van tabindex="0"
kan de <span> focus krijgen bij gebruik van de Tab-toets, terwijl een <span> dat normaal genomen niet kan krijgen. Door als selector iets als span.focus-open + .pop-up
te gebruiken, kan de pop-up nu worden geopend, als de <span> focus heeft. Waarmee de pop-up ook is te openen door gebruikers van de Tab-toets.
De op de <span> volgende <input> is met behulp van display: none;
verborgen en wordt daardoor genegeerd door de Tab-toets. Maar de hier weer op volgende <a> wordt wel aangedaan door de Tab-toets.
De eerste tab geeft de focus aan span.focus-open
, waar mee de pop-up wordt geopend. De daarop volgende tweede tab geeft de focus aan de <a> die iets onder span.focus-open
in de html staat: de pop-up sluit en met Enter kan nu de link worden gevolgd. (Dat de <a> focus heeft wordt met behulp van wat kleurtjes en zo aangegeven.)
Als elders op de pagina nog een tabindex wordt gebruikt, kan een tabindex="0"
problemen geven met de volgorde, zoals iets hierboven beschreven. Op de site zelf, waar ook knoppen voor navigatie op de site aanwezig zijn, gaat het goed. Geen enkele knop heeft daar een tabindex, waardoor in alle browsers eerst de navigatieknoppen en dan pas de <span>'s met de tabindex worden bezocht. Precies zoals de bedoeling is. Maar als je wel een tabindex elders op de pagina gebruikt, moet je in zoveel mogelijk browsers op zoveel mogelijk systemen de volgorde bij gebruik van de Tab-toets controleren.
tabindex="..."
Op de plaats van de puntjes moet een positief getal worden ingevuld: het volgnummer. Positieve tabindexen worden hier niet gebruikt.
Muis, toetsenbord, touchpad en touchscreen
Vroeger, toen het leven nog mooi was en alles beter, waren er alleen monitors. Omdat kinderen daar niet af konden blijven met hun tengels, besloten fabrikanten dan maar touchscreens te gaan maken, omdat je die mag aanraken. Het bleek makkelijker te zijn om volwassenen ook te leren hoe je 'n scherm vies maakt, dan om kinderen te leren met hun vingers van de monitor af te blijven.
Zo ontstonden touchscreens en kreeg het begrip ellende een geheel nieuwe lading. In de perfecte wereld van vroeger, waarin alleen desktops bestonden, werkten dingen als hoveren, klikken en slepen gewoon. Zonder dat je eerst 'n cursus hogere magie op Zweinstein hoefde te volgen. Zelfs in JavaScript was het nog wel te behappen, ook voor mensen zoals ik die toevallig niet Einstein heten.
Op dit moment kun je computerschermen ruwweg in twee soorten indelen: schermen die worden aangeraakt, en schermen die worden bediend met hulpmiddelen als een toetsenbord, muis of touchpad. Omdat ook computerschermen zich kennelijk vermengen, bestaan er inmiddels ook schermen die zowel van aanraken als van muizen houden.
Hieronder staat een lijstje met dingen die zijn aangepast voor de verschillende soorten schermen, zodat dit voorbeeld overal werkt.
:hover
Omdat :hover
mogelijk niet werkt, als css uitstaat, ontbreekt of onvolledig is geïmplementeerd, moet je nooit belangrijke informatie alleen met behulp van :hover
tonen.
Je hovert over een element, als je met behulp van muis of touchpad de cursor boven dat element brengt. Hoveren kan over álle elementen. Het wordt veel gebruikt om iets van uiterlijk te laten veranderen, een pop-up te laten verschijnen, en dergelijke.
Bij gebruik van een muis zit er een verschil tussen hoveren en klikken, maar op een touchscreen is dat verschil er niet: je raakt een touchscreen aan of niet. Dit levert problemen op in iOS en in Edge op een touchscreen.
Als :hover
met :focus
wordt gecombineerd op hetzelfde element, zijn daar op iOS vaak aanpassingen voor nodig. Deze combinatie komt in dit voorbeeld niet voor, dus er zijn geen speciale aanpassingen voor iOS nodig. Ook voor andere touchscreens zijn geen aanpassingen nodig.
:focus
Omdat :focus
mogelijk niet werkt, als css uitstaat, ontbreekt of onvolledig is geïmplementeerd, moet je nooit belangrijke informatie alleen met behulp van :focus
tonen.
De meeste mensen gaan met een muis naar een link, invoerveld, en dergelijke. Waarna ze vervolgens klikken om de link te volgen, tekst in te voeren, of wat ze ook maar willen doen.
Er is echter 'n tweede manier om naar links, invoervelden, en dergelijke te gaan: met behulp van de Tab-toets (sommige browsers gebruiken andere toetsen, maar het principe is hetzelfde). Met behulp van de Tab-toets kun je naar links, invoervelden, en dergelijke 'springen'. (Over het gebruik van de Tab-toets staat meer bij Tabindex.)
Waar je staat, wordt door alle browsers aangegeven met een of ander kadertje. De link en dergelijke met het kadertje eromheen 'heeft focus'. Dat wil zeggen dat je die link volgt, als je op de Enter-toets drukt, of dat je in dat veld tekst kunt gaan invoeren, enz.
Het kadertje dat de focus aangeeft, moet nooit zonder meer worden weggehaald. Gebruikers van de Tab-toets hebben dan geen idee meer, waar ze zijn. In dit voorbeeld is er helemaal geen kadertje, omdat de focus op andere manieren wordt aangegeven.
Bij gebruik van de Tab-toets wordt elke thumbnail als het ware twee keer aangedaan. Bij de eerste tab opent de pop-up en verschijnt de naam van de bijbehorende pagina boven de thumbnail. Bij de tweede tab sluit de pop-up, wordt de thumb minder goed zichtbaar en verschijnt de naam van de achterliggende pagina als link groot op de thumbnail. Een kadertje is hier dus overbodig, want als je dit niet ziet, zie je zeker geen kadertje...
Als :hover
met :focus
wordt gecombineerd op hetzelfde element, zijn daar op iOS vaak aanpassingen voor nodig. Deze combinatie komt in dit voorbeeld niet voor, dus er zijn geen speciale aanpassingen voor iOS nodig. Ook voor andere touchscreens zijn geen aanpassingen nodig.
Wel zijn voor gebruikers van de Tab-toets speciale voorzieningen aangebracht, zodat ook bij gebruik van de Tab-toets de pop-up wordt geopend. Meer daarover is te vinden bij Tabindex.
:active
Omdat :active
mogelijk niet werkt, als css uitstaat, ontbreekt of onvolledig is geïmplementeerd, moet je nooit belangrijke informatie alleen met behulp van :active
tonen.
Een element is actief, als de muis wordt ingedrukt boven dat element. Op sommige touchscreens is het element actief, als het wordt aangeraakt.
:active
wordt hier niet gebruikt.
De code aanpassen aan je eigen ontwerp
- Als je dit voorbeeld gaat aanpassen voor je eigen site, houdt het dan in eerste instantie zo eenvoudig mogelijk. Ga vooral geen details invullen.
-
Gebruik vooral geen FrontPage, Publisher of Word (alle drie van Microsoft). Deze programma's maken niet-standaard code die alleen goed te bekijken is in Internet Explorer. In alle andere browsers zie je grotendeels bagger, áls je al iets ziet.
Publisher en Word zijn niet bedoeld om websites mee te maken. FrontPage is zwaar verouderd en wordt niet meer onderhouden door Microsoft.
Ook OpenOffice en LibreOffice leveren een uiterst beroerd soort html af. Tekstverwerkers met al hun toeters en bellen zijn gewoon niet geschikt om websites mee te bouwen.
Je kunt natuurlijk ook een goed gratis programma gebruiken. Links naar dat soort programma's vind je op de pagina met links onder Gereedschap → wysiwyg-editor.
Maar het allerbeste is om gewoon zelf html, css, enz. te leren, omdat zelfs het allerbeste programma het nog steeds zwaar verliest van 'n op de juiste manier met de hand gemaakte pagina.
-
Ik maak zelf het liefst een site in Firefox. Als je 'n site maakt in Firefox, Opera, Safari, Google Chrome of Edge, is er 'n hele grote kans dat hij in alle browsers werkt. Ik geef de voorkeur aan Firefox, omdat het de enige grote browser is die niet bij een bedrijf hoort dat vooral op je centen of je data uit is.
Google Chrome wordt ook door veel mensen gebruikt, maar ik heb dus wat moeite met hoe Google je hele surfgedrag, je schoenmaat en de kleur van je onderbroek vastlegt. Daarom gebruik ik Google Chrome zelf alleen om in te testen.
-
Het allereerste dat je moet invoeren, is het doctype, vóór welke andere code dan ook. Een lay-out met een missend of onvolledig doctype ziet er totaal anders uit dan een lay-out met een geldig doctype. Wát er anders is, verschilt ook nog 'ns tussen de diverse browsers. Als je klaar bent en dan nog 'ns 'n doctype gaat invoeren, weet je vrijwel zeker dat je van voren af aan kunt beginnen met de lay-out.
Geldige doctypes vind je op www.w3.org/QA/2002/04/valid-dtd-list.
-
Gebruik het volledige doctype, inclusief de eventuele url, anders werkt het niet goed.
Gebruik een 'strict' doctype of (beter!) het doctype voor html5. Deze zijn bedoeld voor nieuwe sites. Het transitional doctype is bedoeld voor al bestaande sites, niet voor nieuwe.
Het transitional doctype staat talloze tags toe, die in html5 zijn verboden. Deze tags worden al zo'n tien jaar afgeraden. Het transitional doctype is echt alleen bedoeld om de puinhoop van vroeger, toen niet volgens standaarden werd gewerkt, enigszins te herstellen.
Het strict doctype staat verouderde tags niet toe. Daardoor kan met 'n strict doctype, of het nu html of xhtml is, probleemloos worden overgestapt naar html5. Met een transitional doctype en het gebruik van afgekeurde tags kun je niet overstappen naar html5. Je moet dan eerst alle verouderde tags verwijderen, wat echt ontzettend veel werk kan zijn.
Het doctype voor html5 is uiterst simpel:
<!DOCTYPE html>
. Omdat het doctype voor html5 in alle browsers werkt, zelfs in de gelukkig vrijwel uitgestorven nachtmerrie Internet Explorer 6, is er geen enkele reden dit uiterst simpele doctype niet te gebruiken. - Als tweede voer je de charset in. Dit vertelt de browser, welke tekenset er gebruikt moet worden, zodat letters met accenten en dergelijke overal goed worden weergegeven. Het beste kun je utf-8 nemen. Als je later van charset verandert, loop je 'n grote kans dat je alle aparte tekens als letters met accenten weer opnieuw moet gaan invoeren. In html5 is het simpele
<meta charset="utf-8">
voldoende. - Test vanaf het allereerste begin in zoveel mogelijk verschillende browsers in 'n aantal resoluties (schermgroottes). Onder het kopje Getest in kun je in deze uitleg vinden, waar ikzelf op test. Ook van Internet Explorer kun je meerdere versies naast elkaar draaien. Op de pagina met links staan onder de kopjes Gereedschap → Meerdere versies van Internet Explorer draaien en Gereedschap → Weergave testen 'n aantal links die daarbij kunnen helpen. De compatibiliteitsweergave in Internet Explorer is niet geschikt om te testen, omdat deze enigszins verschilt van de weergave in échte browsers.
- Voor alle voorbeelden geldt: breng veranderingen stapsgewijs aan. Als je bijvoorbeeld foto's wilt laten weergeven, begin dan met het alleen veranderen van de namen van de foto's, zodat je eigen foto's worden weergegeven. Maakt niet uit als de maten niet kloppen en de teksten fout zijn. Als dat werkt, ga dan bijvoorbeeld de maten aanpassen. Dan de teksten. En controleer steeds, of alles nog goed werkt.
-
Als het om een lay-out of iets dergelijks gaat: zorg eerst dat header, kolommen, footer, menu, en dergelijke staan en bewegen, zoals je wilt. Ga daarna pas details binnen die blokken invullen. In eerste instantie gebruik je dus bijvoorbeeld 'n leeg blok op de plaats, waar uiteindelijk het menu komt te staan.
Als je begint met allerlei details, is er 'n heel grote kans dat die de werking van de blokken gaan verstoren. Bouw eerst het huis, en ga dan pas de kamers inrichten. Zorg eerst dat de blokken werken, zoals je wilt. Dan zul je het daarna gelijk merken, als 'n toegevoegd detail als tekst of 'n afbeelding iets gaat verstoren. Daarvoor moet je natuurlijk wel regelmatig controleren in verschillende browsers, of alles nog wel goed werkt.
Je kunt de blokken tijdens het aanpassen opvullen met bijvoorbeeld <br>1<br>2<br>3 enz., tot ze de juiste hoogte hebben. Het is handig om aan het einde even iets toe te voegen als 'laatste', zodat je zeker weet dat er niet ongemerkt drie regels onderaan naar 't virtuele walhalla zijn verhuisd.
Om de breedte te vullen, kun je het best 'n kort woord als 'huis' duizend keer of zo herhalen. Ook hier is het handig, om aan 't einde (en hier ook aan 't begin) 'n herkenningsteken te maken, zodat je zeker weet dat je de hele tekst ziet.
- Zolang je in grotere dingen zoals 'n lay-out aan 't wijzigen bent, zou ik je aanraden de verschillende delen een achtergrondkleur te geven. Je ziet dan goed, waar 'n deel precies staat. Een achtergrondkleur heeft – anders dan bijvoorbeeld een border – verder geen invloed op de lay-out, dus die is hier heel geschikt voor.
- Als je instellingen verandert in de style, verander er dan maar één, hooguit twee tegelijk. Als je er zeventien tegelijk verandert, is de kans groot dat je niet meer weet, wat je hebt gedaan. En dat je 't dus niet meer terug kunt draaien.
-
margin
,padding
enborder
worden bij de hoogte en breedte van het element opgeteld. Hier worden vaak fouten mee gemaakt. Als je bijvoorbeeld in een lay-out 'n border toevoegt aan een van de 'hoofdvakken' (header, footer, kolommen), dan wordt deze er bij opgeteld. Bij 'n border van 2 px rondom de linkerkolom wordt deze dus plotseling 4 px breder (2 aan beide kanten), en 4 px hoger. Zoiets kan je hele lay-out verstoren, omdat iets net te breed of te hoog wordt. Je moet dan elders iets 4 px kleiner maken. Dat zal vaak zo zijn: als je één maat verandert, zul je vaak ook 'n andere moeten aanpassen.css geeft de mogelijkheid om
margin
,padding
enborder
bínnen de breedte en hoogte van de inhoud te zetten met behulp vanbox-sizing
, als je dat handiger vindt. -
In plaats van een absolute eenheid als
px
kun je ook een relatieve eenheid gebruiken, met nameem
. Voordeel vanem
is dat een lettergrootte, regelhoogte, en dergelijke inem
in alle browsers kan worden veranderd. Nadeel is dat het de lay-out sneller kan verstoren dan bijvoorbeeldpx
. Dit moet je gewoon van geval tot geval bekijken. Voor weergave in mobiele apparaten zijn relatieve eenheden alsem
vrijwel altijd beter dan vaste eenheden alspx
.Zoomen kan trouwens altijd, ongeacht welke eenheid je gebruikt.
-
Valideren, valideren, valideren en dan voor 't slapen gaan nog 'ns valideren.
Valiwie???
Valideren is het controleren van je html en css op 'n hele serie fouten. Computers zijn daar vaak veel beter in dan mensen. Als je 300 keer <h2> hebt gebruikt en 299 keer </h2> vindt 'n computer die ene missende </h2> zonder enig probleem. Jij ook wel, maar daarna ben je misschien wel aan vakantie toe.
Valideren kan helpen om gekmakende fouten te vinden. Valide code garandeert ook dat de weergave in verschillende browsers (vrijwel) hetzelfde is. En valide code is over twintig jaar ook nog te bekijken.
Valideren moet trouwens ook niet worden overdreven. Het is een hulpmiddel om echte fouten te vinden, meer niet. Het gaat erom dat je site goed werkt, niet dat je het braafste kind van de klas bent. Als de code niet valideert, maar daar is een goede reden voor, is daar niets op tegen.
Op deze site is alle css en html gevalideerd. Als de code niet helemaal valide is (wat regelmatig voorkomt), staat daar onder Bekende problemen (en oplossingen) de reden van.
Je kunt je css en html valideren als 't online staat, maar ook als het nog in je computer staat.
html kun je valideren op: validator.w3.org/nu.
css kun je valideren op: jigsaw.w3.org/css-validator.
Toegankelijkheid en zoekmachines
Het eerste deel van deze tekst is voor alle voorbeelden hetzelfde. Eventueel specifiek voor dit voorbeeld geldende dingen staan verderop onder het kopje Specifiek voor dit voorbeeld.
Toegankelijkheid (in het Engels 'accessibility') is belangrijk voor bijvoorbeeld blinden die een schermlezer gebruiken, of voor motorisch gehandicapte mensen die moeite hebben met het bedienen van een muis. Een spider van een zoekmachine (dat is het programmaatje dat de site indexeert voor de zoekmachine) is te vergelijken met een blinde. Als je je site goed toegankelijk maakt voor gehandicapten, is dat gelijk goed voor een hogere plaats in een zoekmachine. Dus als je 't niet uit sociale motieven wilt doen, kun je 't uit egoïstische motieven doen.
(Op die plaats in de zoekmachine heb je maar beperkt invloed. De toegankelijkheid van je site is maar één van de factoren, maar zeker niet onbelangrijk.)
Als je bij het maken van je site al rekening houdt met toegankelijkheid, is dat nauwelijks extra werk. 't Is ongeveer te vergelijken met inbraakbescherming: doe dat bij 'n nieuw huis en 't is nauwelijks extra werk, doe 't bij 'n bestaand huis en 't is al snel 'n enorme klus.
Enkele tips die helpen bij toegankelijkheid:
-
Gebruik altijd een alt-beschrijving bij een afbeelding. De alt-tekst wordt gebruikt, als afbeeldingen niet kunnen worden getoond of gezien (dat geldt dus ook voor zoekmachines). Als je iets wilt laten zien, als je over de afbeelding hovert, gebruik daar dan het title-attribuut voor, niet de alt-beschrijving.
Als een afbeelding alleen maar voor de sier wordt gebruikt, zet je daarbij
alt=""
, om aan te geven dat de afbeelding niet belangrijk is voor het begrijpen van de tekst of zo. - Als uit de tekst bij een link niet duidelijk blijkt, waar de link naartoe leidt, gebruik dan een title bij de link. Een tekst als 'pagina met externe links' is waarschijnlijk duidelijk genoeg, een tekst als alleen 'links' mogelijk niet. Een duidelijke zwart-witregel is niet te geven, omdat dit ook van tekst en dergelijke in de omgeving van de link afhangt.
-
Accesskeys (sneltoetsen) kun je beter niet gebruiken, deze geven te veel problemen, omdat ze vaak dubbelop zijn met sneltoetsen voor de browser of andere al gebruikte sneltoetsen. Bovendien is voor de gebruiker meestal niet duidelijk, welke toetsen het zijn.
Op zichzelf zijn accesskeys een heel goed idee. Maar helaas zijn ze ook in html5 volstrekt onvoldoende gedefinieerd. Er is nog steeds geen standaard voor de meest gebruikelijke accesskeys, zoals Zoek of Home.
Er is nog steeds niet vastgelegd, hoe accesskeys zichtbaar gemaakt kunnen worden. Voor de makers van browsers zou dit 'n relatief kleine moeite zijn, voor de makers van 'n site is het bergen extra werk.
Voor mij redenen om accesskeys (vrijwel) niet te gebruiken. Ik kan me wel voorstellen dat ze, op sites die gericht zijn op 'n specifieke groep gebruikers, nog enig nut kunnen hebben. Maar voor algemene sites zou ik zeggen: niet gebruiken.
-
Met behulp van de Tab-toets (of op 'n soortgelijke manier) kun je in de meeste browsers door links, invoervelden, en dergelijke lopen. Elke tab brengt je één link, invoerveld, en dergelijke verder, Shift+Tab één plaats terug. Met behulp van
tabindex
kun je de volgorde aangeven, waarin de Tab-toets werkt. Zondertabindex
wordt de volgorde van de html aangehouden bij gebruik van de Tab-toets, maar soms is een andere volgorde logischer.In principe is het beter, als
tabindex
niet nodig is, maar gewoon de volgorde van de html wordt aangehouden. Bij verkeerd gebruik kantabindex
heel verwarrend zijn. Het is niet bedoeld om van de pagina een hindernisbaan voor kangoeroes te maken, waarop van beneden via links over rechts naar boven wordt gesprongen. -
In het verleden werd vaak aangeraden de volgorde van de code aan te passen. Een menu bijvoorbeeld kon in de html onderaan worden gezet, terwijl het op het scherm met behulp van css bovenaan werd gezet. Inmiddels zijn schermlezers en dergelijke zo sterk verbeterd dat dit niet meer wordt aangeraden. De volgorde in de html kan tegenwoordig beter hetzelfde zijn als die op het scherm, omdat het anders juist verwarrend kan werken.
Een andere mogelijkheid is een zogenaamde skip-link: een link die je buiten het scherm parkeert met behulp van css, zodat hij normaal genomen niet te zien is. Zo'n link is wel gewoon zichtbaar in speciale programma's zoals tekstbrowsers en schermlezers, want die kijken gewoon naar wat er in de broncode staat.
Zo'n link staat boven menu, header, en dergelijke en linkt naar de eigenlijke inhoud van de pagina, zodat mensen met één toetsaanslag naar de eigenlijke inhoud van de pagina kunnen gaan.
Een skip-link is ook nuttig voor gebruikers van de Tab-toets. Zodra de normaal genomen onzichtbare link door het indrukken van de Tab-toets focus krijgt, kun je hem op het scherm plaatsen, waardoor hij zichtbaar wordt. Bij een volgende tab wordt hij dan weer buiten het scherm geplaatst en is dus niet meer zichtbaar, zodat de lay-out niet wordt verstoord.
Op pagina's waar dat nuttig is, wordt op deze site een skip-link gebruikt.
-
Van oorsprong is html een taal om wetenschappelijke documenten weer te geven, pas later is hij gebruikt voor lay-out. Maar daar is hij dus eigenlijk nooit voor bedoeld geweest. Het gebruiken van html voor lay-out leidt tot enorme problemen voor gehandicapten en tot een lage plaats in zoekmachines.
De html hoort alleen inhoud te bevatten, lay-out doe je met behulp van css. Die css moet in een externe stylesheet staan of, als hij alleen voor één bepaalde pagina van toepassing is, in de <head> van die pagina. Zoekmachines zijn ook niet dol op een oerwoud van inline-stijlen (dat zijn stijlen in de tag zelf:
<div style="...">
.) -
Breng een logische structuur aan in je document. Gebruik een <h1> voor de belangrijkste kop, een <h2> voor een subkop, enz. Schermlezers en dergelijke kunnen van kop naar kop springen. En een zoekmachine gaat ervan uit dat <h1> belangrijke tekst bevat.
Dit geldt voor al dit soort structuurbepalende tags.
Als een <h1> te grote letters geeft, maak daar dan met behulp van je css 'n kleinere letter van, maar blijf die <h1> gewoon gebruiken. Op dezelfde manier kun je al dit soort dingen oplossen.
- <table> is fantastisch, maar alleen als die wordt gebruikt om een echte tabel weer te geven, niet als hij voor opmaak wordt misbruikt. In het verleden is dat op grote schaal gebeurd bij gebrek aan andere mogelijkheden. Een tabel is, als je niet heel erg goed oplet, volstrekt ontoegankelijk voor gehandicapten en zoekmachines. Het lezen van een tabel is ongeveer te vergelijken met het lezen van een krant van links naar rechts: niet per kolom, maar per regel. Dat gaat dus alleen maar goed bij een echte tabel, zoals een spreadsheet. In alle andere gevallen garandeert 'n tabel 'n lagere plaats in een zoekmachine.
-
Frames horen bij een volstrekt verouderde techniek, die heel veel nadelen met zich meebrengt. <iframe>'s hebben voor een deel dezelfde nadelen. Eén van die nadelen is dat de verschillende frames voor zoekmachines, schermlezers, en dergelijke als los zand aan elkaar hangen, omdat ze los van elkaar worden weergegeven. Ze staan wel naast elkaar op het scherm, maar er zit intern geen verband tussen.
Als je 'n stuk code vaker wilt gebruiken, zoals 'n menu dat op elke pagina hetzelfde is, voeg dat dan in met PHP of SSI (Server Side Includes). Dan wordt de pagina niet pas in de browser, maar al op de server samengesteld. Hierdoor zien zoekmachines, schermlezers, en dergelijke één pagina, net zoals wanneer je maar één pagina met html zou hebben geschreven.
- Geef de taal van het document aan, en bij woorden en dergelijke die afwijken van die taal de afwijkende taal met behulp van
lang=".."
. Ik doe dat op mijn eigen site maar af en toe, omdat de tekst (en vooral de code) een mengsel is van Engels, Nederlands en eigengemaakte namen. Dat soort teksten is gewoon niet goed in te delen in een taal. Maar bij enigszins 'normale' teksten hoor je een taalwisseling aan te geven. - Gebruik de tag <abbr> bij afkortingen. Doe dat de eerste keer op een pagina samen met de title-eigenschap:
<abbr title="ten opzichte van">t.o.v.</abbr>
. Daarna kun je op dezelfde pagina volstaan met<abbr>t.o.v.</abbr>
. Doe je dit niet, dan is er 'n grote kans dat 'n schermlezer 't.o.v.' uit gaat spreken als 'tof', en 'n zoekmachine kan er ook geen chocola van maken. -
De spider van 'n zoekmachine, schermlezers, en dergelijke kunnen geen plaatjes 'lezen'. Het is soms verbazingwekkend om te zien hoe veel, of eigenlijk: hoe weinig tekst er overblijft op een pagina, als de plaatjes worden weggehaald. Het zelfde geldt voor die fantastisch mooie flash-pagina's, als daarbij geen voorzieningen voor dit soort programma's zijn aangebracht.
Op Linux kun je met Lynx kijken, hoe je pagina eruitziet zonder plaatjes en dergelijke, als echt alleen de tekst overblijft. Een installatie-programma voor Lynx op Windows is te vinden op invisible-island.net/lynx.
Ook kun je in Windows het gratis programma WebbIE installeren. WebbIE laat de pagina zien, zoals een tekstbrowser en dergelijke hem zien. WebbIE is te downloaden vanaf www.webbie.org.uk.
-
Ten slotte kun je je pagina nog online laten controleren op 'n behoorlijk aantal sites. Ik noem er hier enkele.
lowvision.support Laat zien hoe een kleurenblinde de site ziet. Engelstalig.
wave.webaim.org Deze laat grafisch zien hoe de toegankelijkheid is. Engelstalig.
Op de pagina met links kun je onder Toegankelijkheid links naar testen en dergelijke vinden.
Specifiek voor dit voorbeeld
-
Als de tekst boven de afbeelding in de pop-up alleen met scrollen volledig kan worden gelezen, omdat deze heel erg lang is, levert dit problemen op voor gebruikers van de Tab-toets. Om dit te illustreren is de tekst in de zesde pop-up opzettelijk erg lang gemaakt.
De pop-up opent gewoon bij gebruik van de Tab-toets, maar om de volledige tekst te kunnen lezen moet in de tekst worden geklikt, of het scrollwieltje van de muis moet worden gebruikt. En dat is nou juist waar veel gebruikers van de Tab-toets moeite mee hebben
Het is dus beter om de tekst niet langer te maken, dan in de ruimte boven de afbeeldingen in de pop-up past. (En aangezien die ruimte vrij groot is, past er redelijk veel tekst in.)
- Voor gebruikers van de Tab-toets is een extra
span.focus-open
aangebracht, waardoor ook bij gebruik van de Tab-toets de pop-up kan worden geopend. Meer over deze <span> en de Tab-toets is te vinden bij Tabindex. -
De tekstbrowser Lynx toont de links én de tekst boven de pop-ups. De <input>'s zijn wel zichtbaar en ietwat verwarrend (hoewel gebruikers van Lynx hieraan gewend zullen zijn).
WebbIE daarentegen toont alleen de links en laat de tekst boven de pop-ups weg. Dit is niet zoals het hoort: de tekst zou gewoon getoond moeten worden.
Alle geteste schermlezers lezen de links én de tekst boven de pop-ups voor.
- Omdat de hele constructie met <input>'s, <label>'s en dergelijke uiterst verwarrend kan zijn voor schermlezers, zijn deze voor schermlezers verborgen of is de semantische betekenis verwijderd. Meer hierover is te vinden bij Semantische elementen en WAI-ARIA.
- Zonder css zijn de links en de teksten boven de pop-ups zichtbaar. De pop-ups zelf werken uiteraard niet.
- Zonder afbeeldingen werkt alles gewoon, inclusief de pop-ups (maar uiteraard zonder de achtergrond-afbeelding erin).
-
Bij een lettergrootte van meer dan 150% is het sluitkruisje moeilijk te herkennen als sluitkruisje.
Op bepaalde momenten wordt de korte naam van de achterliggende pagina getoond. Bij vergrotingen van meer dan 130% kan een deel van het einde van die naam wegvallen onder de tekst in het midden, of rechts buiten het venster van de browser. Een gedetailleerder verhaal hierover is te vinden bij Bekende problemen (en oplossingen) onder het kopje Alle browsers → Grotere lettergrootte.
Afgezien hiervan blijft alles gewoon werken.
Getest in
Laatst gecontroleerd op 9 maart 2016
Onder dit kopje staat alleen maar, hoe en waarin is getest. Eventuele problemen, ook die met betrekking tot zoomen en lettergroottes, staan hieronder bij Bekende problemen (en oplossingen). Het is belangrijk dat deel te lezen, want uit een test kan ook prima blijken dat iets totaal niet werkt!
Eventuele opmerkingen over de toegankelijkheid specifiek voor dit voorbeeld staan hierboven bij Toegankelijkheid en zoekmachines onder het kopje Specifiek voor dit voorbeeld.
Dit voorbeeld is getest op de volgende systemen:
- Windows 7:
Firefox, UC Browser, Google Chrome, Internet Explorer 9 en 10, in meerdere resoluties. - Windows 8.1:
Bureaublad-versie: Firefox, UC Browser, Google Chrome en Internet Explorer 11, in meerdere resoluties.
Startscherm-versie: Internet Explorer 11. - Windows 10:
Firefox, UC Browser, Google Chrome, Internet Explorer 11, Edge, in meerdere resoluties. - OS X:
Firefox, Safari en Google Chrome, in meerdere resoluties. In Safari is, voor zover relevant, ook de Reader-weergave getest. - Linux:
Firefox en Google Chrome, in meerdere resoluties. - Windows Phone 8.1 in een resolutie van 800x480 (Nokia Lumia 520):
Internet Explorer (portret en landschap).
UC Browser (portret en landschap). - iPad met iOS 9.2.1 in een resolutie van 1024x768 (device-pixel-ratio: 1)(MC979NF):
Safari (portret en landschap, voor zover relevant ook de reader-weergave).
Chrome for iOS, UC Browser, Firefox (alle portret en landschap). - iPad Air met iOS 9.2.1 in een resolutie van 2048 x 1536 (retina, device-pixel-ratio: 2) (MD785HC/B):
Safari (portret en landschap, voor zover relevant ook de reader-weergave).
Chrome for iOS, UC browser, Firefox (alle portret en landschap). - Android 4.1.2 in een resolutie van 800x480 (Samsung Galaxy Core i8620):
Chrome, Android browser, UC Browser en Firefox (alle portret en landschap). - Android 4.4.2 in een resolutie van 1280x800 (resolutie: 90-99 dpi) (Samsung Galaxy Tab 3 GT-P521):
Android browser, UC Browser, Firefox en Chrome (alle portret en landschap). - Android 4.4.2 in een resolutie van 2560x1600 (hoge resolutie: 190-199 dpi) (Samsung Galaxy Tab PRO (T520):
Android browser, UC Browser, Firefox en Chrome (alle portret en landschap).
Er is steeds getest met de laatste versie van de browsers op de aan het begin van dit hoofdstukje genoemde controledatum, omdat ik geen zin heb om rekening te houden met mensen die met zwaar verouderde browsers surfen. Dat is trouwens vragen om ellende, want updates van browsers hebben heel vaak met beveiligingsproblemen te maken.
Ik maak één uitzondering: Android browser. Omdat Android vaak niet geüpdatet kan worden, test ik ook nog in oudere versies van Android browser.
In resoluties groter dan 800x600 is ook in- en uitzoomen en – voor zover de browser dat kan – een kleinere en grotere letter getest. Er is ingezoomd en vergroot tot zover de browser kan, maar niet verder dan 200%.
Er is getest met behulp van muis en toetsenbord, behalve op de iPad, Android en Windows Phone, waar een touchscreen is gebruikt. Op Windows 8.1 en 10 is getest met een touchscreen, met een combinatie van toetsenbord en touchpad, en met een combinatie van toetsenbord en muis.
Op de desktop is ook getest, als JavaScript uitstaat. Eventuele problemen staan hierboven bij Toegankelijkheid en zoekmachines onder het kopje Specifiek voor dit voorbeeld. (Op iOS, Android en Windows Phone is niet getest zonder JavaScript, omdat je JavaScript in een toenemend aantal mobiele browsers niet uit kunt zetten. Bovendien is een mobiel apparaat zonder JavaScript niet veel meer dan een duur en groot uitgevallen horloge.)
Naast deze 'gewone' browsers is ook getest in Lynx, WebbIE, NVDA, TalkBack en VoiceOver.
Lynx is een browser die alleen tekst laat zien en geen css gebruikt. Er is getest op Linux.
WebbIE is een browser die gericht is op mensen met een handicap. Er is getest op Windows 7.
NVDA is een schermlezer, zoals die door blinden wordt gebruikt. Er is getest in combinatie met Firefox op Windows 7.
TalkBack is een in Android ingebouwde schermlezer. Er is getest in combinatie met Chrome.
VoiceOver is een in iOS en OS X ingebouwde schermlezer. Er is getest in combinatie met Safari op iOS en OS X.
Als het voorbeeld in deze programma's toegankelijk is, zou het in principe toegankelijk moeten zijn in alle aangepaste browsers en dergelijke. En dus ook voor zoekmachines, want een zoekmachine is redelijk vergelijkbaar met een blinde. Eventuele opmerkingen over de toegankelijkheid specifiek voor dit voorbeeld staan hierboven bij Toegankelijkheid en zoekmachines onder het kopje Specifiek voor dit voorbeeld.
Alleen op de hierboven genoemde systemen en browsers is getest. Er is dus niet getest op bijvoorbeeld 'n Blackberry. De kans is (heel erg) groot dat dit voorbeeld niet (volledig) werkt op niet-geteste systemen en apparaten. Om het wel (volledig) werkend te krijgen, zul je vaak (kleine) wijzigingen en/of (kleine) aanvullingen moeten aanbrengen, bijvoorbeeld met JavaScript.
Er is ook geen enkele garantie dat iets werkt in een andere tablet of smartphone dan hierboven genoemd, omdat fabrikanten in principe de software kunnen veranderen. Dit is anders dan op de desktop, waar browsers altijd (vrijwel) hetzelfde werken, zelfs op verschillende besturingssystemen. Iets wat in Android browser werkt, zal in de regel overal werken in die browser, maar een garantie is er niet. De enige garantie is het daadwerkelijk testen op een fysiek apparaat. En aangezien er duizenden mobiele apparaten zijn, is daar eigenlijk geen beginnen aan.
De html is gevalideerd met de validator van w3c, de css ook. Als om een of andere reden niet volledig gevalideerd kon worden, wordt dat bij Bekende problemen (en oplossingen) vermeld.
Nieuwe browsers test ik pas, als ze uit het bèta-stadium zijn, omdat er anders 'n redelijke kans is dat ik 'n bug zit te omzeilen, die voor de uiteindelijke versie nog gerepareerd wordt. Dit voorbeeld is alleen getest in de hierboven met name genoemde browsers. Vragen over niet-geteste browsers kan ik niet beantwoorden, en het melden van fouten in niet-geteste browsers heeft ook geen enkel nut. (Melden van fouten, problemen, enz. in wel geteste browsers: graag!)
Bekende problemen (en oplossingen)
Waarop en hoe is getest, kun je gelijk hierboven vinden bij Getest in.
Als je hieronder geen oplossing vindt voor een probleem dat met dit voorbeeld te maken heeft, kun je op het forum proberen een oplossing te vinden voor je probleem. Om forumspam te voorkomen, moet je je helaas wel registreren, voordat je op het forum een probleem kunt aankaarten.
Onderstaande lijst is nogal lang, omdat ik de gewoonte heb álle bekende problemen op te schrijven. De lengte van de lijst is tamelijk indrukwekkend, maar het gaat eigenlijk vrijwel alleen om hele kleine dingetjes.
Validatie
Bij valideren van de css geeft de validator van w3c twee fouten.
pointer-events
zit nog niet in een officiële specificatie en wordt nog niet herkend.
Bij calc()
worden bepaalde berekeningen met procenten onrechte als fout aangemerkt: deze berekeningen werken gewoon en zijn correct. Hier moet de validator dus kennelijk zelf gevalideerd worden.
In beide gevallen is de oorzaak van de 'fout' bekend en is deze 'fout' daarom onbelangrijk.
Alle browsers
Bij hoveren sluit de pop-up, zodra niet meer over het vraagteken wordt gehoverd
Dit doet zich alleen voor, als met de muis over het vraagteken wordt gehoverd. Het speelt ook alleen in grotere browservensters, want alleen daar zijn pop-ups aanwezig.
Dit is alleen een echt probleem, als er zoveel tekst boven de afbeelding in de pop-up staat, dat niet alle tekst zonder scrollen is te lezen. In dat geval moet op het vraagteken worden geklikt. Dan blijft de pop-up geopend en kan de volledige tekst met scrollen worden gelezen. Precies om het onhandige hiervan duidelijk te maken, is bij de zesde knop een lange tekst gebruikt.
Behalve klikken op het vraagteken is hier helaas geen simpele oplossing voor. (In vorige versies speelde dit probleem niet, maar die vorige versies werkten niet op touchscreens.)
Er is vrij veel ruimte voor tekst boven de pop-up. Als je niet meer tekst gebruikt dan in die ruimte past, speelt dit probleem niet. Als de lettergrootte wordt vergroot, kan de tekst te groot worden voor de beschikbare ruimte. En dan speelt het probleem weer. Dat is niet goed op te lossen: in dat geval ontkom je niet aan klikken om de pop-up geopend te houden. Overigens speelt dit probleem niet bij inzoomen (vergroten), dus heel vaak zal zich dit niet voordoen.
Bij gebruik van de Tab-toets is een lange tekst boven de pop-up niet volledig te lezen
Dit probleem speelt alleen in grotere browservensters, want alleen daar zijn pop-ups aanwezig.
Het verhaal gelijk hierboven geldt voor het openen van de pop-up bij hoveren. De oplossing is daar: klik op het vraagteken en de pop-up blijft open.
Dat is helaas ook voor gebruikers van de Tab-toets de enige mogelijkheid. Een goede oplossing is dit niet, want gebruikers van de Tab-toets kunnen nou juist vaak de muis niet goed gebruiken.
Bovendien moet, na klikken op het vraagteken, ook nog de muis worden gebruikt om de tekst boven de pop-up te kunnen scrollen. (Er moet in de tekst worden geklikt om de pijltjes te kunnen gebruiken, of er moet worden gescrold met behulp van het muiswieltje.)
Om dit probleem duidelijk te maken, is in de zesde pop-up te veel tekst aangebracht boven de afbeelding. Als je met de Tab-toets naar die zesde pop-up gaat en deze opent, zie je dat je zonder muis niet de volledige tekst kunt lezen. (Ja, je kunt de letters verkleinen. Je kunt ook vragen of ze even opbellen, zodat je de tekst kunt voorlezen. Ik bedoel maar: er zijn grenzen aan wat je van een bezoeker aan inspanning mag verwachten.)
De enige oplossing is hier: niet meer tekst gebruiken dan er zonder scrollen boven de afbeelding in de pop-up past.
Grotere lettergrootte
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen. Het geldt alleen voor een grotere lettergrootte, niet bij gewoon inzoomen (vergroten).
Zelfs bij een vergroting van 200% blijft alles gewoon werken. De tekst boven de afbeeldingen in de pop-up kan worden gescrold, als deze niet meer binnen de ruimte boven de afbeelding past.
Als de pop-up door middel van hoveren wordt geopend, verschijnt de naam van de achterliggende pagina boven de thumbnail. Bij vergrotingen van meer dan 150% kan, bij langere namen, een deel van die naam wegvallen onder de pop-up of aan de rechterkant van het browservenster.
Als de pop-up door middel van klikken of aanraken wordt geopend, staat er naast de naam nog een sluitkruis. Hierdoor is er minder ruimte voor de naam en speelt dit probleem al bij vergrotingen van meer dan 130%.
Als de Tab-toets wordt gebruikt om de knoppen af te gaan, verschijnt de naam van de achterliggende pagina boven de thumbnail, als de pop-up is geopend. Bij vergrotingen van meer dan 150% kan ook hier bij langere namen een deel van die naam wegvallen onder de pop-up of aan de rechterkant van het browservenster.
Bij een volgende tab sluit de pop-up weer en wordt de naam van de achterliggende pagina op de pop-up zelf getoond. Nu speelt het probleem alleen aan de rechterkant van het venster, waar een deel van de naam buiten het venster kan komen te staan. Op andere plaatsen is de naam volledig zichtbaar, al kan die gedeeltelijk buiten de thumbnail komen te staan.
Android browser
Niet alle versies tonen een gradiënt
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Niet alle versies van Android browser tonen deze gradiënt, omdat niet alle versies goed met calc()
uit de voeten kunnen.
De knoppen staan niet in alle versies netjes verticaal verdeeld
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Als er geen vier knoppen onder elkaar passen, komen er links en rechts van de kolom twee knoppen te staan. De andere vier knoppen komen dan onder de tekst te staan. In totaal zijn er dus drie regels met knoppen.
De afstand tussen die regels moet gelijk zijn, zodat ze netjes worden verdeeld. De afstand wordt berekend met behulp van calc()
. Niet alle versies van deze browser kunnen goed daarmee overweg. In sommige versies staat de tweede regel met knoppen daardoor gelijk onder de eerste regel.
Gradiënt op verkeerde plaats bij inzoomen (vergroten)
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Als wordt ingezoomd, staat deze gradiënt niet meer op de juiste plaats onderaan de tekst, maar ergens midden op de tekst.
Omdat de gradiënt behoorlijk doorzichtig is en tekst onder de gradiënt gewoon geselecteerd, gekopieerd, en dergelijke kan worden, is dit geen erg groot probleem. Het is meer niet netjes, dan dat het echt heel storend is.
De kop beslaat in portretstand soms de volle breedte van het venster
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
In bredere browservensters wordt de breedte van de <h1> bovenaan de pagina berekend met behulp van van calc()
. Niet alle versies van deze browser kunnen daarmee goed uit de voeten. Er is ook een maximumbreedte van 870 px opgegeven, en die werkt wel altijd. In vensters smaller dan 870 px kan daardoor de <h1> de volle breedte van het venster beslaan. Dat valt nauwelijks op, want de tekst in de <h1> is wel gecentreerd. Alleen aan de achtergrondkleur van de <h1> is dit probleem te zien, want die is breder dan de bedoeling zou moeten.
Firefox (alle versies)
Bij de zesde knop is een extra tab nodig
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij de zesde pop-up staat zoveel tekst boven de afbeelding, dat deze gescrold moet worden om de tekst volledig te kunnen lezen. Om een of andere reden is hierdoor bij gebruik van de Tab-toets een extra aanslag van de Tab-toets nodig. Als de tekst zoveel wordt ingekort dat scrollen niet meer nodig is, is de extra tab ook niet meer nodig.
Wat dit veroorzaakt is mij een raadsel. Het lijkt erop dat Firefox iets doet als het spontaan invoegen van tabindex="0"
bij de <span> met de tekst, als er gescrold moet worden.
Firefox (Android)
Gradiënt op verkeerde plaats bij inzoomen (vergroten)
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Als wordt ingezoomd, staat deze gradiënt niet meer op de juiste plaats onderaan de tekst, maar ergens midden op de tekst.
Omdat de gradiënt behoorlijk doorzichtig is en tekst onder de gradiënt gewoon geselecteerd, gekopieerd, en dergelijke kan worden, is dit geen erg groot probleem. Het is meer niet netjes, dan dat het echt heel storend is.
Internet Explorer 9
Geen gradiënt
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Internet Explorer 9 kent geen gradiënt. Als er onder de kolom met tekst knoppen staan, hoort er een doorzichtige gradiënt onderaan de tekst te staan, zodat duidelijk is dat deze tekst nog doorloopt. Deze gradiënt ontbreekt bij Internet Explorer 9.
Je kunt eventueel een zogenaamde 'polyfill' gebruiken om dit toch voor elkaar te krijgen, maar daar vond ik het niet belangrijk genoeg voor. Op internet kun je zoeken naar polyfills, maar de kwaliteit daarvan is zeer wisselend.
Op de site van modernizr staat een grote verzameling kwalitatief goede polyfills.
iOS
Omdat alle browsers op iOS de weergave-machine van Safari gebruiken, zijn veel van de problemen hetzelfde. Daarom worden alle browsers op iOS hier bij elkaar gezet.
Bij inzoomen (vergroten) staat gradiënt niet op de goede plaats
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Als wordt ingezoomd, staat deze gradiënt niet meer op de juiste plaats onderaan de tekst, maar ergens midden op de tekst.
Omdat de gradiënt behoorlijk doorzichtig is en tekst onder de gradiënt gewoon geselecteerd, gekopieerd, en dergelijke kan worden, is dit geen erg groot probleem. Het is meer niet netjes, dan dat het echt heel storend is.
Verspringend gradiënt (alleen UC browser)
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Deze gradiënt is met behulp van position: fixed;
vastgezet. Als de tekst wordt gescrold, beweegt de gradiënt in UC browser mee met de tekst. Als niet meer wordt gescrold, springt de gradiënt terug naar de plaats, waar hij hoort te staan. Niet heel erg storend, maar het hoort niet.
UC browser op Android
Soms opent de pop-up niet, maar wordt de link gevolgd
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij aanraken van het vraagteken moet een pop-up openen. Om onduidelijke redenen wordt soms niet de pop-up geopend, maar wordt de link gevolgd en opent de achter de knop zittende pagina gelijk.
Enige regelmaat in dit verschijnsel heb ik niet kunnen vinden. Experimenteren met dingen als een andere z-index
had geen enkel effect. Het enige wat ik met zekerheid heb kunnen vaststellen: het gebeurt bij de vraagtekens rechts van de tekst meer dan bij de vraagtekens links van de tekst. In portretstand gebeurt het links zelfs helemaal niet. Als je het scherm ergens aanraakt, voordat je het vraagteken aanraakt, gaat het ook goed.
Kortom: een onduidelijke bug.
Niet alle versies tonen een vinkje, als de pagina is bezocht
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Als een pagina is bezocht, moet naast het vraagteken een vinkje verschijnen. Niet alle versies van UC browser op Android tonen dit vinkje.
De knoppen staan niet netjes verticaal verdeeld
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Als er geen vier knoppen onder elkaar passen, komen er links en rechts van de kolom twee knoppen te staan. De andere vier knoppen komen dan onder de tekst te staan. In totaal zijn er dus drie regels met knoppen.
De afstand tussen die regels moet gelijk zijn, zodat ze netjes worden verdeeld. De afstand wordt berekend met behulp van calc()
. UC browser op Android kent calc()
niet. Daardoor staat de tweede regel met knoppen gelijk onder de eerste regel.
Geen gradiënt
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
Bij tablets in landschapsstand wordt onderaan de tekst een doorzichtige gradiënt neergezet, om aan te geven dat de tekst nog doorloopt. Omdat UC browser op Android calc()
niet kent, ontbreekt daar deze gradiënt.
De kop beslaat in portretstand de volle breedte van het venster
Dit probleem speelt alleen in grotere browservensters, waarin pop-ups verschijnen.
In bredere browservensters wordt de breedte van de <h1> bovenaan de pagina berekend met behulp van van calc()
. UC browser op Android kent dat niet. Er is ook een maximumbreedte van 870 px opgegeven, en die werkt wel altijd. In vensters smaller dan 870 px kan daardoor de <h1> de volle breedte van het venster beslaan. Dat valt nauwelijks op, want de tekst in de <h1> is wel gecentreerd. Alleen de achtergrondkleur van de <h1> beslaat de volle breedte.
Wijzigingen
Alleen grotere wijzigingen worden hier vermeld, geen dingen als een link die is geüpdatet.
:
De code voor deze versie lijkt in niets meer op die van eerdere versies. Daarom zijn eerdere wijzigingen weggehaald. In feite is dit voorbeeld op deze datum nieuw opgenomen.
Inhoud van de download en licenties
De inhoud van deze download kan vrij worden gebruikt, met drie beperkingen:
* Sommige onderdelen die van 'n andere site of zo afkomstig zijn, vallen mogelijk onder een of andere licentie. Dat is hieronder bij het betreffende onderdeel te vinden.
* Je gebruikt het materiaal uit deze download volledig op eigen risico. Het kan prima zijn dat er fouten in de hier verstrekte code en dergelijke zitten. Voor eventuele schade die door gebruik van materiaal uit deze download ontstaat, in welke vorm dan ook, zijn www.css-voorbeelden.nl en medewerkers daarvan op geen enkele manier verantwoordelijk.
* Dit voorbeeld (en de bijbehorende uitleg en dergelijke) wordt regelmatig bijgewerkt. Het is daarom niet toegestaan dit voorbeeld (en de bijbehorende uitleg en dergelijke) op welke manier dan ook te verspreiden, zonder daarbij duidelijk te vermelden dat voorbeeld, uitleg, en dergelijke afkomstig zijn van www.css-voorbeelden.nl en dat daar altijd de nieuwste versie is te vinden. Dit is om te voorkomen dat er verouderde versies worden verspreid.
Een link naar www.css-voorbeelden.nl wordt trouwens altijd op prijs gesteld.
* De foto's zijn gemaakt in het Vondelpark in Amsterdam op Koninginnedag 2009. Als je jezelf herkent en de originele foto wilt hebben, stuur dan even 'n mailtje naar info@css-voorbeelden.nl.
menu-019-dl.html: de pagina met het voorbeeld.
menu-019.pdf: deze uitleg (aangepast aan de inhoud van de download).
menu-019-inhoud-download-en-licenties.txt: een kopie van de tekst onder dit kopje (Inhoud van de download en licenties).
019-css-dl:
menu-019-dl.css: stylesheet voor menu-019-dl.html.
menu-019-hulp-dl.css: stylesheet voor pagina's in 019-files-dl.
019-files-dl:
de pagina's achter de knoppen, in totaal acht html-pagina's.
019-pics:
8 thumbnails (te herkennen aan 'thumb' in de naam).
8 grotere afbeeldingen voor in de pop-up.
HTML
De code is geschreven in een afwijkende
lettersoort. De code die te maken heeft met de basis van dit voorbeeld (essentiële code), is in de hele uitleg onderstippeld blauw
. Alle niet-essentiële code is bruin
. (In de inhoudsopgave staat alles in een gewone letter vanwege de leesbaarheid.)
In de html hieronder wordt alleen de html besproken, waarover iets meer is te vertellen. Een <h1> bijvoorbeeld wordt in de regel niet genoemd, omdat daarover weinig interessants valt te melden. (Als bijvoorbeeld het uiterlijk van de <h1> wordt aangepast met behulp van css, staat dat verderop bij de bespreking van de css.)
Zaken als een doctype
en charset
hebben soms wat voor veel mensen onbekende effecten, dus daarover wordt hieronder wel een en ander geschreven.
Deze uitleg hoort bij het voorbeeld dat in de download zit. Het voorbeeld uit de download verschilt iets van het voorbeeld hier op de site. In de download ontbreekt bijvoorbeeld de navigatie voor de site. Ook in de kopregels zit vaak wat verschil. Daarnaast kunnen er nog andere (meestal kleine) verschillen zijn.
Als je deze uitleg leest naast de broncode van het voorbeeld op de site, kan het dus bijvoorbeeld zijn dat 'n <h1> uit de css bij 'n <h2> uit de html hoort. Maar het gaat niet om hele grote, fundamentele afwijkingen.
Als je dit lastig vindt, kun je bovenaan de pagina de hele handel downloaden. In de download zit 'n voorbeeld dat wel naadloos aansluit op de uitleg in de download.
<!DOCTYPE html>
Een document moet met een doctype beginnen om weergaveverschillen tussen browsers te voorkomen. Zonder doctype is de kans op verschillende (en soms volkomen verkeerde) weergave tussen verschillende browsers heel erg groot.
Geldige doctypes vind je op www.w3.org/QA/2002/04/valid-dtd-list.
Gebruik het volledige doctype, inclusief de eventuele url, anders werkt het niet goed.
Het hier gebruikte doctype is dat van html5. Dit kan zonder enig probleem worden gebruikt: het werkt zelfs in Internet Explorer 6.
<html lang="nl">
De toevoeging lang="nl"
bij <html> geeft aan dat de pagina in het Nederlands is. De taal is van belang voor schermlezers, automatisch afbreken, automatisch genereren van aanhalingstekens, juist gebruik van decimale punt of komma, en dergelijke.
<meta charset="utf-8">
Zorgt dat de browser letters met accenten en dergelijke goed kan weergeven.
utf-8 is de beste charset (tekenset), omdat deze alle talen van de wereld (en nog heel veel andere extra tekens) bestrijkt, maar toch niet meer ruimte inneemt voor de code, dan nodig is. Als je utf-8 gebruikt, hoef je veel minder entiteiten (ä
en dergelijke) te gebruiken, maar kun je bijvoorbeeld gewoon ä gebruiken.
Deze regel moet zo hoog mogelijk komen te staan, als eerste regel binnen de head, omdat hij anders door sommige browsers niet wordt gelezen.
In html5 hoeft deze regel niet langer te zijn, dan wat hier staat.
<meta name="viewport" content="width=device-width, initial-scale=1">
Mobiele apparaten variëren enorm in breedte. En dat is een probleem. Sites waren, in ieder geval tot voor kort, gemaakt voor desktopbrowsers. En die hebben, in vergelijking met bijvoorbeeld een smartphone, heel brede browservensters. Hoe moet je op 'n smartphone een pagina weergeven, die is gemaakt voor de breedte van een desktop? Je kunt natuurlijk wachten tot álle sites zijn omgebouwd voor smartphones, tablets, enz., maar dan moet je waarschijnlijk heel erg lang wachten.
Mobiele browsers gokken erop dat een pagina een bepaalde breedte heeft. Safari voor mobiel bijvoorbeeld gaat ervan uit dat een pagina 980 px breed is. De pagina wordt vervolgens zoveel versmald dat hij binnen het venster van het apparaat past. Op een iPhone wordt de pagina dus veel smaller dan op een iPad. Vervolgens kan de gebruiker inzoomen op het deel van de pagina dat hij of zij wil zien.
Dit betekent ook dat bij het openen van de pagina de tekst meestal heel erg klein wordt weergegeven. (Meestal, want niet alle browsers en apparaten doen het op dezelfde manier.) Niet erg fraai, maar bedenk maar 'ns 'n betere oplossing voor bestaande sites.
Nieuwe sites of pagina's kunnen echter wel rekening houden met de veel kleinere vensters van mobiele apparaten. Op deze pagina bijvoorbeeld worden knoppen, pop-ups, enz. volledig aangepast aan de grootte van het venster.
Maar die stomme mobiele browser weet dat niet, dus die gaat ervan uit dat ook deze pagina 980 px breed is, en verkleint die dan. Dat is ongeveer even behulpzaam als de gedienstige kelner die behulpzaam de stoel naar achteren trekt, net als jij wilt gaan zitten.
Om de door de browser aangeboden hulp vriendelijk maar beslist te weigeren, wordt deze tag gebruikt. Hiermee geef je aan dat de pagina is geoptimaliseerd voor mobiele apparaten.
Een iPad in portretstand bijvoorbeeld is 768 px breed. De kreet width=device-width
zegt tegen de mobiele browser dat de breedte van de weer te geven pagina gelijk is aan de breedte van het apparaat. Voor een iPad in portretstand dus 768 px.
Er staat nog een tweede deel in de tag: initial-scale=1
. Sommige mobiele apparaten zoomen een pagina gelijk in of uit. Ook weer in een poging behulpzaam te zijn. Ook dat is hier niet nodig. Er is ook een instructie om zoomen helemaal onmogelijk te maken, maar die gebruik ik niet. De bezoeker kan zelf nog gewoon zoomen, wat belangrijk is voor mensen die wat slechter zien.
<link rel="stylesheet" href="019-css-dl/menu-019-dl.css">
Dit is een koppeling naar een externe stylesheet (stijlbestand), waarin de css staat. In html5 is de toevoeging type="text/css"
niet meer nodig, omdat dit standaard al zo staat ingesteld. Je moet uiteraard de naam van en het pad naar de stylesheet aanpassen aan de naam en plaats waar je eigen stylesheet staat.
Voordeel van een externe stylesheet is onder andere dat deze geldig is voor alle pagina's, waaraan deze is gelinkt. 'n Verandering in de lay-out hoef je dan maar in één enkele stylesheet aan te brengen, in plaats van in elke pagina apart. Op een grotere site kan dit ontzettend veel werk schelen. Bovendien hoeft de browser zo'n externe stylesheet maar één keer te downloaden, ongeacht hoeveel pagina's er gebruik van maken. Zou je de css in elke pagina opnieuw aanbrengen, dan worden de te downloaden bestanden veel groter.
In dit voorbeeld heeft een extern stylesheet eigenlijk nauwelijks nut, want er is maar één pagina. In dit geval kun je daarom de css beter in de <head> van de html-pagina zelf zetten.
Voor de omvang maakt het hier nauwelijks uit, want de css wordt hoe dan ook altijd precies één keer gedownload, en nooit vaker. Voor het onderhoud maakt het ook geen verschil, want je hoeft de css slechts op één plaats te wijzigen. Maar het scheelt wel een extra aanroep naar de server, omdat geen apart stylesheet hoeft te worden gedownload.
Dat opnemen in de <head> gaat heel simpel: je kopieert gewoon het hele stylesheet en zet die bovenin de <head> van het voorbeeld, tussen <style> en </style>:
<style>
body {color: black;}
(...) rest van de css (...)
div {color: red;}
</style>
Maar zodra een iets groter stylesheet op meerdere pagina's wordt gebruikt, wat meestal het geval zal zijn, is een extern stylesheet beter. Op de site bijvoorbeeld gaat het om tientallen pagina's met dezelfde css.
(De reden dat er toch een extern stylesheet is, terwijl ik hierboven omstandig beweer dat dat in dit voorbeeld eigenlijk geen nut heeft: overzichtelijkheid. Nu kun je html en css los van elkaar bekijken.)
De hulppagina's achter de knoppen hebben een gezamenlijke stylesheet: menu-019-hulp-dl.css. Deze wordt hier verder niet besproken, omdat hij uiterst simpel is. Op de site is deze met de stylesheet voor de pagina's met submenu's gecombineerd tot één gezamenlijke stylesheet.
<span class="focus-open" tabindex="0"></span>
Sommige mensen gebruiken geen muis of aanraking, maar de Tab-toets om links, tekstvelden, en dergelijke af te gaan. Dat kan vanwege een handicap zijn, maar ook omdat het soms veel sneller en makkelijker werkt dan een muis.
Normaal genomen wordt een <span> bij gebruik van de Tab-toets genegeerd. Door het attribuut tabindex="0"
toe te voegen, worden nu ook de <span>'s bezocht. Dat maakt het mogelijk in de css de selector .focus-open:focus te gebruiken om daarmee de pop-up te kunnen openen.
(Elke pop-up heeft een eigen radioknop. Al deze knoppen behoren tot dezelfde groep. Als een knop is geselecteerd, wordt de pop-up geopend. Deze knoppen kunnen niet worden gebruikt om met behulp van :focus de bijbehorende pop-up te openen, want als een radioknop uit een bepaalde groep focus heeft, kan een andere radioknop uit dezelfde groep geen focus krijgen. Om van radioknop naar radioknop te gaan binnen dezelfde groep knoppen, gebruik je niet de Tab-toets, maar pijltjes. Vandaar deze aparte <span> voor gebruikers van de Tab-toets.)
<img src="019-pics/thumb-band.jpg" width="180" height="161" alt="">
De thumbnails. Bij elke thumbnail staat een omschrijving. Deze omschrijving wordt door schermlezers voorgelezen. Daarom heeft het weinig zin om bij de thumbnail ook nog een alt op te nemen. Een alt wordt door sommige schermlezers voorgelezen, waardoor je twee keer hetzelfde verhaal te horen zou krijgen.
Maar schermlezers melden het vaak wel, als een afbeelding aanwezig is. Als er verder geen alt of zoiets in de <img> staat, wordt soms de naam van het bestand voorgelezen.
Door de toevoeging van het attribuut alt=""
weten schermlezers, dat ze deze afbeelding volledig kunnen negeren. Dit werkt alleen als er echt alt=""
staat (niets tussen de aanhalingstekens). Als je alt gewoon weglaat, is er een grote kans dat de naam van het bestand wordt voorgelezen.
<label class="open" for="open-1" role="presentation">
Bij elke thumbnail hoort een radioknop, die zorgt voor het openen van de pop-up door middel van aanraken of klikken. Bij elk van die knoppen hoort een <label>. Deze <label>'s hebben geen enkel nut voor schermlezers, maar kunnen wel heel verwarrend zijn. In sommige gevallen meldt de schermlezer dat er een <label> is, maar het is volstrekt onduidelijk waar die dan voor is.
Daarom is het beter de <label>'s te verbergen voor schermlezers. Dat kan echter bij label.open
niet, want in deze <label>'s zit ook de beschrijving van de thumbnail. En die zou dan ook worden verborgen voor schermlezers.
Met de WAI-ARIA-code role="presentation"
wordt de <label> niet verborgen, maar wordt hij gedegradeerd tot een element zonder enige semantische betekenis. Zeg maar 'n soort <span>. Meer over WAI-ARIA-codes en semantiek is te vinden bij Semantische elementen en WAI-ARIA.
<span class="vraagteken" aria-hidden="true" title="Klik om pop-up open te houden">?</span>
Bij elke thumbnail hoort een <span> met daarin een vraagteken. Deze <span>'s hebben geen enkel nut voor schermlezers, maar kunnen wel heel irritant zijn. Elk vraagteken wordt namelijk – bij gebrek aan andere tekst in de <span> – voorgelezen.
Met behulp van het attribuut aria-hidden="true"
worden de <span>'s verborgen voor schermlezers. Meer hierover bij WAI-ARIA-codes.
<label class="sluit" for="sluit-x" aria-hidden="true">x</label>
Bij elke thumbnail zit een <label>, dat hoort bij de radioknop die zorgt voor het sluiten van de pop-ups na openen door middel van aanraken of klikken. Deze <label>'s hebben geen enkel nut voor schermlezers, maar kunnen wel heel verwarrend zijn. Bovendien wordt de in de <label> zittende letter 'x' voorgelezen, wat ook een tamelijk zinloze onderneming is.
Met behulp van het attribuut aria-hidden="true"
worden de <label>'s verborgen voor schermlezers. Meer hierover bij WAI-ARIA-codes.
<input id="checkbox-voor-focus" type="checkbox" aria-hidden="true" autofocus>
Bovenaan de kolom met tekst zit een <input>, die feitelijk geen enkele werking heeft. Maar door het attribuut autofocus
toe te voegen, wordt de focus bij openen van de pagina op de tekst gezet. Hierdoor kan gelijk gescrold worden met behulp van het muiswieltje of met toetsen als de pijltjes.
Zonder deze <input> moet eerst in de tekst worden geklikt, omdat in de html de knoppen voor de tekst zitten. Pas daarna kan dan worden gescrold en dergelijke.
(Je zou ook in de html de <main> met de tekst voor de <nav> met de knoppen kunnen neerzetten. Op de site kan dat niet, omdat er nog veel meer links in de <nav> zitten. Daarom is dat in dit voorbeeld ook niet gebeurd, want dat zou weer 'n extra verschil met de site opleveren.)
CSS
De code is geschreven in een afwijkende
lettersoort. De code die te maken heeft met de basis van dit voorbeeld (essentiële code) is in de hele uitleg onderstippeld blauw
. Alle niet-essentiële code is bruin
. (In de inhoudsopgave staat alles in een gewone letter vanwege de leesbaarheid.)
Deze uitleg hoort bij het voorbeeld dat in de download zit. Het voorbeeld uit de download verschilt iets van het voorbeeld hier op de site. In de download ontbreekt bijvoorbeeld de navigatie voor de site. Ook in de kopregels zit vaak wat verschil. Daarnaast kunnen er nog andere (meestal kleine) verschillen zijn.
Als je deze uitleg leest naast de broncode van het voorbeeld op de site, kan het dus bijvoorbeeld zijn dat 'n <h1> uit de css bij 'n <h2> uit de html hoort. Maar het gaat niet om hele grote, fundamentele afwijkingen.
Als je dit lastig vindt, kun je bovenaan de pagina de hele handel downloaden. In de download zit 'n voorbeeld dat wel naadloos aansluit op de uitleg in de download.
Technisch gezien is er geen enkel bezwaar om de css in de stylesheet allemaal achter elkaar op één regel te zetten:
div#header-buiten {position: absolute; right: 16px; width: 100%; height: 120px; background: yellow;} div p {margin-left 16px; height: 120px; text-align: center;}
Maar als je dat doet, garandeer ik je hele grote problemen, omdat het volstrekt onoverzichtelijk is. Beter is het om de css netjes in te laten springen:
div#header-buiten {
position: absolute;
right: 16px;
width: 100%;
height: 120px;
background: yellow;
}
div p {
margin-left: 16px;
height: 120px;
text-align: center;
}
Hiernaast is het heel belangrijk voldoende commentaar (uitleg) in de stylesheet te schrijven. Op dit moment weet je waarschijnlijk (hopelijk...), waarom je iets doet. Maar over vijf jaar kan dat volstrekt onduidelijk zijn. Op deze site vind je nauwelijks commentaar in de stylesheets, maar dat heeft een simpele reden: deze uitleg is in feite één groot commentaar.
Op internet zelf is het goed, als de stylesheet juist zo klein mogelijk is. Dus voor het uploaden kun je normaal genomen het beste het commentaar weer verwijderen. Veel mensen halen zelfs alles wat overbodig is weg, voordat ze de stylesheet uploaden. Inspringingen bijvoorbeeld zijn voor mensen handig, een computer heeft ze niet nodig.
Je hebt dan eigenlijk twee stylesheets. De uitgebreide versie waarin je dingen uitprobeert, verandert, enz., met commentaar, inspringingen, en dergelijke. Dat is de mensvriendelijke versie. Daarnaast is er dan een stylesheet die je op de echte site gebruikt: een gecomprimeerde versie.
Dat comprimeren kun je met de hand doen, maar er bestaan ook hulpmiddelen voor. Als je op internet zoekt naar 'css' en 'compress' of 'comprimeren', vind je tal van sites, waar je dat automatisch kunt laten doen.
(Stylesheets op deze site zijn niet gecomprimeerd. Omdat het vaak juist om de css gaat, wil ik dat mensen zonder al te veel moeite de css kunnen bekijken.)
css voor alle vensters
/* menu-019-dl.css */
Om vergissingen te voorkomen is het een goede gewoonte bovenaan het stijlbestand even de naam neer te zetten. Voor je het weet, zit je anders in het verkeerde bestand te werken.
@-webkit-keyframes bugfix {from {padding-left: 0;} to {padding-left: 0;}}
Op een aantal plaatsen wordt in een selector gebruik gemaakt van het teken ~
(de 'general sibling'-selector). Oudere versies van Android browser hebben daar soms problemen mee. In dit voorbeeld wordt het sluitkruisje niet getoond, als de pop-up door middel van aanraking wordt geopend. Het toevoegen van deze animatie op een aantal plaatsen in de css, lost dit probleem op.
Als je nou denkt dat hier niets wordt uitgevoerd, omdat de padding links van 0 px in een padding links van 0 px wordt veranderd, dan heb je helemaal gelijk. Toch neutraliseert deze flauwekul de bug.
Normaal genomen is het een bijzonder slecht idee css te gebruiken voor slechts één weergave-machine: webkit. Maar in dit geval is dit terecht, want de bug zit alleen in op webkit gebaseerde browsers. Het heeft dus geen zin om Internet Explorer of Firefox ook met deze ongein te belasten.
Waarom dit alleen in webkit-browsers werkt, staat bij De voorvoegsels -moz-, -ms- en -webkit-.
body
Het element waarbinnen de hele pagina staat. Veel instellingen die hier worden opgegeven, worden geërfd door de nakomelingen van <body>. Ze gelden voor de hele pagina, tenzij ze later worden gewijzigd. Dit geldt bijvoorbeeld voor de lettersoort, de lettergrootte en de voorgrondkleur.
background: #eee;
Achtergrondkleurtje.
color: black;
Voorgrondkleur zwart. Dit is onder andere de kleur van de tekst.
Hoewel dit de standaardkleur is, wordt deze toch specifiek opgegeven. Hierboven is een achtergrondkleur opgegeven. Sommige mensen hebben zelf de voorgrond- en/of achtergrondkleur veranderd, bijvoorbeeld omdat ze slecht kleuren kunnen onderscheiden. Als nu de achtergrondkleur wordt veranderd, maar niet de voorgrondkleur, loop je het risico dat tekstkleur en achtergrondkleur te veel op elkaar gaan lijken.
Door beide op te geven, is redelijk zeker dat achtergrond- en tekstkleur genoeg van elkaar blijven verschillen. Als de gebruiker !important
heeft gebruikt in een eigen stylesheet, is er nog niets aan de hand, want dan veranderen achtergrond- en voorgrondkleur geen van beide.
font-family: Arial, Helvetica, sans-serif;
Lettersoort. Als er geen Arial is, wordt gezocht naar Helvetica. Als dat er ook niet is in ieder geval 'n lettersoort zonder schreef (dwarsstreepjes).
margin: 0; padding: 0;
Verschillende browsers hebben verschillende standaard-instellingen hiervoor. Door ze gewoon op 0 te zetten, zijn ze overal hetzelfde.
h1
Alle <h1>'s. Dat is er maar eentje: de belangrijkste kop op de pagina.
background: #eee;
Achtergrondkleurtje.
color: black;
Voorgrondkleur zwart. Dit is onder andere de kleur van de tekst.
Hoewel dit de standaardkleur is, wordt deze toch specifiek opgegeven. Hierboven is een achtergrondkleur opgegeven. Sommige mensen hebben zelf de voorgrond- en/of achtergrondkleur veranderd, bijvoorbeeld omdat ze slecht kleuren kunnen onderscheiden. Als nu de achtergrondkleur wordt veranderd, maar niet de voorgrondkleur, loop je het risico dat tekstkleur en achtergrondkleur te veel op elkaar gaan lijken.
Door beide op te geven, is redelijk zeker dat achtergrond- en tekstkleur genoeg van elkaar blijven verschillen. Als de gebruiker !important
heeft gebruikt in een eigen stylesheet, is er nog niets aan de hand, want dan veranderen achtergrond- en voorgrondkleur geen van beide.
Dit is ook al bij <body> opgegeven, maar sommige mensen hebben bij álle elementen de kleuren veranderd. Het heeft immers weinig zin, als ze dat alleen bij de body doen, terwijl de sitebouwer de kleuren ook bij bijvoorbeeld de paragrafen heeft aangepast.
font-size: 1em;
Van zichzelf heeft een <h1> een veel grotere letter. Hier wordt dat veranderd in 'n normale lettergrootte.
Als eenheid wordt de relatieve eenheid em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
line-height: 30px;
Er wordt geen hoogte opgegeven voor de <h1>, alleen een regelhoogte. Bij gebrek aan een hoogte wordt de regelhoogte ook de hoogte van de <h1>. Voordeel is dat tekst automatisch halverwege de regelhoogte wordt neergezet, waardoor de kop netjes verticaal in het midden van de <h1> staat.
text-align: center;
Tekst horizontaal centreren.
margin: 0;
Van zichzelf heeft een <h1> een marge aan boven- en onderkant. Die is hier niet welkom.
ul
Alle <ul>'s. Dat is er hier maar eentje: de <ul> waar de knoppen met toebehoren in staan.
list-style-type: none;
Bolletjes en dergelijke bij de lijst-items verwijderen.
margin: 0; padding: 0;
De standaardinstellingen voor marge en padding zijn niet in alle browsers hetzelfde. Door ze op 0 te zetten, zijn ze overal hetzelfde.
abbr[title]
Deze selector valt in twee delen uiteen.
abbr
: alle <abbr>'s.
[title]
: met de teksthaken geef je aan, dat er een extra voorwaarde aan het element wordt gesteld. In dit geval is dat vrij simpel: het title-attribuut moet aanwezig zijn.
De hele selector: alle <abbr>'s, maar alleen als ze het title-attribuut hebben.
In het voorbeeld staat slechts twee keer een <abbr>. De eerste:
<abbr lang="en" title="Cascading Style Sheets">css</abbr>
Hier is het title-attribuut aanwezig. (Omdat de tekst in het title-attribuut Engelstalig is, is ook nog lang="en"
toegevoegd, de taalcode voor Engels.)
De tweede keer ziet de <abbr> er zo uit:
<abbr>css</abbr>
Hier ontbreekt het title-attribuut.
De eerste <abbr> valt dus onder deze selector, de tweede niet.
De eerste keer wordt de afkorting 'css' voluit aangegeven in de titel. Bij latere herhalingen gebeurt dat niet meer. Wel wordt bij latere afkortingen <abbr> gebruikt, om te voorkomen dat een schermlezer 'css' als woord probeert uit te spreken.
Afhankelijk van schermlezer en instellingen kan het title-attribuut worden voorgelezen door een schermlezer. Bij hoveren over de <abbr> verschijnt de title in een klein venstertje.
Er zijn nogal wat uiteenlopende meningen over dit hele title-gedoe bij <abbr>. Op touchscreens heb je er niets aan. En niet alle schermlezers kunnen er mee uit de voeten. Daarom kiezen sommigen ervoor de eerste keer de title ook volledig weer te geven in de gewone tekst. Maar dat betekent weer, dat sommige schermlezers het twee keer voorlezen.
Er zijn ook sitebouwers die bij élke <abbr> de title toevoegen. Dat is mij te gek, want dat zou betekenen dat in 'n pagina met uitleg honderden keren html en css voluit moeten worden weergegeven in de title. Bovendien is het nogal irritant voor gebruikers van schermlezers als ze elke keer volledig voluit 'Cascading Style Sheets' of 'HyperText Markup Language' horen in plaats van 'css' en 'html'.
Iets wat je ook met enige regelmaat gebruikt ziet worden:
abbr[title]::after {content: " (" attr(title) ")";
Dit zet de titel van de <abbr> achter de afkorting op het scherm, tussen haakjes. Maar alleen als de <abbr> een title-attribuut heeft. Op deze manier kun je de afkorting alleen de eerste keer voluit laten schrijven, door alleen de eerste <abbr> een title te geven. Maar ook dit lost niet alles op, want bij latere <abbr>'s is de volledige afkorting nog steeds onbekend.
Je kunt ook ingewikkelde oplossingen met JavaScript gaan bedenken, maar dat wordt toch 'n beetje al te veel van het goede voor een relatief simpel hulpmiddel.

Ik kies ervoor alleen bij de eerste <abbr> een title-attribuut toe te voegen. Met de css hieronder wordt aangegeven dat onder die afkorting uitleg zit. Op de afbeelding is te zien hoe dat er in Firefox op Linux uitziet. De afkorting 'css' is onderstippeld, en bij hoveren over de afkorting verschijnt een venstertje met de volledige afkorting. De cursor verandert in een vraagteken.
cursor: help;
Cursor veranderen in 'n hulpsymbooltje. Hoe dat er precies uitziet, verschilt per browser en per besturingssysteem.
text-decoration: none; border-bottom: dotted 1px;
Niet alle browsers geven een <abbr> met een title-attribuut aan. En de browsers die het wel doen, gebruiken er verschillende methoden voor. Met text-decoration: none;
wordt de onderstreping overal verwijderd. En met border-bottom: dotted 1px;
wordt overal een onderstippeld lijntje onder de <abbr> geplaatst.
Nu ziet het er in alle browsers hetzelfde uit.
input, .vraagteken, .sluit
Alle <input>'s, de elementen met class="vraagteken en class="sluit".
<input>'s worden voornamelijk gebruikt voor het openen en sluiten van de pop-ups. Maar de feitelijke bediening gebeurt door de bijbehorende <label>'s, de <input>'s zelf hoeven niet zichtbaar te zijn. Voor grotere browservensters wordt input#checkbox-voor-focus
later bij #checkbox-voor-focus weer zichtbaar gemaakt.
Elke thumbnail heeft een bijbehorende span.vraagteken
en label.sluit
. Die worden alleen gebruikt om de pop-ups te openen en te sluiten. Dat gebeurt niet in kleine vensters, dus die kunnen hier worden verborgen.
display: none;
Verbergen.
Door het gebruik van display: none;
worden deze elementen ook voor schermlezers verborgen. Dat is prima, want ze zijn voor schermlezers alleen maar uiterst verwarrend, zonder dat ze nut hebben.
Meer over schermlezers en deze elementen is te vinden bij WAI-ARIA-codes.
.naam
Alle elementen met class="naam". Binnen elke link <a> zit een <span> met deze class. Binnen die <span> zit de korte naam (één woord) van de achterliggende pagina.
(Één woord is nogal kort voor de beschrijving van een pagina. Maar daarnaast zijn er de thumbnails van de pagina en de omschrijving van de thumbnails.)
opacity: 0;
Volledig doorzichtig maken.
Deze naam moet op verschillende momenten op verschillende plaatsen zichtbaar zijn. display: none;
of visibility: hidden;
kunnen niet worden gebruikt, want schermlezers negeren de tekst dan volledig. En buiten deze tekst staat er niets in de <a>. Sommige schermlezers gaan dan, bij gebrek aan beter, de naam van de pagina voorlezen of andere rampzaligheden. Stel je even de wanhoop voor van een schermlezer die probeert '019-files-dl/keyboards-dl.html' begrijpelijk voor te lezen...
Nu is er voor schermlezers in de <a> een korte naam om voor te lezen.
h2
Alle <h2>'s. Dat er hier maar eentje. Daarin staat 'Navigatie site'.
De thumbs met bijbehorende links en dergelijke staan in een <ul> binnen een <nav>. Hierdoor zijn ze goed toegankelijk voor schermlezers, want die kondigen een <nav> op een of andere manier aan als een menu. Maar wat voor soort menu, dat blijft raden. Daarom wordt bovenin de <nav> 'Navigatie site' gezet. Dit wordt voorgelezen door schermlezers, zodat duidelijk is waar het menu voor dient.
Je zou de tekst ook in een gewone <span> of zo kunnen zetten, maar schermlezers kunnen heel makkelijk van <h> naar <h> springen of een lijstje met <h>'s tevoorschijn toveren. Hierdoor is er een extra manier om de navigatie snel te vinden, zonder dat dat ook maar enig extra werk met zich meebrengt.
position: absolute; left: -20000px;
Voor mensen die kunnen zien, is deze titel volstrekt overbodig. Daarom wordt de <h2> links buiten het scherm geparkeerd. Schermlezers lezen hem gewoon voor, maar de lay-out wordt niet verpest door een overbodige mededeling.
li
Alle <li>'s. Dat zijn er hier acht: ééntje voor elke thumbnail met bijbehorende link en dergelijke.
background: #eee;
Achtergrondkleurtje.
color: black;
Voorgrondkleur zwart. Dit is onder andere de kleur van de tekst.
Hoewel dit de standaardkleur is, wordt deze toch specifiek opgegeven. Hierboven is een achtergrondkleur opgegeven. Sommige mensen hebben zelf de voorgrond- en/of achtergrondkleur veranderd, bijvoorbeeld omdat ze slecht kleuren kunnen onderscheiden. Als nu de achtergrondkleur wordt veranderd, maar niet de voorgrondkleur, loop je het risico dat tekstkleur en achtergrondkleur te veel op elkaar gaan lijken.
Door beide op te geven, is redelijk zeker dat achtergrond- en tekstkleur genoeg van elkaar blijven verschillen. Als de gebruiker !important
heeft gebruikt in een eigen stylesheet, is er nog niets aan de hand, want dan veranderen achtergrond- en voorgrondkleur geen van beide.
Dit is ook al bij <body> opgegeven, maar sommige mensen hebben bij álle elementen de kleuren veranderd. Het heeft immers weinig zin, als ze dat alleen bij de body doen, terwijl de sitebouwer de kleuren ook bij bijvoorbeeld de paragrafen heeft aangepast.
box-sizing: border-box;
Normaal genomen worden border
en padding
bij de breedte en hoogte opgeteld. Hier komt het beter uit, als border
en padding
binnen de breedte vallen. Met deze regel wordt dat bereikt.
Iets hieronder wordt een breedte opgegeven van 100%: even breed als het venster van de browser. Daar komen normaal genomen padding
(links en rechts 4 px) en border
(links en rechts 1 px) echter nog bij. Daardoor wordt het totaal breder dan het venster: 100% + 10 px. Door border
en padding
binnen de breedte te laten vallen, geldt de maximumbreedte van 100% nu voor de breedte inclusief border
en padding
.
width: 100%;
Breedte.
Een breedte in procenten wordt altijd genomen ten opzichte van de breedte van de ouder. Dat is hier het blok-element <ul>. Als een blok-element geen breedte heeft gekregen, wordt dat automatisch even breed als z'n ouder. De ouder van <ul> is <nav>, de ouder daarvan is <header>, en de ouder daarvan is <body>. Alle drie blok-elementen, waarbij geen breedte is opgegeven en die dus ook weer even breed worden als hun ouder.
De ouder van <body> is <html>, het laatste element. Ook dit is een blok-element zonder breedte. En dan zijn we er eindelijk: de ouder van <html> is het venster van de browser. <html> en in het kielzog daarvan <body>, <header>, <nav>, <ul> en uiteindelijk <li> worden even breed als het browservenster. Oftewel: de <li>'s vullen altijd de volle breedte van het venster, en daarmee ook de in de <li> zitten de tekst en dergelijke.
(Een <li> is ook een blok-element. Dus dan is deze hele waanzinnige exercitie toch overbodig? Nee, want gelijk hieronder wordt de <li> gefloat. En gefloate elementen worden niet breder, dan nodig is voor de inhoud. Als er maar weinig in de <li> staat, wordt deze hierdoor smaller dan het venster van de browser.)
float: left;

Een <li> is een blok-element. Daardoor wordt elke <li> op een nieuwe regel gezet. Door ze naar links te floaten, worden ze naast elkaar gezet.
Dat is hier echter vrij zinloos, omdat de <li> hier gelijk boven even breed als het venster van de browser is gemaakt, dus er passen er nooit twee of meer naast elkaar.
In dit geval heeft float
een andere functie. Binnen de <li> zit een <img>. Die wordt bij img naar links gefloat, zodat er tekst naast komen te staan. Maar dan ontstaat er een probleem.
Een blok-element, dus ook deze <li>, wordt normaal genomen automatisch precies hoog genoeg om de inhoud ervan weer te geven. Dat is hier de <img> met de ernaast staande tekst. Verder zit er nog een <a> in de <li>. De <li> zou normaal precies hoog genoeg worden, om de erin zittende <img>, de tekst daarnaast en de <a> weer te geven. (Er zit nog meer in de <li>, maar dat gaat pas meedoen in grotere browservensters. Het is hier verborgen.)
De <a> is absoluut gepositioneerd. Absoluut gepositioneerde elementen tellen niet mee voor de hoogte van de <li>. Blijven de <img> en de ernaast staande tekst over.
De <img> is naar links gefloat. Ook gefloate elementen tellen niet mee voor de hoogte van hun ouder. Alleen de tekst blijft over: de <li> wordt niet hoger dan nodig is om de tekst naast de <img> weer te geven.
Bij weinig tekst valt hierdoor een deel van de <img> aan de onderkant weg. Op de afbeelding is te zien dat bij de eerste en derde thumbnail, waarnaast weinig tekst staat, het onderste deel van de thumbnail gewoon wordt afgekapt. (Er gebeuren nog meer vreemde dingen, maar die laat ik even zitten.)
Je kunt dit op een aantal manieren oplossen. In dit geval is de simpelste manier om ook de <li>'s te floaten. In dat geval tellen gefloate kinderen van de <li>, hier de <img>, weer mee voor de hoogte. Hierdoor wordt de <li> automatisch even hoog als de thumbnail of de tekst, afhankelijk van welk van deze twee het hoogst is, en verdwijnen er geen delen van de <img> meer bij weinig tekst.
margin-top: -1px;
Rondom de <li>'s wordt hier gelijk onder een zwart randje van 1 px dik gezet. Omdat de <li>'s onder elkaar staan, komen tussen twee <li>'s twee randjes tegen elkaar te staan. Samen zijn die 2 px dik. Door de <li> 1 px naar boven te verplaatsen, vallen de randjes over elkaar heen en is de rand ook hier 1 px dik.
border: black solid 1px;
Zwart randje rondom de <li>.
padding: 4px 4px 10px;
Omdat voor links geen waarde is opgegeven, krijgt links automatisch dezelfde waarde als rechts. Hier staat dus eigenlijk 4px 4px 10px 4px
in de volgorde boven – rechts – onder – links. Overal wat afstand tussen inhoud en buitenkant van de <li>. Aan de onderkant iets meer, zodat de <li>'s wat minder dicht op elkaar lijken te staan.
position: relative;
Om kinderen van een element te kunnen positioneren ten opzichte van dat element, moet het element zelf zijn gepositioneerd. Omdat verder niets voor top
en dergelijke wordt opgegeven, heeft dit verder geen enkele invloed op het element zelf.
a
Alle <a>'s. Dit zijn de links naar de achter de knoppen zittende pagina's.
Door deze <a>'s even groot te maken als de thumbnails en ze daaroverheen te zetten, gaat de hele thumbnail als link werken.
width: 120px; height: 108px;
Zelfde breedte en hoogte als gelijk hieronder aan de <img>'s met de thumbnails wordt gegeven.
position: absolute;
Om de <a> op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf is gepositioneerd. Dat is hier de <li> waar de <a> in zit.
Een <a> is een inline-element. Daardoor kunnen eigenschappen als breedte en hoogte niet worden gebruikt. Door de <a> absoluut te positioneren, verandert deze in een soort blok-element, waardoor dit soort eigenschappen wel gebruikt kunnen worden.
top: 8px; left: 8px;
Op deze positie komt de <a> precies boven de thumbnail te staan, waardoor de hele thumbnails als link gaat werken.
img
Alle <img>'s. Dat zijn hier de acht thumbnails.
box-shadow: 4px 6px 4px 1px;

Schaduw aan de thumbnail geven.
Met behulp van box-shadow kan schaduw worden gegeven aan een element.
Als je verder niets opgeeft, is de schaduw precies even groot als het element, waar de schaduw bij hoort. Dat schiet niet echt op, want dat betekent dat de schaduw precies onder het element staat en dus onzichtbaar is. De natte droom van de Gevorderde Geheim Agent, maar niet van een sitebouwer.
Daarom wordt de schaduw met behulp van de vier getallen aangepast. De getallen die hier worden gebruikt, leveren de schaduw op, zoals die hierboven bij de afbeelding is te zien: rechtsonder de thumbnail. Hieronder zijn de waarden iets veranderd, zodat het effect van de verschillende waarden duidelijker is te zien.

4px
: het eerste getal, hier 4px, geeft de verplaatsing in horizontale richting aan: 4 px naar rechts. Als dit getal 0 zou zijn, zou de linkerkant van de schaduw gelijkvallen met de linkerkant van de <img>, nu is de schaduw 4 px naar rechts verschoven. Als je hier een negatief getal invult, verschuift de linkerkant van de schaduw naar links. Om bijstaande afbeelding te krijgen, zijn de waarden 30px 0 0 0 gebruikt: alleen een horizontale verschuiving van 30 px.
Hier is gelijk iets te zien, waar je op moet letten: een box-shadow wordt plompverloren bovenop aangrenzende elementen gezet. Op de afbeelding staat de schaduw over de ernaast staande tekst. Je moet dus altijd voor voldoende ruimte rondom het element met de schaduw zorgen.

6px
: voor het tweede getal geldt precies hetzelfde, maar dan in verticale richting. De bovenkant van de schaduw wordt 6 px naar beneden verplaatst.
Om bijstaande afbeelding te krijgen, zijn de waarden 0 30px 0 0 gebruikt: alleen een verticale verschuiving van 30 px.
Ook hier geldt weer dat de schaduw plompverloren bovenop aangrenzende elementen wordt neergepoot, zoals hier over de eronder staande tekst.

4px
: het derde getal geeft de breedte van de vervaging aan. De schaduw vervaagt hier over een afstand van 4 px. Om bijstaande afbeelding te krijgen, zijn de waarden 0 0 30px 0 gebruikt: de schaduw vervaagt over een afstand van 30 px. Negatieve getallen zijn hier niet toegestaan. De vervaging is wat moeilijk te zien, maar dat is nou juist het kenmerk van een vervaging.

1px
: het vierde getal geeft de breedte van de schaduw aan. Om bijstaande artistieke hoogstandje te krijgen, zijn de waarden 0 0 0 30px gebruikt: de schaduw is 30 px breed. Als schaduw is deze zielenpoot duidelijk mislukt, maar je kunt hier wel allerlei andere grapjes mee uithalen, zoals een tweede border. En aangezien je meerdere box-shadows kunt gebruiken, kun je met box-shadow feitelijk een oneindig aantal borders maken.
Je kunt ook nog een kleur opgeven bij box-shadow. Als je geen kleur opgeeft, wordt de voorgrondkleur gebruikt. Die voorgrondkleur is hier zwart, daarom zou het opgeven van een kleur hier niet nodig moeten zijn. Maar sommige versies van Android browser geven geen schaduw, als je geen kleur opgeeft. Daarom wordt toch een kleur opgegeven.
Meestal moet je even wat experimenteren, voordat je de juiste waarden hebt. Vooral de laatste waarden, die voor het vervagen en voor de breedte van de schaduw, beïnvloeden elkaar nogal. Op de pagina met links staan onder het kopje CSS → Online uitproberen, code genereren, en dergelijke sites, waar je online een box-shadow kunt maken.
width: 120px;
Breedte.
In de html is ook een breedte opgegeven, maar zodra in de css een breedte wordt opgegeven, 'wint' die van de breedte in de html. De in de html opgegeven breedte van 180 px is voor bredere browservensters.
De echte breedte van de thumbnail is 180 px. Dit is ook de breedte die in grotere vensters wordt gebruikt. Maar voor kleinere vensters wordt de breedte iets verkleind. Dat is eigenlijk hartstikke verkeerd, omdat hierdoor een groter bestand wordt gedownload, dan nodig is. Normaal genomen zou je voor kleinere vensters thumbnails van 120 px breed maken. Maar het verschil in bestandsgrootte is zo klein, dat ik het hier de moeite niet waard vind.
height: auto;

In de html is bij de <img> ook een hoogte opgeven: 161 px. Dat is de echte hoogte van de thumbnail, maar die wordt alleen gebruikt in grotere browservensters.
Hier gelijk boven is de breedte verkleind van 180 tot 120 px. Als de hoogte hier niet wordt aangepast, blijft deze gewoon 161 px. Dat leidt tot thumbnails van 120 bij 161 px waarop alleen nog wanstaltig lange kinderen staan, zoals op de afbeelding hiernaast is te zien: een broodmagere vijfjarige met de lengte van een forse volwassene.
(Hier gelijk onder staat hetzelfde kind op een thumbnail met de juiste verhoudingen. Nogal 'n verschil.)
Door als hoogte auto
op te geven, bepaalt de browser de hoogte. Daardoor blijven de verhoudingen van de foto intact. Omdat de breedte van 180 naar 120 px is verkleind, een derde minder, wordt ook de hoogte met een derde verminderd. De foto wordt nu niet vervormd, wat een ernstige groeistoornis bij het arme kind voorkomt.
float: left;

Zo ver mogelijk naar links neerzetten. Dat maakt hier voor de <img> eigenlijk niet zoveel uit, want de thumb zou hoe dan ook ongeveer op deze plaats komen te staan.
De <img> wordt hier gefloat, omdat de tekst dan over de volle hoogte van de <img> naast de <img> wordt gezet.
Een <img> is een inline-element. Een ietwat apart inline-element, maar het blijft een inline-element. De <label> waar de tekst in staat is ook een inline-element. Daardoor worden normaal genomen beide elementen, net als gewone tekst, naast elkaar op dezelfde regel gezet. Daarbij bepaalt de thumb, omdat die het hoogst is, de regelhoogte. Dat is op de afbeelding te zien: naast de thumb staat één regel tekst, niet meer.
Door de thumb naar links te floaten, vult de tekst de volledige lege ruimte links van de thumb.
margin: 3px 10px 6px 3px;
Aan alle kanten wat marge, zodat de thumb op een nette manier wordt neergezet. De marge rechts is wat hoog. De box-shadow aan de rechterkant van de thumbnail neemt ongeveer 6 px in beslag, dus er zijn rechts 6 px meer nodig voor voldoende afstand tot de tekst.
border: black solid 1px;
Zwart randje rondom de thumb.
border-radius: 5px;
Aan alle kanten ronde hoeken.
.pop-up-tekst
Alle elementen met class="pop-up-tekst". De <span>'s waarbinnen de toelichting bij de thumbnails staat. In kleinere browservensters zijn deze teksten altijd zichtbaar. Ze staan rechts van de thumbnails (en eronder, als rechts te weinig ruimte is voor alle tekst).
-moz-hyphens: auto; -ms-hyphens: auto; -webkit-hyphens: auto; hyphens: auto;

Hier staat in feite vier keer hetzelfde: hyphens: auto;
. Waarom dat zo is, staat bij De voorvoegsels -moz-, -ms- en -webkit-.
In kleinere browservensters staat de tekst rechts van de thumbnails. Daar kan, in smalle vensters, heel erg weinig ruimte zijn. Daarom wordt hier automatisch afbreken van woorden aangezet.
In heel smalle vensters wordt het nooit echt netjes, maar door afbreken aan te zetten worden in ieder geval de lelijkste lege plekken voorkomen. Op de afbeelding is de tekst rechts minder lelijk verdeeld dan de tekst links.
main
Alle <main>'s. Dat is er maar eentje. Binnen <main> staat de belangrijkste inhoud van de pagina. Dat is hier voornamelijk opvultekst, maar normaal genomen staat daar – hopelijk – wel iets interessants.
display: block;
Oudere browsers kennen <main> niet. Onbekende elementen worden standaard als inline-element weergegeven. Daarom wordt hier expliciet gezegd dat dit een blok-element is.
max-width: 700px;
Maximumbreedte.
Het zal niet vaak voorkomen, maar in browservensters die breder dan 763 px én lager dan 543 px zijn, kan de in <main> staande tekst heel erg breed worden. Waardoor de tekst heel lastig te lezen wordt. Daarom wordt de maximale breedte beperkt tot 700 px.
(Dit geldt ook voor de tekst rechts van de thumbnails: ook die kan heel breed worden. Maar omdat daar maar weinig tekst staat, en omdat het om vensters met een toch tamelijk exotische maat gaat, heb ik daar geen maximumbreedte opgegeven. Als je dat wel wilt doen, kun je bij li een maximumbreedte opgeven. Je moet dan hier bij <main> nog clear: both;
toevoegen, omdat anders de tekst uit <main> rechts in de lege ruimte naast de <li>'s komt te staan.)
margin: 0 auto;
Omdat voor onder en links geen waarde is opgegeven, krijgen die automatisch dezelfde waarde als boven en rechts. Hier staat dus eigenlijk 0 auto 0 auto
in de volgorde boven – rechts – onder – links. Boven en onder geen marge. Rechts en links auto
, wat hier hetzelfde betekent als evenveel. Ongeacht de breedte van het venster van de browser staat <main>, en dus de tekst daarin, altijd horizontaal gecentreerd.
Deze manier van centreren van een blok-element werkt alleen, als het te centreren blok-element een breedte heeft gekregen. Dat is hier het geval, want ook de gelijk hierboven opgegeven maximumbreedte geldt als breedte. (Alleen zie je natuurlijk pas iets van dat centreren in vensters breder dan 700 px.)
padding: 5px;
Aan alle kanten wat ruimte tussen tekst in en buitenkant van <main>.
p
Alle <p>'s. Alle tekst staat in een <p>.
text-indent: 1em;
Eerste regel van elke <p> 1 em laten inspringen. Door als eenheid em
te nemen, verandert de breedte van de inspringing mee met de lettergrootte.
margin: 0.25em 0 0;
Omdat voor links geen waarde is opgegeven, krijgt links automatisch dezelfde waarde als rechts. Hier staat dus eigenlijk 0.25em 0 0 0
in de volgorde boven – rechts – onder – links.
Van zichzelf heeft een <p> een marge aan boven- en onderkant. De marge aan de onderkant wordt hier weggehaald. De marge aan de bovenkant wordt 0.25 em. Door als eenheid em
te nemen, verandert de grootte van de marge mee met de lettergrootte.
css voor vensters minimaal 763 px breed en minimaal 543 px hoog
@media screen and (min-width: 763px) and (min-height: 543px)
De css die hier tot nu toe staat, geldt voor alle browservensters.
De css die binnen deze media query staat, geldt alleen voor vensters die minimaal 763 px breed én minimaal 543 px hoog zijn. In deze vensters zijn de thumbnails groter. Verder is de toelichtende tekst bij de thumbnails verborgen. Deze wordt pas zichtbaar, als een pop-up wordt geopend. In die pop-up zit ook een grotere versie van de thumbnail.
@media
: geeft aan dat het om css gaat die alleen van toepassing is, als aan bepaalde voorwaarden wordt voldaan. Al langer bestond de mogelijkheid om met behulp van zo'n @media-regel css voor bijvoorbeeld printers op te geven. css3 heeft dat uitgebreid tot bepaalde fysieke eigenschappen, zoals de breedte en hoogte van het venster van de browser.
screen
: deze regel geldt alleen voor schermweergave.
and
: er komt nog een voorwaarde, waaraan moet worden voldaan.
(min-width: 763px)
: het venster moet minimaal 763 px breed zijn. Is het venster smaller, dan wordt de css die binnen deze media-regel staat genegeerd.
and
: er komt nog een voorwaarde, waaraan moet worden voldaan.
(min-height: 543px)
: het venster moet minimaal 543 px hoog zijn. Is het venster lager, dan wordt de css die binnen deze media-regel staat genegeerd.
Gelijk na deze regel komt een {
te staan, en aan het einde van de css die binnen deze regel valt een bijbehorende afsluitende }
. Die zijn in de regel hierboven weggevallen, maar het geheel ziet er zo uit:
@media screen and (min-width: 763px) and (min-height: 543px) {
body {color: silver;}
(...) rest van de css voor deze @media-regel (...)
footer {color: gold;}
}
Voor de eerste css binnen deze media-regel staat dus een extra {
, en aan het eind staat een extra }
.
body
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
body {background: #eee; color: black; font-family: Arial, Helvetica, sans-serif; margin: 0; padding: 0;}
Het element waarbinnen de hele pagina staat. Veel instellingen die hier worden opgegeven, worden geërfd door de nakomelingen van <body>. Ze gelden voor de hele pagina, tenzij ze later worden gewijzigd. Dit geldt bijvoorbeeld voor de lettersoort, de lettergrootte en de voorgrondkleur.
background: #ff9;
Voor kleinere browservensters is eerder een lichtgrijze achtergrondkleur opgegeven, omdat die achtergrondkleur achter de tekst staat. Maar de standaardachtergrondkleur van de voorbeelden op de site is eigenlijk beige. Hier wordt de kleur veranderd naar de standaardkleur. Dat kan hier, omdat er in deze grotere vensters geen tekst op deze achtergrond staat.
De voorgrondkleur, die ook de kleur van de tekst bepaalt, hoeft niet opnieuw opgegeven te worden. Normaal genomen is het goed altijd een voorgrondkleur op te geven, als je de achtergrondkleur verandert. Sommige gebruikers passen kleuren aan, omdat ze bijvoorbeeld meer contrast nodig hebben of kleurenblind zijn. Als je dan, zoals hier, de achtergrondkleur verandert in beige en de gebruiker heeft toevallig als voorgrondkleur ook beige of iets wat daarop lijkt, heb je onleesbare tekst.
In dit geval hoeft de voorgrondkleur niet opgegeven te worden, want dat is al eerder bij body gebeurd.
font-size: 110%;
Iets groter dan standaard. 't Zal de leeftijd zijn, maar ik vind de standaardgrootte wat te klein.
Als eenheid wordt de relatieve eenheid %
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
h1
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
h1 {background: #eee; color: black; max-width: 700px; overflow: auto; font-size: 1em; line-height: 30px; text-align: center; margin: 0 auto;}
Alle <h1>'s. Dat is er maar eentje: de belangrijkste kop op de pagina.
Op de site staat boven de pagina's met menu's een menubalk. Deze menubalk blijft altijd bovenaan het browservenster staan, ook bij scrollen. Die balk ontbreekt in dit voorbeeld. De <h1> vervult hier ongeveer de zelfde functie. Bij scrollen blijft de <h1> net als de menubalk bovenaan het venster staan, doordat de eronder zittende <main> absoluut is gepositioneerd.
width: calc(100% - 402px);
De <h1> wordt horizontaal gecentreerd en moet precies boven de <main> met de tekst komen te staan, zodat ze netjes op elkaar aansluiten. Voor dat horizontaal centreren moet de <h1> een breedte hebben. (Logisch: als iets geen breedte heeft, kun je het niet in het midden zetten.)
Links en rechts van de <main> met de tekst moet een ruimte van 201 px overblijven voor de thumbnails (inclusief wat marge en dergelijke). Daarom moet deze ruimte ook openblijven bij de <h1>, zodat deze niet breder wordt dan de <main>.
Om te beginnen wordt een breedte in procenten genomen: 100%. Een breedte in procenten is altijd ten opzichte van de ouder van het element. Dat is hier <body>, een blok-element. Een blok-element krijgt normaal genomen automatisch dezelfde breedte als z'n ouder. De ouder van <body> is <html>, ook een blok-element. Omdat er geen hoger element is, wordt <html> even breed als het venster van de browser. Daardoor worden ook <body> en de <h1> even breed als het venster.
width: calc(100%);
is weinig interessant, want dan kun je ook gewoon width: 100%;
gebruiken. Maar dan komt het handige van calc()
: je kunt er px van aftrekken. Het gebruik van procenten en pixels in dezelfde berekening is geen enkel probleem.
Om de lege ruimte links en rechts van elk 201 px te krijgen, wordt van die 100% (de breedte van het browservenster) 402 px afgetrokken. Dat kan met calc(100% – 402px)
. Ongeacht hoe breed het venster is. Bij een vensterbreedte van 1500 px is de <h1> 1500 – 402 = 1098 px breed, en bij een vensterbreedte van 1000 px is de <h1> 1000 – 402 = 598 px breed.
(UC browser op Android en sommige versies van Android browser kennen calc()
niet. In die browsers vult de achtergrondkleur van de <h1> de volle breedte van het browservenster tot een maximum van 870 px. Dat maximum komt door de gelijk hieronder opgegeven maximumbreedte voor de <h1>, die wel gewoon werkt in deze browsers.)
max-width: 870px;
Maximale breedte. Om te lange en daardoor slecht leesbare zinnen te voorkomen in brede browservensters, wordt de breedte van <main> beperkt. Dus moet ook de breedte van de <h1> worden beperkt, zodat deze niet breder wordt dan <main>.
height: 40px;
Hoogte.
overflow: auto;
Als de letters sterk vergroot worden, verdwijnt het onderste deel van de <h1> onder de <main>. Nu verschijnt een scrollbalk(je), zodat de <h1> in ieder geval is te lezen.
Normaal genomen zou je de hoogte van de <h1> gewoon laten groeien. Maar dat zou ook betekenen dat de plaatsing van tekst, thumbs, en dergelijke moet worden aangepast. Die plaatsing is al tamelijk ingewikkeld. Daarom is er in dit geval voor gekozen de <h1> als het ware in z'n eigen hok te houden, zodat de plaatsing van de rest van de pagina ook bij een grote letter niet wordt verstoord. Overigens wordt de <h1> pas slecht leesbaar bij een sterkere lettervergroting dan 170%.
line-height: 40px;
Tekst wordt automatisch halverwege de regelhoogte gezet. Door de regelhoogte even hoog te maken als de hoogte, staat de tekst niet zo dicht aan de bovenkant van het venster van de browser.
margin: 0 auto;
Omdat voor onder en links geen waarden zijn opgegeven, krijgen die automatisch dezelfde waarde als boven en rechts. Hier staat dus eigenlijk 0 auto 0 auto
in de volgorde boven – rechts – onder – links.
Boven en onder geen marge. Links en rechts auto
, wat hier hetzelfde betekent als evenveel. Oftewel: de <h1> staat altijd horizontaal gecentreerd, ongeacht de breedte van het venster van de browser.
Het op deze manier horizontaal uitlijnen van een blok-element kan alleen, als dat blok-element een breedte heeft.
De <main> wordt op een iets andere manier horizontaal gecentreerd, maar het resultaat is hetzelfde. Omdat de <h1> en de <main> beide horizontaal worden gecentreerd, sluiten ze altijd netjes op elkaar aan, ongeacht de breedte van het browservenster.
border: black solid;
Zwart randje, Hier gelijk onder wordt de breedte opgegeven.
border-width: 0 1px;
Kleur en stijl zijn gelijk hierboven opgegeven.
Omdat voor onder en links geen waarde is opgegeven, krijgen die automatisch dezelfde waarde als boven en rechts. Hier staat dus eigenlijk 0 1px 0 1px
in de volgorde boven – rechts – onder – links. Alleen links en rechts een border.
Door kleur en stijl apart van de breedte op te geven, spaar je een klein beetje css uit.
.blok
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
De elementen met class="blok". Dit zijn de <li>'s, waarbinnen de thumbnails, pop-ups, en dergelijke staan. Elk in een eigen <li>.
width: 180px;
Eerder is een breedte van 100% opgegeven. Hierdoor zouden de <li>'s de volle breedte van het browservenster beslaan. Dat is precies de bedoeling in smallere vensters, maar niet hier. 180 px is de breedte van de thumbnails, breder hoeven de <li>'s niet te zijn.
height: 161px;
Hoogte.
Strikt genomen is dit niet nodig, maar het wordt op de site gebruikt om kleine verschillen door borders en dergelijke op te heffen. Je zou het hier weg kunnen laten, maar dan moet je op 'n aantal plaatsen de positie 1 px veranderen. Wat weer 'n heel gepuzzel is, dus heb ik het gewoon zo van de site overgenomen.
border: none;
Eerder opgegeven border verwijderen.
padding: 0;
Eerder opgegeven padding verwijderen.
position: absolute;
Om de <li>'s en de daarin zittende thumbnails en dergelijke op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder, die zelf een positie heeft. Als er geen voorouder met een positie is, zoals hier het geval is, wordt gepositioneerd ten opzichte van het venster van de browser.
left: 9px;
9 px naar links neerzetten.
#blok-link-1, #blok-link-2
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
De elementen met id="blok-link-1" en id="blok-link-2". De <li>'s met de eerste en tweede knop.
top: 41px;
41 px naar beneden neerzetten. Op deze hoogte komt de bovenkant van een bij deze knoppen geopende pop-up precies tegen de bovenkant van het browservenster te staan.
#blok-link-3, #blok-link-4
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
De elementen met id="blok-link-3" en id="blok-link-4". De <li>'s met de derde en vierde knop.
top: 211px;
211 px naar beneden neerzetten, onder de bovenste twee knoppen. Op deze hoogte komt de bovenkant van een bij deze knoppen geopende pop precies gelijk te staan met de bovenkant van de bovenste twee knoppen.
#blok-link-5, #blok-link-6
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
De elementen met id="blok-link-5" en "id="blok-link-6". De <li>'s met de vijfde en zesde knop.
top: 382px;
382 px naar beneden neerzetten, onder de bovenste vier knoppen.
#blok-link-7, #blok-link-8
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
De elementen met id="blok-link-7" en id="blok-link-8". De <li>'s met de zevende en achtste knop.
top: 553px;
553 px naar beneden neerzetten. Op deze hoogte komt de onderkant van een bij deze knoppen geopende pop-up gelijk te staan met de onderkant van de knoppen zelf. (Hoewel je daarover van mening kunt verschillen, want is die onderkant de border van de thumbnail of de daar nog onder zittende schaduw?)
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-1, #blok-link-2 {top: 41px;}
#blok-link-3, #blok-link-4 {top: 211px;}
#blok-link-5, #blok-link-6 {top: 382px;}
##blok-link-7, #blok-link-8 {top: 553px;}
De elementen met id="blok-link-2", id="blok-link-4", id="blok-link-6" en id="blok-link-8". De <li>'s met de tweede, vierde, zesde en achtste knop. De <li>'s die rechts van de tekst staan.
left: auto; right: 11px;
Op 11 px vanaf de rechterkant neerzetten.
Eerder is left: 9px;
opgegeven. Als left
én right
zijn opgegeven, ontstaat een conflict, want er is eerder ook een breedte van 180 px opgegeven. Dat zou betekenen dat de arme <li> wreed in tweeën wordt gescheurd, of dat deze op middeleeuwse wijze op de pijnbank wordt uitgerekt.
Bij zulke onmogelijke waarden wordt right
genegeerd en left
toegepast. Om dat te voorkomen, wordt left
naar de standaardwaarde auto
teruggezet. Nu is alleen nog een breedte van 180 px en right: 11px;
aanwezig, en dat werkt prima.
De <li>'s en daarmee de thumbnails aan de linkerkant van de tekst worden op 9 px vanaf links neergezet. Hier worden de <li>'s rechts op 11 px vanaf rechts neergezet. Dat zijn 2 px verschil, maar juist hierdoor lijkt de afstand rechts en links voor het oog gelijk, terwijl deze bij gelijke waarden voor het oog juist verschillend lijkt. Ik neem aan dat dit komt door het gebruik van schaduw en dergelijke.
.focus-open
De elementen met class="focus-open". Dit zijn <span>'s speciaal voor gebruikers van de Tab-toets, zodat de pop-ups ook bij gebruik van de Tab-toets openen. Over de werking is meer te vinden bij Tabindex.
position: absolute;
Om de <span> op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat zijn hier de <li>'s, waar de <span> in staat.
left: -20000px;
Ver links buiten het scherm plaatsen. Hierdoor wordt de lay-out niet verstoord, terwijl het voor de Tab-toets niets uitmaakt dat de <span> buiten het scherm staat. Hiermee worden ook eventuele problemen op touchscreens voorkomen: wat je niet aan kunt raken, kan bij aanraking ook geen problemen veroorzaken. (Hmmm, ergens klinkt die laatste zin ietwat eigenaardig. Maar het klopt wel, ondanks de wat vreemde zinsbouw: probeer je touchscreen maar 'ns aan te raken, als je zeven meter links ervan staat. En niet valsspelen door 'n polsstok te gebruiken of zo, gewoon met je handen.)
img
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
img {box-shadow: 4px 6px 4px 1px black; width: 120px; max-width: 100%; height: auto; float: left; margin: 3px 10px 6px 3px; border: black solid 1px; border-radius: 5px;}
Alle afbeeldingen. Dat zijn hier de acht thumbnails.
box-shadow: none;
De eerder opgegeven schaduw verwijderen.
width: auto;
Eerder zijn de <img>'s versmald tot 120 px. Hier krijgen ze de echte grootte weer terug. (In de html staat bij <img> een breedte van 180 px. Eigenlijk heeft dat in dit geval niet zoveel nut, omdat een breedte in de css altijd 'wint' van een breedte in de html. Omdat de thumbnails 180 px breed zijn, krijgen ze hoe dan ook een breedte van 180 px. Waarom ik het dan toch laat staan? Omdat het in het algemeen een goede gewoonte is om wel een breedte en hoogte aan te geven bij een <img>.)
margin: 0;
Eerder opgegeven marge verwijderen.
.open
Alle elementen met class="open".
Binnen elke <li> staat een <input type="radio"> om de pop-up te kunnen openen. De <input>'s zelf zijn verborgen. Het openen gaat via de bij de <input> horende <label> Dit zijn die <label>'s. Binnen deze <label>'s zit de pop-up met bijbehorend vraagteken en sluitkruisje.
text-align: center;
Tekst horizontaal centreren.
Dit zorgt voor het horizontaal centreren van het vraagteken en van de tekst in de pop-up.
position: absolute;
Om de <label>, en dus alles daarin, op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier de <li>, waar de <label> in staat.
left: 1px;

Binnen de <li> zit een <img>: de thumbnail. Daarop volgt in de html een <input>, maar die is verborgen. En daarop volgt deze <label>, met daarin als eerste onderdeel een vraagteken. <img> en <label> zijn inline-elementen, dus worden ze achter elkaar op dezelfde regel gezet. Op de afbeelding is te zien dat het vraagteken hierdoor niet op, maar rechts van de thumb komt te staan. Met deze regel wordt het vraagteken links bovenop de thumb gezet.
(Terzijde: de pagina is nog niet bezocht, dus het vinkje naast het vraagteken hoort er niet te zijn. Op deze afbeelding is te zien dat dat vinkje er gewoon is. Het heeft echter vrijwel dezelfde kleur als de achtergrondkleur van het vraagteken, waardoor het vrijwel onzichtbaar is. Als de pagina is bezocht, wordt de kleur van het vinkje zwart en zie je het duidelijk op de witte achtergrond van het vraagteken.)
#blok-link-2 .open, #blok-link-4 .open, #blok-link-6 .open, #blok-link-8 .open
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.open {text-align: center; position: absolute; left: 1px;}
De elementen met class="open" die binnen een element met id="blok-link-2", id="blok-link-4", id="blok-link-6" of id="blok-link-8" staan.
De <id>'s horen bij de vier <li>'s die rechts van de tekst staan. Binnen elk <li> staat een <input type="radio"> om de pop-up te kunnen openen. De <input>'s zelf zijn verborgen. Het openen gaat via de bij de <input> horende <label> Dit zijn die <label>'s voor de vier <li>'s rechts van de tekst. Binnen deze <label>'s zit de pop-up met bijbehorend vraagteken en sluitkruisje.
left: auto; right: -1px;
Hier gelijk boven zijn de <label>'s gepositioneerd op left: 1px;
. Aan de rechterkant van de tekst moeten ze juist rechts op de thumbnail komen te staan. Daar zorgt right: -1px;
voor.
Je zou verwachten dat het right: 0;
zou moeten zijn, en dat verwachtte ik eigenlijk ook. Maar omdat er nogal veel borders, schaduwen en dergelijke aanwezig zijn, en door de plaatsing van de thumbnail binnen de <li>, blijkt dit net iets beter uit te komen. Ongetwijfeld kun je, na lang zoeken, alles zo aanpassen dat je hier '0' kunt gebruiken, maar erg zinvol lijkt me zo'n exercitie niet. Dus heb ik dat niet gedaan.
Eerder is voor alle <labels>'s met class="open" bij .open left: 1px;
opgegeven. Daardoor worden de <label>'s rechts even breed als de <li>: van left: 1px;
tot right: -1px;
. Dat zie je niet, omdat die <label>'s geen eigen achtergrondkleur of zoiets hebben. Maar het heeft wel tot gevolg dat het blokje met het vraagteken helemaal links komt te staan. Door left
op de standaardwaarde auto
terug te zetten, wordt dat voorkomen.
.vraagteken
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit{display: none;}
Alle elementen met class="vraagteken". Dit zijn de <span>', waarbinnen het vraagteken zit. Met onderstaande css wordt het vraagteken sterk vergroot en in een wit vierkantje gezet. Omdat deze <span>'s binnen een <label> zitten, selecteert aanraken van of klikken op het vraagteken de bij de <label> horende radioknop. Waardoor de bijbehorende pop-up wordt geopend.
background: rgba(255, 255, 255, 0.75);
Vaak wordt voor 'n kleur de hexadecimale notatie gebruikt, iets als color: #33ab01;
. Daarbij worden niet alleen cijfers, maar ook letters gebruikt. 0 tot en met 9 werken precies hetzelfde als altijd, maar na de 9 komen nog A, B, C, D, E en F.
Als je telt, is 't dus: 0 1 2 3 4 5 6 7 8 9 A B C D E F 10 11 12, enz. Daarbij is A gelijk aan het tientallige 10, B aan 11, enz. Op deze manier kun je met twee cijfers en/of letters 256 mogelijkheden aangeven: van 00 tot en met FF.
De eerste drie getallen bij rgba()
geven de kleur aan. Deze lopen van 0 tot en met 255, dus ook hiermee kun je 256 mogelijkheden aangeven. En omdat er drie getallen zijn levert dat 256 x 256 x 256 = 16.777.216 mogelijke kleuren op, net iets meer dan het aantal kleurpotloden in de gemiddelde kleurdoos van 'n kind.
De notatie bij rgba()
geeft dus precies evenveel mogelijkheden als de hexadecimale.
Het eerste getal staat voor rood, het tweede voor groen en het derde voor blauw (feitelijk de Engelse namen, maar de eerste letter is toevallig in het Nederlands hetzelfde). Uit deze drie kleuren zijn alle kleuren op een monitor opgebouwd.
255 wil zeggen volledig aanwezig, 0 wil zeggen helemaal ontbrekend.
255, 255, 255 levert wit op, 0, 0, 0 zwart.
In plaats van getallen mag je ook percentages gebruiken, bijvoorbeeld: rgba(10%, 20%, 100%, 0.3)
.
Omdat in dit voorbeeld drie keer 255 is opgegeven, levert dit een witte kleur op.
Het vierde getal staat voor het alfa-kanaal. Hiermee wordt de doorzichtigheid aangegeven. Dit getal loopt van 0 naar 1. Volledig doorzichtig is 0, volledig ondoorzichtig is 1.
Het getal voor het alfa-kanaal wordt als decimale breuk aangegeven, dus bijvoorbeeld 0.5 wil zeggen halfdoorzichtig. Let erop dat je 'n punt gebruikt, de Amerikaanse manier om breuken aan te geven. Als je 'n komma gebruikt, denkt de browser dat er twee verschillende getallen staan.
In dit voorbeeld is deze achtergrondkleur enigszins doorzichtig: 0.75. Hierdoor zie je de thumbs nog enigszins door de achtergrond heen, maar zijn de donkergrijze vraagtekens en, als de achterliggende pagina is bezocht, zwarte vinkjes toch goed zichtbaar, ook op donkere thumbs.
color: #666;
Voorgrondkleur, dat is onder andere de tekstkleur en daarmee de kleur van het vraagteken, donkergrijs.
display: block;
Eerder zijn deze <span>'s voor kleinere browservensters verborgen met display: none;
. Nu worden ze weer zichtbaar gemaakt.
Een <span> is een inline-element. Daardoor kun je eigenschappen als breedte en hoogte niet gebruiken. Maar door het zichtbaar te maken als blok-element, is dit soort eigenschappen toch te gebruiken.
width: 48px;
Breedte. De hoogte wordt iets hieronder bij line-height
geregeld.
font-size: 2.4em;
Vraagteken fors vergroten.
Als eenheid wordt de relatieve eenheid em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
line-height: 50px;
Regelhoogte. Tekst wordt automatisch halverwege de regelhoogte neergezet. De combinatie van hoogte, regelhoogte, padding, en dergelijke zet het vraagteken ongeveer halverwege de hoogte van het vierkantje neer.
Omdat geen aparte hoogte is opgegeven, is dit gelijk de hoogte van de <span>, en daarmee van het witte blokje. Daardoor staat het vraagteken verticaal in het midden.
De hoogte is iets meer dan de breedte, maar door de borders, schaduw, en dergelijke levert dit voor het oog toch een vierkantje op.
border-radius: 5px 0 5px;
Ronde hoeken.
Omdat voor linksonder geen waarde is opgegeven, krijgt linksonder automatisch dezelfde waarde als rechtsboven. Hier staat dus eigenlijk 5px 0 5px 0
in de volgorde linksboven – rechtsboven – rechtsonder – linksonder.
Linksboven en rechtsonder een kleine ronding. De ronding is even groot als de ronding die eerder bij img aan de thumbnail is gegeven, zodat het witte vierkantje daarop aansluit.
position: relative;
Hier iets onder wordt een z-index gebruikt om het vraagteken altijd zichtbaar te laten zijn. Waarom deze relatieve positie nodig is, staat hieronder bij z-index
.
top: 1px;
Hier gelijk boven is een relatieve positie aan de <span> gegeven. Hierdoor komt het witte blokje boven de border aan de bovenkant te staan. Door de <span> 1 px naar beneden te verplaatsen, wordt dit opgelost.
Het hele verhaal over hoe dit komt, staat gelijk hieronder bij z-index
.
z-index: 40;
Zorgen dat het blokje met het vraagteken gevoelig is voor aanraken, klikken en hoveren.
Als meerdere elementen op dezelfde plaats op het scherm worden gezet, zijn er heel strikte regels, welk element bovenaan komt te staan en dus zichtbaar is. Eén van die regels is dat elementen die zijn gepositioneerd, boven elementen komen te staan die niet zijn gepositioneerd.
Hieronder bij .blok a wordt van de link naar de achter de knop zittende pagina een rechthoek gemaakt, die even groot is als de thumbnail. Die rechthoek wordt over de thumbnail gezet, zodat de hele oppervlakte van de thumbnail als link werkt. Om dat te kunnen doen, wordt onder andere een relatieve positie aan die <a> gegeven.
De <span> met het vraagteken op het witte blokje heeft geen positie. Deze komt daardoor ónder de <a> te staan. Daar merk je niets van, want de <a> is doorzichtig: je ziet het witte blokje met het vraagteken gewoon, door de <a> heen. Alleen werken aanraken, klikken en hoveren niet meer, omdat het blokje is afgedekt door de <a>. En omdat die <a> een link is naar de achterliggende pagina, wordt die pagina ook geopend bij aanraken of aanklikken van het vraagteken.
Dat is niet de bedoeling.
Door nu aan deze <span> ook een positie te geven, wordt hij wat dit betreft gelijkwaardig aan de <a>. Helaas lost dat nog niets op, want de <a> staat ook lager in de html. Omdat de <span> en de <a> nu gelijkwaardig zijn, wordt die verrekte <a> nog steeds over het vraagteken heen gezet.
Daarom wordt een z-index van 40 aan de <span> gegeven. Omdat de <a> geen z-index heeft (althans: geen andere dan de standaardwaarde voor een gepositioneerd element), wint nu eindelijk de <span> met het vraagteken. De <a> wordt nu onder de <span> met het witte vierkantje gezet, waardoor de <span> nu gevoelig is voor aanraken, klikken en hoveren.
Een z-index werkt trouwens alleen maar in bepaalde omstandigheden. Eén van die omstandigheden is een relatieve positie. Omdat de <span> iets hierboven relatief is gepositioneerd, is dat al geregeld.
Maar nu is er weer 'n klein ander probleempje.
Omdat de <span> nu hoger staat, staat deze ook over de border aan de bovenkant heen. Dat is echter snel opgelost. De <span> is al relatief gepositioneerd, en door hem met top: 1px;
iets omlaag te zetten, wordt de border weer zichtbaar.
(Je kunt dit ook op andere manieren dan de hierboven staande oplossen, bijvoorbeeld door iets hierboven een z-index aan .open
te geven. Dat heeft weer iets andere bijwerkingen. Min of meer toevallig is voor deze oplossing gekozen. Maar er zijn ook andere oplossingen mogelijk.)
#blok-link-2 .vraagteken, #blok-link-4 .vraagteken, #blok-link-6 .vraagteken, #blok-link-8 .vraagteken
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.vraagteken {background: rgba(255, 255, 255, 0.75); color: #666; display: block; width: 48px; height: 40px; font-size: 2.4em; line-height: 29px; border-radius: 5px 0 5px; padding-top: 10px; position: relative; top: 1px; z-index: 40;}
De elementen met class="vraagteken" die binnen een element met id="blok-link-2", id="blok‑link-4", id="blok-link-6" of id="blok-link-8" zitten. Dit zijn de <span>'s met de witte blokjes en vraagtekens, die boven de thumbnails rechts van de tekst staan.
border-radius: 0 5px;
Eerder hebben deze <span>'s linksboven en rechtsonder ronde hoeken gekregen. Omdat deze blokjes niet in de linkerrij met thumbs staan, maar in de rechterrij, moeten die ronde hoekjes worden aangepast. Anders sluiten ze niet goed aan op de eerder bij img aan de thumbnails gegeven ronde hoeken.
Omdat voor rechts- en linksonder geen waarde is opgegeven, krijgen die automatisch dezelfde waarde als links‑ en rechtsboven. Hier staat dus eigenlijk 0 5px 0 5px
in de volgorde linksboven – rechtsboven – rechtsonder – linksonder.
Rechtsboven en linksonder ronde hoekjes, de andere twee hoekjes gewoon recht.
.pop-up
De elementen met class="pop-up". De <span>'s met de eigenlijke pop-up. De afbeelding in de pop-up is een achtergrond-afbeelding in deze <span>. Verder staat binnen deze <span> nog een <span> met de tekst die boven de afbeelding in de pop-up verschijnt.
background-position: 0 132px;
Positie van de achtergrond-afbeelding. Gewoon links in de <span> zetten, maar aan de bovenkant 132 px vrijlaten voor de tekst die boven de achtergrond-afbeelding komt te staan.
De css voor de acht achtergrond-afbeeldingen staat bij @media screen and (min-width: 763px) and (min-height: 543px). In dezelfde stylesheet als de rest van de css. Maar op de site, waar het om veel meer pagina's gaat, staat die css voor de achtergrond-afbeeldingen in de <head> van de betreffende pagina. Die css is voor elke pagina anders, dus het heeft geen nut die in een externe stylesheet te zetten.
Maar de regel hierboven kan op de site wel in een externe stylesheet, omdat de positie van de achtergrond-afbeelding overal hetzelfde is. Nu is één regel voldoende voor alle thumbnails op de site.
In dit voorbeeld, waar het maar om één pagina gaat, had deze regel dus net zo goed verderop bij de css voor de achtergrond-afbeeldingen gekund.
height: 464px;
Hoogte van de <span>. De achtergrond-afbeeldingen zijn 332 px hoog, dus boven de afbeelding is 132 px ruimte voor tekst.
Een achtergrond-afbeelding heeft van zichzelf geen grootte. Hij vult alleen de achtergrond van het element, waar hij in wordt gezet. Daarom moet dit element, hier de <span>, een hoogte en breedte krijgen.
De hoogte is hier geregeld, de breedte wordt bij .pop-up-tekst geregeld. In span.pop-up-tekst
staat de tekst, die boven de afbeelding in de pop-up komt te staan. Die <span> krijgt een breedte van 540 px. Samen met wat padding levert dit de breedte van de achtergrond-afbeeldingen op. En omdat .pop-up-tekst
binnen span.pop-up
staat, krijgt .pop-up
dezelfde breedte.
(Feitelijk is die breedte 4 px minder dan de breedte van de achtergrond-afbeelding. Bij zoomen kan anders een foeilelijk kiertje rechts van de afbeelding verschijnen.)
margin-left: -20000px;
De <span>, en daarmee de pop-up, moet alleen worden getoond, als het vraagteken wordt aangeraakt of ‑geklikt, als daarover wordt gehoverd of als de Tab-toets focus geeft aan span.focus-open
. Normaal genomen zou je de <span> verbergen met iets als display: none;
. Dat kan hier echter niet, omdat er tekst in de <span> staat. Schermlezers negeren elementen die zijn verborgen met display: none;
, dus schermlezers zouden de tekst boven de afbeelding in de pop-up dan niet voorlezen.
Daarom wordt de <span> niet verborgen, maar links buiten het scherm geparkeerd. Als de pop-up getoond moet worden, hoeft de <span> dan alleen maar binnen het venster van de browser te worden gezet.
Meestal gebruik je left: -20000px;
om iets buiten het scherm te plaatsen. Hier gebruik ik liever een negatieve marge. Dat werkt ook prima en voorkomt ernstige overspannenheid. Ik werd namelijk een beetje gek van alle verschillende waarden bij left
bij verschillende pop-ups in vensters van verschillende groottes. Door geen left
, maar margin-left
te gebruiken ben ik in ieder geval één van die ellendepukkels, pardon left
's kwijt.
Het zichtbaar maken wordt nu volledig door de marge geregeld, de precieze plaats volledig door left
.
border: #fc3 ridge 13px;
Randje rondom de <span>.
position: absolute;
Om de <span> en dus de pop-up op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier label.open
.
Een <span> is een inline-element. Daardoor kunnen eigenschappen als hoogte niet worden gebruikt. Door de <span> absoluut te positioneren verandert hij in een soort blok-element, waardoor dit soort eigenschappen wel gebruikt kunnen worden.
top: -40px;
Door de <span>'s met de pop-ups 40 px naar boven te zetten, staat de bovenkant van de pop-ups precies tegen de bovenkant van het browservenster. Voor de pop-ups die bij de knoppen in de tweede, derde en vierde regel horen, wordt iets hieronder top
aangepast.
left: 181px;
De linkerkant van de pop-ups precies tegen de rechterkant van de thumbnails zetten. Voor de pop-ups bij de knoppen rechts van de tekst, wordt dit iets hieronder aangepast.
z-index: 60;
De <main> met de tekst komt in de html na de header met de knoppen, pop-ups, enz. Hierdoor komen de pop-ups onder de tekst te staan, waardoor je vrijwel alleen nog (delen van) de border ziet. Nou is die border ongelooflijk artistiek verantwoord en zo, maar het zou toch aardig zijn, als ook de tekst en de afbeelding in de pop-up zichtbaar waren.
Door de z-index te verhogen, komen de pop-ups boven de <main> met de tekst te staan, ook al staat deze lager in de html.
Een z-index werkt alleen in sommige omstandigheden. Eén van die omstandigheden is een absolute positie. Die heeft de <span> iets hierboven gekregen, dus dat is geregeld.
Er zijn meerdere z-indexen voor verschillende elementen: 40, 50 en 60. Deze sluiten niet op elkaar aan. Hierdoor kun je later makkelijk elementen met een z-index toevoegen, zonder dat je bestaande z-indexen moet gaan veranderen.
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
De elementen met class="pop-up" binnen een element met id="blok-link-2", id="blok-link-4", id="blok-link-6" of id="blok-link-8". Dit zijn de <span>'s die voor de pop-ups bij de knoppen rechts van de tekst zorgen.
left: -705px;
Eerder is voor al deze <span>'s left: 181px;
opgegeven. Dat is goed voor de pop-ups bij de knoppen links van de tekst, maar niet voor de pop-ups rechts.
705 px terug naar links verplaatsen. Op deze positie staat de rechterkant van de pop-up precies tegen de linkerkant van de thumbnails rechts van de tekst.
Er wordt gepositioneerd ten opzichte van label.open
, vandaar deze forse verplaatsing terug naar links.
#blok-link-3 .pop-up, #blok-link-4 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up{left: -705px;}
De elementen met class="pop-up" binnen een element met id="blok-link-3" of id="blok-link-4". Dit zijn de <span>'s die voor de pop-ups bij de tweede rij knoppen zorgen.
top: -170px;
Eerder zijn alle <span>'s met pop-ups met top: -40px;
op een bepaalde hoogte gezet. Die hoogte is goed voor de pop-ups bij de eerste regel met thumbs, maar niet voor de andere drie regels.
De pop-ups die bij de tweede rij thumbnails horen, worden hier 170 px naar boven neergezet. Hiermee staat de bovenkant van de pop-up precies gelijk met de bovenkant van de bovenste thumbnails.
#blok-link-5 .pop-up, #blok-link-6 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up{left: -705px;}
De elementen met class="pop-up" binnen een element met id="blok-link-5" of id="blok-link-6". Dit zijn de <span>'s die voor de pop-ups bij de derde rij knoppen zorgen.
top: -255px;
Eerder zijn alle <span>'s met pop-ups met top: -40px;
op een bepaalde hoogte gezet. Die hoogte is goed voor de pop-ups bij de eerste regel met thumbs, maar niet voor de andere drie regels.
De pop-ups die bij de derde rij thumbnails horen, worden hier 255 px naar boven verplaatst, waarmee ze ongeveer in het midden van de knoppen komen te staan.
#blok-link-7 .pop-up, #blok-link-8 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up{left: -705px;}
De elementen met class="pop-up" binnen een element met id="blok-link-7" of id="blok-link-8". Dit zijn de <span>'s die voor de pop-ups bij de vierde rij knoppen zorgen.
top: -326px;
Eerder zijn alle <span>'s met pop-ups met top: -40px;
op een bepaalde hoogte gezet. Die hoogte is goed voor de pop-ups bij de eerste regel met thumbs, maar niet voor de andere drie regels.
De pop-ups die bij de vierde rij thumbnails horen, worden hier 326 px naar boven verplaatst. Hiermee staat de onderkant van de pop-ups precies gelijk met de onderkant van de onderste thumbnails.
.pop-up-tekst
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up-tekst {-moz-hyphens: auto; -ms-hyphens: auto; -webkit-hyphens: auto; hyphens: auto;}
De elementen met class="pop-up-tekst". Dit zijn de <span>'s, waarbinnen de tekst boven de afbeelding in de pop-up staat.
background: white;
Witte achtergrond.
color: black;
Voorgrondkleur zwart. Dit is onder andere de kleur van de tekst.
Hoewel dit de standaardkleur is, wordt deze toch specifiek opgegeven. Hierboven is een achtergrondkleur opgegeven. Sommige mensen hebben zelf de voorgrond- en/of achtergrondkleur veranderd, bijvoorbeeld omdat ze slecht kleuren kunnen onderscheiden. Als nu de achtergrondkleur wordt veranderd, maar niet de voorgrondkleur, loop je het risico dat tekstkleur en achtergrondkleur te veel op elkaar gaan lijken.
Door beide op te geven, is redelijk zeker dat achtergrond- en tekstkleur genoeg van elkaar blijven verschillen. Als de gebruiker !important
heeft gebruikt in een eigen stylesheet, is er nog niets aan de hand, want dan veranderen achtergrond- en voorgrondkleur geen van beide.
Dit is ook al bij <body> opgegeven, maar sommige mensen hebben bij álle elementen de kleuren veranderd. Het heeft immers weinig zin, als ze dat alleen bij de body doen, terwijl de sitebouwer de kleuren ook bij bijvoorbeeld de paragrafen heeft aangepast.
display: block;
Een <span> is een inline-element. Hierdoor zijn eigenschappen als breedte en hoogte niet te gebruiken. Door er een blok-element van te maken, kan dit soort eigenschappen wel worden gebruikt.
width: 540px;
Breedte. Deze <span>'s staan binnen span.pop-up
, de <span> waar de hele pop-up in zit. Aan die <span> is geen breedte gegeven. Daardoor bepaalt deze breedte ook de breedte van span.pop-up
.
height: 125px;
Met deze hoogte wordt precies het lege deel boven de achtergrond-afbeelding gevuld. Dat lege deel is ontstaan, doordat bij .pop-up background-position: 0 132px;
is opgegeven. Dat de getallen wat verschillen (125 px en 132 px) komt door allerlei dingen als borders en zo.
overflow: auto;
Als er veel tekst in de <span> staat, past deze niet boven de afbeelding in de pop-up. In dat geval verschijnt een verticale scrollbalk. Bij de zesde pop-up is dit het geval. Maar dat is eigenlijk vooral gedaan om te laten zien dat dit niet echt heel handig is.
Gebruikers van de muis moeten eerst klikken op het vraagteken, zodat de pop-up open blijft. Pas daarna kunnen ze de tekst scrollen. Voor gebruikers van de Tab-toets is er geen enkele mogelijkheid om de tekst te scrollen: die moeten eerst in de tekst klikken, voordat pijltjes of scrollwieltje werken. En als je de Tab-toets gebruikt, omdat je geen muis kunt bedienen, lukt dat dus niet.
Het is dus beter om niet meer tekst boven de afbeelding te zetten, dan dat er zonder scrollen in kan.
(Bij een grotere lettergrootte bestaat het probleem dan trouwens nog steeds. Als iemand slecht ziet en de tekst daarom heeft vergroot én de muis niet kan gebruiken, is dit onoplosbaar. Maar bij gewoon inzoomen (vergroten) speelt dit probleem niet, dus dit zal niet vaak voorkomen.)
font-size: 0.8em;
Iets kleinere letter, zodat er iets meer tekst boven de afbeelding past.
Als eenheid wordt de relatieve eenheid em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
-moz-hyphens: manual; -ms-hyphens: manual; -webkit-hyphens: manual; hyphens: manual;
Hier staat in feite vier keer hetzelfde: hyphens: manual;
. Waarom dat zo is, staat bij De voorvoegsels -moz-, -ms- en -webkit-.
Omdat er in smalle browservensters weinig ruimte is rechts van de thumbnails, is eerder automatisch afbreken aangezet. In bredere vensters ziet dat er niet mooi uit, daarom wordt het weer teruggezet naar de standaardwaarde.
(Die standaardwaarde is niet none
, zoals je makkelijk kunt denken. Bij none
wordt helemaal niet afgebroken, ook niet als bijvoorbeeld ­
in een woord is gebruikt. De standaardwaarde is manual
: nu wordt niet afgebroken, behalve als in een woord iets als ­
staat.
border-bottom: black solid 1px;
Randje aan de onderkant.
padding: 3px;
Kleine afstand tussen tekst in en buitenkant van de <span>.
.blok a
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
a {width: 120px; height: 108px; position: absolute; top: 8px; left: 8px;}
De <a>'s binnen de elementen met class="blok". De links naar de achter de knoppen zittende pagina's. Binnen elke li.blok
zit zo'n link.
-webkit-animation: bugfix infinite 1s;
In oudere versies van Android browser zit een bug, waardoor de het sluitkruisje soms niet wordt getoond. Met behulp van deze regel wordt het sluitkruisje toch getoond. Meer hierover bij @-webkit-keyframes bugfix.
box-shadow: black 4px 3px 4px 1px;
Rechts en onder wat schaduw aan de <a> geven. Omdat de <a> even groot is als de thumbnail, lijkt de schaduw rondom de thumbnail te staan.
Een uitgebreide uitleg over box-shadow
is te vinden bij box-shadow: 4px 6px 4px 1px black;. Alleen zijn de waarden hier anders: 4 px naar rechts, 3 px omlaag, over 4 px vervagen en 1 px breed. Verder moet hier een kleur worden opgegeven, anders krijgt de schaduw de standaardkleur van een <a>.
display: block;
Een <a> is een inline-element. Daardoor kunnen eigenschappen als breedte en hoogte niet worden gebruikt. Door er een blok-element van te maken, kan dit soort eigenschappen wel worden gebruikt.
width: 180px; height: 161px;
Breedte en hoogte. Dit is precies even groot als de thumbnails. Door de <a> bovenop de thumbnails te zetten, gaat de hele thumbnail als link werken. (In werkelijkheid is het natuurlijk niet de thumbnail die als link werkt, maar de <a>. Maar het lijkt wel zo, en daar gaat het om.)
text-align: center;
In de <a> zit een <span> met de korte naam van de achterliggende pagina. Deze wordt op verschillende momenten op verschillende plaatsen getoond. Hier wordt deze naam horizontaal gecentreerd.
margin: 0 auto;
Omdat voor onder en links geen waarde is ingevuld, krijgen die automatisch dezelfde waarde als boven en rechts. Hier staat dus eigenlijk 0 auto 0 auto
in de volgorde boven – rechts – onder – links. Boven en onder geen marge. Links en rechts auto
, wat hier hetzelfde betekent als evenveel. De <a>'s staan nu altijd in horizontaal gecentreerd in hun ouder, de <li> met de thumb, pop-up, enz.
Deze manier van horizontaal centreren van een blok-element kan alleen, als het te centreren element een breedte heeft.
border: black solid 1px;
Zwart randje.
border-radius: 5px;
Ronde hoeken.
position: relative;
Eerder zijn alle <a>'s absoluut gepositioneerd. Dat is hier niet meer nodig. In het algemeen is het beter een absolute positie te vermijden, als die niet nodig is, omdat het allerlei ongewenste bijwerkingen kan hebben.
Maar binnen de <a> staat een <span> met de korte naam van de pagina. En die moet gepositioneerd worden ten opzichte van de <a>. Dat kan alleen als de <a> zelf een positie heeft. Daarom wordt de absolute positie hier vervangen door een relatieve.
(Feitelijk moet de <span> met de naam worden gepositioneerd ten opzichte van de thumbnail, maar omdat de <a> precies over de thumbnail heen staat, is het eindresultaat hetzelfde: de naam lijkt gepositioneerd ten opzichte van de thumb.)
top: 0; left: 0;
Eerder is voor beide een waarde van 8 px opgegeven. Om te voorkomen dat de <a>'s 8 px naar beneden en naar rechts worden verplaatst, wordt dat hier weer ongedaan gemaakt.
#blok-link-2 a, #blok-link-4 a, #blok-link-6 a, #blok-link-8 a
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
a {width: 120px; height: 108px; position: absolute; top: 8px; left: 8px;}
.blok a {-webkit-animation: bugfix infinite 1s; box-shadow: 4px 3px 4px 1px black; display: block; width: 180px; height: 161px; text-align: center; margin: 0 auto; border: black solid 1px; border-radius: 5px; position: relative; top: 0; left: 0;}
De <a>'s binnen de elementen met id="blok-link-2", id="blok-link-4", id="blok-link-6" of id="blok-link-8". Dit zijn de <a>'s die bij de thumbnails rechts van de tekst horen.
box-shadow: black -4px 3px 4px 1px;
Eerder is rechts en onder wat schaduw aan de <a> gegeven. Omdat de <a> even groot is als de thumbnail, lijkt de schaduw rondom de thumbnail te staan. Hier wordt de schaduw voor de <a>'s links van de tekst van rechts naar links verplaatst.
Een uitgebreide uitleg over box-shadow
is te vinden bij box-shadow: 4px 6px 4px 1px black;. Alleen zijn de waarden hier anders: 4 px naar links (vanwege de negatieve waarde), 3 px omlaag, over 4 px vervagen en 1 px breed. Verder moet hier een kleur worden opgegeven, anders krijgt de schaduw de standaardkleur van een <a>.
.naam
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
Alle elementen met class="naam". Binnen elke <a> zit een <span>, waarbinnen de korte naam van de achterliggende pagina zit.
color: transparent; opacity: 1;
Deze twee eigenschappen hebben in dit geval met elkaar te maken, dus is het makkelijker om ze samen te beschrijven.
Eerder is de <span> met de naam met opacity: 0;
doorzichtig gemaakt. (display: none;
of visibility: hidden;
waren onbruikbaar, omdat schermlezers dan de naam volledig zouden negeren.)
In bredere browservensters moet de naam op verschillende momenten in verschillende kleuren worden getoond. Daarom wordt de naam hier weer zichtbaar gemaakt met opacity: 1;
. En vervolgens weer onzichtbaar gemaakt met
color: transparent;
.
Het voordeel van deze ogenschijnlijk zinloze werkverschaffing: nu hoeft, als de naam zichtbaar moet worden gemaakt, alleen de kleur te worden veranderd. En niet de kleur én de doorzichtigheid.
display: block;
Van zichzelf is een <span> een inline-element. Daardoor kunnen eigenschappen als breedte en hoogte niet worden gebruikt. Door er een blok-element van te maken, kan dit soort eigenschappen toch worden gebruikt.
width: 180px;
Breedte. Dit is dezelfde breedte als die van de thumbnails, waar de naam soms boven wordt gezet. Op sommige plaatsen is een andere breedte nodig. Voor die plaatsen wordt de breedte later aangepast.
height: 39px;
Hoogte.
font-size: 25px;
Tamelijk grote letter.
Meestal wordt als eenheid voor lettergrootte een relatieve eenheid als em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. (Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.)
Hier is het een voordeel, als een browser dat niet kan. Dat voorkomt namelijk dat de naam te groot wordt. Dat is verder geen ernstig probleem, maar in sommige browsers wordt dat nu dus voorkomen.
line-height: 34px;
Regelhoogte. Tekst wordt normaal genomen automatisch halverwege de regelhoogte neergezet.
Iets hierboven is een hoogte van 39 px opgegeven. Dan zou je verwachten dat ook de regelhoogte 39 px is, zodat de tekst halverwege de hoogte komt te staan. In dit geval is het mooier de tekst iets hoger neer te zetten, omdat de tekst is onderstreept. Voor het oog staat de tekst nu verticaal gecentreerd, terwijl die bij een regelhoogte van 39 px voor het oog iets te laag staat.
text-decoration: underline;
Onderstrepen.
margin-top: 50px;
50 px marge aan de bovenkant.
Bij gebruik van de Tab-toets wordt bij de eerste tab de pop-up geopend. Bij een tweede tab wordt de naam van de achterliggende pagina op de thumbnail gezet (en nog wat dingen, die hier verder niet van belang zijn). Met deze marge staat de naam ongeveer halverwege de thumbnail. Bij hoveren en dergelijke verschijnt de naam ook. Daarvoor wordt later de marge aan de bovenkant aangepast.
Je zou dit mogelijk ook met top
kunnen doen, maar dit is min of meer toevallig zo gegroeid. Als dit veranderd zou worden, vereist dat weer het nodige testwerk, dus laat ik het zo.
position: absolute;
Met behulp van ::after
wordt bij span.naam
hier gelijk onder een pseudo-element gemaakt. Binnen dit pseudo-element staat het vinkje dat aangeeft dat de pagina al is bezocht.
Dit pseudo-element wordt absoluut gepositioneerd ten opzichte van span.naam
. Dat kan alleen, als span.naam
zelf een positie heeft, wat hier wordt geregeld. Later wordt span.naam
zelf ook nog verplaatst met behulp van top
en dergelijke, en dat is hier gelijk ook mogelijk gemaakt.
z-index: 50;
Het vinkje, waar gelijk hierboven bij position
over wordt geschreven, verdwijnt onder de witte achtergrond van span.vraagteken
. Om dat te voorkomen, krijgt deze <span> een hogere z-index.
Een z-index werkt alleen in sommige omstandigheden. Eén van die omstandigheden is een absolute positie. Die heeft de <span> iets hierboven gekregen, dus dat is ook geregeld.
Er zijn meerdere z-indexen voor verschillende elementen: 40, 50 en 60. Deze sluiten niet op elkaar aan. Hierdoor kun je later makkelijk elementen met een z-index toevoegen, zonder dat je bestaande z-indexen moet gaan veranderen.
.naam::after

Binnen elke <a> zit een span met class="naam". Hierbinnen zit de korte naam van de achterliggende pagina. Met behulp van ::after
worden bij deze <span>'s pseudo-elementen gemaakt. Deze zorgen voor het verschijnen van de vinkjes naast het vraagteken, als een pagina is bezocht.
Hiernaast staat een sterk vergroot 'vinkje'. De zwarte lijnen vormen het vinkje. In werkelijkheid zijn dit twee borders bij een rechthoek. De achtergrond van het pseudo-element is even rood gemaakt, zodat duidelijker te zien is dat het vinkje echt uit borders bestaat. Die hieronder redelijk ernstig worden mishandeld om ze in de juiste rondingen en zo te meppen.
content: "";
Hoewel er geen tekst of zoiets in het pseudo-element staat, is dit toch nodig. Dat er geen tekst in staat, geef je aan door niets tussen de aanhalingstekens te zetten.
color: #ddd;
Voorgrondkleur. Bij gebrek aan tekst wordt deze kleur hier alleen voor de borders gebruikt.
De vinkjes worden bovenop het witte vierkantje met het vraagteken gezet. Met deze kleur zijn ze vrijwel onzichtbaar. Als de pagina is bezocht, hoeft de kleur alleen maar te worden veranderd naar zwart om de vinkjes zichtbaar te maken.
De witte achtergrond achter het vraagteken is enigszins doorzichtig. Daarom wordt hier geen white
gebruikt als kleur, maar heel lichtgrijs. Dit maakt de meeste vinkjes (vrijwel) onzichtbaar ten opzichte van de achtergrond. De vinkjes bij de vierde en achtste thumbnail moeten een iets andere kleur krijgen om (vrijwel) volledig onzichtbaar te zijn. Dat gebeurt iets hieronder.
width: 6px; height: 12px;

Breedte en hoogte van het pseudo-element. Op de afbeelding is de achtergrond even rood gemaakt, zodat het pseudo-element is te zien. In het uiteindelijke vinkje is de achtergrond weggelaten. Waar het om gaat: het vinkje begint dus echt als een simpele rechthoek.
border: solid;
Stijl van de border. De breedte wordt gelijk hieronder opgegeven.
border-width: 0 2px 2px 0;

Dit levert rechts en onderaan een gewone border van 2 px breedte op. Op de afbeelding is de achtergrond weer weggelaten, zodat alleen twee rechte lijntjes overblijven.
border-top-right-radius: 3px; border-bottom-left-radius: 5px;

Ronde hoeken rechtsboven en linksonder. Dit laat het uiteindelijke vinkje iets meer op en vinkje lijken. Het laatste stukje wordt iets hieronder bij transform
vormgegeven. (Dat komt hier wat onhandig uit, maar ik hanteer een strikte volgorde van eigenschappen binnen de css. En transform
komt in die volgorde een eind onder border-radius
.)
pointer-events: none;
Over de volledige thumbnail staat de <a> met de link naar de achterliggende pagina. Daar weer overheen wordt linksboven met behulp van label.open
en span.vraagteken
een wit vierkantje met vraagteken neergezet. Als je dit vlakje aanraakt of aanklikt, moet de pop-up openen. De link in de <a> werkt niet, omdat deze wordt afgedekt door de <label> met het witte vlakje en het vraagteken.
Naast het vraagteken in het witte vlakje wordt dit pseudo-element met het vinkje gezet. Deze staat bovenop het witte vlakje. Maar dit pseudo-element hoort bij span.naam
, en die <span> zit in de <a>, is onderdeel van de link. Als je het vinkje aanraakt of aanklikt, wordt hierdoor niet de pop-up geopend, maar wordt de link gevolgd.
Bij hoveren met de muis valt dat nog mee, omdat het vinkje verdwijnt als je over het witte vierkantje hovert. En je moet over het witte vierkantje heen, voordat je het vinkje bereikt. Maar als je heel snel en heel precies bent, kan het zelfs met de muis: het vinkje blijft staan en werkt als link.
Op een touchscreen is het vervelender, want daar werkt hoveren niet. Als je het vinkje aanraakt, wordt de link gevolgd.
Deze regel schakelt hoveren, aanraken, klikken en dergelijke uit voor dit pseudo-element. Als je het vinkje aanraakt, wordt die aanraking doorgegeven aan het element onder het pseudo-element met het vinkje. En dat is precies de bedoeling, want dat is label.open
, die zorgt voor het openen van de pop-up.
position: absolute;
Om het vinkje op de juiste plaats neer te kunnen zetten.
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier span.naam
, de <span> waar dit pseudo-element bij hoort.
Een met behulp van ::after
gemaakt pseudo-element is van zichzelf een inline-element. Daardoor zijn eigenschappen als breedte en hoogte niet te gebruiken. Door het absoluut te positioneren verandert het in een soort blok-element, waardoor dit soort eigenschappen wel is te gebruiken.
top: -50px;
Dit pseudo-element hoort bij span.naam
. Bij .naam is die <span> met margin-top: -50px;
50 px omlaag gezet. Waardoor dit pseudo-element met vinkje 50 px te laag komt te staan. Hier wordt het vinkje weer 50 px terug naar boven gezet, waardoor het naast het vraagteken komt te staan.
left: 5px;
Op deze afstand vanaf links staat het vinkje op de goede plaats in de knoppen op de linkerhelft. Bij de knoppen in de rechterhelft moet het vinkje aan de andere kant van het vraagteken komen. Dat wordt iets verderop geregeld.
-ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);
Hier staat in feite vier keer hetzelfde: transform: rotate(45deg) skew(14deg);
. Waarom dat zo is, staat bij De voorvoegsels -moz-, -ms- en -webkit-.

Dit is de laatste stap in de vorming van het vinkje. De eerste stap staat iets omhoog bij width
. (Dat komt hier wat onhandig uit, maar ik hanteer een strikte volgorde van eigenschappen binnen de css. En transform
komt in die volgorde een eind onder border-radius
.)
Met transform
kun je verschillende bewerkingen op een element uitvoeren. In dit geval gaat het om rotate
(draaien) en skew
(vervormen). Als je bij transform
meerdere bewerkingen wilt uitvoeren, zoals hier het geval is, zet je die gewoon achter elkaar.
Met deze combinatie van 45 graden draaien en 14 graden vervormen, lijkt het eindresultaat redelijk op een vinkje. Niet als je het zo sterk vergroot als op de afbeelding hier, maar wel als je het in gewoon formaat ziet.
#blok-link-4 .naam::after, #blok-link-8 .naam::after
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
Binnen elke <a> zit een span met class="naam". Hierbinnen zit de korte naam van de achterliggende pagina. Met behulp van ::after
worden bij deze <span>'s pseudo-elementen gemaakt. Deze zorgen voor het verschijnen van de vinkjes naast het vraagteken, als een pagina is bezocht. Deze selector is alleen bedoeld voor de pseudo-elementen die in de elementen met id="blok-link-4" en id="blok-link-8" zitten. De vinkjes bij de vierde en achtste knop.
color: #ccc;
Iets hierboven is als kleur #ddd
opgegeven voor de vinkjes. De vinkjes staan op een iets doorzichtige witte achtergrond en zijn hierdoor vrijwel onzichtbaar. (Ze worden pas zichtbaar, als de bij de knop horende pagina is bezocht.)
Omdat de witte achtergrond iets doorzichtig is, is het wit niet overal precies hetzelfde. Voor de vierde en achtste knop is deze kleur beter om het vinkje onzichtbaar te maken.
#blok-link-2 .naam::after, #blok-link-4 .naam::after, #blok-link-6 .naam::after, #blok-link-8 .naam::after
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
#blok-link-4 .naam::after, #blok-link-8 .naam::after {color: #ccc;}
Binnen elke <a> zit een span met class="naam". Hierbinnen zit de korte naam van de achterliggende pagina. Met behulp van ::after
worden bij deze <span>'s pseudo-elementen gemaakt. Deze zorgen voor het verschijnen van de vinkjes naast het vraagteken, als een pagina is bezocht. Deze selector is alleen bedoeld voor de pseudo-elementen die in de elementen met id="blok-link-2", id="blok-link-4", id="blok-link-6" en id="blok-link-8" zitten. De vinkjes bij de knoppen rechts van de tekst.
left: auto; right: 3px;
Op 3 px vanaf de rechterkant neerzetten.
Eerder is left: 5px;
opgegeven. Als left
én right
zijn opgegeven, ontstaat een conflict, want er is eerder ook een breedte van 6 px opgegeven. Aan deze drie voorwaarden kan onmogelijk gelijktijdig worden voldaan.
Bij deze onmogelijke waarden wordt right
genegeerd. Om dat te voorkomen, wordt left
naar de standaardwaarde auto
teruggezet. Nu is alleen nog een breedte van 6 px en right: 3px;
aanwezig, en dat werkt prima.
De vinkjes op de knoppen rechts van de tekst worden hiermee rechts van het vraagteken geplaatst.
.blok a:visited .naam::after, #blok-link-4 a:visited .naam::after, #blok-link-8 a:visited .naam::after
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
#blok-link-4 .naam::after, #blok-link-8 .naam::after {color: #ccc;}
#blok-link-2 .naam::after, #blok-link-4 .naam::after, #blok-link-6 .naam::after, #blok-link-8 .naam::after { left: auto; right: 3px;}
Dit zijn drie selectors, gescheiden door een komma. Het ziet er mogelijk wat ingewikkeld uit, maar in feite zijn de drie selectors vrijwel hetzelfde.
De eerste selector: .blok a:visited .naam::after
.blok
: de elementen met class="blok". Dit zijn de <li>'s, waarbinnen de acht knoppen en dergelijke staan.
a
: de binnen deze <li>'s zittende links naar de achterliggende pagina's.
:visited
: als deze links zijn bezocht.
.naam
: de binnen de <a> zittende <span> met de korte naam van de achterliggende pagina.
::after
: het met behulp van ::after
gemaakte pseudo-element bij .naam
. In dit pseudo-element zit het vinkje naast het vraagteken, dat zichtbaar wordt als de bijbehorende pagina is bezocht.
Alles bij elkaar: doe iets met het met behulp van ::after bij .naam gemaakte pseudo-element (het vinkje) dat binnen een bezochte link in een <li> zit. Oftewel: doe iets met het vinkje, als de bijbehorende pagina is bezocht.
De tweede selector: #blok-link-4 a:visited .naam::after
Deze heeft exact dezelfde werking als de eerste selector gelijk hierboven. Alleen wordt in plaats van het algemene .blok
(de class die elke <li> heeft), het meer specifieke #blok-link-4
gebruikt: de id die specifiek bij de vierde <li> hoort.
In deze regel wordt de kleur van het vinkje veranderd in zwart, zodat het vinkje zichtbaar wordt, als de bijbehorende pagina is bezocht. Die kleur is eerder bij .naam::after voor alle pseudo-elementen met de vinkjes veranderd in #ddd
. Voor het vierde en achtste vinkje was dit echter niet de beste kleur. Daarom is voor die twee vinkjes bij #blok-link-4 .naam::after, #blok-link-8 .naam::after de kleur veranderd in #ccc
.
Voor het vierde vinkje is de kleur dus met de selector #blok-link-4 .naam::after
veranderd in #ccc
. In die selector zit, behalve .naam::after
, ook de id #blok-link-4
. Daarom is het onmogelijk om die kleur weer te veranderen met alleen .blok a.visited .naam::after
, want een id als #blok-link-4
heeft meer gewicht, meer specifiteit, dan de veel minder specifieke class .blok
.
Normaal genomen 'wint' de laatste selector in de css, maar dat geldt alleen als de selectors dezelfde specificiteit hebben. En dat is hier niet het geval: .blok a:visited .naam::after
heeft minder specificiteit dan #blok-link-4 .naam::after
. Daar verandert de volgorde in de css niets aan.
Omdat .blok a:visited .naam::after
dus onvoldoende specificiteit heeft om de kleur van het vierde vinkje te veranderen, wordt voor dit vierde vinkje de selector #blok-link-4 a:visited .naam::after
toegevoegd. Deze heeft dezelfde specificiteit als de eerder gebruikte selector #blok-link-4 .naam::after
. (Feitelijk zelfs iets meer, omdat er ook nog a:visited
in staat.) En nu werkt de selector wel voor het vierde vinkje, omdat hij later in de css staat én iets meer specificiteit heeft.
De derde selector: #blok-link-8 a:visited .naam::after
.
Hiervoor geldt precies hetzelfde als voor #blok-link-4 a:visited .naam::after
gelijk hierboven, maar dan voor het achtste vinkje.
color: black;
De vinkjes hebben eerder dezelfde kleur gekregen als de achtergrond, waar ze op staan. Daardoor zijn ze (vrijwel) onzichtbaar. Als de pagina is bezocht, wordt de kleur zwart, waardoor ze duidelijk zichtbaar worden.
.sluit
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
De elementen met class="sluit". Binnen elk van de acht <li>'s staat onderaan een <label>. Deze toont, als de pop-up door aanraken of klikken is geopend, het sluitkruisje. Door op de <label> met het sluitkruisje te te klikken of dit aan te raken, wordt de bij label.sluit
horende radioknop geselecteerd en sluit de pop-up weer.
-webkit-animation: bugfix infinite 1s;
In oudere versies van Android browser zit een bug, waardoor de het sluitkruisje soms niet wordt getoond. Met behulp van deze regel wordt het sluitkruisje toch getoond. Meer hierover bij @-webkit-keyframes bugfix.
background: white;
Witte achtergrond.
color: red;
Voorgrondkleur rood. Dit is ook de letterkleur. Het sluitkruisje is niets anders dan een wat opgeblazen letter 'x'.
display: block;
Eerder is .sluit
met display: none;
verborgen. Nu wordt het weer zichtbaar gemaakt. Een <label> is van zichzelf een inline-element. Daardoor kunnen eigenschappen als hoogte en breedte niet worden gebruikt. Door het weer te geven als blok-element, kunnen dit soort eigenschappen wel worden gebruikt.
width: 38px; height: 39px; overflow: hidden; font-size: 77px; line-height: 25px;
Deze eigenschappen zorgen gezamenlijk voor een acceptabele weergave in alle browsers. Omdat elke browser zo z'n eigen kleine afwijkingen heeft, moet je de benodigde eigenschappen en waarden gewoon door uitproberen uitvogelen.
width en height
: met deze breedte en hoogte komt de 'x' het beste uit.
overflow
: hieronder worden een grote lettergrootte opgegeven. Te groot voor de hierboven opgegeven breedte en hoogte. Door overflow
op hidden
te zetten, wordt alles verborgen wat niet binnen de opgegeven breedte en hoogte past.
font-size
: 77 px is een forse lettergrootte. Maar dat is ook de bedoeling.
Meestal wordt als eenheid een relatieve eenheid als em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. (Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.)
Hier is het een voordeel, als een browser dat niet kan. Dat voorkomt namelijk dat de 'x' te groot wordt. Dat is verder geen ernstig probleem, maar in sommige browsers wordt dat nu dus voorkomen.
line-height
: bij een regelhoogte van 25 px staat de 'x' in alle browsers verticaal in het midden van de witte achtergrond.
border: black solid;
Zwart randje. De breedte wordt gelijk hieronder opgegeven.
border-width: 1px 1px 0;
De kleur en stijl zijn gelijk hierboven al opgegeven.
Omdat voor links geen breedte is opgegeven, krijgt die automatisch dezelfde waarde als rechts. Hier staat dus eigenlijk 1px 1px 0 1px
in de volgorde boven – rechts – onder – links. Overal een randje, behalve aan de onderkant.
Door kleur en stijl te scheiden van de breedte, wordt wat css uitgespaard. Dit is minder css dan drie aparte regels voor boven, rechts en links.
border-top-left-radius: 5px;
Linksboven ronde hoek.
position: absolute;
Om de <label> met het sluitkruisje op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier de <li>, waar label.sluit
in staat.
top: -40px;
40 px naar boven verplaatsen.
Als de pop-up is geopend door aanraking of aanklikken, wordt boven de thumbnail de korte naam van de bijbehorende achterliggende pagina getoond. Op deze hoogte komt het sluitkruisje daar precies naast te staan.
Als je geen top
op zou geven, komt de <label> op z'n normale plaats te staan: onder de <a> die er in de html gelijk voor zit. Omdat die <a> even groot is als de thumbnail, komt het sluitkruisje dan niet boven, maar helemaal onder de thumbnail te staan.
left: -20000px;
Links buiten het scherm parkeren, zodat het onzichtbaar is. Als dat nodig is wordt het sluitkruisje binnen het scherm geplaatst, waarna het zichtbaar is.
Normaal genomen zou het sluitkruisje worden verborgen met display: none;
. Dat wordt hier niet gedaan, omdat het dan niet zichtbaar blijkt te worden in oudere versies van Android browser, dat fantastische wonder der techniek dat bij tijd en wijle bij mij een slecht humeur, leverkolieken en een hoge bloeddruk veroorzaakt.
z-index: 50;
In bepaalde groottes van het browservenster komen sommige thumbnails en de bijbehorende links en dergelijke niet naast, maar onder de kolom met tekst te staan. Omdat die tekst in de html onder de knoppen staat, verdwijnen hierdoor de sluitkruisjes onder de tekst.
Door een hogere z-index te geven aan de <label>, is het sluitkruisje toch altijd zichtbaar boven de tekst.
Een z-index werkt alleen in sommige omstandigheden. Eén van die omstandigheden is een absolute positie. Die heeft de <span> iets hierboven gekregen, dus dat is geregeld.
Er zijn meerdere z-indexen voor verschillende elementen: 40, 50 en 60. Deze sluiten niet op elkaar aan. Hierdoor kun je later makkelijk elementen met een z-index toevoegen, zonder dat je bestaande z-indexen moet gaan veranderen.
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up {left: -705px;}
#blok-link-3 .pop-up, #blok-link-4 .pop-up {top: -170px;}
#blok-link-5 .pop-up, #blok-link-6 .pop-up {top: -255px;}
#blok-link-7 .pop-up, #blok-link-8 .pop-up {top: -326px;}
Drie nogal verschillende selectors, gescheiden door een komma. Ze hebben elk hetzelfde resultaat: ze zetten de eerder links buiten het scherm geparkeerde span.pop-up
, waarbinnen de pop-up zit, binnen het scherm, waardoor deze zichtbaar wordt. Het uiterlijke van de pop-up is al eerder opgegeven, hier wordt alleen het zichtbaar maken geregeld.
De eerste selector: .focus-open:focus ~ .open .pop-up
:
.focus-open:focus
: de <span> die alleen met de Tab-toets is te bereiken, speciaal aangebracht voor gebruikers van de Tab-toets. Maar alleen als deze <span> focus heeft, als deze bereikt is door de Tab-toets een bepaald aantal keren – afhankelijk van de hoeveelste <span> het is – in te drukken.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: span.focus-open
voor de ~
en label.open
na de ~
hebben beide als ouder dezelfde <li>.
.open
: de <label> met class = "open". De <label> die bij de <input> hoort, die zorgt voor het openen van de betreffende pop-up.
Deze 'tussenliggende' <label> is nodig, omdat de selector .focus-open:focus .pop-up
niet zou werken: .pop-up
zit niet binnen .focus-open
. Ook .focus-open:focus ~ .pop-up
zou niet werken, want .focus-open
en .pop-up
hebben niet dezelfde ouder.
.pop-up
: de elementen met class="pop-up" binnen label.open. Dit is er maar eentje: de <span> waar de hele pop-up in zit.
In normale mensentaal: als span.focus-open
focus heeft, doe dan iets met span.pop-up
die binnen de op span.focus-open
volgende label.open
zit.
De tweede selector: input:checked + .open .pop-up
:
input:checked
: als een <input> is geselecteerd. (De <input>'s waar het hier om gaat, zijn radioknoppen, waarvan er negen in één groep zitten. Als je er eentje selecteert, wordt daardoor een eventuele eerder geselecteerde knop automatisch gedeselecteerd.
Dit is 'n heel grove selector, maar er volgt nog meer, en dat maakt hem preciezer.
+
: de elementen voor en na de +
moeten in de html gelijk op elkaar volgen.
.open
: de elementen met class="open". Dit zijn de <label>'s die bij de <input>'s horen, die voor het openen van de pop-ups zorgen. Ze volgen in de html gelijk op de radioknop waar ze bij horen. Waarmee is voldaan aan de voorwaarde input + .open
.
Deze combinatie van .open
gelijk volgend op 'n <input> komt alleen binnen elke <li> met thumbs en dergelijke één keer voor, waarmee deze selector toch heel precies is, ondanks het wat ruige begin met alle <input>'s.
.pop-up
: de elementen met class="pop-up". Dit zijn de <span>'s, waarbinnen de pop-ups zitten.
In normale mensentaal: als een radioknop is geselecteerd, doe dan iets met de pop-up die in de <label> zit die gelijk op de radioknop volgt. Als de derde radioknop is geselecteerd, doe dan iets met de pop-up bij de derde thumbnail.
De derde selector: .open:hover .pop-up
:
.open:hover
: als wordt gehoverd over de elementen met class="open". Binnen elke <li> zit een <input>, waarmee de bijbehorende pop-up kan worden geopend. De elementen met class="open" zijn de bij die <input>'s horende <label>'s. Ze zijn zichtbaar als de witte vlakjes met het vraagteken.
.pop-up
: de elementen met class="pop-up". Dit zijn de <span>'s, waarbinnen de pop-ups zitten.
In normale mensentaal: als wordt gehoverd over label.open
, doe dan iets met de binnen die <label> zittende span.pop-up
.
Door in de selectors alleen classes te gebruiken, geldt deze regel voor álle acht de pop-ups. Als id's waren gebruikt, zouden acht verschillende regels nodig zijn geweest.
margin-left: 0;
Na het volschrijven van anderhalve pagina dat er iets gaat gebeuren, is de spanning ongetwijfeld tot het kookpunt gestegen. Wat gaat er gebeuren, na zo'n gigantische aankondiging?????
Nou, niet zoveel eigenlijk. Want het meeste is al gebeurd bij .pop-up. Daar is de hele lay-out van de pop-up al gemaakt. En daar is de pop-up ook met margin-left: -20000px;
links buiten het scherm geparkeerd.
Door die marge weg te halen, wordt de pop-up binnen het scherm geplaatst en daardoor zichtbaar.
Met behulp van left
is eerder de exacte plaats al opgegeven. Die is voor pop-ups bij thumbs links naast de tekst anders dan bij pop-ups bij thumbs rechts van de tekst.
.blok a:focus .naam
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
Als een link binnen een element met class="blok" focus heeft, doe dan iets met de daarin zittende elementen met class"=naam".
De elementen met class="blok" zijn de acht <li>'s, waarbinnen thumbnails, pop-ups, en dergelijke zitten. Binnen elke <li> zit een link naar de achterliggende pagina. En binnen die link zit weer een <span> met class="naam", waarbinnen de korte naam naar de achter de link zittende pagina zit.
color: blue;

De voorgrondkleur van span.naam
is eerder doorzichtig (transparent
) gemaakt, waarmee ook de tekst doorzichtig en dus onzichtbaar is geworden.
Als gebruikers van de Tab-toets de knoppen afgaan, brengt de eerste toetsaanslag ze bij een speciaal voor hen aangebrachte span.focus-open
. (Meer daarover is te vinden bij <span class="focus-open" tabindex="0"><span>). Dat opent de pop-up. Een tweede toetsaanslag sluit de pop-up weer, en zet de focus op de link: als de Enter-toets wordt ingedrukt, wordt de link gevolgd.
Om duidelijk te maken bij welke thumbnail naar welke pagina wordt gegaan, wordt de naam zichtbaar gemaakt. Die naam stond al die tijd al braaf op de thumbnail, maar was onzichtbaar, omdat de kleur van de tekst doorzichtig was. Door simpelweg de voorgrondkleur, en daarmee de kleur van de tekst, in blauw te veranderen, wordt de naam zichtbaar.
Gelijktijdig wordt bij input:not(:checked) ~ a:focus gezorgd voor een doorzichtig witte afdekking van de thumbnail, omdat de blauwe naam anders vaak niet goed te zien is. Het geheel ziet er dan uit zoals op bijgaande afbeelding.
input:checked ~ a .naam
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
.blok a:focus .naam {color: blue;}

Als een <input> is geselecteerd wordt de bij die <input> horende pop-up getoond. Gelijktijdig wordt de korte naam van de bij de <input> horende achterliggende pagina boven de thumbnail getoond, zoals op de afbeelding is te zien.
Omdat de naam binnen een <span> zit, die weer binnen de link naar de achterliggende pagina zit, werkt de naam als een link: bij aanraking of aanklikken van de naam, opent de achterliggende pagina.
input:checked
: als een <input> is geselecteerd. Binnen elke <li> staat onder andere een <input> van de soort radioknop. Dit is een tamelijk grove selector, omdat hij voor élke <input> geldt. Maar de rest van de selector beperkt dit tot een heel specifieke volgorde, die alleen binnen een <li> voorkomt.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: input
voor de ~
en a
na de ~
hebben beide als ouder de <li>, waarbinnen ze staan.
a
: alle links. Dat is er hier maar eentje, de link naar de achterliggende pagina.
.naam
: alle elementen met class="naam". Dat is er ook maar eentje: de binnen de <a> zittende <span> met de korte naam van de achterliggende pagina.
In normale mensentaal: als een radioknop is geselecteerd, doe dan iets met de naam die in span.naam
binnen de op die radioknop volgende link zit.
background: white;
Witte achtergrond.
color: blue;
Niet omdat ik zo dol ben op blauw, hoewel het mijn lievelingskleur is, maar blauw is een gebruikelijke kleur voor een link. De gebruikelijke onderstreping is eerder al opgegeven.
width: 141px;
Breedte. Samen met het ernaast staande sluitkruisje is dit even breed als de thumb.
font-size: 20px;
Iets grotere letter.
Meestal wordt als eenheid een relatieve eenheid als em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. (Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.)
Hier is het een voordeel, als een browser dat niet kan. Dat voorkomt namelijk dat de naam te groot wordt. Dat is verder geen ernstig probleem, maar in sommige browsers wordt dat nu dus voorkomen.
margin: 0 0 0 39px;
Links een marge van 39 px.
Eerder is aan de bovenkant een negatieve marge van 50 px opgegeven. Die wordt hier weggehaald. De marge links plaatst de naam precies naast het sluitkruisje.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
border: black solid 1px;
Zwart randje.
border-top-right-radius: 5px;
Rechterbovenhoek rond.
top: -41px;
Op deze hoogte staat de naam precies boven de thumbnail.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
left: -1px;
Kleine verplaatsing naar links, zodat de naam goed aansluit op het ernaast staande sluitkruisje.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
#blok-link-2 input:checked ~ a .naam, #blok-link-4 input:checked ~ a .naam, #blok-link-6 input:checked ~ a .naam, #blok-link-8 input:checked ~ a .naam
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
.blok a:focus .naam {color: blue;}
input:checked ~ a .naam {background: white; color: blue; width: 141px; font-size: 20px; margin: 0 0 0 39px; border: black solid 1px; border-top-right-radius: 5px; top: -41px; left: -1px;}
Dit zijn vier selectors, gescheiden door een komma. Ze eindigen alle vier op input:checked ~ a .naam
. In span.naam
zit de korte naam van de achterliggende pagina. Dit deel van de selector wordt hier gelijk boven bij input:checked ~ a .naam uitgebreid besproken.
Het eerste deel van de selector is bij alle vier de selectors verschillend: de elementen met id="blok-link-2", id="blok-link-4", id="blok-link-6" en id="blok-link-8". Dit zijn de tweede, vierde, zesde en achtste <li>: de vier <li>'s rechts van de tekst in het midden. Deze selector geldt dus alleen voor de vier korte namen, die bij de thumbs rechts van de tekst horen.
margin: 0 39px 0 0;
Eerder is de naam met behulp van margin
op de juiste plaats gezet. Voor de thumbs rechts van de tekst in het midden moet die marge worden aangepast. Nu is niet links, maar rechts een marge van 39 px nodig, zodat daar ruimte voor het sluitkruisje ontstaat.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
border-radius: 5px 0 0;
Omdat voor linksonder geen waarde is opgegeven, krijgt linksonder automatisch dezelfde waarde als rechtsboven. Hier staat dus eigenlijk 5px 0 0 0
in de volgorde linksboven – rechtsboven – rechtsonder – linksonder.
Linksboven een ronde hoek, en de eerder opgegeven ronde hoek rechtsboven wordt weer een gewone rechte hoek.
input:not(:checked) ~ a:focus
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
a {width: 120px; height: 108px; position: absolute; top: 8px; left: 8px;}
.blok a {-webkit-animation: bugfix infinite 1s; box-shadow: 4px 3px 4px 1px black; display: block; width: 180px; height: 161px; text-align: center; margin: 0 auto; border: black solid 1px; border-radius: 5px; position: relative; top: 0; left: 0;}
#blok-link-2 a, #blok-link-4 a, #blok-link-6 a, #blok-link-8 a {box-shadow: -4px 3px 4px 1px black;}
input:not(:checked)
: <input>'s die niet (:not
) zijn geselecteerd (:checked
). Dit is een tamelijk grove selector, die voor alle niet-geselecteerde radioknoppen zou gelden. Maar er volgt nog een deel op, waardoor de selector veel specifieker wordt.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: de input
voor de ~
en de a
na de ~
hebben beide als ouder dezelfde <li>.
a:focus
: als de link focus heeft. Dit is de link naar de achterliggende pagina bij de thumb. Deze link staat over de thumbnail heen, waardoor hij de thumb volledig afdekt.
In normale mensentaal: doe iets met de link naar de achterliggende pagina, maar alleen als deze focus heeft en de ervoor zittende <input> niet is geselecteerd.
Dit is bedoeld voor gebruikers van de Tab-toets. Bij de eerste tab wordt onder andere de naam getoond op de thumb, zoals beschreven bij .blok a:focus .naam. Omdat die naam soms nogal onduidelijk is, wordt een doorzichtige witte achtergrond op de thumb gezet.
background: rgba(255, 255, 255, 0.5);
Doorzichtig witte achtergrondkleur. Hoe rgba()
precies werkt, is te vinden bij background: rgba(255, 255, 255, 0.75);. Het enige verschil is dat de doorzichtigheid hier geen 0.5, maar 0.75 is: iets minder.
input:not(:checked) + .open:hover ~ a .naam, .focus-open:focus ~ input:not(:checked) ~ a .naam
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
.blok a:focus .naam {color: blue;}
input:checked ~ a .naam {background: white; color: blue; width: 141px; font-size: 20px; margin: 0 0 0 39px; border: black solid 1px; border-top-right-radius: 5px; top: -41px; left: -1px;}
#blok-link-2 input:checked ~ a .naam, #blok-link-4 input:checked ~ a .naam, #blok-link-6 input:checked ~ a .naam, #blok-link-8 input:checked ~ a .naam {margin: 0 39px 0 0; border-radius: 5px 0 0;}
Dit ziet er weer gezellig ingewikkeld uit. Maar zoals gewoonlijk: als je het in stukjes hakt, wordt het al 'n stuk overzichtelijker.
Deze regel zorgt ervoor dat de korte naam van de achterliggende pagina boven de thumbnail wordt gezet bij hoveren over het witte vlakje met het vraagteken, of als de speciaal voor de Tab-toets aangebrachte span.focus-open
focus heeft. (Meer over span.focus-open
is te vinden bij Tabindex.)
Er zijn twee selectors: eentje voor en eentje na de komma.
De eerste selector: input:not(:checked) + .open:hover ~ a .naam
input:not(:checked)
: alle <input>'s – dat zijn hier radioknoppen –, maar alleen als deze niet (:not
) zijn geselecteerd (:checked
). De naam moet ook worden getoond als de pop-up is geopend door het selecteren van een radioknop. Maar in dat geval staat er ook een kruisvakje naast de naam, waardoor de op een iets andere plaats moet worden neergezet.
Door deze selector niet te laten werken, als de radioknop is geselecteerd en het sluitkruisje zichtbaar is, wordt voorkomen dat de naam op de verkeerde plaats naast het sluitkruisje wordt gezet.
Op de afbeelding staat bovenaan de naam naast het sluitkruisje. Dit is de situatie als de pop-up door klikken of aanraken geopend blijft: links boven de thumb het sluitkruisje, rechts de naam.
In het midden staat de situatie, als de speciaal voor de Tab-toets aangebrachte <span> focus heeft, of als over het witte vlakje met het vraagteken wordt gehoverd: de naam wordt boven de thumbnail weergegeven, maar zonder sluitkruisje.
Onderaan staat, wat er gebeurt bij een combinatie van deze twee dingen: het sluitkruisje staat er, maar de naam staat – net zoals bij hoveren of als de <span> voor de Tab-toets focus heeft – in het midden boven de thumbnail. Waardoor deze gedeeltelijk onder het sluitkruisje verdwijnt.
Dit wordt voorkomen door hoveren en focus voor de Tab-toets alleen te laten werken, als de radioknop niet is geselecteerd. Als de radioknop is geselecteerd, wordt de bijbehorende korte naam nu niet verplaatst bij hoveren of focus.
Dit is een tamelijk grove selector, omdat hij voor álle <input>'s geldt. Maar de rest van de selector beperkt dit tot een heel specifieke volgorde van elementen, die alleen binnen de <li>'s met de thumbnails en dergelijke voorkomt.
+
: het element achter de +
moet in de html direct volgen op het element voor de +
. In dit geval gaat het om element met class="open" (de <label> die onder andere voor het openen van de pop-up zorgt) die gelijk op een button type radioknop volgt.
.open:hover
: de elementen met class="open", maar alleen als hierover wordt gehoverd. In dit <label> zit onder andere de <span> die zorgt voor het witte vlakje met het vraagteken.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: label.open
voor de ~
en de <a> na de ~
hebben beide als ouder dezelfde <li>.
a
: alle links. Dat is er hier maar eentje: de link naar de achterliggende pagina.
.naam
: de elementen met class="naam". Binnen elke <a> zit een span.naam
, waarbinnen de korte naam van de achterliggende pagina staat.
In normale mensentaal: doe iets met de korte naam van de pagina, die binnen een <span> binnen de <a> zit, als over het witte vlakje met het vraagteken wordt gehoverd, maar niet als de ervoor zittende radioknop is geselecteerd.
De tweede selector: .focus-open:focus ~ input:not(:checked) ~ a .naam
.focus-open:focus
: een speciaal voor gebruikers van de Tab-toets aangebrachte span.focus-open
zorgt ervoor dat de pop-up ook met de Tab-toets kan worden geopend. Er is meer over te lezen bij Tabindex. Als deze <span> focus heeft.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: span.focus-open
voor de ~
en de <input> na de ~
hebben beide als ouder dezelfde <li>.
input:not(:checked)
: alle <input>'s – die zijn hier van het type radioknop –, maar alleen als deze niet zijn geselecteerd. Waarom dit nodig is, staat hier iets boven bij input:not(:checked)
bij de eerste selector.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: de input
voor de ~
en de <a> na de ~
hebben beide als ouder dezelfde <li>.
a
: alle links. Dat is er hier maar eentje: de link naar de achterliggende pagina.
.naam
: de elementen met class="naam". Binnen elke <a> zit een span.naam
, waarbinnen de korte naam van de achterliggende pagina staat.
In normale mensentaal: doe iets met de korte naam van de pagina, die binnen een <span> binnen de <a> zit, als de speciaal voor de Tab-toets aangebrachte <span> focus heeft, maar niet als de op die <span> volgende radioknop is geselecteerd.
background: white;
Witte achtergrond.
color: black;
De voorgrondkleur, en dus ook de kleur van de tekst, is eerder doorzichtig (transparent
) gemaakt. Daardoor is de tekst onzichtbaar. Hier wordt de korte naam van de achterliggende pagina weer zichtbaar gemaakt.
font-size: 22px;
Tamelijk grote letter.
Meestal wordt als eenheid een relatieve eenheid als em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. (Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.)
Hier is het een voordeel, als een browser dat niet kan. Dat voorkomt namelijk dat de naam te groot wordt. Dat is verder geen ernstig probleem, maar in sommige browsers wordt dat nu dus voorkomen.
margin: 0;
Alle eerder opgegeven marges weghalen.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
border: black solid 1px;
Zwart randje.
border-radius: 5px 5px 0 0;
Links‑ en rechtsboven ronde hoekjes.
top: -41px;
41 px naar boven verplaatsen. Op deze hoogte staat de naam precies boven de thumbnail.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
left: -1px;
Kleine verschuiving naar links om de naam op precies de juiste plaats te krijgen.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
input:checked ~ a .naam::after, .open:hover + a .naam::after, .focus-open:focus ~ a .naam::after
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
#blok-link-4 .naam::after, #blok-link-8 .naam::after {color: #ccc;}
#blok-link-2 .naam::after, #blok-link-4 .naam::after, #blok-link-6 .naam::after, #blok-link-8 .naam::after {left: auto; right: 3px;}
.blok a:visited .naam::after, #blok-link-4 a:visited .naam::after, #blok-link-8 a:visited .naam::after {color: black;}
Drie selectors, gescheiden door een komma. Het tweede deel van alle drie is hetzelfde, daarom beschrijf ik ze hier gezamenlijk.
Het eerste deel van de drie selectors geeft aan, wanneer iets moet gebeuren:
input:checked
: de <input>'s – dat zijn hier radioknoppen – die zijn geselecteerd.
.open:hover
: als over de elementen met class="open" wordt gehoverd. Dit zijn de <label>'s, waarbinnen onder andere het witte vlakje met het vraagteken zit.
.focus-open:focus
: een speciaal voor gebruikers van de Tab-toets aangebrachte span.focus-open
zorgt ervoor dat de pop-up ook met de Tab-toets kan worden geopend. Er is meer over te lezen bij Tabindex. Als deze <span> focus heeft.
Samengevat: als een radioknop is geselecteerd, of als wordt gehoverd over het witte vlakje met het vraagteken, of als de <span> voor gebruikers van de Tab-toets focus heeft. Deze drie dingen hebben alle drie tot gevolg, dat de pop-up wordt geopend.
+ en ~
: het element voor de +
of ~
moet in de html voor het element achter de +
of ~
staan.
Bij de +
moeten de elementen gelijk op elkaar volgen. Bij de ~
mogen er andere elementen tussen zitten, als het tweede element maar na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: de input
voor de ~
en de <a> na de ~
hebben beide als ouder dezelfde <li>.
Het derde deel, dat bij alle drie de selectors hetzelfde is:
.naam::after
: bij .naam::after is met behulp van ::after
bij .naam
een pseudo-element gemaakt, waarbinnen een vinkje is gezet. Dit vinkje wordt naast het vraagteken zichtbaar, als de bijbehorende pagina al is bezocht.
In normale mensentaal: doe iets met het vinkje naast het vraagteken als de pop-up is geopend doordat een radioknop is geselecteerd, over het witte vlakje met het vraagteken wordt gehoverd, of de <span> voor de Tab-toets focus heeft.
display: none;
Het pseudo-element met het vinkje hoort bij span.naam
. Bij input:not(:checked) + .open:hover ~ a .naam, .focus-open:focus ~ input:not(:checked) ~ a .naam is span.naam
een eind naar boven verplaatst. Hierdoor gaat ook het vinkje mee naar boven, waardoor dit niet meer naast het vraagteken, maar een eind daarboven wordt neergezet. Om precies te zijn: op de thumbnail erboven.
Dit onaangepaste gedrag wordt niet getolereerd. De zich misdragende vinkjes worden gewoon helemaal verborgen. Eigen schuld, dikke bult.
(Je zou ze waarschijnlijk ook 'n eind omlaag kunnen neerzetten, maar zo belangrijk zijn ze niet. En er zitten al zoveel marges, posities, enz. in de css, dat ik kies voor de simpelste oplossing: weg met die handel.)
input:checked ~ .sluit
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.sluit {-webkit-animation: bugfix infinite 1s; background: white; color: red; display: block; width: 38px; height: 39px; overflow: hidden; font-size: 77px; line-height: 25px; border: black solid; border-width: 1px 1px 0; border-top-left-radius: 5px; position: absolute; top: -40px; left: -20000px; z-index: 50;}
input:checked
: als een <input> – dat zijn hier radioknoppen – is geselecteerd.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: de <input> voor de ~
en label.sluit
na de ~
hebben beide als ouder dezelfde <li>.
.sluit
: de elementen met class="sluit". Onderaan elke <li> zit een label.sluit
. Hierbinnen zit de letter 'x'. Deze wordt wat opgeleukt tot een rood sluitkruisje.
In normale mensentaal: doe iets met label.sluit
, het sluitkruisje, als de ervoor zittende radioknop is geselecteerd.
left: 0;
Bij .sluit is het sluitkruisje al helemaal opgemaakt. Daar is het ook links buiten het scherm geparkeerd, zodat het onzichtbaar is. Hier wordt het sluitkruisje binnen het scherm gezet en daardoor zichtbaar.
Als de pop-up is geopend door aanraken van of klikken op het witte vlakje met het vraagteken, wordt feitelijk een radioknop geselecteerd. Deze knop zorgt voor het openblijven van de pop-up. Alleen door het selecteren van een andere radioknop uit dezelfde groep, kan de pop-up weer worden gesloten.
Daar is dit sluitkruisje voor. De radioknop die bij de <label> met het sluitkruisje hoort, zit in dezelfde groep radioknoppen, waarmee de pop-ups worden geopend. Door op deze <label>, het sluitkruisje, te klikken of dit aan te raken, wordt de negende radioknop geselecteerd. Deze negende radioknop hoort niet bij een pop-up. Als deze negende knop wordt geselecteerd via dit <label>, is de eerder geselecteerde radioknop niet meer geselecteerd, waardoor de bij die knop horende pop-up weer verdwijnt.
#blok-link-2 input:checked ~ .sluit, #blok-link-4 input:checked ~ .sluit, #blok-link-6 input:checked ~ .sluit, #blok-link-8 input:checked ~ .sluit
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.sluit {-webkit-animation: bugfix infinite 1s; background: white; color: red; display: block; width: 38px; height: 39px; overflow: hidden; font-size: 77px; line-height: 25px; border: black solid; border-width: 1px 1px 0; border-top-left-radius: 5px; position: absolute; top: -40px; left: -20000px; z-index: 50;}
input:checked ~ .sluit {left: 0;}
Deze vier selectors eindigen alle vier op input:checked ~ .sluit
: doe iets met het sluitkruisje als de ervoor zittende radioknop is geselecteerd. De uitleg hiervan staat iets hierboven bij input:checked ~ .sluit.
Voor dit gemeenschappelijke laatste deel staan vier id's: "blok-link-2", "blok-link-4", "blok-link-6" en "blok-link-8". Dit zijn de vier id's die bij de <li>'s rechts van de tekst horen. De sluitkruisjes rechts van de tekst moeten op een aantal punten iets worden aangepast.
width: 41px;
Iets breder maken dan de eerder voor de sluitkruisjes links van de tekst opgegeven 38 px.
Het is goed mogelijk dat dit niet nodig zou zijn, als je nog uren zou gaan zitten pielen om alles exact op de pixel precies neer te zetten. Persoonlijk ga ik dan liever 'n wandeling maken of zoiets, want dit lost het ook prima op.
border-radius: 0 5px 0 0;
De eerder opgegeven ronde hoek linksboven wordt hier naar rechtsboven verplaatst.
left: 139px;
De sluitknoppen rechts van de tekst in het midden worden rechts van de naam neergezet.
main
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
main {display: block; max-width: 700px; margin: 0 auto; padding: 5px;}
Alle <main>'s. Dat is er maar eentje. Binnen <main> staat de belangrijkste inhoud van de pagina. Dat is hier voornamelijk opvultekst, maar normaal genomen staat daar – hopelijk – wel iets interessants.
background: #eee;
Lichtgrijze achtergrondkleur.
color: black;
Voorgrondkleur zwart. Dit is onder andere de kleur van de tekst.
Hoewel dit de standaardkleur is, wordt deze toch specifiek opgegeven. Hierboven is een achtergrondkleur opgegeven. Sommige mensen hebben zelf de voorgrond- en/of achtergrondkleur veranderd, bijvoorbeeld omdat ze slecht kleuren kunnen onderscheiden. Als nu de achtergrondkleur wordt veranderd, maar niet de voorgrondkleur, loop je het risico dat tekstkleur en achtergrondkleur te veel op elkaar gaan lijken.
Door beide op te geven, is redelijk zeker dat achtergrond- en tekstkleur genoeg van elkaar blijven verschillen. Als de gebruiker !important
heeft gebruikt in een eigen stylesheet, is er nog niets aan de hand, want dan veranderen achtergrond- en voorgrondkleur geen van beide.
Dit is ook al bij <body> opgegeven, maar sommige mensen hebben bij álle elementen de kleuren veranderd. Het heeft immers weinig zin, als ze dat alleen bij de body doen, terwijl de sitebouwer de kleuren ook bij bijvoorbeeld de paragrafen heeft aangepast.
width: calc(100% - 412px);
Breedte.
Een blok-element zoals <main> wordt normaal genomen even breed als z'n ouder. Dat is hier <body>, ook een blok-element. Ook <body> wordt hierdoor even breed als z'n ouder: het blok-element <html>. Omdat <html> geen ouder meer heeft, wordt dit even breed als het venster van de browser. Normaal genomen zou <main> daardoor ook even breed worden als het venster van de browser.
Dat is hier niet de bedoeling, want links en rechts van de <main> met de tekst staan nog thumbnails. Met behulp van calc()
wordt daarom hier een breedte opgegeven.
Een breedte in procenten is altijd ten opzichte van de ouder van het element. Bij calc(100%)
zou <main> daarom even breed zijn als <body> (en uiteindelijk even breed als het venster van de browser). Dat is weinig interessant.
Maar met calc()
kun je verschillende eenheden in één berekening gebruiken. Door van 100% (de breedte van het venster van de browser) 412 px af te trekken, is er links en rechts van <main> altijd ruimte voor de thumbnails, ongeacht hoe breed het venster is.
Deze breedte zou eigenlijk niet nodig moeten zijn, omdat hieronder de <main> een maximumbreedte krijgt. In bredere vensters zou deze hetzelfde moeten werken als een gewone breedte, waardoor de <main> – in combinatie met de absolute positie en left
en right
– horizontaal gecentreerd zou moeten staan. Dat gebeurt echter niet in Internet Explorer en Edge.
Op een of andere manier zorgt het opgeven van deze breedte voor horizontaal centreren in deze browsers. Vreemd, omdat de uitkomst van deze berekening groter kan zijn dan de hieronder opgegeven maximumbreedte van 860 px. Maar het werkt, en daar gaat het maar om.
(In smallere vensters speelt dit niet: left: 200px;
en right: 200px;
zorgen er dan voor dat <main> horizontaal gecentreerd staat.)
max-width: 860px;
Maximumbreedte voorkomt te lange en daardoor slecht leesbare regels. Het is bovendien nodig om <main> horizontaal te kunnen centreren. Hoe dat centreren precies gebeurt, staat iets hieronder bij position
.
(Hierboven wordt ook een gewone breedte opgegeven. Dat is alleen nodig vanwege een bug in Internet Explorer en Edge.)
overflow: auto;
<main> wordt hieronder absoluut gepositioneerd met onder andere top: 40px;
en bottom: 0;
. Dit zorgt ervoor dat de erboven staande <h1> niet meescrolt, maar dat deze <h1> altijd bovenaan het venster van de browser blijft staan.
Als er nu zoveel tekst in <main> staat dat dit niet binnen het venster past, verschijnt een verticale scrollbalk aan de rechterkant van het venster, waarmee de hele pagina gescrold kan worden. Ook de boven de tekst staande <h1> scrolt dan mee.
Door overflow
bij <main> op auto
te zetten, verschijnt de scrollbalk niet aan de rechterkant van het venster, maar aan de rechterkant van <main>. De tekst kan nu binnen <main> worden gescrold, zonder dat de rest van de pagina meescrolt. De <h1> blijft nu netjes bovenaan het venster van de browser staan.
-webkit-overflow-scrolling: touch;
Zoals gelijk hierboven beschreven scrolt de tekst binnen het element <main>. Als op iOS niet de hele pagina, maar binnen een element wordt gescrold, gaat dat ongelooflijk schokkerig. De reden daarvan is volstrekt onduidelijk, want Apple is bepaald niet open met informatie over dit soort dingen.
Dit zorgt ervoor dat op iOS ook binnen <main> soepel gescrold kan worden.
Omdat deze eigenschap alleen nodig is voor iOS, wordt alleen de -webkit-
vorm gebruikt. Normaal genomen is dat hartstikke fout, omdat je dan onbetaald Apple helpt bij z'n pogingen sites alleen in Safari goed weer te geven. Maar in dit geval is deze eigenschap allen op iOS nodig.
border: black solid;
Zwart randje. De breedte wordt gelijk hieronder opgegeven.
border-width: 0 1px;
Kleur en stijl zijn gelijk hierboven al opgegeven.
Omdat voor onder en links geen breedte is opgegeven, krijgen die automatisch dezelfde breedte als boven en rechts. Hier staat dus eigenlijk 0 1px 0 1px
in de volgorde boven – rechts – onder – links. Alleen links en rechts een randje.
Het op deze manier opgeven van de borders gebruikt iets minder css dan twee volledig losse regels voor de borders links en rechts.
position: absolute;
Om de <main> op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Als die er niet is, zoals hier het geval is, wordt gepositioneerd ten opzichte van het venster van de browser.
Met top: 40px;
en bottom: 0;
wordt <main> in verticale richting vastgezet. In de ruimte van 40 px aan de bovenkant staat de <h1>.
Iets hierboven is overflow: auto;
opgegeven. Als er te veel tekst is voor het venster, scrolt de tekst hierdoor binnen <main>, zonder dat de hele pagina meescrolt. De <h1> scrolt hierdoor ook niet mee, maar blijft altijd bovenaan het venster van de browser staan.
Het verhaal voor left
en right
is iets ingewikkelder.
Bij beide wordt 200 px opgegeven. Dat is ten opzichte van het browservenster. Hierdoor is er links en rechts van de <main> met de tekst altijd ruimte voor de thumbnails.
Als je verder niets zou doen, zou je in brede vensters heel lange regels krijgen, die daardoor heel slecht leesbaar worden. Daarom is iets hierboven een maximumbreedte van 860 px opgegeven. (En nog iets hoger ook een gewone breedte, maar die doet hier verder niet mee, want die is alleen nodig voor een bug in Internet Explorer en Edge.)
En dan ontstaat er in brede vensters een onmogelijke situatie. Stel dat het venster 1500 px breed is. left: 200px;
, dan blijft er rechts daarvan nog 1300 px over. right: 200px;
. Nu is er in het midden nog 1300 px over. Maar de maximumbreedte is 860 px. Dat levert een gat op van 440 px.
Een middeleeuwse pijnbank of vierendelen (eigenlijk tweedelen hier) zou kunnen helpen, maar dat levert mogelijk wat problemen van justitiële aard op. Een krant kun je in zo'n geval gezellig in tweeën scheuren, maar het in tweeën slaan van de monitor wordt al snel een begrotelijke hobby en bevordert ook de kwaliteit van het beeld niet echt.
Dan vallen we maar heel saai terug op de specificatie. In deze onmogelijke gevallen wordt rechts en links de afstand gelijk verdeeld. Oftewel: <main> wordt netjes horizontaal gecentreerd.
(Dit is trouwens ook een weinig bekende truc om absoluut gepositioneerde blok-elementen horizontaal te centreren. En het werkt zelfs ook bij verticaal centreren. De enige voorwaarde is dat er een breedte (of hoogte) aanwezig is, en dat right
en left
(of top
en bottom
) een andere waarde dan de standaardwaarde auto
moeten hebben.
top: 40px; right: 200px; bottom: 0; left: 200px;
Deze eigenschappen worden gelijk hierboven bij position
besproken.
#checkbox-voor-focus
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
Het element met id="checkbox-voor-focus".
Aan het begin van de tekst in de middelste kolom is een <input> neergezet:
<input id="checkbox-voor-focus" type="checkbox" aria-hidden="true" autofocus>
Deze <input> heeft feitelijk geen enkele werking. Maar door het gebruik van het attribuut autofocus wordt de focus op de tekst gezet. Als dat niet zou gebeuren, moet eerst in de tekst worden geklikt, voordat de tekst kan worden gescrold met behulp van scrollwieltje of pijltjes.
(Dit komt doordat in de html de <nav> met de knoppen voor de <main> met de tekst staat. Je zou die volgorde ook kunnen veranderen, en dan is deze <input> niet nodig. Op de site kan dat niet, omdat er nog veel meer links en dergelijke in de <nav> staan. In het voorbeeld heb ik de volgorde hetzelfde gelaten, omdat er anders nog 'n verschil met de site zou ontstaan.)
display: block;
Eerder is deze <input> verborgen met display: none;
. In kleinere browservensters is dat prima, want daar is hij niet nodig. Maar in bredere vensters kan dat niet, omdat de truc niet werkt als de <input> met display: none;
wordt verborgen. Daarom wordt de <input> hier weer zichtbaar gemaakt.
position: absolute;
Om de <input> op een bepaalde plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier <main>.
left: -20000px;
Ik heb verder helemaal niets tegen <input>'s, maar ze zijn niet echt het allermooiste element dat er is. Daarom wordt de <input> links buiten het scherm geparkeerd. Nu kan hij, anders dan bij display: none;
, rustig z'n nuttige werk doen, zonder dat artistieke zielen zoals ik zich aan z'n uiterlijk hoeven te ergeren.
css voor vensters minimaal 543 px en maximaal 712 px hoog en minimaal 763 px breed
@media screen and (min-height: 543px) and (max-height: 712px) and (min-width: 763px)

De css die hier tot nu toe staat, geldt voor alle browservensters.
De css die binnen deze media query staat, geldt alleen voor vensters die minimaal 543 px hoog én maximaal 712 px hoog én minimaal 763 px breed zijn. Deze vensters zijn te laag om links en rechts van de tekst vier thumbnails onder elkaar te kunnen zetten. Daarom worden links en rechts van de tekst twee thumbnails neergezet en worden de overige vier onder de tekst neergezet.
Ook de css die eerder bij @media screen and (min-width: 763px) and (min-height: 543px) is opgegeven, blijft hier gewoon gelden. Er wordt binnen deze media-regel alleen extra css opgegeven die alleen geldt voor vensters die maximaal 712 hoog zijn.
@media
: geeft aan dat het om css gaat, die alleen van toepassing is, als aan bepaalde voorwaarden wordt voldaan. Al langer bestond de mogelijkheid om met behulp van zo'n @media-regel css voor bijvoorbeeld printers op te geven. css3 heeft dat uitgebreid tot bepaalde fysieke eigenschappen, zoals de breedte en hoogte van het venster van de browser.
screen
: deze regel geldt alleen voor schermweergave.
and
: er komt nog een voorwaarde, waaraan moet worden voldaan.
(min-height: 543px)
: het venster moet minimaal 543 px hoog zijn. Is het venster lager, dan wordt de css die binnen deze media-regel staat genegeerd.
and
: er komt nog een voorwaarde, waaraan moet worden voldaan.
(max-height: 712px)
: het venster mag maximaal 712 px hoog zijn. Is het venster hoger, dan wordt de css die binnen deze media-regel staat genegeerd.
and
: er komt nog een voorwaarde, waaraan moet worden voldaan.
(min-width: 763px)
: het venter moet minimaal 763 px breed zijn. Is het venster smaller, dan wordt de css die binnen deze media-regel staat genegeerd.
Gelijk na deze regel komt een {
te staan, en aan het einde van de css die binnen deze regel valt een bijbehorende afsluitende }
.
Die zijn in de regel hierboven weggevallen, maar het geheel ziet er zo uit:
@media screen and (min-width: 760px) and (min-height: 500px) {
body {color: silver;}
(...) rest van de css voor deze @media-regel (...)
footer {color: gold;}
}
Voor de eerste css binnen deze media-regel staat dus een extra {
, en aan het eind staat een extra }
.
#blok-link-3, #blok-link-4
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-3, #blok-link-4 {top: 211px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
De elementen met id="blok-link-3" en id="blok-link-4". De <li>'s met de derde en vierde thumbnail, pop-up, en dergelijke.
top: calc(50% - 65px);
Eerder zijn met top: 211px
; de derde en vierde <li> op een vaste hoogte vanaf de bovenkant van het browservenster neergezet. (Vanaf de bovenkant van het venster, omdat er geen voorouders met een positie zijn.)
In browsers die calc()
niet kennen (die staan bij Bekende problemen (en oplossingen) blijft top: 211px;
gewoon gelden. Maar in andere browsers kunnen de derde en vierde <li>, en dus de daarin zittende thumbs, netjes verticaal worden gecentreerd tussen de bovenste en onderste rij thumbs.
calc(50%)
: zet de derde en vierde <li> op halve hoogte van de eerste voorouder die zelf een positie heeft. Als die er niet is, zoals hier het geval is, worden ze halverwege het venster van de browser neergezet. Alleen dit is niet zo heel interessant, want dat zou je ook met top: 50%;
kunnen doen.
Maar dan komt het handige van calc()
: je kunt verschillende eenheden door elkaar heen gebruiken. Van die 50% wordt 65 px afgetrokken. Hierdoor staan de derde en vierde <li> altijd 65 px boven het midden van het browservenster, ongeacht hoe hoog dit is. Daardoor staan de erin zittende thumbnails altijd verticaal gecentreerd tussen de eerste en de laatste rij met thumbnails.

De hoogte van de <li>'s is 161 px. Je zou dus denken dat geen 65, maar 80 px afgetrokken moet worden. Dat is niet zo: enig uitproberen levert 65 px op. Dat komt door het gebruik van dingen als box-shadow
, marges, en dergelijke bij de diverse elementen.
Op bijgaande afbeelding zijn de thumbnails even weggelaten en zijn de derde en vierde <li> van een nummer voorzien. Hierdoor is duidelijker te zien, dat het midden van het browservenster niet precies het midden tussen de bovenste en onderste rij thumbnails is, bijvoorbeeld door de lege ruimte boven de bovenste rij. Als je 80 px zou aftrekken, komen de derde en vierde <li> daardoor uiteindelijk te hoog te staan.
#blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
#blok-link-5, #blok-link-6 {top: 382px;}
#blok-link-7, #blok-link-8 {top: 553px;}
De elementen met id="blok-link-5", id="blok-link-6", id="blok-link-7" en id="blok-link-8". De vijfde, zesde, zevende en achtste <li>. Dit zijn de vier <li>'s, en dus ook de daarin zittende thumbs, die niet naast, maar onder de tekst komen te staan.
background: none;
Hier gelijk onder wordt een breedte van 25% opgegeven. Zoals hieronder beschreven, is dat een breedte van 25% van het venster van de browser. Samen beslaan deze vier <li>'s 100%, de volle breedte van het venster. De eerder opgegeven achtergrondkleur is daardoor ook zichtbaar over de volle breedte van het venster. Weg ermee.
width: 25%;
Een <li> is een inline-element. Maar door de eerder opgegeven absolute positie, zijn ze veranderd in een soort blok-element. Een blok-element wordt normaal genomen even breed als z'n ouder. Hier is echter een breedte van 25% opgegeven, en dan wordt het blok-element 25% van de breedte van z'n ouder.
De ouder van de <li>'s is de <ul>, waar ze in staan. Dit is een blok-element, waardoor dit even breed wordt als z'n ouder. Dat is hier de <nav>, ook een blok-element dat even breed wordt als z'n ouder: <header>. Het wordt eentonig: een blok-element, dat even breed wordt als z'n ouder <body>. En het blok-element <body> wordt weer even breed als de ouder ervan: <html>. Meer ouders zijn er niet.
Omdat ook bij <html> geen breedte is opgegeven, wordt dat even breed als het venster van de browser. Dat betekent, dat alle voorouders van de <li>'s ook even breed worden als het venster van de browser. En uiteindelijk wordt elke <li> dan 25% van de breedte van het venster.
Omdat er vier <li>'s zijn die elk 25% breed zijn, vullen deze gezamenlijk de volle breedte van het browservenster.
top: auto;
Eerder is voor een aantal deze vier <li>'s een hoogte vanaf de bovenkant van het browservenster opgegeven. Hier moeten ze worden neergezet vanaf de onderkant, wat gelijk hieronder met bottom
gebeurt.
Om bottom
te laten werken, moet top
eerst op auto
worden gezet, de standaardwaarde. Als top
én bottom
zijn opgegeven, 'wint' anders top
.
bottom: 10px;
10 px vanaf de onderkant van het browservenster neerzetten.
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Als die ontbreekt, wat hier het geval is, wordt gepositioneerd ten opzichte van het venster van de browser. Precies de bedoeling: door later ook de <main> met de tekst te positioneren ten opzichte van dat venster, blijft de tekst altijd iets boven de thumbnails staan, ongeacht de hoogte van het venster.
left: 0;
Bij een aantal van deze vier <li>'s geldt nog een eerder opgegeven left
. Die verstoort hier de plaatsing, die op een andere manier wordt geregeld. Dus wordt die hier verwijderd.
(Omdat voor de zesde, zevende en achtste <li> hieronder een eigen left
wordt opgegeven, geldt deze left
eigenlijk alleen voor de vijfde <li>. Maar het zit de andere <li>'s niet dwars, en door het hier op te geven, hoef je niet een aparte regel voor deze vijfde <li> te schrijven.)
#blok-link-6
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
#blok-link-5, #blok-link-6 {top: 382px;}
#blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8 {background: none; width: 25%; top: auto; bottom: 10px; left: 0;}
Het element met id="blok-link-6". De zesde <li>.
left: 25%;
Op 25% vanaf links neerzetten. Omdat er geen enkele voorouder met een positie is, geldt dit ten opzichte van het venster van de browser. De <li> wordt altijd op een kwart van de breedte van het venster gezet, ongeacht hoe breed het venster is.
#blok-link-7
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-7, #blok-link-8 {top: 553px;}
#blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8 {background: none; width: 25%; top: auto; bottom: 10px; left: 0;}
Het element met id="blok-link-7". De zevende <li>.
left: 50%;
Op 50% vanaf links neerzetten. Omdat er geen enkele voorouder met een positie is, geldt dit ten opzichte van het venster van de browser. De <li> wordt altijd halverwege de breedte van het venster gezet, ongeacht hoe breed het venster is.
#blok-link-8
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-7, #blok-link-8 {top: 553px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
#blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8 {background: none; width: 25%; top: auto; bottom: 10px; left: 0;}
Het element met id="blok-link-8". De achtste <li>.
margin-left: -1px;
Deze achtste <li> vult het laatste kwart van de breedte van het browservenster. Door afrondingsverschillen is dit soms net 1 px meer dan het venster breed is. Hierdoor verschijnt een horizontale scrollbalk onderaan het venster. Door deze achtste <li> 1 px terug naar links te zetten, wordt dat voorkomen. Deze verplaatsing is zo klein, dat zelfs een muggenzifter op hbo-niveau dit niet kan zien.
left: 75%;
Op 75% vanaf links neerzetten. Omdat er geen enkele voorouder met een positie is, geldt dit ten opzichte van het venster van de browser. De <li> wordt altijd op driekwart van de breedte van het venster gezet, ongeacht hoe breed het venster is.
#blok-link-5 .open
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.open {text-align: center; position: absolute; left: 1px;}
De elementen met class="open" die binnen het element met id="blok-link-5" liggen. Dat is er maar eentje: de <label> waarbinnen de pop-up, de toelichtende tekst, en dergelijke zitten.
Als de pop-up niet is geopend, is hiervan alleen het witte blokje met vraagteken zichtbaar.
margin-left: -90px;

Binnen de <li> zitten onder andere ook nog een <a> en de thumbnail. Deze zijn beide 180 px breed en worden halverwege de <li> neergezet.
Hier gelijk onder wordt ook de <label> halverwege de <li> gezet. Als je de <label> 90 px naar links terugzet, staat de linkerkant van de <label> gelijk met de linkerkant van de thumbnail en de <a>. (De thumb en de <a> zijn 180 px breed en staan horizontaal gecentreerd in de <li>, dus 90 px van beide staat links van het midden van de <li>.)
Van de <label> is, als de pop-up niet is geopend, alleen het witte vlakje met het vraagteken zichtbaar. De linkerkant van dit vlakje staat nu gelijk met de linkerkant van de thumbnail.
Op de afbeelding heeft de <li> even een rode border gekregen. De box-shadow bij de <a> is weggehaald. Zo is goed te zien, dat de thumbnail horizontaal is gecentreerd binnen de <li>. Door dat ook met het witte blokje met het vraagteken te doen, en dit dan de helft van de breedte van de thumbnail naar links terug te zetten, komt het netjes in de linkerbovenhoek van de thumbnail te staan.
Dat het in werkelijkheid ten opzichte van de <li> is neergezet en niet ten opzichte van de thumb, maakt niet uit. Voor het oog staan thumb en witte blokje goed ten opzichte van elkaar, en daar gaat het om.
left: 50%;
Horizontaal halverwege de eerste voorouder met een positie neerzetten. Dat is hier de <li>, waar de <label> in zit.
#blok-link-6 .open
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.open {text-align: center; position: absolute; left: 1px;}
#blok-link-2 .open, #blok-link-4 .open, #blok-link-6 .open, #blok-link-8 .open {left: auto; right: -1px;}
De elementen met class="open" die binnen het element met id="blok-link-6" liggen. Dat is er maar eentje: de <label> waarbinnen de pop-up, de toelichtende tekst, en dergelijke zitten.
Als de pop-up niet is geopend, is hiervan alleen het witte blokje met vraagteken zichtbaar.
margin-left: -89px; left: 50%;
Precies hetzelfde verhaal als iets hierboven bij #blok-link-5 .open, alleen is hier de verplaatsing naar links 1 px minder.
#blok-link-6 .vraagteken
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.vraagteken {background: rgba(255, 255, 255, 0.75); color: #666; display: block; width: 48px; height: 40px; font-size: 2.4em; line-height: 29px; border-radius: 5px 0 5px; padding-top: 10px; position: relative; top: 1px; z-index: 40;}
#blok-link-2 .vraagteken, #blok-link-4 .vraagteken, #blok-link-6 .vraagteken, #blok-link-8 .vraagteken {border-radius: 0 5px;}
De elementen met class="vraagteken" binnen het element met id="blok-link-6". De <span> die in de zesde <li> voor het witte blokje met het vraagteken zorgt.
border-radius: 5px 0;
Omdat voor rechts- en linksonder geen waarde is opgegeven, krijgen die automatisch dezelfde waarde als links‑ en rechtsboven. Hier staat dus eigenlijk 5px 0 5px 0
in de volgorde linksboven – rechtsboven – rechtsonder – linksonder.
Eerder stond dit zesde vraagteken rechts van de tekst. Nu staat het onder de tekst links van het midden. De eerder opgegeven ronde hoeken rechtsboven en linksonder moeten daarom worden omgekeerd naar ronde hoeken linksboven en rechtsonder.
#blok-link-7 .open, #blok-link-8 .open
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.open {text-align: center; position: absolute; left: 1px;}
#blok-link-2 .open, #blok-link-4 .open, #blok-link-6 .open, #blok-link-8 .open {left: auto; right: -1px;}
De elementen met class="open" die binnen het element met id="blok-link-7" of id="blok-link-8" liggen. Dat is er maar eentje: de <label> waarbinnen de pop-up, de toelichtende tekst, en dergelijke zitten.
Als de pop-up niet is geopend, is hiervan alleen het witte blokje met vraagteken zichtbaar.
margin-left: 43px; left: 50%;
Ook hier is het verhaal weer hetzelfde als bij #blok-link-5 .open, met één belangrijk verschil: de <label> en daarmee het erin zittende witte blokje wordt nu naar rechts verplaatst, omdat het aan de rechterkant van de thumb moet komen te staan. De verplaatsing van 43 px naar links zorgt ervoor, samen met de bij .vraagteken aan het witte blokje gegeven breedte van 48 px, dat het precies in de rechterbovenhoek van de thumb komt te staan.
#blok-link-7 .vraagteken
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.vraagteken {background: rgba(255, 255, 255, 0.75); color: #666; display: block; width: 48px; height: 40px; font-size: 2.4em; line-height: 29px; border-radius: 5px 0 5px; padding-top: 10px; position: relative; top: 1px; z-index: 40;}
De elementen met class="vraagteken" binnen het element met id="blok-link-7". De <span> die in de zevende <li> voor het witte blokje met het vraagteken zorgt.
border-radius: 0 5px;
Omdat voor rechts- en linksonder geen waarde is opgegeven, krijgen die automatisch dezelfde waarde als links‑ en rechtsboven. Hier staat dus eigenlijk 0 5px 0 5px
in de volgorde linksboven – rechtsboven – rechtsonder – linksonder.
Eerder stond dit zevende vraagteken links van de tekst. Nu staat het onder de tekst rechts van het midden. De eerder opgegeven ronde hoeken linksboven en rechtsonder moeten daarom worden omgekeerd naar ronde hoeken rechtsboven en linksonder.
#blok-link-3 .pop-up, #blok-link-4 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up {left: -705px;}
#blok-link-3 .pop-up, #blok-link-4 .pop-up {top: -170px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
De elementen met class="pop-up" binnen een element met id="blok-link-3" of id="blok-link-4". Dit zijn de <span>'s die voor de pop-ups bij de knoppen op de tweede rij, de middelste, zorgen.
top: -206px;
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier label.open
.
De kleinst mogelijke hoogte van het venster van de browser, waarop nog pop-ups worden getoond, is 543 px. Als het venster deze hoogte heeft, staat de bovenkant van de pop-up precies tegen de bovenkant van het venster aan. In hogere vensters staan ze iets meer of minder onder de bovenkant van het venster.
#blok-link-5 .pop-up
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-5 .pop-up, #blok-link-6 .pop-up {top: -255px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
De elementen met class="pop-up" binnen een element met id="blok-link-5". Dit is de <span> die voor de pop-up bij de knop linksonder zorgt.
top: -326px;
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier label.open
.
Op deze hoogte staat de onderkant van de pop-up precies gelijk met de onderkant van de onderste rij thumbs.
#blok-link-6 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up {left: -705px;}
#blok-link-5 .pop-up, #blok-link-6 .pop-up {top: -255px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
De elementen met class="pop-up" binnen een element met id="blok-link-6". Dit is de <span> die voor de pop-up bij de tweede knop van links op de onderste rij knoppen zorgt.
top: -326px;
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Dat is hier label.open
.
Op deze hoogte staat de onderkant van de pop-up precies gelijk met de onderkant van de onderste rij thumbs.
left: 181px;
Op deze afstand vanaf links staat de pop-up precies rechts van de thumbnail.
De zesde thumbnail stond eerst rechts van de tekst. Nu staat deze onder de tekst. Daarom moet ook de horizontale positie van de pop-up worden aangepast. Eerst stond deze links van de thumbnail, nu rechts.
#blok-link-7 .pop-up
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-7 .pop-up, #blok-link-8 .pop-up {top: -326px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
De elementen met class="pop-up" binnen een element met id="blok-link-7". Dit is de <span> die voor de pop-up bij de derde knop van links op de onderste rij knoppen zorgt.
left: -705px;
Met deze verplaatsing naar links staat de pop-up precies links van de thumbnail.
De zevende thumbnail stond eerst links van de tekst. Nu staat deze onder de tekst. Daarom moet ook de horizontale positie van de pop-up worden aangepast. Eerst stond deze rechts van de thumbnail, nu links.
#blok-link-6 a
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
a {width: 120px; height: 108px; position: absolute; top: 8px; left: 8px;}
.blok a {-webkit-animation: bugfix infinite 1s; box-shadow: 4px 3px 4px 1px black; display: block; width: 180px; height: 161px; text-align: center; margin: 0 auto; border: black solid 1px; border-radius: 5px; position: relative; top: 0; left: 0;}
#blok-link-2 a, #blok-link-4 a, #blok-link-6 a, #blok-link-8 a {box-shadow: -4px 3px 4px 1px black;}
input:not(:checked) ~ a:focus {background: rgba(255, 255, 255, 0.5);}
De links binnen het element met id="blok-link-6". Dit is de link naar de achterliggende pagina in de zesde <li>.
box-shadow: 4px 3px 4px 1px black;
Deze <a> hoort bij een thumbnail die eerst rechts van de tekst stond. Nu staat deze linksonder de tekst. Daarom moet de box-shadow niet meer links, maar rechts van de <a> worden neergezet.
Hoe box-shadow precies werkt, is te vinden bij box-shadow: 4px 6px 4px 1px black;.
left: 1px;
Kleine correctie om dubbele border links van thumbnail te voorkomen.
Waarom dit precies nodig is, heb ik verder niet uitgezocht. De plaatsing van diverse elementen is nogal ingewikkeld. Mogelijk zou je deze kleine correctie overbodig kunnen maken, maar dat vergt waarschijnlijk uren zoeken. En controleren of dat niet elders weer problemen veroorzaakt. Dit werkt, dus houd ik het zo.
#blok-link-6 .naam::after
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
#blok-link-2 .naam::after, #blok-link-4 .naam::after, #blok-link-6 .naam::after, #blok-link-8 .naam::after {left: auto; right: 3px;}
.blok a:visited .naam::after, #blok-link-4 a:visited .naam::after, #blok-link-8 a:visited .naam::after {color: black;}
input:checked ~ a .naam::after, .open:hover + a .naam::after, .focus-open:focus ~ a .naam::after {display: none;}
Binnen elke <a> zit een span met class="naam". Hierbinnen zit de korte naam van de achterliggende pagina. Met behulp van ::after
worden bij deze <span>'s pseudo-elementen gemaakt. Deze zorgen voor het verschijnen van de vinkjes naast het vraagteken, als een pagina is bezocht. Deze selector is alleen bedoeld voor het pseudo-element dat in het element met id="blok-link-6" zit. Het vinkje naast het vraagteken bij de zesde thumb.
margin-left: -86px; left: 50%;
Bij #blok-link-6 .open is het witte blokje met het vraagteken naar links verplaatst, omdat de zesde thumbnail nu links van het midden staat.
Hier wordt het vinkje ook naar links verplaatst. Omdat dit op dezelfde manier gebeurt als bij het blokje met het vraagteken, staat het vinkje goed ten opzichte van het vraagteken.
#blok-link-7 a
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
a {width: 120px; height: 108px; position: absolute; top: 8px; left: 8px;}
.blok a {-webkit-animation: bugfix infinite 1s; box-shadow: 4px 3px 4px 1px black; display: block; width: 180px; height: 161px; text-align: center; margin: 0 auto; border: black solid 1px; border-radius: 5px; position: relative; top: 0; left: 0;}
input:not(:checked) ~ a:focus {background: rgba(255, 255, 255, 0.5);}
De links binnen het element met id="blok-link-7". Dit is de link naar de achterliggende pagina in de zevende <li>.
box-shadow: -4px 3px 4px 1px black;
Deze <a> hoort bij een thumbnail die eerst links van de tekst stond. Nu staat deze rechtsonder de tekst. Daarom moet de box-shadow niet meer rechts, maar links van de <a> worden neergezet.
Hoe box-shadow precies werkt, is te vinden bij box-shadow: 4px 6px 4px 1px black;.
#blok-link-7 .naam::after
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam::after {content: ""; color: #ddd; width: 6px; height: 12px; border: solid; border-width: 0 2px 2px 0; border-top-right-radius: 3px; border-bottom-left-radius: 5px; pointer-events: none; position: absolute; top: -50px; left: 5px; -ms-transform: rotate(45deg) skew(14deg); -webkit-transform: rotate(45deg) skew(14deg); transform: rotate(45deg) skew(14deg);}
.blok a:visited .naam::after, #blok-link-4 a:visited .naam::after, #blok-link-8 a:visited .naam::after {color: black;}
input:checked ~ a .naam::after, .open:hover + a .naam::after, .focus-open:focus ~ a .naam::after {display: none;}
Binnen elke <a> zit een span met class="naam". Hierbinnen zit de korte naam van de achterliggende pagina. Met behulp van ::after
worden bij deze <span>'s pseudo-elementen gemaakt. Deze zorgen voor het verschijnen van de vinkjes naast het vraagteken, als een pagina is bezocht. Deze selector is alleen bedoeld voor het pseudo-element dat in het element met id="blok-link-7" zit. Het vinkje naast het vraagteken bij de zevende thumb.
margin-left: 80px; left: 50%;
Bij #blok-link-7 .open, #blok-link-8 .open is het witte blokje met het vraagteken naar rechts verplaatst, omdat de zevende thumbnail nu rechts van het midden staat.
Hier wordt het vinkje ook naar rechts verplaatst. Omdat dit op dezelfde manier gebeurt als bij het blokje met het vraagteken, staat het vinkje goed ten opzichte van het vraagteken.
#blok-link-6 input:checked ~ a .naam
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
.blok a:focus .naam {color: blue;}
input:checked ~ a .naam {background: white; color: blue; width: 141px; height: 39px; font-size: 20px; margin: 0 0 0 39px; border: black solid 1px; border-top-right-radius: 5px; top: -41px; left: -1px;}
#blok-link-2 input:checked ~ a .naam, #blok-link-4 input:checked ~ a .naam, #blok-link-6 input:checked ~ a .naam, #blok-link-8 input:checked ~ a .naam {margin: 0 39px 0 0; border-radius: 5px 0 0;}
input:not(:checked) + .open:hover ~ a .naam, .focus-open:focus ~ input:not(:checked) ~ a .naam {background: white; color: black; height: 39px; font-size: 22px; margin: 0; border: black solid 1px; border-radius: 5px 5px 0 0; top: -41px; left: -1px;}
Als een <input> is geselecteerd wordt de bij die <input> horende pop-up getoond. Gelijktijdig wordt de korte naam van de bij de <input> horende achterliggende pagina getoond boven de thumbnail.
Omdat de naam binnen een <span> zit, die weer binnen de link naar de achterliggende pagina zit, werkt de naam als een link: bij aanraking of aanklikken van de naam, opent de achterliggende pagina.
#blok-link-6
: het element met id="blok-link-6", de zesde <li>.
input:checked
: als een <input> is geselecteerd. Binnen elke <li> staat onder andere een <input> van de soort radioknop. Dit is een tamelijk grove selector, omdat hij voor élke <input> geldt. Maar de rest van de selector beperkt dit tot een heel specifieke volgorde, die alleen binnen een <li> voorkomt.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: input
voor de ~
en a
na de ~
hebben beide als ouder de <li>, waarbinnen ze staan.
a
: alle links. Dat is er hier maar eentje, de link naar de achterliggende pagina.
.naam
: alle elementen met class="naam". Dat is er ook maar eentje: de binnen de <a> zittende <span> met de korte naam van de achterliggende pagina.
In normale mensentaal: als binnen de zesde <li> een radioknop is geselecteerd, doe dan iets met de naam die in span.naam
binnen de op die radioknop volgende link zit.
margin: 0 0 0 39px;
De zesde thumbnail stond eerst rechts van de tekst. Nu staat hij daar linksonder. Daarom is het sluitkruisje boven de thumbnail van rechts naar links verplaatst. Daarom moet de marge bij de naam ook van rechts naar links worden verplaatst, zodat de naam niet onder, maar naast het sluitkruisje komt te staan.
De verschillende marges, top
en left
die op verschillende plaatsen worden gebruikt om de naam op de goede plaats te zetten, zouden mogelijk iets efficiënter gebruikt kunnen worden. Dat scheelt echter niet zo heel veel css, en het is heel veel werk dit steeds in alle browsers in tig verschillende resoluties te testen.
Deze instellingen werken, en daarom laat ik ze zo.
border-top-right-radius: 5px;
Hoek rechtsboven ook rond maken.
#blok-link-7 input:checked ~ a .naam
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.naam {opacity: 0;}
.naam {color: transparent; opacity: 1; display: block; width: 180px; height: 39px; font-size: 25px; line-height: 34px; text-decoration: underline; margin-top: 50px; position: absolute; z-index: 50;}
.blok a:focus .naam {color: blue;}
input:checked ~ a .naam {background: white; color: blue; width: 141px; height: 39px; font-size: 20px; margin: 0 0 0 39px; border: black solid 1px; border-top-right-radius: 5px; top: -41px; left: -1px;}
input:not(:checked) + .open:hover ~ a .naam, .focus-open:focus ~ input:not(:checked) ~ a .naam {background: white; color: black; height: 39px; font-size: 22px; margin: 0; border: black solid 1px; border-radius: 5px 5px 0 0; top: -41px; left: -1px;}
Deze selector is precies hetzelfde als die iets hierboven bij #blok-link-6 input:checked ~ a .naam, alleen is deze voor het element met id="blok-link-7", de zevende <li>.
margin: 0 39px 0 0; border-top-left-radius: 5px; border-top-right-radius: 0;
Ook dit is precies hetzelfde als bij #blok-link-6 input:checked ~ a .naam iets hierboven, alleen moeten marge en ronde hoek aan de andere kant komen.
#blok-link-5 input:checked ~ .sluit
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit {display: none;}
.sluit {-webkit-animation: bugfix infinite 1s; background: white; color: red; display: block; width: 38px; height: 39px; overflow: hidden; font-size: 77px; line-height: 25px; border: black solid; border-width: 1px 1px 0; border-top-left-radius: 5px; position: absolute; top: -40px; left: -20000px; z-index: 50;}
input:checked ~ .sluit {left: 0;}
#blok-link-5
: het element met id="blok-link-5". De vijfde <li>
input:checked
: als een <input> – dat zijn hier radioknoppen – is geselecteerd.
~
: het hierachter staande element moet ergens in de html staan, na het hiervoor staande element. Het hoeft er, anders dan bij de +
, niet gelijk op te volgen, als het maar ergens na het eerste element in de html staat.
De enige voorwaarde is verder dat het voor en het na de ~
staande element dezelfde ouder hebben. Dat is hier het geval: de <input> voor de ~
en label.sluit
na de ~
hebben beide als ouder dezelfde <li>.
.sluit
: de elementen met class="sluit". Onderaan elke <li> zit een label.sluit. Hierbinnen zit de letter 'x'. Deze wordt wat opgeleukt tot een rood sluitkruisje.
In normale mensentaal: doe iets met de vijfde label.sluit
, het sluitkruisje, als de ervoor zittende radioknop is geselecteerd.
margin-left: -90px; left: 50%;
Er wordt gepositioneerd ten opzichte van de eerste voorouder die een positie heeft. Dat is de <li> waar deze <label> in zit. Bij #blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8 heeft de <li> een breedte van 25% van de breedte van het browservenster gekregen. Omdat de breedte van het venster kan variëren, kan ook de breedte van de <li> variëren. Daarom is een simpele left
met een vaste waarde niet meer voldoende.
Het sluitkruisje wordt nu halverwege de <li> gezet met left: 50%;
. Door het weer 90 px terug naar links te zetten, komt het precies boven de linkerkant van de thumbnail te staan, want die staat ook horizontaal in het midden van de <li>. De thumb is 180 px breed, dus de linkerzijkant daarvan ligt ook 90 px naar links.
#blok-link-6 input:checked ~ .sluit
{margin-left: -90px; border-radius: 5px 0 0; left: 50%;}
#blok-link-7 input:checked ~ .sluit
{margin-left: 51px; border-radius: 0 5px 0 0; left: 50%;}
#blok-link-8 input:checked ~ .sluit
{margin-left: 49px; left: 50%;}
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
input, .vraagteken, .sluit{display: none;}
.sluit {-webkit-animation: bugfix infinite 1s; background: white; color: red; display: block; width: 38px; height: 39px; overflow: hidden; font-size: 77px; line-height: 25px; border: black solid; border-width: 1px 1px 0; border-top-left-radius: 5px; position: absolute; top: -40px; left: -20000px; z-index: 50;}
input:checked ~ .sluit {left: 0;}
#blok-link-2 input:checked ~ .sluit, #blok-link-4 input:checked ~ .sluit, #blok-link-6 input:checked ~ .sluit, #blok-link-8 input:checked ~ .sluit {width: 41px; border-radius: 0 5px 0 0; left: 139px;}
De sluitkruisjes binnen de zesde, zevende en achtste <li> worden op precies dezelfde manier opnieuw gepositioneerd, als hierboven bij #blok-link-5 input:checked ~ .sluit is gebeurd voor het vijfde sluitkruisje. Alleen verschillen de marges wat en moeten sommige ronde hoeken worden verplaatst.
#blok-link-5 img, #blok-link-6 img, #blok-link-7 img, #blok-link-8 img
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
img {box-shadow: 4px 6px 4px 1px black; width: 120px; max-width: 100%; height: auto; float: left; margin: 3px 10px 6px 3px; border: black solid 1px; border-radius: 5px;}
img {box-shadow: none; width: auto; margin: 0;}
De afbeeldingen binnen de elementen met id="blok-link-5", id="blok-link-6", id="blok-link-7" en id="blok-link-8". Dit zijn de thumbnails binnen de vijfde, zesde, zevende en achtste <li>. Deze stonden eerst links en rechts van de tekst, maar komen daar nu onder te staan.
margin-left: -90px; position: relative; left: 50%;

Bij #blok-link-5, #blok-link-6, #blok-link-7, #blok-link-8 hebben de onderste vier <li>'s elk een breedte van 25% van de breedte van het browservenster gekregen. Hierdoor zet de eerder opgegeven float: left;
de <img>'s niet meer op de goede plaats, omdat ze hierdoor helemaal links in de <li> worden gezet.
Op de afbeelding hebben de vier <li>'s een rode border gekregen, zodat ze zijn te zien. Elke <li> vult een kwart van de breedte van het browservenster. Zonder correctie komen de <img>'s helemaal links in de <li> te staan, in plaats van netjes te worden verdeeld over de breedte van het venster, zoals op de afbeelding is te zien.
Door de <img>'s relatief te positioneren, kunnen ze met left: 50%;
horizontaal in het midden van de <li> worden neergezet. (Een verplaatsing met als eenheid een percentage wordt, ook bij een relatieve positie, gemeten ten opzichte van de ouder van het element. De ouder van de <img> is de <li>, dus de <img> wordt halverwege de <li> neergezet.)
De <img>'s zijn 180 px breed. Als ze 90 px, de halve breed, naar links worden teruggezet, staan ze precies horizontaal gecentreerd binnen de <li>'s. En omdat elke <li> 25% van de breedte van het browservenster vult, staan ze nu netjes verdeeld over het venster, ongeacht de breedte van het venster.
main
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
main {display: block; max-width: 700px; margin: 0 auto; padding: 5px;}
main {background: #eee; color: black; width: calc(100% - 412px); max-width: 860px; overflow: auto; -webkit-overflow-scrolling: touch; border: black solid; border-width: 0 1px; position: absolute; top: 40px; right: 200px; bottom: 0; left: 200px;}
Alle <main>'s. Dat is er maar eentje. Binnen <main> staat de belangrijkste inhoud van de pagina. Dat is hier voornamelijk opvultekst, maar normaal genomen staat daar – hopelijk – wel iets interessants.
bottom: 181px;
Er wordt gepositioneerd ten opzichte van de eerste voorouder die zelf een positie heeft. Als die er niet is, zoals hier het geval is, wordt gepositioneerd ten opzichte van het venster van de browser.
Aan de onderkant wordt een ruimte van 181 px vrijgehouden, waarin de thumbnails kunnen staan, zonder dat deze over de tekst in <main> heen komen te staan.
main::before
Bij het element <main> wordt met behulp van ::before
een pseudo-element gemaakt. Dit pseudo-element wordt gebruikt om aan de onderkant van <main> een gradiënt neer te zetten. Deze gradiënt staat over ruwweg de onderste drie regels van de tekst. Bovenaan is hij doorzichtig, onderaan ondoorzichtig.
Op touchscreens is geen scrollbalk aanwezig. Daardoor is niet duidelijk dat de tekst onderaan nog doorloopt. Als het 'n beetje ongelukkig uitkomt en de onderste zichtbare regel is toevallig de laatste regel van een paragraaf, lijkt het of er niet meer tekst is.
Met de gradiënt wordt duidelijk gemaakt dat de tekst nog doorloopt.
content: "";
Dit moet altijd worden opgegeven bij een met behulp van ::before
gemaakt pseudo-element, ook als er geen echte tekst of zo aanwezig is. Dat geef je aan met twee aanhalingstekens, waar niets tussen staat.
background-image: -webkit-linear-gradient(to bottom, rgba(204, 204, 204, 0) 0%, rgba(204, 204, 204, 0.5) 20%, rgba(204, 204, 204, 0.8) 80%, rgba(204, 204, 204, 1) 100%); background-image: linear-gradient(to bottom, rgba(204, 204, 204, 0) 0%, rgba(204, 204, 204, 0.5) 20%, rgba(204, 204, 204, 0.8) 80%, rgba(204, 204, 204, 1) 100%);
Hier staat in feite twee keer hetzelfde: background-image: linear-gradient(to bottom, rgba(204, 204, 204, 0) 0%, rgba(204, 204, 204, 0.5) 20%, rgba(204, 204, 204, 0.8) 80%, rgba(204, 204, 204, 1) 100%);
. Waarom dat zo is, staat bij De voorvoegsels -moz-, -ms- en -webkit-. Hieronder wordt alleen de tweede vorm uitgelegd, want dat is de vorm volgens de uiteindelijke standaard.
Internet Explorer 9 kent linear-gradient
niet en negeert deze regel daarom. Oudere versies van Android browser en UC browser op Android hebben ook geen gradiënt, omdat bij de positionering calc()
wordt gebruikt, wat deze browsers niet kennen.
Je kunt een gradiënt zelf uitvogelen, maar vaak is het makkelijker om gebruik te maken van een gradiënt-editor, zoals die op colorzilla.com. Deze levert ook gelijk de oudere vormen van de code, zodat je je daar zelf niet in hoeft te verdiepen. Je kunt zelfs code voor oudere versies van Internet Explorer laten maken. (Nachtmerrie-code die gebruik maakt van een eigen techniek van Microsoft: filters.)
(Overigens is het wel raadzaam die code op te schonen, omdat er wel heel erg veel code voor heel erg oude versies van verschillende browsers in staat.)
In dit geval heb ik geen gradiënt-editor gebruikt, omdat het hier allemaal mooie ronde getallen en codes zijn.
linear-gradient
valt in een aantal delen uiteen:
to bottom
: de kant waar de gradiënt naartoe gaat. Omdat alleen de onderkant is opgegeven, loopt de gradiënt loodrecht van boven naar onder.
Na de richting staan vier keer twee waarden, gescheiden door een komma. De eerste waarde is steeds de kleur, de tweede de plaats waar die kleur staat.
rgba(204, 204, 204, 0) 0%
: de kleur rgba(204, 204, 204, 0)
(wit) op 0% vanaf de bovenkant neerzetten (dat is helemaal bovenaan).
Dit is een lichtgrijze kleur, die volledig doorzichtig is. (Hoe rgba()
precies werkt, is te vinden bij background: rgba(255, 255, 255, 0.75);.)
rgba(204, 204, 204, 0.5) 20%
: de kleur is hetzelfde als gelijk hierboven, maar nu is de kleur halfdoorzichtig: 0.5, waardoor de tekst vager wordt. Deze doorzichtigheid wordt op 20% vanaf de bovenkant bereikt.
De lichtgrijze gradiënt verandert geleidelijk van volledig doorzichtig (0%, bovenaan) in halfdoorzichtig (20% vanaf de bovenkant).
rgba(204, 204, 204, 0.8) 80%
: de kleur is nog steeds hetzelfde als hierboven, maar nu is de gradiënt vrijwel ondoorzichtig: 0.8, waardoor de tekst nog moeilijk te zien is. Deze doorzichtigheid wordt op 80% vanaf de bovenkant bereikt.
De lichtgrijze gradiënt verandert geleidelijk van halfdoorzichtig (20% vanaf de bovenkant) in vrijwel ondoorzichtig (80% vanaf de bovenkant).
rgba(204, 204, 204, 1) 100%)
: de kleur is nog steeds hetzelfde als hierboven, maar nu is de gradiënt volledig ondoorzichtig: 1. Deze ondoorzichtigheid wordt op 100% vanaf de bovenkant bereikt, oftewel: aan de onderkant.
De lichtgrijze gradiënt verandert geleidelijk van vrijwel ondoorzichtig (80% vanaf de bovenkant) in volledig ondoorzichtig (100% vanaf de bovenkant.)
Er zijn vier plaatsen opgegeven, waartussen de doorzichtigheid verandert: tussen 0% en 20%, tussen 20% en 80%, en tussen 80% en 100%. De overgang tussen de verschillende graden van doorzichtigheid verloopt geleidelijk, dat regelt de browser verder. Dit is een vrij simpele gradiënt, maar je kunt ook tig kleuren op tig plaatsen aangeven. En ook nog in allerlei richtingen.
width: calc(100% - 402px);
Hieronder wordt het pseudo-element fixed gepositioneerd. Dat betekent dat het wordt gepositioneerd ten opzichte van het venster van de browser. Ook breedte en dergelijke worden berekend ten opzichte van het venster, niet ten opzichte van <main>, de ouder van het pseudo-element.
<main> heeft bij main een breedte van calc(100% – 412px)
gekregen: 412 px smaller dan het venster van de browser. Omdat het pseudo-element alleen de tekst binnen <main> moet afdekken, en niet de thumbnails ernaast, moet het pseudo-element dezelfde breedte krijgen. Met een kleine correctie.
calc(100%)
zou de breedte van het venster van de browser opleveren. Dat is weinig interessant. Maar met calc()
kun je berekeningen maken met verschillende eenheden. Van de 100% wordt 402 px afgetrokken, waardoor het pseudo-element altijd 402 px smaller is dan het venster van de browser, ongeacht de breedte van het venster.
Van <main> is 412 px van de 100% vensterbreedte afgetrokken. Het pseudo-element is dus 10 px smaller dan <main>. Iets hieronder wordt het ook nog met margin-left: -5px;
5 px naar links gezet. Met deze breedte en de verschuiving van 5 px dekt het pseudo-element, en dus de daarin zittende gradiënt, precies de tekst binnen <main> af.
Althans: niet alleen de tekst wordt afgedekt, maar ook de scrollbalk aan de rechterkant van <main>. Dat is ook de reden dat het pseudo-element 10 px smaller moet zijn en 5 px naar links wordt verplaatst. De scrollbalk is ongeveer 17 px breed en komt buiten <main> te staan. Met deze breedte en verplaatsing naar links staat de linkerkant van het pseudo-element precies gelijk met de linkerkant van <main>, en staat de rechterkant van het pseudo-element precies gelijk met de rechterkant van de scrollbalk bij <main>
Het onderste deel van de scrollbalk wordt dus afgedekt door het pseudo-element, maar dat is nauwelijks een probleem, omdat de gradiënt doorzichtig is. Als de gradiënt binnen de scrollbalk zou vallen, wat makkelijk is te doen, zou je op touchscreens zonder scrollbalk rechts van de gradiënt een lelijke kier van 17 px breed overhouden.
max-width: 870px;
De breedte van het pseudo-element wordt genomen ten opzichte van het venster van de browser. In heel brede vensters zou het pseudo-element, en dus de daarin zittende gradiënt, daardoor breder kunnen worden dan <main>. Een maximumbreedte voorkomt dat.
height: 70px;
Hoogte. Dit bestrijkt ongeveer 3 regels tekst. Omdat de gradiënt hieronder met bottom: 181px;
aan de onderkant van <main> wordt neergezet, wordt de hoogte vanaf de onderkant van <main> gemeten.
margin-left: -5px;
Kleine correctie om de linkerkant van de gradiënt gelijk te krijgen met de linkerkant van <main>.
pointer-events: none;
Het pseudo-element met de gradiënt staat over de onderste regels tekst heen. Hierdoor kan deze tekst niet worden geselecteerd om bijvoorbeeld te worden gekopieerd. Dit zorgt ervoor dat een aanraking, muisklik, en dergelijke als het ware door de gradiënt heen naar het onderliggende element gaan: de <main> met de tekst. Hierdoor is ook de tekst onder de gradiënt gewoon te selecteren, kopiëren, enz.
position: fixed;
De gradiënt positioneren ten opzichte van het venster van de browser. Hierdoor scrolt de gradiënt niet mee met de tekst binnen <main>, maar blijft altijd aan de onderkant van <main> staan.
Een met behulp van ::before
gemaakt pseudo-element is van zichzelf een inline-element. Daardoor zijn eigenschappen als breedte en hoogte niet te gebruiken. Door het fixed te positioneren verandert het in 'n soort blok-element, waardoor dit soort eigenschappen wel is te gebruiken.
bottom: 181px;
Op 181 vanaf de onderkant van het venster van de browser neerzetten. Bij main is ook <main> op deze afstand vanaf de onderkant van het venster neergezet. Hierdoor staat de gradiënt precies over de onderste regels van de tekst in <main>.
css voor vensters minimaal 900 px breed
@media screen and (min-width: 900px)
De opbouw van deze regel staat beschreven bij @media screen and (min-width: 763px) and (min-height: 543px). Er zijn twee verschillen: het browservenster moet minimaal 900 px breed zijn, en de hoogte is onbelangrijk.
Binnen deze media query wordt alleen de lettergrootte van de <h1> iets groter gemaakt voor deze bredere vensters.
h1
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
h1 {background: #eee; color: black; max-width: 700px; overflow: auto; font-size: 1em; line-height: 30px; text-align: center; margin: 0 auto;}
h1 {width: calc(100% - 402px); max-width: 870px; height: 40px; overflow: auto; line-height: 40px; margin: 0 auto; border: black solid; border-width: 0 1px; position: absolute; left: 200px; right: 200px;}
Alle <h1>'s. Dat is er maar eentje: de belangrijkste kopregel op de pagina.
font-size: 1.6em;
Grotere letter.
Als eenheid wordt de relatieve eenheid em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
font-weight: normal;
Een <h1> is van zichzelf vet. In combinatie met de grotere letter hierboven doet dat aan De Telegraaf bij de aankondiging van de Derde Wereldoorlog denken. Ik houd niet van De Telegraaf en ik houd niet van wereldoorlogen, dus niet vet, maar gewoon weergeven.
css voor vensters maximaal 712 px hoog en minimaal 763 px en maximaal 1073 px breed
@media screen and (max-height: 712px) and (min-width: 763px) and (max-width: 1073px)
De opbouw van deze regel staat beschreven bij @media screen and (min-height: 543px) and (max-height: 712px) and (min-width: 763px). Er zijn twee verschillen: er is geen minimumhoogte en er is een maximumbreedte van 1073 px.
In browservensters van deze breedte worden pop-ups getoond. Maar de twee middelste pop-ups onderaan zijn te groot: ze vallen gedeeltelijk buiten het venster van de browser. Daarom worden die zesde en zevende pop-up hier verkleind voor deze vensters.
#blok-link-6 .pop-up, #blok-link-7 .pop-up
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up {left: -705px;}
#blok-link-5 .pop-up, #blok-link-6 .pop-up {top: -255px;}
#blok-link-7 .pop-up, #blok-link-8 .pop-up {top: -326px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
#blok-link-6 .pop-up {top: -326px; left: 181px;}
#blok-link-7 .pop-up {left: -705px;}
De elementen met class="pop-up" binnen een element met id="blok-link-6" of id="blok-link-7". De <span>'s met de eigenlijke pop-up binnen de zesde en zevende <li>.
top: -240px; left: 81px;
Hier gelijk onder worden deze pop-ups met behulp van transform: scale()
verkleind, omdat ze anders deels buiten het venster van de browser vallen. De pop-ups blijven echter op de oorspronkelijke plaats staan. Hier worden ze neergezet op een plaats die beter bij de verkleining past.
(Voor de zevende pop-up wordt iets lager left
weer aangepast. De left
hier is geschikt voor de zesde pop-up.)
-ms-transform: scale(0.65); -webkit-transform: scale(0.65); transform: scale(0.65);
Hier staat in feite drie keer hetzelfde: transform: scale(0.65);
. Waarom dat zo is, staat bij De voorvoegsels -moz-, -ms- en -webkit-.
De simpelste manier om deze twee pop-ups te verkleinen, zodat ze binnen het venster van de browser passen, is ze gewoon te schalen. Door ze te verkleinen tot 0,65 keer de oorspronkelijke grootte (ruwweg te verkleinen tot twee derde), passen ze binnen deze smallere vensters.
#blok-link-7 .pop-up
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-7 .pop-up, #blok-link-8 .pop-up {top: -326px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
#blok-link-7 .pop-up {left: -705px;}
#blok-link-6 .pop-up, #blok-link-7 .pop-up {top: -240px; left: 81px; -ms-transform: scale(0.65); -webkit-transform: scale(0.65); transform: scale(0.65);}
Het element met class="pop-up" binnen het element met id="blok-link-7". De <span> met de eigenlijke pop-up binnen de zevende <li>.
left: -606px;
De horizontale positie van de zevende pop-up aanpassen aan de gelijk hierboven opgegeven verkleining.
#blok-link-6 .pop-up-tekst, #blok-link-7 .pop-up-tekst
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up-tekst {-moz-hyphens: auto; -ms-hyphens: auto; -webkit-hyphens: auto; hyphens: auto;}
.pop-up-tekst {background: white; color: black; display: block; width: 540px; height: 125px; overflow: auto; font-size: 0.8em; -moz-hyphens: manual; -ms-hyphens: manual; -webkit-hyphens: manual; hyphens: manual; border-bottom: black solid 1px; padding: 3px;}
De elementen met class="pop-up-tekst" binnen een element met id="blok-link-6" of id="blok-link-7". Dit zijn de <span>'s, waarbinnen de tekst boven de afbeelding in de zesde en zevende pop-up staat.
font-size: 1.3em;
Hier iets boven zijn de zesde en zevende pop-up verkleind, zodat ze binnen het venster van de browser passen. Hierdoor is echter ook de tekst verkleind, waardoor deze slecht leesbaar wordt. Daarom wordt de tekst hier weer vergroot.
Als eenheid wordt de relatieve eenheid em
gebruikt, omdat bij gebruik van een absolute eenheid zoals px
niet alle browsers de lettergrootte kunnen veranderen. Zoomen kan wel altijd, ongeacht welke eenheid voor de lettergrootte wordt gebruikt.
css voor vensters minimaal 1500 px breed en minimaal 712 px hoog
@media screen and (min-width: 1500px) and (min-height: 710px)
De opbouw van deze regel staat beschreven bij @media screen and (min-width: 763px) and (min-height: 543px). Er zijn twee verschillen: het browservenster moet minimaal 1500 px breed zijn, en de hoogte minimaal 710 px.
In brede vensters zouden de thumbnails te ver links en rechts van de tekst komen te staan, wat lelijke open ruimtes oplevert. Dat wordt hier gecorrigeerd.
.blok
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
#blok-link-1, #blok-link-2 {top: 41px;}
#blok-link-3, #blok-link-4 {top: 211px;}
#blok-link-5, #blok-link-6 {top: 382px;}
#blok-link-7, #blok-link-8 {top: 553px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
De elementen met class="blok". Dit zijn de <li>'s, waarbinnen de thumbnails, pop-ups, en dergelijke staan. Elk in een eigen <li>.
margin-left: -630px; left: 50%;
Om de <li>'s en de daarin zittende thumbnails en dergelijke op de juiste plaats neer te kunnen zetten. Er wordt gepositioneerd ten opzichte van de eerste voorouder, die zelf een positie heeft. Als er geen voorouder met een positie is, zoals hier het geval is, wordt gepositioneerd ten opzichte van het venster van de browser. De <li>'s, en dus de daarin zittende thumbnails, worden horizontaal in het midden van het venster neergezet.
De <li>'s, en de daarin zittende thumbs, zijn 180 px breed. Door ze weer 630 px naar links terug te zetten, staan ze 20 px links van de tekst in <main>.
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
li {background: #eee; color: black; box-sizing: border-box; width: 100%; float: left; margin-top: -1px; border: black solid 1px; padding: 4px 4px 10px; position: relative;}
.blok {width: 180px; height: 161px; border: none; padding: 0; position: absolute; left: 9px;}
.blok {margin-left: -630px; left: 50%;}
#blok-link-1, #blok-link-2 {top: 41px;}
#blok-link-3, #blok-link-4 {top: 211px;}
#blok-link-5, #blok-link-6 {top: 382px;}
#blok-link-7, #blok-link-8 {top: 553px;}
#blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 {left: auto; right: 11px;}
De elementen met id="blok-link-2", id="blok-link-4", id="blok-link-6" en id="blok-link-8". De tweede, vierde, zesde en achtste <li>. De <li>'s die rechts van de tekst komen te staan.
margin-left: 446px;
Hier iets boven bij .blok {margin-left: -630px; left: 50%;} zijn alle <li>'s met margin-left: -630px; terug naar links gezet. Dat is leuk voor de <li>', met de daarin zittende thumbnails, die links van de tekst moeten komen, maar niet voorde <li>'s die rechts daarvan moeten komen. Daarom worden hier de vier <li>'s die rechts moeten komen naar rechts verplaatst. Met deze marge staan ze 20 px rechts van de tekst.
left: 50%;
Dit staat ook al iets hierboven bij .blok {margin-left: -630px; left: 50%;}. Toch moet het hier worden herhaald.
Voor deze vier <li>'s is eerder bij #blok-link-2, #blok-link-4, #blok-link-6, #blok-link-8 left: auto;
opgegeven. In die selectors wordt een id gebruikt. In de selector iets hierboven bij .blok
wordt een class gebruikt. En een selector met een id 'wint', heeft meer specificiteit, dan een selector met een class.
Normaal genomen 'wint' lager staande css van hoger staande, maar niet in dit geval. In de selector hier worden ook vier id's gebruikt. Door de left: 50%;
hier nog eens te herhalen, gaat het gewicht van de id meespelen en nu 'wint' dit wel van de eerdere selector met id's, omdat het lager in de css staat.
css voor vensters minimaal 763 px breed en minimaal 543 px hoog
De css hieronder is voor elke pagina anders. Daarom staat deze op de site bovenaan de pagina. Het heeft geen zin de externe stylesheet nodeloos groot te maken met css, die slechts op één pagina wordt gebruikt. Omdat het op de site apart staat, is het hier ook apart gezet. Normaal genomen zou je het natuurlijk combineren met de eerder opgegeven css voor deze maat browservensters.
@media screen and (min-width: 763px) and (min-height: 543px)
De opbouw van deze regel staat beschreven bij @media screen and (min-width: 763px) and (min-height: 543px). Hier wordt het tonen van de afbeelding in de pop-up geregeld.
#blok-link-1 .focus-open:focus ~ .open .pop-up, #blok-link-1 input:checked + .open .pop-up, #blok-link-1 .open:hover .pop-up
Voor dit element is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
Deze drie selectors zijn precies hetzelfde als die bij .focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up. Het enige verschil is dat er hier #blok-link-1
voor staat, waardoor deze selectors alleen werken voor li#blok-link-1
, en niet voor alle acht de <li>'s. Uitleg over deze selectors is bij de eerdere selectors te vinden.
background-image: url(../019-pics/band.jpg);
Achtergrond-afbeelding in span.pop-up
zetten. Eerder is al een background-position
opgegeven, waardoor de afbeelding onder de tekst in de pop-up komt te staan. Omdat dit voor alle acht de afbeeldingen hetzelfde is, kon dit eerder voor allemaal in één keer worden opgegeven.
Een achtergrond-afbeelding heeft geen breedte en hoogte, maar vult alleen de breedte en hoogte van het element – hier span.pop-up
–, waar hij in staat. Daarom moet de <span> een breedte en hoogte krijgen. Ook dit is voor alle acht hetzelfde en daarom al eerder opgegeven.
#blok-link-2 .focus-open:focus ~ .open .pop-up, #blok-link-2 input:checked + .open .pop-up, #blok-link-2 .open:hover .pop-up
{background-image: url(../019-pics/buikdanseres.jpg);}
#blok-link-3 .focus-open:focus ~ .open .pop-up, #blok-link-3 input:checked + .open .pop-up, #blok-link-3 .open:hover .pop-up
{background-image: url(../019-pics/drummer.jpg);}
#blok-link-4 .focus-open:focus ~ .open .pop-up, #blok-link-4 input:checked + .open .pop-up, #blok-link-4 .open:hover .pop-up
{background-image: url(../019-pics/gitarist.jpg);}
#blok-link-5 .focus-open:focus ~ .open .pop-up, #blok-link-5 input:checked + .open .pop-up, #blok-link-5 .open:hover .pop-up
{background-image: url(../019-pics/keyboard.jpg);}
#blok-link-6 .focus-open:focus ~ .open .pop-up, #blok-link-6 input:checked + .open .pop-up, #blok-link-6 .open:hover .pop-up
{background-image: url(../019-pics/standbeeld.jpg);}
#blok-link-7 .focus-open:focus ~ .open .pop-up, #blok-link-7 input:checked + .open .pop-up, #blok-link-7 .open:hover .pop-up
{background-image: url(../019-pics/violist.jpg);}
#blok-link-8 .focus-open:focus ~ .open .pop-up, #blok-link-8 input:checked + .open .pop-up, #blok-link-8 .open:hover .pop-up
{background-image: url(../019-pics/zangeres.jpg);}
Voor deze elementen is eerder css opgegeven. Deze wordt binnen dit blokje herhaald in de volgorde, waarin deze in de stylesheet staat, zodat alles hier overzichtelijk bij elkaar staat. (Alleen wat binnen deze media query geldig is, wordt binnen dit blokje herhaald.)
.pop-up {background-position: 0 132px; height: 464px; margin-left: -20000px; border: #fc3 ridge 13px; position: absolute; top: -40px; left: 181px; z-index: 60;}
#blok-link-2 .pop-up, #blok-link-4 .pop-up, #blok-link-6 .pop-up, #blok-link-8 .pop-up {left: -705px;}
#blok-link-3 .pop-up, #blok-link-4 .pop-up {top: -170px;}
#blok-link-5 .pop-up, #blok-link-6 .pop-up {top: -255px;}
#blok-link-7 .pop-up, #blok-link-8 .pop-up {top: -326px;}
.focus-open:focus ~ .open .pop-up, input:checked + .open .pop-up, .open:hover .pop-up {margin-left: 0;}
#blok-link-3 .pop-up, #blok-link-4 .pop-up {top: -206px;}
#blok-link-5 .pop-up {top: -326px;}
#blok-link-6 .pop-up {top: -326px; left: 181px;}
#blok-link-7 .pop-up {left: -705px;}
Alleen in vensters met een breedte tussen 763 en 1063 px:
#blok-link-6 .pop-up, #blok-link-7 .pop-up {top: -240px; left: 81px; -ms-transform: scale(0.65); -webkit-transform: scale(0.65); transform: scale(0.65);}
#blok-link-7 .pop-up {left: -606px;}
Precies hetzelfde verhaal als iets hierboven bij #blok-link-1 .focus-open:focus ~ .open .pop-up, #blok-link-1 input:checked + .open .pop-up, #blok-link-1 .open:hover .pop-up
, alleen nu voor de tweede tot en met achtste span.pop-up
. Alleen de id's en de naam van de achtergrond-afbeelding zijn anders dan hierboven.