<hgroup>
<h1><span>Interaction States:</span> <br/> Label Wrapped Checkbox</h1>
<p>Visualizing the states of a <code>label</code> wrapping an <code>input[type="checkbox"]</code>.</p>
</hgroup>
<div class="container">
<section class="demo one">
<label for="cb_1">
<input type="checkbox" id="cb_1" />
<span>Label with Visible Checkbox</span>
</label>
<section class="states">
<span class="default state">label</span>
<span class="hover state">:hover</span>
<span class="active state">:active</span>
<span class="focus-within state">:focus-within</span>
<span class="checked state">:has(:checked)</span>
</section>
</section>
<section class="demo two">
<nav>
<label for="cb_2">
<input type="checkbox" id="cb_2" />
<span>Label with Hidden Checkbox</span>
</label>
</nav>
<section class="states">
<span class="default state">label</span>
<span class="hover state">:hover</span>
<span class="active state">:active</span>
<span class="focus-within state">:focus-within</span>
<span class="checked state">:has(:checked)</span>
</section>
</section>
</div>
@import url(https://fonts.bunny.net/css?family=libre-franklin:400,700);
:root {
--gap: 1rem;
--padding: 2%;
}
html, body { }
body {
color: hsl(40 10% 30%);
font-family: "Libre Franklin", sans-serif;
line-height: 1.2;
padding: calc(var(--padding) * 2);
}
code { background: hsl(40 30% 90%); border-radius: 3px; color: hsl(40 30% 30%); font-weight: bold; padding: .15rem .5rem .25rem; }
label { cursor: pointer; user-select: none; }
h1, p { margin: 0; }
hgroup {
margin-bottom: calc(var(--gap) * 3);
h1 span { font-weight: 400; }
p {
line-height: 1.5;
margin-top: calc(var(--gap) / 2);
}
}
.container {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(420px, 1fr));
gap: calc(var(--gap) * 2) var(--gap);
}
.demo {
--bg: hsl(40 60% 20%);
--color: color-mix(in lab, var(--bg), black 10%);
--border-color: transparent;
--padding: 3rem;
background: color-mix(in lab, var(--bg), white 95%);
border: 2px solid var(--border-color);
display: grid;
height: 8rem;
position: relative;
label {
background: inherit; /* for filter */
color: var(--color);
display: flex;
gap: .6rem;
place-items: center;
transition: all .12s ease-in-out;
z-index: 3;
input {
appearance: none;
aspect-ratio: 1;
background: transparent;
border-radius: 1px;
outline: 2px solid var(--color);
outline-offset: 2px;
position: relative;
width: .5rem;
&:checked {
background: var(--color);
padding: 3px;
}
}
span {
background: inherit;
background-clip: text;
color: var(--color);
display: inline-block;
font-weight: 700;
}
}
/* :hover shading */
/* &:before {
background: color-mix(in lab, var(--bg), white 70%);
opacity: 0;
pointer-events: none;
transition: opacity .15s;
content: "";
inset: 0;
position: absolute;
z-index: 3;
} */
/* State Pills */
.states {
display: flex;
justify-content: center;
gap: calc( var(--gap) / 4);
width: 100%;
position: absolute;
left: 50%;
bottom: 0;
transform: translateX(-50%) translateY(50%);
z-index: 5;
}
.state {
--opacity: 0;
--transformY: 3dvh;
--visibility: hidden;
opacity: var(--opacity);
transform: translateY(var(--transformY));
visibility: var(--visibility);
background: color-mix(in lab, var(--bg), white 80%);
border-radius: 2rem;
color: var(--color);
font-family: monospace;
font-size: .75rem;
font-weight: bold;
max-width: max-content;
padding: .5rem .72rem .47rem;
user-select: none;
white-space: nowrap;
transition-duration: .15s;
transition-property: all;
}
.state.default,
&:active .state.active,
&:hover .state.hover,
&:focus-within .state.focus-within,
&:focus-within:has(:checked) .state.focus-within-checked,
&:has(:checked) .state.checked {
--opacity: 1;
--transformY: 0px;
--visibility: visible;
}
/* shading */
/* &:hover::after { opacity: 1; } */
&:hover { --bg: hsl(40 60% 40%) }
&:focus-within {
--bg: hsl(40 100% 40%);
--border-color: color-mix(in lab, var(--bg), white 75%);
border-style: dashed;
&:hover { border-style: solid; }
}
&:focus-within:has(:checked) {
--bg: hsl(130 80% 36%);
}
&:has(:checked) {
--bg: hsl(130 50% 30%);
}
&:active {
--bg: hsl(200 100% 30%) !important;
--border-color: color-mix(in lab, var(--bg), white 75%);
}
&.one,
&.two {
nav {
display: grid;
background: inherit;
}
label {
grid-area: 1 / 1;
place-content: center;
text-align: center;
}
}
&.two {
input {
opacity: 0;
height: 0;
width: 0;
&:checked { padding: 0; }
}
}
}
This Pen doesn't use any external CSS resources.
This Pen doesn't use any external JavaScript resources.