Je 'perfecte' button is een bug in de dop

Je 'perfecte' button is een bug in de dop

Jul 04, 2026 semantic-html web-development accessibility frontend best-practices

Waarom die <div> Geen Vervanging Is Voor Een <button>

Je herkent het vast. Je bouwt een design system en de designer heeft weer eens een "creatieve" button bedacht. Een gradient hier, een animated hover-effect daar, misschien zelfs een subtiele scale op het moment dat je hem indrukt. Typisch werk voor een <div> met wat CSS, toch?

Het ziet er fantastisch uit in Figma. Het werkt perfect in je demo. En dan... dan gaat een echte gebruiker aan de slag. Die tabt door de interface. Die probeert een formulier te versturen met alleen het toetsenbord. Die gebruikt een screen reader. En ineens valt alles uit elkaar.

Het ligt niet aan je CSS. Het probleem is dat je een <div> vraagt om een taak te doen waarvoor het nooit bedoeld is.

De Div Die Dacht Dat Het Een Button Was

Wat gebeurt er meestal? Je hebt een button nodig die er op een specifieke manier uitziet. Dus pak je een <div>, geef je het class="btn", en style het totdat het matcht met het design. Ziet er goed uit.

Maar nu moet die button ook daadwerkelijk werken als een button.

Dus voeg je een click handler toe. Een hover state. Een focus ring voor keyboard gebruikers. Dan ontdek je dat Space en Enter niet werken, dus daar komt nog een keydown listener bij. De button moet soms disabled zijn, dus daar komt een .disabled class bij die hopelijk alle juiste interacties blokkeert. Ondertussen voeg je role="button" en tabindex="0" toe zodat assistive technology je creatie niet volledig negeert.

Gefeliciteerd. Je hebt een button-vormig object gebouwd dat ongeveer 200 regels JavaScript nodig heeft om te benaderen wat de browser je gratis had gegeven.

Dit is wat we bedoelen met "rente betalen" op slechte architectuurkeuzes. Elke regel workaround code is rente op de originele keuze om het verkeerde element te gebruiken.

De Onzichtbare Overeenkomst

Het ding is: native HTML elementen komen met een heel interactie-contract waar de meeste developers nooit over nadenken—tot het ontbreekt.

Als je een echte <button> gebruikt, krijg je:

  • Automatische keyboard handling — Enter en Space werken precies zoals gebruikers verwachten
  • Goed focus management — Het komt van nature in de tab-volgorde, kan programmatisch gefocused worden
  • Disabled state gedrag — Blokkeert alle interactie, wordt niet focusbaar, wordt aangekondigd als disabled
  • Form participatie — Verstuurt formulieren, respecteert validatie, doet mee aan form.reset()
  • Accessibility semantics — Screen readers kondigen het aan als button zonder extra ARIA
  • Platform conventies — Gebruikers weten al hoe buttons zich gedragen omdat buttons zich overal consistent gedragen

Met een <div> verkleed als button krijg je... de CSS. De rest is aan jou om te implementeren. En hier komt het vervelende geheim: hoe grondig je ook bent, je implementatie zal slechter zijn dan wat browsers leveren. Browsers hebben teams van engineers die dit gedrag optimaliseren voor platforms, edge cases en assistive technologies. Jouw custom button heeft alleen jou.

De Vraag Is Niet "Kan Ik Het Stylen?"

Dit is waar design-engineering samenwerking ofwel schittert ofwel technische schuld creëert. Developers interpreteren "semantic HTML" vaak als " accepteren wat de browser lelijk uit de doos geeft". Daar gaat het helemaal niet over.

De vraag is niet "kan ik dit er custom laten uitzien?" — dat kan absoluut. De vraag is: "welke native behaviors moeten de styling overleven?"

Een <button> kan elke visuele behandeling krijgen die je wilt. Je kunt alle default styling verwijderen met appearance: none. Je kunt gradients toevoegen, shadows, animaties, custom fonts—wat het design ook vraagt. Het interactie-contract van de browser kan het niet schelen hoe je button eruitziet.

Wat je niet makkelijk kunt namaken met een <div> is wat de browser je automatisch geeft. Dus kies je gevechten verstandig: besteed je engineering-inspanning aan wat je product uniek maakt, niet aan het opnieuw uitvinden van buttons.

Bouwen Voor Het Echte Web

Je gebruikers gebruiken je product niet in een vacuüm. Ze tabben tussen velden terwijl hun handen op het toetsenbord blijven. Ze navigeren met spraakbesturing. Ze vergroten het scherm naar 300% omdat dat voor hen werkt. Ze hebben verschillende browsers, besturingssystemen, assistive technologies.

Het web platform geeft je een flinke voorsprong met semantic HTML. Native elementen zijn toegankelijk by default, keyboard-navigeerbaar by default, cross-platform by default. Als je tegen die infrastructuur vecht, maak je niet alleen meer werk voor jezelf—je creëert componenten die op subtiele manieren zullen falen voor echte gebruikers.

De volgende keer dat je op het punt staat om een <div> met role="button" te pakken, vraag jezelf af: bouw ik iets dat daadwerkelijk een custom implementatie nodig heeft, of ben ik gewoon bang voor het <button>-element? Want de saaie oplossing is meestal de juiste. En "de browser handelt het correct af" is een feature, geen beperking.

Het semantische web draait niet om regels volgen. Het draait om de juiste tool voor de klus gebruiken—en je energie besteden waar het daadwerkelijk verschil maakt.

Read in other languages:

EL CS UZ TR SV FI RO PT PL NB HU IT FR ES DE DA ZH-HANS EN