class Buildoz extends HTMLElement { constructor(){ super() // always call super() first! this.attrs = {} } static get observedAttributes(){ //observable attributes triggering attributeChangedCallback // anything added here will be observed for all buildoz tags // in your child, add you local 'color' observable attr with : // return([...super.observedAttributes, 'color']) return([]) } static define(name, cls){ const tag = `bz-${name}` if(!customElements.get(tag)) { // no wild redefinition customElements.define(tag, cls) } return cls } connectedCallback(){ // added to the DOM this.classList.add('buildoz') } disconnectedCallback(){ // removed from the DOM } attributeChangedCallback(name, oldValue, newValue) { this.attr[name] = newValue //console.log(`attr ${name} changed from ${oldValue} to ${newValue}`) } } class BZselect extends Buildoz { constructor(){ super() this.open = false //defaults, can be changed by corresponding attributes this.attrs = { size: 0, label: 'Select...', } } connectedCallback() { super.connectedCallback() this.button = document.createElement('button') this.button.textContent = this.attrs.label this.prepend(this.button) this.button.addEventListener('click', this.toggle.bind(this)) this.options = this.querySelectorAll('option') // let toShow = this.attrs.size // for(const opt of this.options){ // if(toShow>0){ // opt.style.display = 'block' // } else { // opt.style.display = 'none' // } // toShow-- // } } static get observedAttributes(){ return [...super.observedAttributes, 'label', 'size'] } attributeChangedCallback(name, oldValue, newValue) { super.connectedCallback() // on the fly changes here } toggle(evt){ for(const opt of this.options){ if(this.open) opt.classList.remove('open') else opt.classList.add('open') } this.open = !this.open } fill(opts){ this.el.innerHTML ='' if(!Array.isArray(opts)) opts = [opts] const ul = Object.assign(document.createElement('ul'), { className: `bz-selector ${this.config.ulClass ? this.config.ulClass :''}`, }) for(const opt of opts){ const li = document.createElement('li') li.innerHTML = `${opt.markup}` li.setAttribute('data-value', opt.value) ul.append(li) } this.el.append(ul) } } Buildoz.define('select', BZselect)