1import{LitElement,html,css,unsafeHTML}from"https://cdn.jsdelivr.net/gh/lit/dist@3/all/lit-all.min.js";export class SkioPlanPicker extends LitElement{static properties={key:{type:String},product:{type:Object},productHandle:{type:String},selectedVariant:{type:Object},options:{type:Object},availableSellingPlanGroups:{state:!0},selectedSellingPlanGroup:{type:Object},selectedSellingPlan:{type:Object},debug:{type:Boolean}};static styles=[css` 2 .skio-plan-picker { 3 display: flex; 4 gap: 1rem; 5 padding: 0; 6 border: 0; 7 font-size: 15px; 8 color: black; 9 } 10 11 :host([layout='hidden']) .skio-plan-picker { 12 display: none; 13 } 14 15 :host([layout='vertical']) .skio-plan-picker { 16 flex-direction: column; 17 } 18 19 :host([layout='horizontal']) .skio-plan-picker { 20 flex-direction: row; 21 } 22 23 .sr-only { 24 position: absolute; 25 overflow: hidden; 26 clip: rect(0, 0, 0, 0); 27 width: 1px; 28 height: 1px; 29 margin: -1px; 30 padding: 0; 31 border: 0; 32 } 33 34 .group-container { 35 display: block; 36 position: relative; 37 transition: border-color 0.2s ease; 38 border: var(--skio-group-border-width, 1px) solid var(--skio-group-border-color, #ccc); 39 border-radius: var(--skio-group-border-radius, 0); 40 background-color: var(--skio-group-background-color, transparent); 41 color: var(--skio-group-text-color, #000); 42 } 43 44 .group-container--selected { 45 border-color: var(--skio-group-border-selected-color, #333); 46 } 47 48 .group-container--last { 49 order: 1; 50 } 51 52 .group-input { 53 position: absolute; 54 opacity: 0; 55 width: 0px; 56 height: 0px; 57 } 58 59 .group-input:focus-visible ~ .group-label { 60 outline: 2px #ccc solid; 61 outline-offset: 4px; 62 } 63 64 .group-label { 65 display: flex; 66 flex-direction: column; 67 padding: 10px; 68 cursor: pointer; 69 } 70 71 .group-topline { 72 display: flex; 73 align-items: center; 74 width: 100%; 75 76 gap: 8px; 77 } 78 79 .skio-radio__container { 80 display: flex; 81 color: var(--skio-group-border-color, #333); 82 } 83 84 .group-container--selected .skio-radio__container { 85 color: var(--skio-group-border-selected-color, #333); 86 } 87 88 .skio-radio { 89 transform-origin: center; 90 opacity: 0; 91 transform: scale(0); 92 transition: transform 0.25s cubic-bezier(0.4, 0, 0.2, 1); 93 } 94 95 .group-label:hover .skio-radio { 96 opacity: 0.75; 97 transform: scale(1); 98 } 99 100 .group-container--selected .group-label .skio-radio { 101 opacity: 1; 102 transform: scale(1); 103 } 104 105 .skio-price { 106 display: flex; 107 justify-content: flex-end; 108 flex-wrap: wrap; 109 align-items: center; 110 text-align: right; 111 gap: 4px; 112 113 line-height: 1; 114 115 margin-left: auto; 116 vertical-align: middle; 117 118 font-weight: 500; 119 120 display: none; 121 } 122 123 .skio-price s { 124 font-size: 13px; 125 126 font-weight: 400; 127 opacity: 0.75; 128 } 129 130 .group-content { 131 display: flex; 132 flex-direction: column; 133 opacity: 1; 134 width: auto; 135 max-height: 1000px; 136 transition: 137 max-height 0.15s cubic-bezier(0.4, 0, 0.2, 1), 138 opacity 0.25s cubic-bezier(0.4, 0, 0.2, 1); 139 } 140 141 .group-content.margin-left { 142 margin-left: 25px; 143 } 144 145 .group-content p { 146 margin: 0.5rem 0 0 0; 147 font-size: 13px; 148 color: #000; 149 } 150 151 /* Hide frequency if not selected */ 152 .group-container:not(.group-container--selected) .group-content { 153 pointer-events: none; 154 opacity: 0; 155 max-height: 0; 156 visibility: hidden; 157 } 158 159 .group-title { 160 width: 100%; 161 max-width: 80%; 162 line-height: 1.5; 163 } 164 165 .savings { 166 color: var(--skio-discount-text-color, #fff); 167 } 168 169 .savings.bubble { 170 padding: 0px 8px; 171 background-color: var(--skio-discount-color, #0fa573); 172 border: 1px var(--skio-discount-color, #0fa573) solid; 173 border-radius: 4px; 174 font-size: 12px; 175 color: var(--skio-discount-text-color, #fff); 176 177 white-space: nowrap; 178 } 179 180 .selling-plan-dropdown { 181 appearance: none; 182 -webkit-appearance: none; 183 -moz-appearance: none; 184 display: flex; 185 align-items: center; 186 gap: 5px; 187 width: 100%; 188 margin-top: 5px; 189 padding: 8px 30px 8px 10px; 190 /* background-color: #f7f7f7; */ 191 background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' class='h-6 w-6' fill='none' viewBox='0 0 24 24' stroke='currentColor' stroke-width='2'%3E%3Cpath stroke-linecap='round' stroke-linejoin='round' d='M19 9l-7 7-7-7' /%3E%3C/svg%3E"); 192 background-repeat: no-repeat; 193 background-position: right 10px top 50%; 194 background-size: 16px; 195 border: 1px solid #ccc; 196 border-radius: 2px; 197 font-size: 14px; 198 text-overflow: ellipsis; 199 white-space: nowrap; 200 } 201 202 .skio-frequency.skio-frequency--one { 203 background-image: none; 204 } 205 206 .skio-frequency span { 207 text-transform: lowercase; 208 } 209 210 .selling-plan-buttons { 211 display: grid; 212 grid-template-columns: repeat(auto-fill, minmax(var(--skio-button-plan-selector-width, 20px), 1fr)); 213 gap: 10px; 214 padding: 0.75rem 0; 215 border: 0; 216 font-size: 13px; 217 } 218 219 .selling-plan-buttons input[type='radio'] { 220 position: absolute; 221 opacity: 0; 222 width: 0; 223 height: 0; 224 } 225 226 .selling-plan-buttons label { 227 display: flex; 228 align-items: center; 229 justify-content: center; 230 cursor: pointer; 231 border: 1px solid #ccc; 232 text-align: center; 233 padding: 1rem 0.5rem; 234 } 235 236 .selling-plan-buttons input[type='radio']:checked + label { 237 border-color: #000; 238 } 239 240 .selling-plan-buttons input:focus-visible + label { 241 outline: 2px #ccc solid; 242 outline-offset: 4px; 243 } 244 245 .setupMode { 246 position: relative; 247 color: black; 248 padding: 1rem; 249 display: flex; 250 flex-direction: column; 251 gap: 10px; 252 margin-bottom: 1rem; 253 font-size: 14px; 254 border-style: solid; 255 border-width: 4px; 256 border-image: repeating-linear-gradient(-55deg, #000, #000 20px, #ffb101 20px, #ffb101 40px) 10; 257 } 258 259 .setupMode:after { 260 content: 'Setup Mode'; 261 position: absolute; 262 top: 0; 263 right: 0; 264 background-color: black; 265 color: white; 266 padding: 0.25rem 1rem; 267 font-size: 13px; 268 } 269 270 .setupMode .detection { 271 display: grid; 272 grid-template-columns: auto 1fr; 273 gap: 10px; 274 } 275 276 .setupMode .detection small { 277 grid-column: 1/-1; 278 } 279 `];constructor(){super(),this.currency=window.Shopify.currency.active||"USD",this.language=window.Shopify.locale||"en-US",this.moneyFormatter=new Intl.NumberFormat(this.language,{style:"currency",currency:this.currency,minimumFractionDigits:2,maximumFractionDigits:2}),this.debug=window?.Shopify?.designMode,this.variantChanged=!1}connectedCallback(){super.connectedCallback(),this.productHandle&&(this.loading=!0,this.fetchProduct(this.productHandle)),this.bindFormEvents()}radioTemplate(){return html` 280 <div class="skio-radio__container"> 281 <svg width="18" height="18" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg"> 282 <circle cx="12" cy="12" r="10" stroke="currentColor" stroke-width="1"></circle> 283 <circle class="skio-radio" cx="12" cy="12" r="7" fill="currentColor"></circle> 284 </svg> 285 </div> 286 `}sellingPlanDropdown(group){return html` 287 <select 288 class="selling-plan-dropdown" 289 @change=${e=>{this.selectSellingPlan(e.target.value)}} 290 > 291 ${group?this.getAvailableSellingPlans(group).map(selling_plan=>html` <option ?selected=${group.selected_selling_plan.id===selling_plan.id} value=${selling_plan.id}>${selling_plan.name}</option> `):""} 292 </select> 293 `}sellingPlanButtons(group){return html` 294 <fieldset class="selling-plan-buttons"> 295 <legend class="sr-only">Select subscription interval</legend> 296 ${group?this.getAvailableSellingPlans(group).map(selling_plan=>html` 297 <input 298 type="radio" 299 name="selling_plan_button" 300 value="${selling_plan}" 301 id="selling_plan_button-${selling_plan.id}" 302 @change="${e=>this.selectSellingPlan(selling_plan.id)}" 303 ?checked=${group.selected_selling_plan===selling_plan} 304 /> 305 306 <label for="selling_plan_button-${selling_plan.id}"> ${selling_plan.name} </label> 307 `):""} 308 </fieldset> 309 `}invalidIcon(){return html` 310 <svg width="24" height="24" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="#D22B2B" class="w-6 h-6"> 311 <path stroke-linecap="round" stroke-linejoin="round" d="M9.75 9.75l4.5 4.5m0-4.5l-4.5 4.5M21 12a9 9 0 11-18 0 9 9 0 0118 0z" /> 312 </svg> 313 `}validIcon(){return html` 314 <svg width="24" height="24" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="#0BDA51" class="w-6 h-6"> 315 <path stroke-linecap="round" stroke-linejoin="round" d="M9 12.75L11.25 15 15 9.75M21 12a9 9 0 11-18 0 9 9 0 0118 0z" /> 316 </svg> 317 `}setupMode(){return html` 318 <div class="setupMode"> 319 Skio Plan Picker 320 <small>This will not appear on the live site.</small> 321 322 <small>Key: ${this.key}</small> 323 324 <div class="detection">${this.product?this.validIcon():this.invalidIcon()} Product</div> 325 326 <div class="detection">${this.selectedVariant?this.validIcon():this.invalidIcon()} Selected Variant</div> 327 328 <div class="detection">${this.form?this.validIcon():this.invalidIcon()} Form</div> 329 330 <div class="detection">${this.variantInput?this.validIcon():this.invalidIcon()} Variant Input</div> 331 332 <div class="detection"> 333 ${this.variantChanged?this.validIcon():this.invalidIcon()} Variant Change Detection 334 <small>Please attempt to change the selected variant.</small> 335 </div> 336 337 <small>If any of these don't pass please troubleshoot using our <a target="_blank" rel="noreferrer" href="https://integrate.skio.com/troubleshooting">troubleshooting guide</a>.</small> 338 </div> 339 `}groupContent(group){return html` 340 <div class="group-content ${this.options?.show_radio_selector?"margin-left":""}"> 341 ${this.options?.selector_type=="dropdown"?this.sellingPlanDropdown(group):""} 342 343 <!-- TODO: Make the label have the border instead of the group --> 344 ${this.options?.selector_type=="button"?this.sellingPlanButtons(group):""} ${this.additionalContentText()} 345 </div> 346 `}render(){return!this.viable()||this.options?.layout==="hidden"?this.debug?this.setupMode():"":this.selectedVariant.selling_plan_allocations.length===0&&!this.options?.show_without_subscription?this.debug?this.setupMode():"":html` 347 ${this.debug?this.setupMode():null} 348 349 <fieldset class="skio-plan-picker" role="radiogroup" aria-labelledby="skio-plan-picker-legend"> 350 <legend id="skio-plan-picker-legend" class="${this.options?.show_legend?"":"sr-only"}">${unsafeHTML(this.options?.legend_content)}</legend> 351 352 ${!this.product.requires_selling_plan&&this.availableSellingPlanGroups?.length?html` 353 <div 354 class="group-container ${this.selectedSellingPlanGroup==null?"group-container--selected":""} ${this.options?.onetime_first?"":"group-container--last"}" 355 @click=${()=>this.selectSellingPlanGroup(null)} 356 > 357 <input 358 id="one-time-${this.key}" 359 class="group-input" 360 name="skio-group-${this.key}" 361 type="radio" 362 value="One time purchase" 363 ?checked=${!this.selectedSellingPlanGroup} 364 @change=${()=>this.selectSellingPlanGroup(null)} 365 /> 366 367 <label class="group-label" for="one-time-${this.key}"> 368 <div class="group-topline"> 369 ${this.options?.show_radio_selector?this.radioTemplate():""} 370 371 <div class="group-title">${this.options?.onetime_title?this.options?.onetime_title:"One time purchase"}</div> 372 373 <div class="skio-price" aria-live="polite"> 374 ${this.options?.show_compare_price&&this.selectedVariant?.compare_at_price>this.selectedVariant.price?html`<s aria-hidden="true">${this.money(this.selectedVariant.compare_at_price)}</s>`:""} 375 ${this.money(this.selectedVariant.price)} 376 </div> 377 </div> 378 </label> 379 </div> 380 `:""} 381 ${this.availableSellingPlanGroups?.length?this.availableSellingPlanGroups.map((group,index)=>html` 382 <div class="group-container ${this.selectedSellingPlanGroup==group?"group-container--selected":""}"> 383 <input 384 id="group-${index}-${this.key}" 385 class="group-input" 386 name="skio-group-${this.key}" 387 type="radio" 388 value="${group.id}" 389 @change=${()=>this.selectSellingPlanGroup(group)} 390 ?checked=${this.selectedSellingPlanGroup==group} 391 /> 392 393 <label class="group-label" for="group-${index}-${this.key}"> 394 <div class="group-topline"> 395 ${this.options?.show_radio_selector?this.radioTemplate():""} 396 397 <div class="group-title"> 398 ${group.name=="Subscription"&&this.options?.subscription_title?this.options?.subscription_title:group.name=="Prepaid"&&this.options?.prepaid_title?this.options?.prepaid_title:group.name} 399 ${this.discount(group.selected_selling_plan).percent>0?html` <span class="savings ${this.options?.discount_style}"> ${this.discountText(group.selected_selling_plan)} </span> `:html``} 400 </div> 401 402 <div class="skio-price" aria-live="polite"> 403 ${this.options?.show_compare_price&&(this.selectedVariant?.compare_at_price>this.selectedVariant.price||this.selectedVariant.price>this.price(group.selected_selling_plan,!1))?html`<s aria-hidden="true">${this.money(this.selectedVariant.compare_at_price?this.selectedVariant.compare_at_price:this.selectedVariant.price)}</s>`:""} 404 ${this.price(group.selected_selling_plan)} 405 </div> 406 </div> 407 408 ${this.options?.layout=="vertical"?this.groupContent(group):""} 409 </label> 410 </div> 411 `):""} 412 </fieldset> 413 ${this.options?.layout=="horizontal"?this.groupContent(this.selectedSellingPlanGroup):""} 414 `}bindFormEvents(){this.form=document.querySelector(`#${this.options?.form_id}`)||this.closest('form[action*="/cart/add"]'),this.form&&(this.variantInput=this.form.querySelector('[name="id"]'),this.variantInput&&this.variantInput.addEventListener("change",e=>{this.selectedVariant=this.product.variants.find(variant=>variant.id==e.target.value),this.variantChanged=!0}))}updated(changed){if(this.viable()){if(changed.has("product")&&this.product&&(this.key=this.key?this.key:this.product.id),changed.has("selectedVariant")&&this.selectedVariant){const filteredSellingPlanGroups=this.product.selling_plan_groups.filter(selling_plan_group=>selling_plan_group.app_id==="SKIO"&&!selling_plan_group.name.toLowerCase().includes("hidden-")&&!selling_plan_group.name.toLowerCase().includes("dynamic box subscription"));if(this.availableSellingPlanGroups=filteredSellingPlanGroups.filter(selling_plan_group=>selling_plan_group.sell
414ing_plans.some(selling_plan=>this.selectedVariant.selling_plan_allocations.some(selling_plan_allocation=>selling_plan_allocation.selling_plan_id===selling_plan.id))),this.options?.combine_groups&&(this.availableSellingPlanGroups=[{name:this.options?.combined_group_name,selling_plans:this.availableSellingPlanGroups.flatMap(group=>group.selling_plans),id:"combined_group",app_id:"SKIO"}]),this.availableSellingPlanGroups?.length){const urlSelectedSellingPlanId=new URL(window.location.href).searchParams.get("selling_plan");if(this.availableSellingPlanGroups.forEach(group=>{const availableSellingPlans=this.getAvailableSellingPlans(group),urlSelectedSellingPlan=availableSellingPlans.find(plan=>plan.id==urlSelectedSellingPlanId),nameSelectedSellingPlan=availableSellingPlans.find(plan=>plan.name===this.selectedSellingPlan?.name),defaultSellingPlan=this.options?.default_subscription&&this.options.default_subscription.trim()!==""?availableSellingPlans.find(plan=>plan.name.toLowerCase().includes(this.options.default_subscription.toLowerCase())):null;group.selected_selling_plan=urlSelectedSellingPlan||nameSelectedSellingPlan||defaultSellingPlan||availableSellingPlans[0];const isAnyPlanSelected=urlSelectedSellingPlan||nameSelectedSellingPlan||defaultSellingPlan;group.selected=!!isAnyPlanSelected}),!this.variantChanged&&this.options?.start_onetime==!1||this.product.requires_selling_plan==!0||urlSelectedSellingPlanId||this.selectedSellingPlan){let selectedSellingPlanId=(this.availableSellingPlanGroups.find(group=>group.selected)||this.availableSellingPlanGroups[0]).selected_selling_plan.id;this.selectSellingPlan(selectedSellingPlanId)}else this.selectSellingPlanGroup(null)}else this.selectSellingPlanGroup(null)}if(changed.has("selectedSellingPlan")){document.querySelectorAll(`[skio-price][skio-key="${this.key}"]`).forEach(el=>{el.innerHTML=this.price(this.selectedSellingPlan)}),document.querySelectorAll(`[skio-price][skio-key="${this.key}"]`).forEach(el=>{el.innerHTML=this.price(this.selectedSellingPlan)});const event=new CustomEvent("skio::update-selling-plan",{bubbles:!0,composed:!0,detail:{variant:this.selectedVariant,sellingPlan:this.selectedSellingPlan,key:this.key}});this.dispatchEvent(event),this.dispatchEvent(new CustomEvent("change",{detail:{value:this.selectedSellingPlan?.id}}))}this.updateForm(),this.updateURLParams()}}log(...args){args.unshift(`%c[skio plan picker][${this.key}]`,"color: #8770f2;"),console.log.apply(console,args)}error(...args){args.unshift(`%c [skio plan picker][${this.key}]`,"color: #ff0000"),console.error.apply(console,args)}appendOrdinalSuffix(num){const j=num%10,k=num%100;return j==1&&k!=11?num+"st":j==2&&k!=12?num+"nd":j==3&&k!=13?num+"rd":num+"th"}money(price){return this.moneyFormatter.format(price/100)}viable(){const errors=[];return this.querySelector("input[name=selling_plan]")||errors.push("Missing selling plan input"),this.product||errors.push("No product found. Please pass a product or productHandle to the skio-plan-picker component."),this.selectedVariant||errors.push("No variant found. Please pass a product or productHandle to the skio-plan-picker component."),this.form||errors.push('No form found. Please add a form_id to the plan picker through the Shopify customizer or ensure that the element is in a form that has an input with name="id".'),this.variantInput||errors.push('No variant input found. Please add a form_id to the plan picker through the Shopify customizer or ensure that the element is in a form that has an input with name="id"'),errors.length==0?!0:(this.error("Errors",errors),!1)}getAvailableSellingPlans(group){return group.selling_plans.filter(selling_plan=>this.selectedVariant.selling_plan_allocations.some(selling_plan_allocation=>selling_plan_allocation.selling_plan_id===selling_plan.id))}selectSellingPlanGroup(group){this.selectedSellingPlanGroup=group,this.selectedSellingPlan=group?.selected_selling_plan}selectSellingPlan(selling_plan_id){const selectedGroup=this.availableSellingPlanGroups.find(group=>group.selling_plans.some(plan=>plan.id==selling_plan_id)),selectedSellingPlan=selectedGroup.selling_plans.find(plan=>plan.id==selling_plan_id);selectedGroup.selected_selling_plan=selectedSellingPlan,this.selectedSellingPlanGroup=selectedGroup,this.selectedSellingPlan=selectedSellingPlan}additionalContentText(){if(!(!this.options?.additional_subscription_content||this.options?.additional_subscription_content==""))return unsafeHTML(this.options?.additional_subscription_content.replaceAll("[discount]",this.options?.discount_format==="absolute"?this.money(this.discount(this.selectedSellingPlan).absolute):this.discount(this.selectedSellingPlan).percent+"%").replaceAll("[future_price_adjustments]",this.postCheckoutDiscountsText(this.selectedSellingPlan)||""))}discountText(selling_plan){const discount=this.discount(selling_plan);return unsafeHTML(this.options?.discount_text.replaceAll("[discount]",this.options?.discount_format==="absolute"?this.money(discount.absolute):discount.percent+"%").replaceAll("[future_price_adjustments]",this.postCheckoutDiscountsText(selling_plan)||""))}discount(selling_plan){return selling_plan?this.getDiscountFromPriceAdjustment(selling_plan,selling_plan.price_adjustments[0]):{percent:0,amount:0}}postCheckoutPriceAdjustments(selling_plan){const{price_adjustments}=selling_plan;return price_adjustments.filter(({position})=>position!==1).map(price_adjustment=>this.getDiscountFromPriceAdjustment(selling_plan,price_adjustment))}postCheckoutDiscountsText(sellingPlan=this.selectedSellingPlan){if(!sellingPlan||!this.options?.future_price_adjustments_text||this.future_price_adjustments_text=="")return;const postCheckoutPriceAdjustments=this.postCheckoutPriceAdjustments(sellingPlan);if(postCheckoutPriceAdjustments.length)return postCheckoutPriceAdjustments.map((discount,index)=>this.options?.future_price_adjustments_text.replaceAll("[discount]",this.options?.discount_format==="absolute"?this.money(discount.absolute):discount.percent+"%").replaceAll("[order_count]",index+1).replaceAll("[order_count_ordinal]",this.appendOrdinalSuffix(index+1)))}getDiscountFromPriceAdjustment(selling_plan,price_adjustment){const discount={percent:0,amount:0,absolute:0};let multiplier=1;if(this.product.selling_plan_groups.find(group=>group.selling_plans.some(plan=>plan.id==selling_plan.id))?.name==="Prepaid"){const str=selling_plan.name,intervalDate=/\b\d+\s*(days|weeks|months|years)\b/gi,intervals=str.match(intervalDate)[0].match(/\d+/g);multiplier=intervals[0]/(intervals[1]||1),multiplier=multiplier>1?multiplier:1}const price=this.selectedVariant.price,compareAtPrice=this.selectedVariant.compare_at_price&&this.selectedVariant.compare_at_price>price?this.selectedVariant.compare_at_price:price;switch(price_adjustment.value_type){case"percentage":discount.percent=price_adjustment.value,discount.absolute=Math.round(price*price_adjustment.value/100),discount.amount=Math.round(price*price_adjustment.value/100);break;case"fixed_amount":discount.percent=Math.round(price_adjustment.value*1/price*100),discount.absolute=price_adjustment.value,discount.amount=price_adjustment.value;break;case"price":discount.percent=Math.round((compareAtPrice*multiplier-price_adjustment.value)*1/(compareAtPrice*multiplier)*100),discount.absolute=compareAtPrice*multiplier-price_adjustment.value,discount.amount=price-price_adjustment.value;break}return discount}price(selling_plan,formatted=!0){return formatted?this.money(this.selectedVariant.price-this.discount(selling_plan).amount):this.selectedVariant.price-this.discount(selling_plan).amount}updateForm(){let $sellingPlan=this.querySelector("input[name=selling_plan]");$sellingPlan&&($sellingPlan.value=this.selectedSellingPlan?this.selectedSellingPlan.id:"")}updateURLParams(){const url=new URL(window.location.href);this.selectedSellingPlan?(url.searchParams.set("selling_plan",this.selectedSellingPlan.id),window.history.replaceState({},"",url.href)):(url.searchParams.delete("selling_plan"),window.history.replaceState({},"",url.href))}addToCart(quantity){const items=[{id:this.selectedVariant.id,quantity,...this.selectedSellingPlan&&{selling_plan:this.selectedSellingPlan?.id}}];fetch("/cart/add.js",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({items})}).then(response=>response.json()).then(response=>{this.log("Added item to cart: ",response);const event=new CustomEvent("skio::added-to-cart",{bubbles:!0,composed:!0,detail:{response,key:this.key}});this.dispatchEvent(event)}).catch(error=>{this.error(`SKIO ${this.key} error adding item to cart: `,error)})}fetchProduct=handle=>fetch(`/products/${handle}.js`).then(response=>response.json()).then(product=>(this.product=product,this.selectedVariant=product.variants[0],product))}customElements.get("skio-plan-picker")||customElements.define("skio-plan-picker",SkioPlanPicker),window&&(window.SkioPlanPicker=SkioPlanPicker); 415//# sourceMappingURL=/cdn/shop/t/99/assets/skio-plan-picker-component.js.map?v=118556644771927324341762321222
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.