figma guide

Designing compare products UI in Figma: tables, sticky headers, and handoff

Design product comparison tables, sticky attribute columns, add-to-compare chips, and mobile compare drawers in Figma with variants and Dev Mode specs for ecommerce.

Published
Updated
Jun 22, 2026
Read time
7 min
Level
Beginner

Quick answer

Compare UI connects PLP selection, a dedicated comparison page, and optional mini compare bar—use one CompareProductColumn per product and CompareAttributeRow for spec alignment across columns. Build CompareCheckbox on product cards, a sticky CompareBar (“Compare 2 of 4”), and a CompareTable with category-grouped rows (Overview, Dimensions, Warranty). Cap at 3–4 products on desktop and 2 on mobile; model empty slots, remove column, and highlight-differences toggle. Pair with PDP, tables, and badges. Start from the Figma guides hub.


Who this is for

  • Product designers shipping electronics, appliances, B2B catalog, and spec-heavy retail where side-by-side decisions drive conversion.
  • Design system teams aligning compare patterns across PLP, search results, and PDP.
  • Engineers implementing compare session storage, attribute normalization, and responsive column collapse.

Compare surfaces

SurfaceGoalKey components
PLP / search cardAdd to compareCompareCheckbox, compare count badge
PDPAdd from detail pageCompareButton text + checkbox variant
Sticky compare barNavigate while browsingCompareBar with thumbnails
Compare page (desktop)Full attribute matrixCompareTable, CompareProductColumn
Compare drawer (mobile)Swipeable columnsCompareDrawer, horizontal scroll
Empty compareNo products selectedEmpty state + PLP CTA

Verdict: attribute rows must be data-driven in spec—design row templates (label column + N product cells), not one-off frames per product pair that break when a third item is added.


CompareProductColumn header

PartPurposeSpec tip
Remove (×)Drop from compareTop-right icon button
ThumbnailProduct image120px; link to PDP
TitleProduct name2-line clamp
PriceCurrent priceSale + was price if applicable
RatingSocial proofCompact stars + count
Primary CTAAdd to cartFull width under header
SecondaryView detailsText link
CompareProductColumn
├── Variant: slot=filled | empty
├── Variant: breakpoint=desktop | mobile
├── Property: productId (string)
└── Layers:
    ├── RemoveButton
    ├── ProductHeader (thumb + title + price + rating)
    ├── AddToCartButton
    └── AttributeCells (mirrored row IDs)

Empty slot shows dashed border card: “Add another product” with search or browse CTA.


CompareAttributeRow structure

Row typeExampleCell content
TextColor”Midnight Black”
BooleanWaterproof✓ / ✗ icons with a11y labels
Numeric + unitWeight”1.2 kg”
ListIncluded accessoriesBulleted mini list
LinkManual PDF”Download” link
Unavailable”—” em dash, muted
CompareAttributeRow
├── Property: attributeId (string)
├── Property: category (overview | specs | shipping)
├── Property: highlightDiff (boolean)
└── Layers:
    ├── RowLabel (sticky left column desktop)
    └── Cell[] (one per CompareProductColumn)

Group rows under section headers: “General,” “Technical specifications,” “Shipping & returns”—use accordion sections on mobile to reduce scroll.


Sticky compare bar

Shown when ≥1 product in compare tray and user navigates away from compare page.

ElementSpec
Thumbnails40px, max 4, +N overflow badge
Label”Compare (3)“
Clear allText button
CTA”Compare now” → compare page
PositionFixed bottom mobile; top below nav desktop optional
CompareBar
├── Variant: visible | hidden
├── Property: count (0-4)
├── Property: productThumbs (array)
└── z-index: above PLP filters, below [modals](/designing-modals-and-dialogs-in-figma-overlays-and-handoff/)

When count hits max (4), toast: “Remove an item to compare more products.”


PLP and PDP entry points

EntryControlMax behavior
PLP grid cardCheckbox “Compare”Disabled at max with tooltip
PLP list rowIcon toggleSame
PDP below title”Add to compare” linkToggle on/off state
Wishlist rowOptional compare iconDon’t merge wishlist + compare state

CompareCheckbox states: unchecked, checked, disabled-max, loading.

On product listing cards, place compare control away from wishlist heart to prevent mis-taps—bottom-left vs top-right corners.


Highlight differences toggle

StateRow styling
OffAll rows equal weight
OnRows where all values identical → collapsed or hidden
OnRows with mismatch → subtle background highlight on differing cells

Toggle sits top-right of compare page: switch “Highlight differences only.”

Engineering note: normalization matters—“Yes” vs “yes” vs ✓ should not false-highlight; spec string equality rules in Dev Mode.


Desktop compare table layout

ComparePageDesktop
├── PageTitle: "Compare products"
├── Toolbar: HighlightDiffToggle | Print | Share link
├── CompareTable
│   ├── StickyHeaderRow (product columns stick on vertical scroll)
│   ├── Section: Overview
│   │   └── CompareAttributeRow × n
│   ├── Section: Specifications
│   │   └── CompareAttributeRow × n
│   └── Section: Shipping
│       └── CompareAttributeRow × n
├── EmptyColumnSlot (if < max products)
└── BackToPLP link

Left label column width: 200–240px fixed; product columns share remaining width equally (3-col) or horizontal scroll (4-col).

Use layout grids for row height consistency—attribute cells in the same row must equal height per auto layout “fill container.”


Mobile compare patterns

PatternWhen to use
Horizontal scroll columns2 products visible; peek third
Product picker tabsSwitch active pair in 3+ compare set
Full-screen drawerFrom sticky bar “Compare now”
Stacked cardsLow-spec categories only—avoid for 20+ rows

Sticky CompareProductColumn header on horizontal scroll—product image and ATC stay visible while specs scroll.

Collapse long text attributes with “Show more” link inside cell.


Add to cart from compare

ScenarioUX
Single winner obviousOne primary ATC per column
Multi-buy bundleNot compare’s job—link to PDP
Out of stock columnDisabled ATC + badge “Out of stock”
Variant requiredATC opens modal variant picker

After add, optional toast with link to cart—do not navigate away from compare unless user chooses.


Dev Mode handoff checklist

SpecDocument
Max compare count4 desktop, 2 recommended mobile
Session persistencelocalStorage vs account-backed
Attribute schemaJSON example with attributeId, type, category
Icon setcheck, x, dash for boolean cells
Empty cell token”—” character + muted color variable
Analyticscompare_add, compare_remove, compare_view, compare_atc
SEOCompare page noindex if session-only (note for PM)

Cross-link table component patterns for sortable spec sources on admin side.


Common mistakes

MistakeWhy it hurtsFix
Static 2-product mock onlyBreaks when adding thirdColumn + row component model
Misaligned attribute rowsUnreadable comparisonShared row component, equal heights
Compare on every SKU variantTray explosionCompare at parent product level
No max limitOverwhelming tableCap at 4 with disabled add
Identical columns not collapsibleNoiseHighlight differences toggle
Missing empty compare stateDead endCTA back to PLP categories

  1. Define compare-eligible categories with PM (electronics yes, fashion often no).
  2. Build CompareProductColumn header with remove, price, rating, ATC.
  3. Create CompareAttributeRow with text, boolean, and unavailable variants.
  4. Add CompareCheckbox to PLP card component set.
  5. Design CompareBar sticky tray and max-reached toast.
  6. Lay out desktop CompareTable with 3 filled + 1 empty column.
  7. Design mobile horizontal scroll with sticky mini headers.
  8. Prototype add/remove, highlight diff toggle, and out-of-stock column.

FAQ

Compare vs wishlist?

Different jobs—wishlist is save for later; compare is decision support. Allow both on PDP; separate icons and state.

Variant-level compare (size/color)?

Default to parent product in tray; if user compared from specific variant PDP, pass variant ID to ATC only—not separate columns per size.

Optional toolbar icon generates print stylesheet—design simplified B&W table frame without sticky chrome.

Deep link with product IDs query param—design shared view read-only without edit controls; note loading skeleton state.

Faceted search filters with compare?

Compare tray persists across filter changes—products removed from results stay in tray until user removes them; show bar badge if item unavailable.


Next steps

Share on X

§ Keep reading

Related guides.