Notched Badge System
Four 46 px status badges (info, success, warning, error), each cut with a 6 px square notch at every corner by a pixel-based clip-path: polygon(), with a 22 px round counter and a slight grow on hover: the technical label, in plain CSS.
Updated
This effect is part of Effect.Labs — 840 vanilla effects, some free, some premium. Glassmorphism has 47 effects, including 6 free. Explore the category →
3 usage examples



How it works
Each .notch-badge is an inline-flex (12 × 24 px padding, 12.8 px text at weight 700, uppercase with 0.5 px spacing): 46 px tall, and a width that follows the label — 152.6, 125.9, 141.4 and 133.8 px for Messages, Active, Warning and Errors (measured). It is cut by clip-path: var(--ntb-notch), a twelve-point polygon() in calc() that removes a 6 × 6 px square at each corner: 0 6px, 6px 6px, 6px 0, calc(100% - 6px) 0…. Because the notch is in pixels, it keeps the same size on a 120 px badge as on a 200 px one. It removes about 2% of the area (measured: 1.9 to 2.3%) and, in Chromium 151, Firefox 153 and WebKit 26, the point 2 px from the corner does not get the click.
Four color variants: --info (#3b82f6 → #6366f1), --success (#10b981 → #059669), --danger (#ef4444 → #dc2626), all three with white text, and --warning (#f59e0b → #d97706) with #1a1a2e text. The .nb-count counter is a 22 px circle in 25% white, 10.4 px text. On hover, over 0.3 s with a bounce (cubic-bezier(0.34, 1.56, 0.64, 1)): scale(1.06) and brightness(1.2). No JavaScript.
The notch lives in a CSS variable on the badge, --ntb-notch, with no SVG <clipPath> and no id: nothing to add to the page, and a single line to change to retouch the four corners of every badge. Its points mix pixels and percentages (calc(100% - 6px)): the notch keeps 6 px whether the badge is short or long.
Accessibility
- Contrast (12.8 px at weight 700: normal text, 4.5:1 threshold), measured on the start color: warning 7.9:1 (dark text); info 3.7:1, error 3.8:1 and success 2.5:1 with white text — below the threshold. Darken the start color:
#2563eb,#b91c1cand#047857go above 4.5:1. The counter digit, on a lighter circle, loses a little more. - Color alone: the label states the status (“Late”, “Incident”), color only doubles it — always keep a word. The counter alone (“3”) means nothing to a screen reader: put
aria-label="Errors: 3"on the badge, or visually hidden text inside.nb-count. - Keyboard and motion:
divs withcursor: pointer, no role and notabindex(Tab never stops on them, measured). For clickable filters, use<button aria-pressed>;clip-pathclips the focus ring, so plan a:focus-visiblethat changes the background. Noprefers-reduced-motion: the 6% grow stays active under the preference.
Browser compatibility
CSS only: clip-path: polygon() with calc(), the --ntb-notch custom property, flexbox, gradients, filter: brightness(). Zero JavaScript, zero SVG. Measured pasted into a blank page: identical notches in Chromium 151, Firefox 153 and WebKit 26.
Without clip-path (Firefox before 54, Safari before 13.1 without the -webkit-clip-path prefix), the badges are readable rectangles, colors and counters intact.
The code
HTML structure to paste into your page (the CSS + JS come with Premium):
<div class="demo-preview">
<div class="notch-badges-wrap">
<div class="notch-badge notch-badge--info">… <span class="nb-count">…</span></div>
<div class="notch-badge notch-badge--success">… <span class="nb-count">…</span></div>
<div class="notch-badge notch-badge--warning">… <span class="nb-count">…</span></div>
<div class="notch-badge notch-badge--danger">… <span class="nb-count">…</span></div>
</div>
</div>
The full HTML + CSS + JS of Notched Badge System, ready to paste — plus all 840 effects. Or $299 once, lifetime access.
Customize
Options passed to the API or data-* attributes:
| Option / property | Default | Effect |
|---|---|---|
Notch size (CSS — --ntb-notch on .notch-badge) |
6 px square at each corner | Replace the sixteen 6px in the polygon() (twelve points): 4 px for a small badge, 10 px for a 60 px tall badge. Beyond a quarter of the height, the notch bites into the text. |
Colors (CSS — .notch-badge--info, --success, --warning, --danger) |
blue, green, amber, red as 135° gradients | Add a variant by copying a rule: .notch-badge--neutral { background: linear-gradient(135deg, #475569, #334155); color: #fff }. |
Padding (CSS — padding of .notch-badge) |
12 px × 24 px (46 px tall) | 8px 14px for a compact 38 px badge; the pixel notch stays the same. |
Counter (CSS — .nb-count) |
22 px circle, 25% white, 10.4 px | Beyond two digits, switch to a pill: width: auto; min-width: 22px; padding: 0 6px; border-radius: 11px. |
Hover (CSS — .notch-badge:hover) |
scale(1.06), brightness(1.2), 0.3 s with bounce |
Remove the rule for non-clickable information badges: the grow suggests a button. |
FAQ
calc(100% - 6px), each corner loses the same 6 × 6 px square, whatever the label length.polygon(0 6px, 6px 6px, 6px 0, 100% 0, 100% calc(100% - 6px), calc(100% - 6px) calc(100% - 6px), calc(100% - 6px) 100%, 0 100%) notches the top left and bottom right. Replace the value of --ntb-notch, nothing else changes.div with a <button type="button" class="notch-badge notch-badge--info" aria-pressed="false">: shape and colors follow the class. Add border: none and font: inherit to .notch-badge, which a button does not inherit. On click, flip aria-pressed and filter your list; mark the active filter by more than color, for example .notch-badge[aria-pressed="true"] { box-shadow: inset 0 0 0 2px #fff }. As clip-path clips the default focus ring, give the badge a :focus-visible that changes its background (background: #1a1a2e; color: #fff): Tab then stops on it, and the selection shows.