Web Component
A web component is the <dkl-price> tag written directly into your theme’s Liquid. On a
product page it needs zero attributes — it clones a pre-staged carrier and renders
the primary product’s price server-side.
On a product page, add the <dkl-price> web component — it renders the primary product’s price server-side:
<dkl-price></dkl-price>Reacting to changes
Section titled “Reacting to changes”<dkl-price> emits a discount-kit-live:price:change event whenever its displayed price
updates — the recommended hook for running your own code when the price moves. It carries the
previous and new price (see the Events reference). See
Listen for price changes below.
Two narrower alternatives:
- Listen for the tier event — the volume picker’s
discount-kit-live:volume-discount:tier-change, e.g. to read the selected tier’s quantity. See Listen for tier changes. - Watch the discounted state — if you only care about whether this element is showing a
discount, observe its
data-dkl-discountedattribute (set while a tier is active) with aMutationObserver:
// Handles any number of <dkl-price> elements on the pagedocument.querySelectorAll('dkl-price').forEach((price) => { new MutationObserver(() => { const discounted = price.hasAttribute('data-dkl-discounted') // e.g. flag the surrounding card while a discounted tier is selected price.closest('.product-card')?.classList.toggle('is-discounted', discounted) }).observe(price, { attributes: true, attributeFilter: ['data-dkl-discounted'] })})Examples
Section titled “Examples”For the full list of data-* attributes you can set, see
Styling & Data Attributes.
<dkl-price data-show-savings="true" data-savings-format="amount" data-savings-label="You save" style=" --dkl-price-font-size: 1.4rem; --dkl-price-font-weight: 700; --dkl-price-sale-color: #c0392b; --dkl-price-compare-opacity: 1; "></dkl-price>// The recommended hook: fires whenever the displayed price updates, with the// previous and new price states.document.addEventListener('discount-kit-live:price:change', (event) => { const { productId, previousPrice, currentPrice } = event.detail.resource
const fmt = (cents) => (cents / 100).toLocaleString(undefined, { style: 'currency', currency: window.Shopify?.currency?.active ?? 'USD', })
console.log( `Product ${productId}: ` + `${previousPrice ? fmt(previousPrice.priceCents) : '—'} → ${fmt(currentPrice.priceCents)}` + (currentPrice.discounted ? ' (discounted)' : ''), )})// React to volume-tier selections to drive your own UI alongside the price —// here, a custom "Buy N at X each" summary element somewhere on the page:// <p data-tier-summary="7820000000001" hidden></p>const summary = document.querySelector('[data-tier-summary]')
const money = (major) => major.toLocaleString(undefined, { style: 'currency', currency: window.Shopify?.currency?.active ?? 'USD', })
document.addEventListener('discount-kit-live:volume-discount:tier-change', (event) => { const { productId, currentTier } = event.detail.resource
// Scope to the product this summary belongs to — handy when several pickers // / prices share a page (e.g. the main product plus recommendations). if (productId !== Number(summary.dataset.tierSummary)) return
// currentTier is null when the shopper clears their selection. if (!currentTier) { summary.hidden = true return }
// unitPriceCents is the per-item price; discountAmount is a percentage for // 'percentage' tiers, or a major-unit amount for 'fixedAmount' tiers. const { quantity, unitPriceCents, discountType, discountAmount } = currentTier const saving = discountType === 'percentage' ? `${discountAmount}% off` : `${money(discountAmount)} off each`
summary.hidden = false summary.textContent = `Buy ${quantity}+ at ${money(unitPriceCents / 100)} each — ${saving}`})Next steps
Section titled “Next steps”Styling & Data AttributesEvery data-* attribute, --dkl-* token, and CSS part.
App blockThe no-code, theme-editor placement.