Skip to content

Instantly share code, notes, and snippets.

@hemant-tivlabs
Created July 8, 2021 09:49
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save hemant-tivlabs/f33f2e3491ce9fcb69dbba122f49a78b to your computer and use it in GitHub Desktop.
Save hemant-tivlabs/f33f2e3491ce9fcb69dbba122f49a78b to your computer and use it in GitHub Desktop.
Magic Swatches - convert Shopify PDP variant option dropdowns to swatches

Magic Swatches

Convert the basic variant option dropdowns on Shopify PDP to swatches.

Usage

let mSwatches = new magicSwatches();
mSwatches.render();
class magicSwatches {
constructor(config) {
config = typeof config == 'undefined' ? {} : config;
this.option_wrapper_selector = typeof config.option_wrapper != 'undefined' ? config.option_wrapper : '.selector-wrapper';
this.product_form_selector = typeof config.product_form != 'undefined' ? config.product_form : 'form.product-form';
this.strip_giftcard_values = typeof config.strip_giftcard_values != 'undefined' ? config.strip_giftcard_values : true;
this.form = document.querySelector(this.product_form_selector);
this.option_wrappers = document.querySelectorAll(this.option_wrapper_selector);
this.variant_selectbox = this.form.querySelector('[name="id"]');
};
triggerChangeEvent(element) {
if("createEvent" in document) {
var evt = document.createEvent("HTMLEvents");
evt.initEvent("change", false, true);
element.dispatchEvent(evt);
} else {
element.fireEvent("onchange");
}
}
render() {
let styles = [];
this.option_wrappers.forEach((option_wrapper, i) => {
let selectbox = option_wrapper.querySelector('select'),
nodeInnerHTML = '';
selectbox.setAttribute('data-optionuid', `ms-option-selectbox-${i}`);
selectbox.querySelectorAll('option').forEach((option) => {
let activeClass = selectbox.value == option.getAttribute('value') ? ' class="active-option"' : '',
optionDisplayValue = this.strip_giftcard_values && window.location.href.indexOf('gift') > -1 && window.location.href.indexOf('card') > -1 ? option.getAttribute('value').replace(/[^\d.-]/g, '').replace('.00', '') : option.getAttribute('value');
nodeInnerHTML = `${nodeInnerHTML}<span${activeClass} data-option="${option.getAttribute('value')}">${optionDisplayValue}</span>`;
});
styles.push(`.swatch-selector[data-optionuid="ms-option-selectbox-${i}"] { line-height: ${selectbox.offsetHeight}px; min-height: ${selectbox.offsetHeight}px }`);
selectbox.style.display = 'none';
let newNode = document.createElement('div');
newNode.setAttribute('class', 'swatch-selector');
newNode.setAttribute('data-optionuid', `ms-option-selectbox-${i}`);
newNode.innerHTML = nodeInnerHTML;
selectbox.parentElement.insertBefore(newNode, selectbox);
});
document.querySelectorAll(`.swatch-selector span[data-option]`).forEach((swatchOptionSpan) => {
swatchOptionSpan.addEventListener('click', (e) => {
e.preventDefault();
let swatchOption = e.target,
swatchValue = swatchOption.getAttribute('data-option'),
swatchSelectbox = document.querySelector(`select[data-optionuid="${swatchOptionSpan.parentElement.getAttribute('data-optionuid')}"]`);
swatchOption.parentElement.querySelectorAll('span').forEach((opt) => {
if(opt.getAttribute('data-option') == swatchValue) {
opt.classList.add('active-option');
} else {
opt.classList.remove('active-option');
}
});
swatchSelectbox.value = swatchValue;
this.triggerChangeEvent(swatchSelectbox);
}, false);
});
let basicStyles = [
'.swatch-selector { display: flex; flex-wrap: wrap; margin-left: -.25em; margin-right: -.25em }',
'.swatch-selector span { border: 1px solid #DDD; border-radius: 4px; cursor: pointer; margin: .25em; padding: 0 1em }',
'.swatch-selector span:hover { border-color: #666; box-shadow: -2px -2px 5px rgba(0,0,0,0.15) inset }',
'.swatch-selector span.active-option { background-color: #666; border-color: #333; box-shadow: -2px -2px 5px rgba(0,0,0,0.15) inset; color: #FFF }'
];
let styleSheetElement = document.createElement('style');
styleSheetElement.setAttribute('type', 'text/css');
styleSheetElement.innerHTML = basicStyles.join('') + styles.join('');
document.getElementsByTagName('head')[0].appendChild(styleSheetElement);
};
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment