1import{Component}from"@theme/component";import{fetchConfig,debounce,onAnimationEnd,prefersReducedMotion,resetShimmer,startViewTransition}from"@theme/utilities";import{morphSection,sectionRenderer}from"@theme/section-renderer";import{ThemeEvents,QuantitySelectorUpdateEvent,CartSectionRestoredEvent}from"@theme/events";import{cartPerformance}from"@theme/performance";import{createViewEventElement,CartErrorEvent,CartLinesUpdateEvent,StandardEvents}from"@shopify/events";export class CartItemsComponent extends createViewEventElement(Component){static#pendingQuantityUpdates=new Set;static get pendingQuantityUpdates(){return Array.from(CartItemsComponent.#pendingQuantityUpdates)}#debouncedOnChange=debounce(event=>{event instanceof QuantitySelectorUpdateEvent&&this.#onQuantityChange(event)},300);#pendingCartFetch=null;#isExternalCartUpdate(event){return!(event.target instanceof Node)||!this.contains(event.target)}async#refreshCartSection(options={}){try{await sectionRenderer.renderSection(this.sectionId,{cache:!1,mode:this.isDrawer?"hydration":"full",...options}),this.#updateCartQuantitySelectorButtonStates()}catch(error){if(error?.name==="AbortError")return;this.dispatchEvent(new CartErrorEvent({error:error?.message||"Failed to refresh cart",code:"SERVICE_UNAVAILABLE"}))}}#handleDiscountUpdate=event=>{const isExternalCartUpdate=this.#isExternalCartUpdate(event);event.promise?.then(({detail})=>{if(!isExternalCartUpdate)return;const sectionsHtml=detail?.sections?.[this.sectionId];sectionsHtml?(sectionRenderer.abortRender(this.sectionId),morphSection(this.sectionId,sectionsHtml,{mode:this.isDrawer?"hydration":"full"}),this.#updateCartQuantitySelectorButtonStates()):this.#refreshCartSection()}).catch(error=>{error?.name!=="AbortError"&&console.warn("[cart-items] Event promise rejected:",error)})};#handleNoteUpdate=event=>{this.#isExternalCartUpdate(event)&&event.promise?.then(({detail})=>{const sectionsHtml=detail?.sections?.[this.sectionId];sectionsHtml?(sectionRenderer.abortRender(this.sectionId),morphSection(this.sectionId,sectionsHtml,{mode:this.isDrawer?"hydration":"full"})):this.#refreshCartSection()}).catch(error=>{error?.name!=="AbortError"&&console.warn("[cart-items] Event promise rejected:",error)})};connectedCallback(){super.connectedCallback(),document.addEventListener(StandardEvents.cartLinesUpdate,this.#handleCartUpdate),document.addEventListener(ThemeEvents.quantitySelectorUpdate,this.#debouncedOnChange),document.addEventListener(StandardEvents.cartDiscountUpdate,this.#handleDiscountUpdate),document.addEventListener(StandardEvents.cartNoteUpdate,this.#handleNoteUpdate),window.addEventListener("pageshow",this.#handlePageShow)}disconnectedCallback(){super.disconnectedCallback(),document.removeEventListener(StandardEvents.cartLinesUpdate,this.#handleCartUpdate),document.removeEventListener(ThemeEvents.quantitySelectorUpdate,this.#debouncedOnChange),document.removeEventListener(StandardEvents.cartDiscountUpdate,this.#handleDiscountUpdate),document.removeEventListener(StandardEvents.cartNoteUpdate,this.#handleNoteUpdate),window.removeEventListener("pageshow",this.#handlePageShow)}#handlePageShow=event=>{const navigationEntry=globalThis.performance?.getEntriesByType?.("navigation")[0],navigationType=CartItemsComponent.#isNavigationTiming(navigationEntry)?navigationEntry.type:void 0;!event.persisted&&navigationType!=="back_forward"||this.dataset.sectionId&§ionRenderer.renderSection(this.sectionId,{cache:!1,mode:this.isDrawer?"hydration":"full",injectStylesheet:this.isDrawer&&this.querySelector("[data-cart-drawer-empty]")!==null}).then(()=>{this.#updateCartQuantitySelectorButtonStates(),this.dispatchEvent(new CartSectionRestoredEvent)}).catch(error=>{error?.name!=="AbortError"&&console.warn("[cart-items] bfcache restore render failed:",error)})};#onQuantityChange(event){if(!(event.target instanceof Node)||!this.contains(event.target))return;const{quantity,cartLine:line}=event.detail;if(!line)return;if(quantity===0)return this.onLineItemRemove(line);this.updateQuantity({line,quantity,action:"change"});const lineItemRow=this.refs.cartItemRows[line-1];if(!lineItemRow)return;lineItemRow.querySelector("text-component")?.shimmer()}onLineItemRemove(line){this.updateQuantity({line,quantity:0,action:"clear"});const cartItemRowToRemove=this.refs.cartItemRows[line-1];if(!cartItemRowToRemove)return;const rowsToRemove=[cartItemRowToRemove,...this.refs.cartItemRows.filter(row=>row.dataset.parentKey===cartItemRowToRemove.dataset.key)],isEmptyCart=rowsToRemove.length==this.refs.cartItemRows.length,template=document.getElementById("empty-cart-template");if(isEmptyCart&&template instanceof HTMLTemplateElement){const clone=document.importNode(template.content,!0);startViewTransition(()=>{document.getElementById("cart-drawer-heading")?.remove(),this.replaceChildren(clone)},[this.isDrawer?"empty-cart-drawer":"empty-cart-page"]);return}rowsToRemove.forEach(row=>{const remove=()=>row.remove();if(prefersReducedMotion())return remove();row.style.setProperty("--row-height",`${row.clientHeight}px`),row.classList.add("removing"),onAnimationEnd(row,remove)})}async updateQuantity(config){const cartPerformaceUpdateMarker=cartPerformance.createStartingMarker(`${config.action}:user-action`),deferredUpdatePromise=CartLinesUpdateEvent.createPromise();let completeQuantityUpdate=()=>{};const quantityUpdate=new Promise(resolve=>{completeQuantityUpdate=()=>resolve()});CartItemsComponent.#pendingQuantityUpdates.add(quantityUpdate);try{this.#disableCartItems();const{line,quantity}=config,{cartTotal}=this.refs,cartItemsComponents=document.querySelectorAll("cart-items-component"),sectionsToUpdate=new Set([this.sectionId]);for(const item of cartItemsComponents)item instanceof HTMLElement&&item.dataset.sectionId&§ionsToUpdate.add(item.dataset.sectionId);for(const sectionId of sectionsToUpdate)sectionRenderer.abortRender(sectionId);const body=JSON.stringify({line,quantity,sections:Array.from(sectionsToUpdate).join(","),sections_url:window.location.pathname});
1cartTotal?.shimmer();const lineId=this.refs.cartItemRows[line-1]?.dataset.key??"";this.dispatchEvent(new CartLinesUpdateEvent({action:config.action==="change"&&quantity>0?"update":"remove",context:"cart",lines:[{id:lineId,quantity}],promise:deferredUpdatePromise.promise}));const responseText=await(await fetch(`${Theme.routes.cart_change_url}`,fetchConfig("json",{body}))).text(),parsedResponseText=JSON.parse(responseText);if(resetShimmer(this),parsedResponseText.errors){this.#handleCartError(line,parsedResponseText),deferredUpdatePromise.reject(new Error(parsedResponseText.errors));return}const sections=parsedResponseText.sections,sectionHTML=sections?.[this.sectionId],parsedItemCount=Number(parsedResponseText.item_count);let newCartItemCount=Number.isFinite(parsedItemCount)?parsedItemCount:0;if(this.#updateQuantitySelectors(parsedResponseText),!sectionHTML){deferredUpdatePromise.resolve({cart:CartLinesUpdateEvent.createCartFromAjaxResponse(parsedResponseText),detail:{sections:sections??void 0,items:parsedResponseText.items,itemCount:newCartItemCount,source:"cart-items-component",didError:!1}}),await this.#refreshCartSection();return}const newCartHiddenItemCount=new DOMParser().parseFromString(sectionHTML,"text/html").querySelector('[ref="cartItemCount"]')?.textContent;newCartItemCount=newCartHiddenItemCount?parseInt(newCartHiddenItemCount,10):newCartItemCount,deferredUpdatePromise.resolve({cart:CartLinesUpdateEvent.createCartFromAjaxResponse(parsedResponseText),detail:{sections:sections??void 0,items:parsedResponseText.items,itemCount:newCartItemCount,source:"cart-items-component",didError:!1}}),sectionRenderer.abortRender(this.sectionId),await morphSection(this.sectionId,sectionHTML,{mode:this.isDrawer?"hydration":"full"}),this.#updateCartQuantitySelectorButtonStates()}catch(error){console.error(error),deferredUpdatePromise.reject(error),this.dispatchEvent(new CartErrorEvent({error:error?.message||"Failed to update cart",code:"SERVICE_UNAVAILABLE"}))}finally{try{this.#enableCartItems(),cartPerformance.measureFromMarker(cartPerformaceUpdateMarker)}finally{CartItemsComponent.#pendingQuantityUpdates.delete(quantityUpdate),completeQuantityUpdate()}}}#handleCartError=(line,parsedResponseText)=>{const quantityInput=this.refs.quantitySelectors[line-1]?.querySelector("input");if(!quantityInput)throw new Error("Quantity input not found");quantityInput.value=quantityInput.defaultValue;const cartItemError=this.refs[`cartItemError-${line}`],cartItemErrorContainer=this.refs[`cartItemErrorContainer-${line}`];if(!(cartItemError instanceof HTMLElement))throw new Error("Cart item error not found");if(!(cartItemErrorContainer instanceof HTMLElement))throw new Error("Cart item error container not found");cartItemError.textContent=parsedResponseText.errors,cartItemErrorContainer.classList.remove("hidden"),this.dispatchEvent(new CartErrorEvent({error:parsedResponseText.errors||"Cart update failed",code:"INVALID"}))};#handleCartUpdate=event=>{event.target!==this&&event.promise?.then(async({detail})=>{const cartItemsHtml=detail?.sections?.[this.sectionId],wasEmptyCartDrawer=this.isDrawer&&this.querySelector("[data-cart-drawer-empty]")!==null,morphOptions={mode:this.isDrawer?"hydration":"full",injectStylesheet:wasEmptyCartDrawer};if(cartItemsHtml){sectionRenderer.abortRender(this.sectionId);const existingKeys=new Set(this.refs.cartItemRows?.map(row=>row.dataset.key)??[]);if(wasEmptyCartDrawer?startViewTransition(()=>{morphSection(this.sectionId,cartItemsHtml,morphOptions)},["fill-cart-drawer"]):await morphSection(this.sectionId,cartItemsHtml,morphOptions),!wasEmptyCartDrawer&&!prefersReducedMotion())for(const row of this.refs.cartItemRows??[])existingKeys.has(row.dataset.key)||(row.classList.add("adding"),onAnimationEnd(row,()=>row.classList.remove("adding")));this.#updateCartQuantitySelectorButtonStates()}else this.#refreshCartSection(morphOptions)}).catch(error=>{error?.name!=="AbortError"&&console.warn("[cart-items] Event promise rejected:",error)})};#disableCartItems(){this.classList.add("cart-items-disabled")}#enableCartItems(){this.classList.remove("cart-items-disabled")}#updateQuantitySelectors(updatedCart){if(updatedCart.items)for(const item of updatedCart.items){const variantId=item.variant_id.toString(),selectors=document.querySelectorAll(`quantity-selector-component[data-variant-id="${variantId}"]`);for(const selector of selectors){const input=selector.querySelector("input[data-cart-quantity]");input&&(input.setAttribute("data-cart-quantity",item.quantity.toString()),"updateCartQuantity"in selector&&typeof selector.updateCartQuantity=="function"&&selector.updateCartQuantity())}}}#updateCartQuantitySelectorButtonStates(){for(const selector of document.querySelectorAll("cart-quantity-selector-component"))selector.updateButtonStates?.()}async fetchCartData(){return this.#pendingCartFetch?this.#pendingCartFetch:(this.#pendingCartFetch=(async()=>{const response=await fetch(`${Theme.routes.cart_url}.json`,{headers:{Accept:"application/json"},credentials:"same-origin"});if(!response.ok)throw new Error(`Failed to fetch cart: ${response.status} ${response.statusText}`);return await response.json()})().finally(()=>{this.#pendingCartFetch=null}),this.#pendingCartFetch)}get sectionId(){const{sectionId}=this.dataset;if(!sectionId)throw new Error("Section id missing");return sectionId}get isDrawer(){return this.dataset.drawer!==void 0}static#isNavigationTiming(entry){return entry?.entryType==="navigation"}}customElements.get("cart-items-component")||customElements.define("cart-items-component",CartItemsComponent); 2//# sourceMappingURL=/cdn/shop/t/19/assets/component-cart-items.js.map?v=128607540178034746111790544831
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.