Character Counter

Live count of characters entered.

128 / 160 characters — approaching the limit

html

<div class="charcount" style="--accent:#E8A020;">
  <label class="charcount__label" for="charcount-field">Bio</label>
  <textarea id="charcount-field" class="charcount__field" aria-describedby="charcount-help" readonly>Write a short bio that captures who you are in a couple of sentences.</textarea>
  <p id="charcount-help" class="charcount__help charcount__help--warn" role="status">
    128 / 160 characters
    <span class="charcount__warn-text"> &#8212; approaching the limit</span>
  </p>
</div>
<style>
.charcount { font: 14px/1.5 system-ui, sans-serif; color: #241430; max-width: 320px; }
.charcount__label { display: block; font-weight: 600; margin-bottom: 6px; }
.charcount__field { width: 100%; box-sizing: border-box; min-height: 76px; padding: 10px 12px; border-radius: 8px; border: 1.5px solid #24143033; background: #FAF7F2; color: #241430; font: inherit; resize: vertical; }
.charcount__field:focus-visible { outline: 2px solid var(--accent); outline-offset: 1px; }
.charcount__help { margin: 6px 2px 0; font-size: 12px; color: #24143099; }
.charcount__help--warn { color: #b3261e; font-weight: 600; }
.charcount__warn-text { font-weight: 600; }
</style>

tailwind

<div style="--accent:#E8A020;" class="font-sans text-sm text-[#241430] max-w-[320px]">
  <label for="charcount-tw-field" class="block font-semibold mb-1.5">Bio</label>
  <textarea id="charcount-tw-field" aria-describedby="charcount-tw-help" readonly class="w-full box-border min-h-[76px] px-3 py-2.5 rounded-lg border-[1.5px] border-[#24143033] bg-[#FAF7F2] text-[#241430] resize-y">Write a short bio that captures who you are in a couple of sentences.</textarea>
  <p id="charcount-tw-help" role="status" class="mt-1.5 mx-0.5 text-xs text-[#b3261e] font-semibold text-[#241430]/60">
    128 / 160 characters
    <span class="font-semibold"> &#8212; approaching the limit</span>
  </p>
</div>

react

export function CharacterCounter({
  value = "Write a short bio that captures who you are in a couple of sentences.",
  count = 128,
  limit = 160,
  nearLimit = true,
  accent = "#E8A020",
}) {
  return (
    <div style={{ fontFamily: "system-ui, sans-serif", fontSize: 14, lineHeight: 1.5, color: "#241430", maxWidth: 320 }}>
      <label htmlFor="charcount-react-field" style={{ display: "block", fontWeight: 600, marginBottom: 6 }}>Bio</label>
      <textarea id="charcount-react-field" aria-describedby="charcount-react-help" readOnly value={value} style={{
        width: "100%", boxSizing: "border-box", minHeight: 76, padding: "10px 12px", borderRadius: 8,
        border: "1.5px solid #24143033", background: "#FAF7F2", color: "#241430", font: "inherit", resize: "vertical" }} />
      <p id="charcount-react-help" role="status" style={{ margin: "6px 2px 0", fontSize: 12,
        color: nearLimit ? "#b3261e" : "#24143099", fontWeight: nearLimit ? 600 : 400 }}>
        {count} / {limit} characters
        {nearLimit && <span style={{ fontWeight: 600 }}> &#8212; approaching the limit</span>}
      </p>
      <style>{`#charcount-react-field:focus-visible { outline: 2px solid ${accent}; outline-offset: 1px; }`}</style>
    </div>
  );
}