Felix Riesterer: wie kann ich optisch eine checkbox verstecken? (oder code auf radiobuttons anpassen)

Beitrag lesen

Liebe(r) AnLu,

Dein HTML empfinde ich als kaputt. Die Bedienbarkeit von Checkboxen ist an sich schon eine haklige Sache (pun intended), daher sind Beschriftungen unverzichtbar. Auch der Tabellensalat ist mit den heute zur Verfügung stehenden Mitteln nicht mehr entschuldbar - nimm eine Liste!

Was die ganzen onClick-Attribute angeht, so muss da eine andere Lösung her. Das ist fehlerträchtig (siehe 47 und 48) und von daher schlecht.

Besser:

<head>
  <style>
#lotto ol {
  list-style: none;
  margin: 0;
  padding: 0;
}

#lotto li {
  display: inline-block;
}

#lotto input {
  clip: rect(0 0 0 0);
  clip-path: inset(50%);
  height: 1px;
  overflow: hidden;
  position: absolute;
  white-space: nowrap;
  width: 1px;
}

#lotto em {
  border: 1px solid black;
  border-radius: 0.3em;
  cursor: pointer;
  display: block;
  padding: 1em;
  text-align: center;
  width: 2em;
}

#lotto :checked + em {
  background: #8f8;
}
  </style>
</head>
<body>
  <h1>6 aus 49</h1>
  <form id="lotto">
    <ol>
      <li><label><input type="checkbox"><em>1</em></label></li>
      <li><label><input type="checkbox"><em>2</em></label></li>
      <li><label><input type="checkbox"><em>3</em></label></li>
      ...
    </ol>
  </form>
</body>

Mit dieser Struktur haben wir die Möglichkeit, die Checkboxen zu verstecken und trotzdem ein visuelles Feedback zu erhalten. Die Bedienbarkeit ist dadurch gegeben, dass ein Klick/Touch auf die Zahl (hier visuell die Zahlenbox) wegen des label-Elements die unsichtbare Checkbox erreicht. Der Trick mit dem Feedback liegt im Nachbarkombinator und der Pseudoklasse :checked, der die Darstellung der Zahlenbox in Abhängigkeit der selektierten Checkbox ändert.

Dein Eventhandler wird auf das form-Element registriert. Er muss wissen, von welchem Element er ausgelöst wurde (event.target). Dabei solltest Du prüfen, ob der Klick auf einem label-Element (oder einem seiner Kinder) lag, um dann von diesem Label-Element das input-Kindelement (aka die Checkbox) zu ermitteln. Dann kannst Du insgesamt prüfen, wieviele Checkboxen bereits selektiert wurden:

const numChecked = document.querySelectorAll(
  '#lotto input[type="checkbox"]:checked'
).length;

Sollte checked > 6 sein, wird die aktuelle Checkbox deselektiert, ansonsten wird ihre Selektion zugelassen. Das Deselektieren sollte so immer erlaubt sein.

Liebe Grüße

Felix Riesterer