我可能不是唯一一個對瀏覽器的預設<input type="checkbox">感到沮喪的開發人員。

首先:它不可擴展。在此範例中,字體大小已縮放至200% ,但複選框仍保持其根大小,即13.333333px

預設複選框

在本教程中,我們將剖析瀏覽器的預設複選框,看看是否可以做得更好。


首先,我們需要使用appearance:none清除預設樣式並設定初始大小 - 這將是一個相對單位em

[type=checkbox] {
  appearance: none;
  aspect-ratio: 1;
  box-sizing: border-box;
  font-size: 1em;
  width: 1em;
}

background-color應該適應深色模式,因此我們將檢查它是否與任何系統顏色相符。它似乎與Field系統顏色匹配,所以讓我們使用它。

對於 Chrome 中的邊框顏色,它與系統顏色ButtonBorder匹配,但由於 Safari 使用更輕的ButtonBorder ,我們將使用適用於兩種瀏覽器的GrayCanvas

我們將加入一些 CSS 自訂屬性,稍後我們將使用它們來建立變體。

對於border-radiusmargin ,我們將使用預設值,但將它們轉換為相對單位em

border-width似乎使用以下公式進行縮放:

(4/3) / root size

由於根大小為13.333333px ,我們現在有:

[type=checkbox] {
  --_bdw: calc(1em * (4/3) / 13.333333);
  appearance: none;
  aspect-ratio: 1;
  background: var(--_bg, Field);
  border: var(--_bdw) solid var(--_bdc, GrayText);
  border-radius: var(--_bdrs, .2em);
  box-sizing: border-box;
  font-size: 1em;
  margin: var(--_m, .1875em .1875em .1875em .25em);
  position: relative;
  width: 1em;
}

讓我們看看它是否可擴展:

可擴充複選框

好的!深色模式呢?

深色模式

這就是為什麼我喜歡系統顏色!接下來,讓我們新增瀏覽器在未選取的複選框上使用的相同懸停效果。

我們將混合CanvasText ,它在淺色模式下為黑色,在深色模式下為白色,並簡單地更新我們在上一步中加入的--_bdc屬性:

@media (hover: hover) {
  &:not(:checked):hover {
    --_bdc: color-mix(in srgb, GrayText 60%, CanvasText 40%);
  }
}

複選標記

現在是複選標記。我們可以::after元素中使用旋轉的 CSS 方塊來做到這一點:

[type=checkbox]::after {
  border-color: GrayText;
  border-style: solid;
  border-width: 0 0.15em 0.15em 0;
  box-sizing: border-box;
  content: '';
  aspect-ratio: 1 / 1.8;
  rotate: 40deg;
  width: 0.375em;
}

CSS 中的複選標記

雖然這工作得很好,但我更喜歡在蒙版中使用 SVG,因為它更靈活。為此,我們將為遮罩加入一個屬性,並為::after元素的背景加入另一個--_bga ,該屬性將是複選標記的顏色

[role=checkbox] {
--_bga: Field;
--_mask: url('data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" stroke-width="3" stroke="%23000" fill="none" stroke-linecap="round" stroke-linejoin="round"> <path d="M5 12l5 5l10 -10"/></svg>');

  &::after {
    background: var(--_bga, transparent);
    content: "";
    inset: 0;
    position: absolute;
    mask: var(--_mask) no-repeat center / contain;
    -webkit-mask: var(--_mask) no-repeat center / contain;
  }
}

所以,我們現在確實有一個複選標記,只是看不到它,因為蒙版顏色設定為transparent

讓我們使用:checked -state 更新點擊時複選框的顏色。但在此之前,我們需要先弄清楚哪種顏色!

Safari 是唯一支援系統顏色AccentColor瀏覽器,因此我們需要為此建立自己的變數--_accent ,在 Mac 上對應於#0075ff

[type=checkbox] {
  --_accent: #0075ff;
  &:checked {
    --_bdc: transparent;
    --_bg: var(--_accent);
    --_bga: Field;
  }
}

讓我們看看我們建構了什麼:

複選框樣式

還有深色模式?我們需要先更新--_accent屬性,因為AccentColor尚未在所有瀏覽器中運作:

@media (prefers-color-scheme: dark) {
  --_accent: #99C8FF;
}

讓我們檢查:

複選框深色模式

涼爽的!現在我們需要加入的是:checked:hover -state,它類似於我們之前新增的 border-hover:

@media (hover: hover) {
  &:checked:hover {
    --_bg: color-mix(in srgb, var(--_accent) 60%, CanvasText 40%);
  }
}

讓我們比較一下它在 Chrome、Safari 和 Firefox 中的外觀:

瀏覽器比較

看來我們通過考驗了!


變體

建立變體非常簡單:您只需要更新一些屬性。例子:

.rounded { --_bdrs: 50%; }
.square { --_bdrs: 0; }

然後在 HTML 中:

<input type="checkbox" class="rounded">
<input type="checkbox" class="square">

變體

— 或全力以赴並建立老式複選框:

老派複選框

關於圓形複選框的註釋:這是不好的做法,正如您可以在這篇精彩的文章中讀到的那樣。不過,也有一些例外,例如這個「影像選擇器」:

圓形影像選擇

開關

對於開關,我們將加入一個role="switch" ,所以它是:

<input type="checkbox" role="switch">

蘋果最近加入了自己的 switch-control ,但role="switch"是跨瀏覽器的。同樣,我們只需要更新我們之前建立的許多屬性:

[role=switch] {
    --_bdc--hover: transparent;
    --_bdrs: 1em;
    --_bg: #d1d1d1;
    --_bga: Field;
    --_mask: none;
    aspect-ratio: 1.8 / 1;
    border: 0;
    display: grid;
    padding: .125em;
    place-content: center start;
    width: 1.8em;
    &::after {
      border-radius: 50%;
      height: .75em;
      inset: unset;
      position: static;
      width: .75em;
    }
    &:checked {
      --_bg: var(--_bg--checked, var(--_accent));
      justify-content: end;
    }
  }

這給了我們:

開關


示範

就是這樣!下面是帶有演示的 Codepen:

https://codepen.io/stoumann/pen/OJqQNgm


駭客與縫合

以下是我在 Codepen 上使用複選框所做的一系列工作:

複選框電影院

選擇座位。還可以修改為在火車、飛機上選擇座位......

https://codepen.io/stoumann/pen/eYXpEBa

天際線複選框

點擊窗戶打開公寓裡的燈…

https://codepen.io/stoumann/pen/KKbGJqd

按數字繪畫

先選擇一種顏色(使用<input type="radio"> ),然後按一下對應的數字(複選框)...

https://codepen.io/stoumann/pen/VwRejpR

點對點

不需要 JavaScript,但我把它留在那裡供你玩…

https://codepen.io/stoumann/pen/zYbNRNL

來自地獄的條款和條件

檢查全部…

https://codepen.io/stoumann/pen/GRwRjYP


每日 toggle

Alvaro Montoro 正在建立大量開關/撥動開關 - 2024 年每天一個。請在此處查看。


原文出處:https://dev.to/madsstoumann/styling-checkboxes-and-switches-pf0

按讚的人:

共有 1 則留言

這篇很受用,工作上確實遇到checkbox這類的問題!

按讚的人: