When running a Shopify store, creating a seamless and intuitive shopping experience is key to increasing conversions and customer satisfaction. One often-overlooked feature is the quantity selector—a simple UI element that allows shoppers to choose how many of a particular item they want to purchase before adding it to their cart.
In this post, we’ll explore why a quantity selector is important, where it makes the most sense to use it, and how it can impact your store’s performance.
Why Add a Quantity Selector?
A quantity selector gives customers more control over their purchase. Whether they want to buy multiples of a product for themselves or are purchasing items in bulk, this small feature can make the process quicker and more intuitive. It’s especially important for products that are:
- Frequently bought in multiples (e.g., food items, party supplies)
- Part of bundles or kits
- Offered at discounted rates for bulk purchases
Adding a quantity selector ensures your store looks professional and functions efficiently for customers with different buying needs.
How to Add a Quantity Selector to Your Shopify Theme
<product-detail-quantities class="prd-DetailQuantities_Rows"> <fieldset class="prd-DetailQuantities_Row" data-product-detail-quantities-el="option" data-name="menge"> <legend class="prd-DetailQuantities_Legend"> Menge: <span class="prd-DetailQuantities_Indicator" data-product-detail-quantities-el="indicator">1</span> </legend> <product-detail-progress-bar class="prd-Detail_ProgressBar" aria-hidden="false"> <ul class="prd-ProgressBar" data-quantity="1" data-product-detail-progress-bar-el="list"> <li class="prd-ProgressBar_Item" data-product-detail-progress-bar-el="item" data-quantity="1" aria-current="true"></li> <li class="prd-ProgressBar_Item" data-product-detail-progress-bar-el="item" data-quantity="2" aria-current="false"> <div class="prd-ProgressBarItem_TextContainer"> <span class="prd-ProgressBarItem_Text prd-ProgressBarItem_Text-active"> 🤑 du sparst <span data-product-progress-discount-amount>€0,00 </span> </span> <span class="prd-ProgressBarItem_Text prd-ProgressBarItem_Text-inactive"> Spare <span data-product-progress-discount-amount>€0,00</span> </span> </div> </li> <li class="prd-ProgressBar_Item" data-product-detail-progress-bar-el="item" data-quantity="3" aria-current="false"> <div class="prd-ProgressBarItem_TextContainer"> <span class="prd-ProgressBarItem_Text prd-ProgressBarItem_Text-active"> 🤑 du sparst <span data-product-progress-discount-amount>€0,00 </span> </span> <span class="prd-ProgressBarItem_Text prd-ProgressBarItem_Text-inactive"> Spare <span data-product-progress-discount-amount>€0,00</span> </span> </div> </li> </ul> </product-detail-progress-bar> <div class="prd-DetailQuantities_Options"> <div class="prd-DetailQuantities_Option prd-DetailQuantities_Option-radio" data-product-quantity-option-radio> <input class="prd-DetailQuantities_Input" type="radio" id="menge-1" name="menge" value="1" data-units="1" data-discount="0" data-default-discount="0" data-product-detail-quantities-el="option-choice" data-hide-recharge="false" checked> <label class="prd-DetailQuantities_Button" for="menge-1"> <span class="prd-DetailQuantities_Units">1 Stück</span> </label> </div> <div class="prd-DetailQuantities_Option prd-DetailQuantities_Option-radio" data-product-quantity-option-radio> <input class="prd-DetailQuantities_Input" type="radio" id="menge-2" name="menge" value="2" data-units="" data-discount="0.0" data-default-discount="0.0" data-product-detail-quantities-el="option-choice" data-hide-recharge="false"> <label class="prd-DetailQuantities_Button" for="menge-2"> <span class="prd-DetailQuantities_Units"> Stück</span> <div class="prd-DetailQuantities_Discount" aria-hidden="false"> <span class="prd-DetailQuantities_DiscountText">Spare</span> <span class="prd-DetailQuantities_DiscountPercentage" data-product-quantity-discount-percentage> % </span> </div> </label> </div> <div class="prd-DetailQuantities_Option prd-DetailQuantities_Option-radio" data-product-quantity-option-radio> <input class="prd-DetailQuantities_Input" type="radio" id="menge-3" name="menge" value="3" data-units="" data-discount="0.0" data-default-discount="0.0" data-product-detail-quantities-el="option-choice" data-hide-recharge="false"> <label class="prd-DetailQuantities_Button" for="menge-3"> <span class="prd-DetailQuantities_Units"> Stück</span> <div class="prd-DetailQuantities_Discount" aria-hidden="false"> <span class="prd-DetailQuantities_DiscountText">Spare</span> <span class="prd-DetailQuantities_DiscountPercentage" data-product-quantity-discount-percentage> % </span> </div> </label> </div> </div> </fieldset> </product-detail-quantities> <style> .prd-DetailQuantities_Rows { display: block; margin-bottom: 20px; margin-top: 15px } .prd-DetailQuantities_Row { border: 0; margin: 0; padding: 0 } .prd-DetailQuantities_RowTop { align-items: center; display: flex; justify-content: space-between } .prd-DetailQuantities_Legend { grid-gap: 5px; align-items: baseline; color: #000; display: flex; gap: 5px; line-height: 1; padding-left: 0; padding-right: 0 } .prd-DetailQuantities_Legend .prd-DetailQuantities_Indicator,.prd-DetailQuantities_Legend .prd-DetailQuantities_Title { color: var(--text-color); display: block; font-family: Gordita Bold; font-size: 14px } .prd-DetailQuantities_Options { grid-gap: 10px; align-items: center; display: grid; gap: 10px; grid-template-columns: repeat(3,1fr); margin-top: 15px; position: relative } .prd-DetailQuantities_Option { height: 100% } .prd-DetailQuantities_Option input { display: none } .prd-DetailQuantities_Button { grid-gap: 2px; align-items: center; background-color: #fff; border: 1px solid #ddd; border-radius: 50px; cursor: pointer; display: flex; flex-direction: column; font-size: .8em; gap: 2px; height: 100%; justify-content: center; min-width: 60px; padding: 10px; position: relative; text-align: center; transition: border-color .3s ease } .prd-DetailQuantities_Button:hover { border-color: #1c1c1c } .prd-DetailQuantities_Button-soldOut { background-color: #f4f4f5; border: 1px solid #d8d8d8 } .prd-DetailQuantities_Units { display: block; font-size: 11px; line-height: 1; text-transform: capitalize } .prd-DetailQuantities_Discount { grid-gap: 5px; display: flex; gap: 5px; line-height: 1 } .prd-DetailQuantities_Discount[aria-hidden=true] { display: none } .prd-DetailQuantities_Discount-reversed { flex-direction: row-reverse } .prd-DetailQuantities_DiscountPercentage,.prd-DetailQuantities_DiscountText { color: #008B13; display: flex; font-size: 11px; line-height: 1; text-transform: capitalize } .prd-DetailQuantities_Input:checked+.prd-DetailQuantities_Button { border-color: #1c1c1c } .prd-DetailQuantities_Input:checked+.prd-DetailQuantities_Button:before { background-image: url("data:image/svg+xml;charset=utf-8,%3Csvg width='18' height='18' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Crect width='18' height='18' rx='9' fill='%23000'/%3E%3Cpath d='M7.333 12.5 4 9.521 5.167 8.48l2.166 1.936 5.5-4.915L14 6.543 7.333 12.5Z' fill='%23fff'/%3E%3C/svg%3E"); content: ""; height: 18px; position: absolute; right: 0; top: -8px; width: 18px; z-index: 1 } .prd-Detail_ProgressBar { display: block; margin-bottom: 15px; margin-top: 15px } .prd-Detail_ProgressBar[aria-hidden=true] { display: none } .prd-ProgressBar { grid-gap: 10px; align-items: center; background-color: #e8e8e8; border-radius: 5px; display: grid; gap: 10px; grid-template-columns: repeat(3,1fr); height: 4px; list-style: none; margin-top: 15px; position: relative } .prd-ProgressBar[data-quantity="1"]:after { width: calc(33.33333% - 8px) } .prd-ProgressBar[data-quantity="2"]:after { width: calc(66.66667% - 5px) } .prd-ProgressBar[data-quantity="3"]:after { width: 100% } .prd-ProgressBar:after { background-color: #008B12; border-radius: 5px; content: ""; height: 4px; left: 0; position: absolute; top: 0; transition: inline-size .1s ease-in-out } .prd-ProgressBar_Item { position: relative } .prd-ProgressBar_Item:after,.prd-ProgressBar_Item:before { content: ""; left: 50%; opacity: 0; position: absolute; transition: opacity .2s ease-in-out } .prd-ProgressBar_Item:before { border-bottom: 12px solid #008B13; bottom: 0 } .prd-ProgressBar_Item:after,.prd-ProgressBar_Item:before { border-left: 6px solid transparent; border-right: 6px solid transparent; transform: translate(-50%) } .prd-ProgressBar_Item:after { border-top: 12px solid #e8e8e8; top: 0 } .prd-ProgressBar_Item[data-quantity="2"]:after,.prd-ProgressBar_Item[data-quantity="2"]:before,.prd-ProgressBar_Item[data-quantity="3"]:after,.prd-ProgressBar_Item[data-quantity="3"]:before { opacity: 0 } .prd-ProgressBar_Item[data-quantity="2"][aria-current=true],.prd-ProgressBar_Item[data-quantity="2"][aria-current=true]:before,.prd-ProgressBar_Item[data-quantity="3"][aria-current=true],.prd-ProgressBar_Item[data-quantity="3"][aria-current=true]:before { opacity: 1 } .prd-ProgressBar_Item[data-quantity="2"][aria-current=true]:after,.prd-ProgressBar_Item[data-quantity="3"][aria-current=true]:after { opacity: 0 } [data-quantity="1"] .prd-ProgressBar_Item[data-quantity="2"],[data-quantity="1"] .prd-ProgressBar_Item[data-quantity="3"] { opacity: 1 } [data-quantity="1"] .prd-ProgressBar_Item[data-quantity="2"]:before,[data-quantity="1"] .prd-ProgressBar_Item[data-quantity="3"]:before { opacity: 0 } [data-quantity="1"] .prd-ProgressBar_Item[data-quantity="2"]:after,[data-quantity="1"] .prd-ProgressBar_Item[data-quantity="3"]:after,[data-quantity="2"] .prd-ProgressBar_Item[data-quantity="2"][data-quantity="3"]:after,[data-quantity="2"] .prd-ProgressBar_Item[data-quantity="3"][data-quantity="3"]:after { opacity: 1 } [data-quantity="3"] .prd-ProgressBar_Item[data-quantity="2"][data-quantity="2"],[data-quantity="3"] .prd-ProgressBar_Item[data-quantity="3"][data-quantity="2"] { opacity: 0 } .prd-ProgressBarItem_TextContainer { bottom: 32px; left: 0; opacity: 0; position: absolute; transition: opacity .2s ease-in-out; width: 100% } .prd-ProgressBarItem_TextContainer .prd-ProgressBarItem_Text { display: block; font-size: 10px; height: 0; left: 50%; opacity: 0; position: absolute; text-align: center; top: 50%; transform: translate(-50%,-50%); width: -webkit-max-content; width: -moz-max-content; width: max-content } .prd-ProgressBarItem_TextContainer .prd-ProgressBarItem_Text-inactive,[aria-current=true] .prd-ProgressBarItem_TextContainer,[aria-current=true] .prd-ProgressBarItem_TextContainer .prd-ProgressBarItem_Text-active { opacity: 1 } [aria-current=true] .prd-ProgressBarItem_TextContainer .prd-ProgressBarItem_Text-inactive { opacity: 0 } [aria-current=false] .prd-ProgressBarItem_TextContainer { opacity: .5 } </style> <script> // Option 1: Using DOMContentLoaded document.addEventListener('DOMContentLoaded', () => { class ProductDetailQuantities extends HTMLElement { constructor() { super(); this.init(); } init() { const inputs = this.querySelectorAll('[data-product-detail-quantities-el="option-choice"]'); const indicator = this.querySelector('[data-product-detail-quantities-el="indicator"]'); const progressItems = this.querySelectorAll('[data-product-detail-progress-bar-el="item"]'); const progressBar = this.querySelector('[data-product-detail-progress-bar-el="list"]'); const form = document.querySelector('form[action="/cart/add"]'); let quantityInput = form.querySelector('input[name="quantity"]'); if (!quantityInput) { quantityInput = document.createElement('input'); quantityInput.type = 'hidden'; quantityInput.name = 'quantity'; quantityInput.value = '1'; form.appendChild(quantityInput); } inputs.forEach(input => { input.addEventListener('change', () => { if (input.checked) { if (indicator) { indicator.textContent = input.dataset.units; } if (progressBar) { progressBar.setAttribute('data-quantity', input.value); } progressItems.forEach(item => { const isCurrentItem = item.dataset.quantity === input.value; item.setAttribute('aria-current', isCurrentItem); }); if (quantityInput) { quantityInput.value = input.dataset.units; quantityInput.dispatchEvent(new Event('change', { bubbles: true })); } document.querySelectorAll('form[action="/cart/add"]').forEach(cartForm => { let formQuantityInput = cartForm.querySelector('input[name="quantity"]'); if (!formQuantityInput) { formQuantityInput = document.createElement('input'); formQuantityInput.type = 'hidden'; formQuantityInput.name = 'quantity'; cartForm.appendChild(formQuantityInput); } formQuantityInput.value = input.dataset.units; formQuantityInput.dispatchEvent(new Event('change', { bubbles: true })); }); } }); }); } } customElements.define('product-detail-quantities', ProductDetailQuantities); }); </script>
Kostenlose Shopify Sections. Jede Woche. 🤩
Erhalte neue, verkaufsstarke Sections und Snippets für deinen Shopify-Shop – ganz ohne Programmierkenntnisse.
- Wenn du dich für eine Auswahl entscheidest, wird die Seite komplett aktualisiert.
- Wird in einem neuen Fenster geöffnet.