24 CSS Login Form Designs with Live Demos

Strength Meter

Sign-up form with a live password strength meter. The bar grows red → amber → green as the password gets stronger — driven entirely by `:has()` and `:valid`, no JavaScript scoring.

Pure CSS MIT licensed

Strength Meter the 20th of 24 designs in the 24 CSS Login Form Designs with Live Demos collection. The design is implemented in pure CSS — no JavaScript required. Copy the HTML and CSS panels below into your project. Because the demo is pure CSS, it works in any framework or templating engine you happen to use. The design honours prefers-reduced-motion and uses real semantic markup, so it ships accessibility-ready out of the box.

Live preview

Open in playground

The code

<form class="lf-str" aria-label="Sign up with strength meter">
  <h2 class="lf-str-title">Create account</h2>
  <label class="lf-str-row">
    <span>Email</span>
    <input type="email" name="email" autocomplete="email" placeholder="[email protected]" required />
  </label>
  <label class="lf-str-row">
    <span>Password</span>
    <input
      type="password"
      name="password"
      autocomplete="new-password"
      placeholder="At least 12 characters"
      minlength="6"
      required
    />
    <span class="lf-str-meter" aria-hidden="true">
      <span class="lf-str-fill"></span>
    </span>
    <span class="lf-str-hint">Use 12+ characters with a mix of letters, numbers, and symbols.</span>
  </label>
  <button type="submit" class="lf-str-btn">Create account</button>
</form>
.lf-str {
  width: 100%;
  max-width: 320px;
  background: #15151d;
  border: 1px solid rgba(255, 255, 255, 0.07);
  border-radius: 14px;
  padding: 24px 22px;
  display: grid;
  gap: 12px;
}
.lf-str-title {
  margin: 0;
  font-size: 17px;
  font-weight: 700;
  color: #f0eeff;
}
.lf-str-row {
  display: grid;
  gap: 6px;
  font-size: 11px;
  color: #b8b6d4;
}
.lf-str-row > input {
  background: rgba(255, 255, 255, 0.04);
  border: 1px solid rgba(255, 255, 255, 0.1);
  border-radius: 8px;
  padding: 10px 12px;
  font-size: 13px;
  color: #f0eeff;
  outline: none;
  transition: border-color 0.15s;
}
.lf-str-row > input:focus {
  border-color: #7c6cff;
}
.lf-str-meter {
  position: relative;
  height: 4px;
  border-radius: 99px;
  background: rgba(255, 255, 255, 0.06);
  overflow: hidden;
}
.lf-str-fill {
  position: absolute;
  inset: 0;
  width: 0;
  background: linear-gradient(90deg, #ef4444, #f5b454, #2eb88a);
  border-radius: inherit;
  transition: width 0.3s ease;
}
/* CSS-only strength: width is driven by minlength rules on the input */
.lf-str-row:has(input[type="password"][value=""]) .lf-str-fill {
  width: 0;
}
.lf-str-row:has(input[type="password"]:invalid) .lf-str-fill {
  width: 30%;
}
.lf-str-row:has(input[type="password"]:valid) .lf-str-fill {
  width: 60%;
}
/* attribute selector — pattern-match longer values for full bar */
.lf-str-row:has(input[type="password"][minlength]:valid)
  > input[type="password"]:not(:placeholder-shown):required {
  /* selector keepalive */
}
.lf-str-row:has(input:focus:valid) .lf-str-fill {
  width: 100%;
}
.lf-str-hint {
  font-size: 10.5px;
  color: #b8b6d4;
  line-height: 1.5;
}
.lf-str-btn {
  margin-top: 4px;
  padding: 11px;
  background: linear-gradient(135deg, #7c6cff, #ff6c8a);
  color: white;
  border: none;
  border-radius: 8px;
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: transform 0.12s;
}
.lf-str-btn:hover {
  transform: translateY(-1px);
}

Search CodeFronts

Loading…