diff --git a/bundle.js b/bundle.js index 4018053..3312a2b 100644 --- a/bundle.js +++ b/bundle.js @@ -1,7 +1,7 @@ -(()=>{"use strict";(()=>{class t{#t;#e;#i;#s;constructor(t){this.#t=t,this.#e=t.querySelector("input"),this.#i=!0,this.#s=""}get isValid(){return this.#i}get errorMessage(){return this.#s}checkValidity(){this.setCustomValidity(""),this.#e.checkValidity();let t=this.#e.validity;return t.valid&&(t=this.#n()),this.#i=t.valid,this.#s=this.#l(t),this.isValid}setCustomValidity(t){this.#e.setCustomValidity(t),this.#i=this.#e.validity.valid,this.#s=t}#n(){const{badInput:t,customError:e,patternMismatch:i,typeMismatch:s,valid:n,rangeOverflow:l,rangeUnderflow:a,tooLong:o,tooShort:r,valueMissing:h,stepMismatch:d}=this.#e.validity,u=Object.assign({},{badInput:t,customError:e,patternMismatch:i,typeMismatch:s,valid:n,rangeOverflow:l,rangeUnderflow:a,tooLong:o,tooShort:r,valueMissing:h,stepMismatch:d},this.#a(),this.#o());return u.valid=!u.valueMissing&&!u.rangeUnderflow&&!u.rangeOverflow,u}#a(){const t=this.#e.value.trim();return{valueMissing:this.#t.hasAttribute("required")&&""===t}}#o(){if("number"!==this.#e.type)return{rangeUnderflow:!1,rangeOverflow:!1};const{min:t,max:e,value:i}=this.#e;return{rangeUnderflow:""!==t&&+i<+t,rangeOverflow:""!==e&&+i>+e}}#l(t){const e="number"===this.#e.type,{badInput:i,rangeOverflow:s,rangeUnderflow:n,tooLong:l,tooShort:a,valueMissing:o,stepMismatch:r}=t;return e&&i?"Invalid number":e&&r&&"1"===this.#e.step?"Must be an integer":s?"Greater than "+this.#e.max:n?"Less than "+this.#e.min:l?"Max length is "+this.#e.maxLength:a?"Min length is "+this.#e.minLength:!i&&o?"Required":this.#e.validationMessage}}const e=Object.freeze({Shift:"ShiftLeft",Esc:"Escape",Enter:"Enter",Up:"ArrowUp",Down:"ArrowDown"}),i=(t,...e)=>{let i=t[0];for(let n=0;n/g,">").replace(/"/g,""").replace(/'/g,"'"):"",i+=t[n+1];var s;return i};class s extends HTMLElement{static#r=new Set(["autocomplete","autofocus","disabled","max","maxlength","min","minlength","name","pattern","readonly","step","type","value"]);#e;#h;#d;#u={onTrailingIconClick:[],onChangeValue:[],onInput:[]};#c;connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("input"),this.#h=this.querySelector(".text-input__error"),this.#d=new t(this),this.#m(),this.#E(),this.hasAttribute("value")&&(this.value=this.getAttribute("value"))}disconnectedCallback(){this.setAttribute("value",this.value),window.removeEventListener("visibilitychange",this.#g.bind(this),{capture:!0})}get value(){return this.rawValue.trim()}get rawValue(){return this.#e.value}set value(t){this.#e.value=function(t){return!(void 0===t||!Number.isFinite(t))}(t)||"string"==typeof t?t:"",this.checkValidity()}checkValidity(){const t=this.#d.checkValidity();return this.errorMessage=this.#d.errorMessage,t}get errorMessage(){return this.#h.textContent}set errorMessage(t){this.#c=null,this.#d.setCustomValidity(t),this.#h.textContent=this.#d.errorMessage}onTrailingIconClick(t){this.#u.onTrailingIconClick.push(t)}onInput(t){this.#u.onInput.push(t)}onChangeValue(t){this.#u.onChangeValue.push(t)}focus(t){this.#e.focus(t)}setDisabled(t){this.toggleAttribute("disabled",t),this.#e.toggleAttribute("disabled",t)}#b(t){"number"!==this.#e.type||t.key!==e.Up&&t.key!==e.Down||t.preventDefault(),t.key!==e.Enter||t.repeat||this.#v()}#w(){const t=this.checkValidity();this.#u.onInput.forEach((e=>e(this.value,t)))}#v(){this.#c!==this.value&&(this.#c=this.value,this.#y())}#V(){this.#u.onTrailingIconClick.forEach((t=>t()))}#y(){this.checkValidity(),this.#u.onChangeValue.forEach((t=>t(this.value)))}#m(){for(const t of this.attributes)s.#r.has(t.name)&&this.#e.setAttribute(t.name,t.value);"number"!==this.getAttribute("type")||this.hasAttribute("step")||this.#e.setAttribute("step","any")}#E(){this.#e.addEventListener("keydown",this.#b.bind(this)),this.#e.addEventListener("input",this.#w.bind(this)),this.#e.addEventListener("focusout",this.#v.bind(this)),this.querySelector(".text-input__trailing-icon").addEventListener("click",this.#V.bind(this)),window.addEventListener("visibilitychange",this.#g.bind(this),{capture:!0})}#g(){document.activeElement===this.#e&&this.#e.blur()}#p(){const t=this.getAttribute("data-icon")||"";return i` +(()=>{"use strict";(()=>{class t{#t;#e;#i;#s;constructor(t){this.#t=t,this.#e=t.querySelector("input"),this.#i=!0,this.#s=""}get isValid(){return this.#i}get errorMessage(){return this.#s}checkValidity(){this.setCustomValidity(""),this.#e.checkValidity();let t=this.#e.validity;return t.valid&&(t=this.#n()),this.#i=t.valid,this.#s=this.#l(t),this.isValid}setCustomValidity(t){this.#e.setCustomValidity(t),this.#i=this.#e.validity.valid,this.#s=t}#n(){const{badInput:t,customError:e,patternMismatch:i,typeMismatch:s,valid:n,rangeOverflow:l,rangeUnderflow:a,tooLong:o,tooShort:r,valueMissing:h,stepMismatch:d}=this.#e.validity,u=Object.assign({},{badInput:t,customError:e,patternMismatch:i,typeMismatch:s,valid:n,rangeOverflow:l,rangeUnderflow:a,tooLong:o,tooShort:r,valueMissing:h,stepMismatch:d},this.#a(),this.#o());return u.valid=!u.valueMissing&&!u.rangeUnderflow&&!u.rangeOverflow,u}#a(){const t=this.#e.value.trim();return{valueMissing:this.#t.hasAttribute("required")&&""===t}}#o(){if("number"!==this.#e.type)return{rangeUnderflow:!1,rangeOverflow:!1};const{min:t,max:e,value:i}=this.#e;return{rangeUnderflow:""!==t&&+i<+t,rangeOverflow:""!==e&&+i>+e}}#l(t){const e="number"===this.#e.type,{badInput:i,rangeOverflow:s,rangeUnderflow:n,tooLong:l,tooShort:a,valueMissing:o,stepMismatch:r}=t;return e&&i?"Invalid number":e&&r&&"1"===this.#e.step?"Must be an integer":s?"Greater than "+this.#e.max:n?"Less than "+this.#e.min:l?"Max length is "+this.#e.maxLength:a?"Min length is "+this.#e.minLength:!i&&o?"Required":this.#e.validationMessage}}const e=Object.freeze({Shift:"ShiftLeft",Esc:"Escape",Enter:"Enter",Up:"ArrowUp",Down:"ArrowDown"}),i=(t,...e)=>{let i=t[0];for(let n=0;n/g,">").replace(/"/g,""").replace(/'/g,"'"):"",i+=t[n+1];var s;return i};class s extends HTMLElement{static#r=new Set(["autocomplete","autofocus","disabled","max","maxlength","min","minlength","name","pattern","readonly","step","type","value"]);#e;#h;#d;#u={onTrailingIconClick:[],onChangeValue:[],onInput:[]};#c;connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("input"),this.#h=this.querySelector(".text-input__error"),this.#d=new t(this),this.#m(),this.#g(),this.hasAttribute("value")&&(this.value=this.getAttribute("value"))}disconnectedCallback(){this.setAttribute("value",this.value),window.removeEventListener("visibilitychange",this.#E.bind(this),{capture:!0})}get value(){return this.rawValue.trim()}get rawValue(){return this.#e.value}set value(t){this.#e.value=function(t){return!(void 0===t||!Number.isFinite(t))}(t)||"string"==typeof t?t:"",this.checkValidity()}checkValidity(){const t=this.#d.checkValidity();return this.errorMessage=this.#d.errorMessage,t}get errorMessage(){return this.#h.textContent}set errorMessage(t){this.#c=null,this.#d.setCustomValidity(t),this.#h.textContent=this.#d.errorMessage}onTrailingIconClick(t){this.#u.onTrailingIconClick.push(t)}onInput(t){this.#u.onInput.push(t)}onChangeValue(t){this.#u.onChangeValue.push(t)}focus(t){this.#e.focus(t)}setDisabled(t){this.toggleAttribute("disabled",t),this.#e.toggleAttribute("disabled",t)}#b(t){"number"!==this.#e.type||t.key!==e.Up&&t.key!==e.Down||t.preventDefault(),t.key!==e.Enter||t.repeat||this.#v()}#w(){const t=this.checkValidity();this.#u.onInput.forEach((e=>e(this.value,t)))}#v(){this.#c!==this.value&&(this.#c=this.value,this.#y())}#V(){this.#u.onTrailingIconClick.forEach((t=>t()))}#y(){this.checkValidity(),this.#u.onChangeValue.forEach((t=>t(this.value)))}#m(){for(const t of this.attributes)s.#r.has(t.name)&&this.#e.setAttribute(t.name,t.value);"number"!==this.getAttribute("type")||this.hasAttribute("step")||this.#e.setAttribute("step","any")}#g(){this.#e.addEventListener("keydown",this.#b.bind(this)),this.#e.addEventListener("input",this.#w.bind(this)),this.#e.addEventListener("focusout",this.#v.bind(this)),this.querySelector(".text-input__trailing-icon").addEventListener("click",this.#V.bind(this)),window.addEventListener("visibilitychange",this.#E.bind(this),{capture:!0})}#E(){document.activeElement===this.#e&&this.#e.blur()}#p(){const t=this.getAttribute("data-icon")||"";return i` ${t} -

`}static get is(){return"text-input"}}window.customElements.define(s.is,s);class n extends HTMLElement{#f;#x=[];#k=0;#C=-1;#u={onOptionClick:[]};get options(){return this.#x}set options(t){this.#S(t),this.innerHTML=this.#p(),this.#f=this.querySelector("ul"),this.#A(),this.#E()}set filter(t){const e=t.toLowerCase();for(const t of this.querySelectorAll("li")){const{displayName:i}=this.#x[t.dataset.index],s=i.toLowerCase().indexOf(e);t.innerHTML=this.#M(i,s,e.length),t.toggleAttribute("hidden",-1===s)}const i=this.#I();i&&(i.hasAttribute("hidden")?this.#L():i.scrollIntoView({block:"nearest"}))}show(){this.style.display="block",this.#A()}hide(){this.style.display="none",this.#L()}selectNextItem(){const t=this.#T();if(this.hasSelectedElement()){const e=t.indexOf(this.#I());if(t.length-1<=e)return;this.#D(t[e+1].dataset.index)}else{if(0===t.length)return;this.#D(t[0].dataset.index)}}selectPrevItem(){const t=this.#T();if(this.hasSelectedElement()){const e=t.indexOf(this.#I());if(0===e)return;this.#D(t[e-1].dataset.index)}else{if(0===t.length)return;this.#D(t[t.length-1].dataset.index)}}triggerClickOnSelectedItem(){this.hasSelectedElement()&&this.#I().dispatchEvent(new MouseEvent("mousedown"))}hasSelectedElement(){return null!=this.#I()}isVisible(){return"none"!==window.getComputedStyle(this).display}onOptionClick(t){this.#u.onOptionClick.push(t)}connectedCallback(){this.innerHTML=this.#p(),this.#f=this.querySelector("ul"),this.#E()}#S(t){this.#x=[...t].sort(((t,e)=>t.displayName.localeCompare(e.displayName)))}#T(){return[...this.#f.querySelectorAll("li:not([hidden])")]}#E(){for(const t of this.querySelectorAll("li"))t.addEventListener("mousedown",(()=>{const e=this.#x[t.dataset.index];this.#u.onOptionClick.forEach((t=>t(e)))}))}#p(){return`\n `}#A(){const t=this.parentElement.getBoundingClientRect();0===this.#k&&(this.#k=Math.max(...this.#x.map((t=>function(t){const e=document.createElement("span");document.body.appendChild(e),e.textContent=t,e.style.fontSize="1rem",e.style.visibility="hidden",e.style.position="absolute";const i=Math.ceil(e.getBoundingClientRect().width)+1;return e.remove(),i}(t.displayName))),0));const e=Math.max(this.#k+24+22,t.width),i=document.documentElement.clientWidth-t.left;this.#f.style.right=e>i?0:null,this.#f.style.width=`${Math.min(e,document.documentElement.clientWidth)}px`}#I(){return this.querySelector(`li[data-index="${this.#C}"]`)}#D(t){this.#L(),this.#C=t;const e=this.#I();e.classList.add("list-box__item--active"),e.scrollIntoView({block:"nearest"})}#L(){this.#C>=0&&(this.#I().classList.remove("list-box__item--active"),this.#C=-1)}#M(t,e,s){if(e>=0){const n=t.substring(0,e),l=t.substring(e,e+s),a=t.substring(e+s);return i`${n}${l}${a}`}return t}static get is(){return"list-box"}}window.customElements.define(n.is,n);class l extends HTMLElement{#e;#N;#q;#O=null;#$;#u={onChangeValue:[]};connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("text-input"),this.#N=this.querySelector("list-box"),this.#$=this.hasAttribute("shouldMatchOptions"),this.#E()}get value(){return this.#q}get rawValue(){return this.#e.value}set value(t){this.#q=t,this.#e.value=t&&t.displayName?t.displayName:""}set initialValue(t){this.value=t,this.#O=t}set options(t){this.#N.options=t,this.#_()}set errorMessage(t){this.#e.errorMessage=t}checkValidity(){return this.#P()&&this.#e.checkValidity()}onChangeValue(t){this.#u.onChangeValue.push(t)}setDisabled(t){this.toggleAttribute("disabled",t),this.#e.setDisabled(t)}#w(){this.errorMessage="",this.#_(),this.#N.isVisible()||this.#N.show()}#U(){this.#_(),this.#N.show()}#H(){this.#R()}#B(t){this.value=t,this.#R()}#K(){this.value={displayName:""},this.#e.querySelector("input").focus()}#F(t){switch([e.Up,e.Down].includes(t.code)&&(t.preventDefault(),t.stopImmediatePropagation()),t.key){case e.Esc:this.#R();break;case e.Enter:this.#N.isVisible()&&(this.#N.hasSelectedElement()?this.#N.triggerClickOnSelectedItem():this.#R());break;case e.Down:this.#N.isVisible()||this.#N.show(),this.#N.selectNextItem();break;case e.Up:this.#N.isVisible()||this.#N.show(),this.#N.selectPrevItem()}}#z(){this.#y()}#R(){this.#N.hide(),this.#y()}#y(){this.#P()&&this.#W()&&(this.#O=this.value,this.#u.onChangeValue.forEach((t=>t(this.value))))}#P(){const t=this.#e.value;if(""===t)return this.#q=null,!0;if(this.value&&this.value.displayName===t)return this.errorMessage="",!0;if(!this.#$)return this.errorMessage="",this.#q={displayName:t},!0;for(const e of this.#N.options)if(e.displayName===t)return this.errorMessage="",this.#q=e,this.#e.value=e.displayName,!0;return this.#q=null,this.errorMessage="Select from list",!1}#_(){this.#N.filter=this.#e.value}#W(){return this.#O!==this.value}#E(){const t=this.#e.querySelector("input");this.addEventListener("keydown",this.#F.bind(this)),t.addEventListener("input",this.#w.bind(this)),t.addEventListener("blur",this.#H.bind(this)),t.addEventListener("focus",this.#U.bind(this)),this.#e.onTrailingIconClick(this.#K.bind(this)),this.#e.onChangeValue(this.#z.bind(this)),this.#N.onOptionClick(this.#B.bind(this))}#p(){const t=this.hasAttribute("required")?"required":"",e=this.hasAttribute("disabled")?"disabled":"",s=this.hasAttribute("no-icon")?"":"close";return i` +

`}static get is(){return"text-input"}}window.customElements.define(s.is,s);class n extends HTMLElement{#f;#x=[];#k=0;#C=-1;#u={onOptionClick:[]};get options(){return this.#x}set options(t){this.#S(t),this.innerHTML=this.#p(),this.#f=this.querySelector("ul"),this.#A(),this.#g()}set filter(t){const e=t.toLowerCase();for(const t of this.querySelectorAll("li")){const{displayName:i}=this.#x[t.dataset.index],s=i.toLowerCase().indexOf(e);t.innerHTML=this.#I(i,s,e.length),t.toggleAttribute("hidden",-1===s)}const i=this.#M();i&&(i.hasAttribute("hidden")?this.#L():i.scrollIntoView({block:"nearest"}))}show(){this.style.display="block",this.#A()}hide(){this.style.display="none",this.#L()}selectNextItem(){const t=this.#T();if(this.hasSelectedElement()){const e=t.indexOf(this.#M());if(t.length-1<=e)return;this.#D(t[e+1].dataset.index)}else{if(0===t.length)return;this.#D(t[0].dataset.index)}}selectPrevItem(){const t=this.#T();if(this.hasSelectedElement()){const e=t.indexOf(this.#M());if(0===e)return;this.#D(t[e-1].dataset.index)}else{if(0===t.length)return;this.#D(t[t.length-1].dataset.index)}}triggerClickOnSelectedItem(){this.hasSelectedElement()&&this.#M().dispatchEvent(new MouseEvent("mousedown"))}hasSelectedElement(){return null!=this.#M()}isVisible(){return"none"!==window.getComputedStyle(this).display}onOptionClick(t){this.#u.onOptionClick.push(t)}connectedCallback(){this.innerHTML=this.#p(),this.#f=this.querySelector("ul"),this.#g()}#S(t){this.#x=[...t].sort(((t,e)=>t.displayName.localeCompare(e.displayName)))}#T(){return[...this.#f.querySelectorAll("li:not([hidden])")]}#g(){for(const t of this.querySelectorAll("li"))t.addEventListener("mousedown",(()=>{const e=this.#x[t.dataset.index];this.#u.onOptionClick.forEach((t=>t(e)))}))}#p(){return`\n `}#A(){const t=this.parentElement.getBoundingClientRect();0===this.#k&&(this.#k=Math.max(...this.#x.map((t=>function(t){const e=document.createElement("span");document.body.appendChild(e),e.textContent=t,e.style.fontSize="1rem",e.style.visibility="hidden",e.style.position="absolute";const i=Math.ceil(e.getBoundingClientRect().width)+1;return e.remove(),i}(t.displayName))),0));const e=Math.max(this.#k+24+22,t.width),i=document.documentElement.clientWidth-t.left;this.#f.style.right=e>i?0:null,this.#f.style.width=`${Math.min(e,document.documentElement.clientWidth)}px`}#M(){return this.querySelector(`li[data-index="${this.#C}"]`)}#D(t){this.#L(),this.#C=t;const e=this.#M();e.classList.add("list-box__item--active"),e.scrollIntoView({block:"nearest"})}#L(){this.#C>=0&&(this.#M().classList.remove("list-box__item--active"),this.#C=-1)}#I(t,e,s){if(e>=0){const n=t.substring(0,e),l=t.substring(e,e+s),a=t.substring(e+s);return i`${n}${l}${a}`}return t}static get is(){return"list-box"}}window.customElements.define(n.is,n);class l extends HTMLElement{#e;#O;#N;#q=null;#$;#u={onChangeValue:[]};connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("text-input"),this.#O=this.querySelector("list-box"),this.#$=this.hasAttribute("shouldMatchOptions"),this.#g()}get value(){return this.#N}get rawValue(){return this.#e.value}set value(t){this.#N=t,this.#e.value=t&&t.displayName?t.displayName:""}set initialValue(t){this.value=t,this.#q=t}set options(t){this.#O.options=t,this.#_()}set errorMessage(t){this.#e.errorMessage=t}checkValidity(){return this.#P()&&this.#e.checkValidity()}onChangeValue(t){this.#u.onChangeValue.push(t)}setDisabled(t){this.toggleAttribute("disabled",t),this.#e.setDisabled(t)}#w(){this.errorMessage="",this.#_(),this.#O.isVisible()||this.#O.show()}#U(){this.#_(),this.#O.show()}#H(){this.#R()}#B(t){this.value=t,this.#R()}#K(){this.value={displayName:""},this.#e.querySelector("input").focus()}#F(t){switch([e.Up,e.Down].includes(t.code)&&(t.preventDefault(),t.stopImmediatePropagation()),t.key){case e.Esc:this.#R();break;case e.Enter:this.#O.isVisible()&&(this.#O.hasSelectedElement()?this.#O.triggerClickOnSelectedItem():this.#R());break;case e.Down:this.#O.isVisible()||this.#O.show(),this.#O.selectNextItem();break;case e.Up:this.#O.isVisible()||this.#O.show(),this.#O.selectPrevItem()}}#z(){this.#y()}#R(){this.#O.hide(),this.#y()}#y(){this.#P()&&this.#W()&&(this.#q=this.value,this.#u.onChangeValue.forEach((t=>t(this.value))))}#P(){const t=this.#e.value;if(""===t)return this.#N=null,!0;if(this.value&&this.value.displayName===t)return this.errorMessage="",!0;if(!this.#$)return this.errorMessage="",this.#N={displayName:t},!0;for(const e of this.#O.options)if(e.displayName===t)return this.errorMessage="",this.#N=e,this.#e.value=e.displayName,!0;return this.#N=null,this.errorMessage="Select from list",!1}#_(){this.#O.filter=this.#e.value}#W(){return this.#q!==this.value}#g(){const t=this.#e.querySelector("input");this.addEventListener("keydown",this.#F.bind(this)),t.addEventListener("input",this.#w.bind(this)),t.addEventListener("blur",this.#H.bind(this)),t.addEventListener("focus",this.#U.bind(this)),this.#e.onTrailingIconClick(this.#K.bind(this)),this.#e.onChangeValue(this.#z.bind(this)),this.#O.onOptionClick(this.#B.bind(this))}#p(){const t=this.hasAttribute("required")?"required":"",e=this.hasAttribute("disabled")?"disabled":"",s=this.hasAttribute("no-icon")?"":"close";return i` - `}static get is(){return"typeahead-input"}}window.customElements.define(l.is,l);class a extends HTMLElement{#e;#N;#q;#O=null;#u={onShowDropdown:[],onChangeValue:[]};get value(){return this.#q}set value(t){this.#e.value=t&&t.displayName?t.displayName:"",this.#q=t}set options(t){this.#N.options=t}showDropdown(){this.#N.show(),this.#u.onShowDropdown.forEach((t=>t()))}onShowDropdown(t){this.#u.onShowDropdown.push(t)}onChangeValue(t){this.#u.onChangeValue.push(t)}checkValidity(){return this.#P()}connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("text-input"),this.#N=this.querySelector("list-box"),this.#E()}#E(){this.addEventListener("keydown",this.#F.bind(this));const t=this.#e.querySelector("input");t.addEventListener("focus",this.#U.bind(this)),t.addEventListener("focusout",this.#j.bind(this)),t.addEventListener("click",this.#G.bind(this)),this.#N.onOptionClick(this.#B.bind(this))}#U(){this.showDropdown()}#j(){this.#R()}#B(t){this.#e.value=t.displayName,this.#q=t,this.#R()}#G(){this.showDropdown()}#F(t){switch([e.Up,e.Down].includes(t.code)&&(t.preventDefault(),t.stopImmediatePropagation()),t.key){case e.Esc:t.preventDefault(),this.#R(),this.#e.focus();break;case e.Enter:this.#N.isVisible()&&(t.stopPropagation(),this.#N.hasSelectedElement()?this.#N.triggerClickOnSelectedItem():this.#N.hide());break;case e.Down:this.#N.isVisible()||this.#N.show(),this.#N.selectNextItem();break;case e.Up:this.#N.isVisible()||this.#N.show(),this.#N.selectPrevItem()}}#R(){this.#N.hide(),this.#y()}#y(){this.#P()&&this.#O!==this.value&&(this.#O=this.value,this.#u.onChangeValue.forEach((t=>t(this.value))))}#P(){return this.#e.hasAttribute("required")&&!this.#e.value?this.#e.errorMessage="Required":this.#e.errorMessage="",this.#e.checkValidity()}#p(){const t=this.hasAttribute("required")?"required":"",e=this.hasAttribute("disabled")?"disabled":"";return i` + `}static get is(){return"typeahead-input"}}window.customElements.define(l.is,l);class a extends HTMLElement{#e;#O;#N;#q=null;#u={onShowDropdown:[],onChangeValue:[]};get value(){return this.#N}set value(t){this.#e.value=t&&t.displayName?t.displayName:"",this.#N=t}set options(t){this.#O.options=t}showDropdown(){this.#O.show(),this.#u.onShowDropdown.forEach((t=>t()))}onShowDropdown(t){this.#u.onShowDropdown.push(t)}onChangeValue(t){this.#u.onChangeValue.push(t)}checkValidity(){return this.#P()}connectedCallback(){this.innerHTML=this.#p(),this.#e=this.querySelector("text-input"),this.#O=this.querySelector("list-box"),this.#g()}#g(){this.addEventListener("keydown",this.#F.bind(this));const t=this.#e.querySelector("input");t.addEventListener("focus",this.#U.bind(this)),t.addEventListener("focusout",this.#j.bind(this)),t.addEventListener("click",this.#G.bind(this)),this.#O.onOptionClick(this.#B.bind(this))}#U(){this.showDropdown()}#j(){this.#R()}#B(t){this.#e.value=t.displayName,this.#N=t,this.#R()}#G(){this.showDropdown()}#F(t){switch([e.Up,e.Down].includes(t.code)&&(t.preventDefault(),t.stopImmediatePropagation()),t.key){case e.Esc:t.preventDefault(),this.#R(),this.#e.focus();break;case e.Enter:this.#O.isVisible()&&(t.stopPropagation(),this.#O.hasSelectedElement()?this.#O.triggerClickOnSelectedItem():this.#O.hide());break;case e.Down:this.#O.isVisible()||this.#O.show(),this.#O.selectNextItem();break;case e.Up:this.#O.isVisible()||this.#O.show(),this.#O.selectPrevItem()}}#R(){this.#O.hide(),this.#y()}#y(){this.#P()&&this.#q!==this.value&&(this.#q=this.value,this.#u.onChangeValue.forEach((t=>t(this.value))))}#P(){return this.#e.hasAttribute("required")&&!this.#e.value?this.#e.errorMessage="Required":this.#e.errorMessage="",this.#e.checkValidity()}#p(){const t=this.hasAttribute("required")?"required":"",e=this.hasAttribute("disabled")?"disabled":"";return i` - `}static get is(){return"select-input"}}window.customElements.define(a.is,a);class o extends HTMLElement{#X;#i=!0;#Y;#J="";#Q="";#Z=new ResizeObserver(this.#tt.bind(this));#u={onChangeValue:[]};connectedCallback(){this.innerHTML=this.#p(),this.#X={text:this.querySelector(".edit-text__text"),popup:this.querySelector(".edit-text__popup"),input:this.querySelector("text-input")},this.#E(),this.#Z.observe(document.body),this.#et(),this.#it()}disconnectedCallback(){this.#Z.unobserve(document.body)}value(){return this.#Y}onChange(t){this.#u.onChangeValue.push(t)}#st(){let t=this.#Y;return this.#nt()&&(t=+t),`${this.#Q}${t}${this.#J}`}#E(){this.#X.text.addEventListener("click",this.#lt.bind(this)),this.#X.popup.addEventListener("click",this.#at.bind(this)),this.#X.popup.addEventListener("keydown",this.#F.bind(this)),this.#X.input.onInput(this.#w.bind(this)),this.addEventListener("cancel",this.#ot.bind(this)),this.querySelector(".popup-content").addEventListener("click",(t=>{t.stopPropagation()}))}#lt(){this.#rt(),this.#tt(),this.#X.popup.showModal(),this.#X.input.focus()}#w(t,e){this.#i=e}#ot(){this.#X.popup.close()}#at(){this.#i&&(this.#X.popup.close(),this.#Y!==this.#X.input.value&&(this.#it(),this.#u.onChangeValue.forEach((t=>t(this.value())))))}#F(t){t.stopPropagation(),t.key!==e.Enter||t.repeat||this.#at()}#rt(){this.#X.input.value=this.#Y}#it(){this.#Y=this.#X.input.value,this.#X.text.textContent=this.#st()}#tt(){let{top:t,left:e}=this.getBoundingClientRect();this.#X.popup.style.top=t+window.scrollY+"px",this.#X.popup.style.left=e+window.scrollX+"px"}#nt(){return"number"===this.getAttribute("type")}#et(){this.hasAttribute("suffix")&&(this.#J=this.getAttribute("suffix")),this.hasAttribute("prefix")&&(this.#Q=this.getAttribute("prefix")),this.#Y=this.getAttribute("value")||""}#p(){const t=this.hasAttribute("required")?"required":"",e=this.getAttribute("type")||"text";let i="";this.hasAttribute("step")&&(i=`step="${this.getAttribute("step")}"`);let s="";this.hasAttribute("min")&&(s=`min="${this.getAttribute("min")}"`);let n="";return this.hasAttribute("max")&&(n=`max="${this.getAttribute("max")}"`),`\n \n \n `}static get is(){return"edit-text"}}window.customElements.define(o.is,o)})()})(); + `}static get is(){return"select-input"}}window.customElements.define(a.is,a);class o extends HTMLElement{#X;#i=!0;#Y;#J="";#Q="";#Z=new ResizeObserver(this.#tt.bind(this));#u={onChangeValue:[]};connectedCallback(){this.innerHTML=this.#p(),this.#X={text:this.querySelector(".edit-text__text"),popup:this.querySelector(".edit-text__popup"),input:this.querySelector("text-input")},this.#g(),this.#Z.observe(document.body),this.#et(),this.#it()}disconnectedCallback(){this.#Z.unobserve(document.body)}value(){return this.#Y}onChange(t){this.#u.onChangeValue.push(t)}#st(){let t=this.#Y;return this.#nt()&&(t=+t),`${this.#Q}${t}${this.#J}`}#g(){this.#X.text.addEventListener("click",this.#lt.bind(this)),this.#X.popup.addEventListener("click",this.#at.bind(this)),this.#X.popup.addEventListener("keydown",this.#F.bind(this)),this.#X.input.onInput(this.#w.bind(this)),this.addEventListener("cancel",this.#ot.bind(this)),this.querySelector(".popup-content").addEventListener("click",(t=>{t.stopPropagation()}))}#lt(){this.#rt(),this.#tt(),this.#X.popup.showModal(),this.#X.input.focus()}#w(t,e){this.#i=e}#ot(){this.#X.popup.close()}#ht(){this.#i&&this.#dt()}#at(){this.#X.popup.close(),this.#ht()}#dt(){this.#Y!==this.#X.input.value&&(this.#it(),this.#u.onChangeValue.forEach((t=>t(this.value()))))}#F(t){t.stopPropagation(),t.key!==e.Enter||t.repeat||this.#ht()}#rt(){this.#X.input.value=this.#Y}#it(){this.#Y=this.#X.input.value,this.#X.text.textContent=this.#st()}#tt(){let{top:t,left:e}=this.getBoundingClientRect();this.#X.popup.style.top=t+window.scrollY+"px",this.#X.popup.style.left=e+window.scrollX+"px"}#nt(){return"number"===this.getAttribute("type")}#et(){this.hasAttribute("suffix")&&(this.#J=this.getAttribute("suffix")),this.hasAttribute("prefix")&&(this.#Q=this.getAttribute("prefix")),this.#Y=this.getAttribute("value")||""}#p(){const t=this.hasAttribute("required")?"required":"",e=this.getAttribute("type")||"text";let i="";this.hasAttribute("step")&&(i=`step="${this.getAttribute("step")}"`);let s="";this.hasAttribute("min")&&(s=`min="${this.getAttribute("min")}"`);let n="";return this.hasAttribute("max")&&(n=`max="${this.getAttribute("max")}"`),`\n \n \n `}static get is(){return"edit-text"}}window.customElements.define(o.is,o)})()})(); //# sourceMappingURL=bundle.js.map \ No newline at end of file diff --git a/bundle.js.map b/bundle.js.map index 4eb211d..77d078a 100644 --- a/bundle.js.map +++ b/bundle.js.map @@ -1 +1 @@ -{"version":3,"file":"bundle.js","mappings":"yBAAe,MAAMA,EACpB,GACA,GACA,GACA,GAEA,WAAAC,CAAYC,GACXC,MAAK,EAAaD,EAClBC,MAAK,EAAgBD,EAAUE,cAAc,SAC7CD,MAAK,GAAW,EAChBA,MAAK,EAAgB,EACtB,CAEA,WAAIE,GACH,OAAOF,MAAK,CACb,CAEA,gBAAIG,GACH,OAAOH,MAAK,CACb,CAEA,aAAAI,GAECJ,KAAKK,kBAAkB,IACvBL,MAAK,EAAcI,gBAEnB,IAAIE,EAAWN,MAAK,EAAcM,SAMlC,OALIA,EAASC,QACZD,EAAWN,MAAK,KAEjBA,MAAK,EAAWM,EAASC,MACzBP,MAAK,EAAgBA,MAAK,EAAsBM,GACzCN,KAAKE,OACb,CAEA,iBAAAG,CAAkBG,GACjBR,MAAK,EAAcK,kBAAkBG,GACrCR,MAAK,EAAWA,MAAK,EAAcM,SAASC,MAC5CP,MAAK,EAAgBQ,CACtB,CASA,KACC,MAAM,SAACC,EAAQ,YAAEC,EAAW,gBAAEC,EAAe,aAAEC,EAAY,MAAEL,EAAK,cAAEM,EAAa,eAAEC,EAAc,QAAEC,EAAO,SACzGC,EAAQ,aAAEC,EAAY,aAAEC,GAAgBlB,MAAK,EAAcM,SACtDa,EAAKC,OAAOC,OAAO,CAAC,EACzB,CAACZ,WAAUC,cAAaC,kBAAiBC,eAAcL,QAAOM,gBAAeC,iBAAgBC,UAC5FC,WAAUC,eAAcC,gBACzBlB,MAAK,IACLA,MAAK,KAGN,OADAmB,EAAGZ,OAASY,EAAGF,eAAiBE,EAAGL,iBAAmBK,EAAGN,cAClDM,CACR,CAMA,KACC,MAAMG,EAActB,MAAK,EAAcuB,MAAMC,OAC7C,MAAO,CAACP,aAAcjB,MAAK,EAAWyB,aAAa,aAA+B,KAAhBH,EACnE,CASA,KACC,GAAgC,WAA5BtB,MAAK,EAAc0B,KACtB,MAAO,CAACZ,gBAAgB,EAAOD,eAAe,GAC/C,MAAM,IAACc,EAAG,IAAEC,EAAG,MAAEL,GAASvB,MAAK,EAC/B,MAAO,CAACc,eAAyB,KAARa,IAAeJ,GAASI,EAAMd,cAAwB,KAARe,IAAeL,GAASK,EAChG,CAEA,GAAsBC,GACrB,MAAMC,EAA2C,WAA5B9B,MAAK,EAAc0B,MAClC,SAACjB,EAAQ,cAAEI,EAAa,eAAEC,EAAc,QAAEC,EAAO,SAAEC,EAAQ,aAAEC,EAAY,aAAEC,GAAgBW,EACjG,OAAIC,GAAgBrB,EACZ,iBACJqB,GAAgBZ,GAA4C,MAA5BlB,MAAK,EAAc+B,KAE/C,qBAEJlB,EACI,gBAAkBb,MAAK,EAAc4B,IACzCd,EACI,aAAed,MAAK,EAAc2B,IACtCZ,EACI,iBAAmBf,MAAK,EAAcgC,UAC1ChB,EACI,iBAAmBhB,MAAK,EAAciC,WACzCxB,GAAYQ,EACT,WACDjB,MAAK,EAAckC,iBAC3B,ECxGM,MAAMC,EAAUf,OAAOgB,OAAO,CACjC,MAAS,YACT,IAAO,SACP,MAAS,QACT,GAAM,UACN,KAAQ,cA0BCC,EAAW,CAACC,KAAYC,KACjC,IAAIC,EAASF,EAAQ,GACrB,IAAK,IAAIG,EAAI,EAAGA,EAAIF,EAAOG,OAAQD,IAC/BD,IAtBiBG,EAsBEC,OAAOL,EAAOE,KAnB9BE,EACFE,QAAQ,KAAM,SACdA,QAAQ,KAAM,QACdA,QAAQ,KAAM,QACdA,QAAQ,KAAM,UACdA,QAAQ,KAAM,UANR,GAqBPL,GAAUF,EAAQG,EAAI,GAvBN,IAACE,EAyBrB,OAAOH,CAAM,ECjCF,MAAMM,UAAkBC,YACnCC,SAA2B,IAAIC,IAAI,CAAC,eAAgB,YAAa,WAAY,MAAO,YAChF,MAAO,YAAa,OAAQ,UAAW,WAAY,OAAQ,OAAQ,UAIvE,GAEA,GAEA,GACA,GAAa,CAETC,oBAAqB,GAErBC,cAAe,GAEfC,QAAS,IAGb,GAEA,iBAAAC,GACIrD,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAgBA,KAAKC,cAAc,SACxCD,MAAK,EAAgBA,KAAKC,cAAc,sBACxCD,MAAK,EAAiB,IAAIH,EAAuBG,MACjDA,MAAK,IACLA,MAAK,IACDA,KAAKyB,aAAa,WAClBzB,KAAKuB,MAAQvB,KAAKuD,aAAa,SACvC,CAEA,oBAAAC,GAGIxD,KAAKyD,aAAa,QAASzD,KAAKuB,OAChCmC,OAAOC,oBAAoB,mBAAoB3D,MAAK,EAAoB4D,KAAK5D,MAAO,CAAE6D,SAAS,GACnG,CAMA,SAAItC,GACA,OAAOvB,KAAK8D,SAAStC,MACzB,CAMA,YAAIsC,GACA,OAAO9D,MAAK,EAAcuB,KAC9B,CAGA,SAAIA,CAAMA,GACNvB,MAAK,EAAcuB,MDLpB,SAAyBA,GAC5B,aAAqB,IAAVA,IAAyBwC,OAAOC,SAASzC,GAIxD,CCAoC0C,CAAe1C,IAA0B,iBAATA,EAAoBA,EAAQ,GACxFvB,KAAKI,eACT,CAEA,aAAAA,GACI,MAAMF,EAAUF,MAAK,EAAeI,gBAEpC,OADAJ,KAAKG,aAAeH,MAAK,EAAeG,aACjCD,CACX,CAEA,gBAAIC,GACA,OAAOH,MAAK,EAAckE,WAC9B,CAEA,gBAAI/D,CAAaK,GAEbR,MAAK,EAAoB,KACzBA,MAAK,EAAeK,kBAAkBG,GACtCR,MAAK,EAAckE,YAAclE,MAAK,EAAeG,YACzD,CAGA,mBAAA+C,CAAoBiB,GAChBnE,MAAK,EAAWkD,oBAAoBkB,KAAKD,EAC7C,CAEA,OAAAf,CAAQe,GACJnE,MAAK,EAAWoD,QAAQgB,KAAKD,EACjC,CAEA,aAAAhB,CAAcgB,GACVnE,MAAK,EAAWmD,cAAciB,KAAKD,EACvC,CAGA,KAAAE,CAAMC,GACFtE,MAAK,EAAcqE,MAAMC,EAC7B,CAGA,WAAAC,CAAYC,GACRxE,KAAKyE,gBAAgB,WAAYD,GACjCxE,MAAK,EAAcyE,gBAAgB,WAAYD,EACnD,CAGA,GAAWE,GACyB,WAA5B1E,MAAK,EAAc0B,MAAsBgD,EAAMC,MAAQxC,EAAQyC,IAAMF,EAAMC,MAAQxC,EAAQ0C,MAC3FH,EAAMI,iBACNJ,EAAMC,MAAQxC,EAAQ4C,OAAUL,EAAMM,QACtChF,MAAK,GACb,CAEA,KACI,MAAME,EAAUF,KAAKI,gBACrBJ,MAAK,EAAWoD,QAAQ6B,SAAQd,GAAYA,EAASnE,KAAKuB,MAAOrB,IACrE,CAEA,KAEQF,MAAK,IAAsBA,KAAKuB,QAEpCvB,MAAK,EAAoBA,KAAKuB,MAC9BvB,MAAK,IACT,CAEA,KACIA,MAAK,EAAWkD,oBAAoB+B,SAAQd,GAAYA,KAC5D,CAEA,KACInE,KAAKI,gBACLJ,MAAK,EAAWmD,cAAc8B,SAAQd,GAAYA,EAASnE,KAAKuB,QACpE,CAEA,KACI,IAAK,MAAM2D,KAAalF,KAAKmF,WACrBrC,GAAU,EAAkBsC,IAAIF,EAAUG,OAC1CrF,MAAK,EAAcyD,aAAayB,EAAUG,KAAMH,EAAU3D,OAGhC,WAA9BvB,KAAKuD,aAAa,SAAyBvD,KAAKyB,aAAa,SAC7DzB,MAAK,EAAcyD,aAAa,OAAQ,MAChD,CAEA,KACIzD,MAAK,EAAcsF,iBAAiB,UAAWtF,MAAK,EAAW4D,KAAK5D,OACpEA,MAAK,EAAcsF,iBAAiB,QAAStF,MAAK,EAAS4D,KAAK5D,OAChEA,MAAK,EAAcsF,iBAAiB,WAAYtF,MAAK,EAAU4D,KAAK5D,OACpEA,KAAKC,cAAc,8BAA8BqF,iBAAiB,QAAStF,MAAK,EAAqB4D,KAAK5D,OAC1G0D,OAAO4B,iBAAiB,mBAAoBtF,MAAK,EAAoB4D,KAAK5D,MAAO,CAAE6D,SAAS,GAChG,CAkBA,KACQ0B,SAASC,gBAAkBxF,MAAK,GAChCA,MAAK,EAAcyF,MAC3B,CAEA,KACI,MAAMC,EAAmB1F,KAAKuD,aAAa,cAAgB,GAC3D,OAAOlB,CAAQ;mDAC4BrC,KAAKuD,aAAa;iFACYmC;kDAE7E,CAEA,aAAWC,GACP,MAAO,YACX,EAGJjC,OAAOkC,eAAeC,OAAO/C,EAAU6C,GAAI7C,GC3L5B,MAAMgD,UAAgB/C,YACjC,GACA,GAAU,GACV,GAAgB,EAChB,IAAyB,EACzB,GAAa,CACTgD,cAAe,IAMnB,WAAIzB,GACA,OAAOtE,MAAK,CAChB,CAKA,WAAIsE,CAAQ/B,GACRvC,MAAK,EAAWuC,GAChBvC,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAeA,KAAKC,cAAc,MACvCD,MAAK,IACLA,MAAK,GACT,CAKA,UAAIgG,CAAOA,GACP,MAAMC,EAAeD,EAAOE,cAC5B,IAAK,MAAMC,KAAMnG,KAAKoG,iBAAiB,MAAO,CAC1C,MAAM,YAACC,GAAerG,MAAK,EAAQmG,EAAGG,QAAQC,OACxCC,EAAUH,EAAYH,cAAcM,QAAQP,GAClDE,EAAG7C,UAAYtD,MAAK,EAAeqG,EAAaG,EAASP,EAAavD,QACtEyD,EAAG1B,gBAAgB,UAAuB,IAAb+B,EACjC,CACA,MAAMC,EAAkBzG,MAAK,IACzByG,IACIA,EAAgBhF,aAAa,UAC7BzB,MAAK,IAELyG,EAAgBC,eAAe,CAACC,MAAO,YAEnD,CAEA,IAAAC,GACI5G,KAAK6G,MAAMC,QAAU,QACrB9G,MAAK,GACT,CAEA,IAAA+G,GACI/G,KAAK6G,MAAMC,QAAU,OACrB9G,MAAK,GACT,CAEA,cAAAgH,GACI,MAAMC,EAAkBjH,MAAK,IAC7B,GAAKA,KAAKkH,qBAIH,CACH,MAAMV,EAAUS,EAAgBT,QAAQxG,MAAK,KAC7C,GAAIiH,EAAgBvE,OAAS,GAAK8D,EAC9B,OACJxG,MAAK,EAAoBiH,EAAgBT,EAAU,GAAGF,QAAQC,MAClE,KATgC,CAC5B,GAA+B,IAA3BU,EAAgBvE,OAChB,OACJ1C,MAAK,EAAoBiH,EAAgB,GAAGX,QAAQC,MACxD,CAMJ,CAEA,cAAAY,GACI,MAAMF,EAAkBjH,MAAK,IAC7B,GAAKA,KAAKkH,qBAIH,CACH,MAAMV,EAAUS,EAAgBT,QAAQxG,MAAK,KAC7C,GAAgB,IAAZwG,EACA,OACJxG,MAAK,EAAoBiH,EAAgBT,EAAU,GAAGF,QAAQC,MAClE,KATgC,CAC5B,GAA+B,IAA3BU,EAAgBvE,OAChB,OACJ1C,MAAK,EAAoBiH,EAAgBA,EAAgBvE,OAAS,GAAG4D,QAAQC,MACjF,CAMJ,CAEA,0BAAAa,GACQpH,KAAKkH,sBACLlH,MAAK,IAAsBqH,cAAc,IAAIC,WAAW,aAChE,CAEA,kBAAAJ,GACI,OAAqC,MAA9BlH,MAAK,GAChB,CAEA,SAAAuH,GACI,MAAiD,SAA1C7D,OAAO8D,iBAAiBxH,MAAM8G,OACzC,CAEA,aAAAf,CAAc0B,GACVzH,MAAK,EAAW+F,cAAc3B,KAAKqD,EACvC,CAEA,iBAAApE,GACIrD,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAeA,KAAKC,cAAc,MACvCD,MAAK,GACT,CAEA,GAAWuC,GACPvC,MAAK,EAAU,IAAIuC,GAAQmF,MAAK,CAACC,EAAGC,IAAMD,EAAEtB,YAAYwB,cAAcD,EAAEvB,cAC5E,CAEA,KACI,MAAO,IAAIrG,MAAK,EAAaoG,iBAAiB,oBAClD,CAEA,KACI,IAAK,MAAMD,KAAMnG,KAAKoG,iBAAiB,MACnCD,EAAGb,iBAAiB,aAAa,KAC7B,MAAMwC,EAAS9H,MAAK,EAAQmG,EAAGG,QAAQC,OACvCvG,MAAK,EAAW+F,cAAcd,SAAQwC,GAAMA,EAAGK,IAAQ,GAGnE,CAEA,KACI,MAAO,uCAEG9H,MAAK,EAAQ+H,KAAI,CAACxG,EAAOkB,IAC/BJ,CAAQ,mBAAmBI,aAAalB,EAAM8E,gBAAgB9E,EAAM8E,qBACtE2B,KAAK,wBAEX,CAEA,KACI,MAAMC,EAAmBjI,KAAKkI,cAAcC,wBACjB,IAAvBnI,MAAK,IACLA,MAAK,EAAgBoI,KAAKxG,OAAO5B,MAAK,EAAQ+H,KAAIxG,GFlGvD,SAAsB8G,GACzB,MAAMC,EAAO/C,SAASgD,cAAc,QACpChD,SAASiD,KAAKC,YAAYH,GAC1BA,EAAKpE,YAAcmE,EACnBC,EAAKzB,MAAM6B,SAAW,OACtBJ,EAAKzB,MAAM8B,WAAa,SACxBL,EAAKzB,MAAM+B,SAAW,WACtB,MAAMC,EAAQT,KAAKU,KAAKR,EAAKH,wBAAwBU,OAAS,EAE9D,OADAP,EAAKS,SACEF,CACX,CEwFuEG,CAAazH,EAAM8E,eAAe,IAEjG,MAAM4C,EAAYb,KAAKxG,IAAI5B,MAAK,EAAgB,GAAiB,GAAiBiI,EAAiBY,OAE7FK,EAAkB3D,SAAS4D,gBAAgBC,YAAcnB,EAAiBoB,KAE5ErJ,MAAK,EAAa6G,MAAMyC,MADxBL,EAAYC,EACoB,EAEA,KAEpClJ,MAAK,EAAa6G,MAAMgC,MAAQ,GAAGT,KAAKzG,IAAIsH,EAAW1D,SAAS4D,gBAAgBC,gBACpF,CAEA,KACI,OAAOpJ,KAAKC,cAAc,kBAAkBD,MAAK,MACrD,CAEA,GAAoBuJ,GAChBvJ,MAAK,IACLA,MAAK,EAAwBuJ,EAC7B,MAAMC,EAAUxJ,MAAK,IACrBwJ,EAAQC,UAAUC,IAAI,0BACtBF,EAAQ9C,eAAe,CAACC,MAAO,WACnC,CAEA,KACQ3G,MAAK,GAAyB,IACNA,MAAK,IACbyJ,UAAUV,OAAO,0BACjC/I,MAAK,GAAyB,EAEtC,CAEA,GAAeqI,EAAMsB,EAAYjH,GAC7B,GAAIiH,GAAc,EAAG,CACjB,MAAMC,EAASvB,EAAKwB,UAAU,EAAGF,GAC3BG,EAAQzB,EAAKwB,UAAUF,EAAYA,EAAajH,GAChDqH,EAAQ1B,EAAKwB,UAAUF,EAAajH,GAE1C,OAAOL,CAAQ,SAASuH,UAAeE,WAAeC,UAC1D,CACI,OAAO1B,CAEf,CAEA,aAAW1C,GACP,MAAO,UACX,EAGJjC,OAAOkC,eAAeC,OAAOC,EAAQH,GAAIG,GCzL1B,MAAMkE,UAAuBjH,YAIxC,GAIA,GACA,GACA,GAAkB,KAClB,GACA,GAAa,CACTI,cAAe,IAGnB,iBAAAE,GACIrD,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAgBA,KAAKC,cAAc,cACxCD,MAAK,EAAmBA,KAAKC,cAAc,YAC3CD,MAAK,EAAsBA,KAAKyB,aAAa,sBAC7CzB,MAAK,GACT,CAEA,SAAIuB,GACA,OAAOvB,MAAK,CAChB,CAEA,YAAI8D,GACA,OAAO9D,MAAK,EAAcuB,KAC9B,CAEA,SAAIA,CAAMA,GACNvB,MAAK,EAAgBuB,EACrBvB,MAAK,EAAcuB,MAAQA,GAASA,EAAM8E,YAAc9E,EAAM8E,YAAc,EAChF,CAKA,gBAAI4D,CAAa1I,GACbvB,KAAKuB,MAAQA,EACbvB,MAAK,EAAkBuB,CAC3B,CAEA,WAAI+C,CAAQA,GACRtE,MAAK,EAAiBsE,QAAUA,EAChCtE,MAAK,GACT,CAEA,gBAAIG,CAAaK,GACbR,MAAK,EAAcG,aAAeK,CACtC,CAEA,aAAAJ,GACI,OAAOJ,MAAK,KAAeA,MAAK,EAAcI,eAClD,CAEA,aAAA+C,CAAcgB,GACVnE,MAAK,EAAWmD,cAAciB,KAAKD,EACvC,CAGA,WAAAI,CAAYC,GACRxE,KAAKyE,gBAAgB,WAAYD,GACjCxE,MAAK,EAAcuE,YAAYC,EACnC,CAGA,KACIxE,KAAKG,aAAe,GACpBH,MAAK,IACAA,MAAK,EAAiBuH,aACvBvH,MAAK,EAAiB4G,MAC9B,CAEA,KACI5G,MAAK,IACLA,MAAK,EAAiB4G,MAC1B,CAEA,KACI5G,MAAK,GACT,CAEA,GAAe8H,GACX9H,KAAKuB,MAAQuG,EACb9H,MAAK,GACT,CAEA,KACIA,KAAKuB,MAAQ,CAAC8E,YAAa,IAC3BrG,MAAK,EAAcC,cAAc,SAASoE,OAC9C,CAEA,GAAWK,GAKP,OAJI,CAACvC,EAAQyC,GAAIzC,EAAQ0C,MAAMqF,SAASxF,EAAMyF,QAC1CzF,EAAMI,iBACNJ,EAAM0F,4BAEF1F,EAAMC,KACV,KAAKxC,EAAQkI,IACTrK,MAAK,IACL,MAEJ,KAAKmC,EAAQ4C,MACL/E,MAAK,EAAiBuH,cAClBvH,MAAK,EAAiBkH,qBACtBlH,MAAK,EAAiBoH,6BAEtBpH,MAAK,KACb,MAEJ,KAAKmC,EAAQ0C,KACJ7E,MAAK,EAAiBuH,aACvBvH,MAAK,EAAiB4G,OAC1B5G,MAAK,EAAiBgH,iBACtB,MAEJ,KAAK7E,EAAQyC,GACJ5E,MAAK,EAAiBuH,aACvBvH,MAAK,EAAiB4G,OAC1B5G,MAAK,EAAiBmH,iBAIlC,CAEA,KACInH,MAAK,GACT,CAEA,KACIA,MAAK,EAAiB+G,OACtB/G,MAAK,GACT,CAEA,KACQA,MAAK,KAAeA,MAAK,MACzBA,MAAK,EAAkBA,KAAKuB,MAC5BvB,MAAK,EAAWmD,cAAc8B,SAAQd,GAAYA,EAASnE,KAAKuB,SAExE,CAEA,KACI,MAAM+I,EAAYtK,MAAK,EAAcuB,MACrC,GAAkB,KAAd+I,EAEA,OADAtK,MAAK,EAAgB,MACd,EAEX,GAAIA,KAAKuB,OAASvB,KAAKuB,MAAM8E,cAAgBiE,EAEzC,OADAtK,KAAKG,aAAe,IACb,EAEX,IAAKH,MAAK,EAGN,OAFAA,KAAKG,aAAe,GACpBH,MAAK,EAAgB,CAACqG,YAAaiE,IAC5B,EAEX,IAAK,MAAMxC,KAAU9H,MAAK,EAAiBsE,QACvC,GAAIwD,EAAOzB,cAAgBiE,EAIvB,OAHAtK,KAAKG,aAAe,GACpBH,MAAK,EAAgB8H,EACrB9H,MAAK,EAAcuB,MAAQuG,EAAOzB,aAC3B,EAKf,OAFArG,MAAK,EAAgB,KACrBA,KAAKG,aAAe,oBACb,CACX,CAEA,KACIH,MAAK,EAAiBgG,OAAShG,MAAK,EAAcuB,KACtD,CAEA,KACI,OAAOvB,MAAK,IAAoBA,KAAKuB,KACzC,CAEA,KACI,MAAMgJ,EAAQvK,MAAK,EAAcC,cAAc,SAC/CD,KAAKsF,iBAAiB,UAAWtF,MAAK,EAAW4D,KAAK5D,OACtDuK,EAAMjF,iBAAiB,QAAStF,MAAK,EAAS4D,KAAK5D,OACnDuK,EAAMjF,iBAAiB,OAAQtF,MAAK,EAAQ4D,KAAK5D,OACjDuK,EAAMjF,iBAAiB,QAAStF,MAAK,EAAS4D,KAAK5D,OACnDA,MAAK,EAAckD,oBAAoBlD,MAAK,EAAkB4D,KAAK5D,OACnEA,MAAK,EAAcmD,cAAcnD,MAAK,EAAoB4D,KAAK5D,OAC/DA,MAAK,EAAiB+F,cAAc/F,MAAK,EAAe4D,KAAK5D,MACjE,CAEA,KACI,MAAMwK,EAAoBxK,KAAKyB,aAAa,YAAc,WAAa,GACjEgJ,EAAoBzK,KAAKyB,aAAa,YAAc,WAAa,GACjEiJ,EAAW1K,KAAKyB,aAAa,WAAa,GAAK,QACrD,OAAOY,CAAQ;;;yBAGErC,KAAKuD,aAAa;kBACzBiH;kBACAC;6BACWC;;;kCAIzB,CAEA,aAAW/E,GACP,MAAO,iBACX,EAGJjC,OAAOkC,eAAeC,OAAOmE,EAAerE,GAAIqE,GCtNjC,MAAMW,UAAoB5H,YACrC,GACA,GACA,GACA,GAAkB,KAElB,GAAa,CACT6H,eAAgB,GAChBzH,cAAe,IAGnB,SAAI5B,GACA,OAAOvB,MAAK,CAChB,CAEA,SAAIuB,CAAMA,GACNvB,MAAK,EAAcuB,MAAQA,GAASA,EAAM8E,YAAc9E,EAAM8E,YAAc,GAC5ErG,MAAK,EAAgBuB,CACzB,CAEA,WAAI+C,CAAQA,GACRtE,MAAK,EAAiBsE,QAAUA,CACpC,CAEA,YAAAuG,GACI7K,MAAK,EAAiB4G,OACtB5G,MAAK,EAAW4K,eAAe3F,SAAQd,GAAYA,KACvD,CAEA,cAAAyG,CAAezG,GACXnE,MAAK,EAAW4K,eAAexG,KAAKD,EACxC,CAEA,aAAAhB,CAAcgB,GACVnE,MAAK,EAAWmD,cAAciB,KAAKD,EACvC,CAEA,aAAA/D,GACI,OAAOJ,MAAK,GAChB,CAEA,iBAAAqD,GACIrD,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAgBA,KAAKC,cAAc,cACxCD,MAAK,EAAmBA,KAAKC,cAAc,YAC3CD,MAAK,GACT,CAEA,KACIA,KAAKsF,iBAAiB,UAAWtF,MAAK,EAAW4D,KAAK5D,OACtD,MAAMuK,EAAQvK,MAAK,EAAcC,cAAc,SAC/CsK,EAAMjF,iBAAiB,QAAStF,MAAK,EAAS4D,KAAK5D,OACnDuK,EAAMjF,iBAAiB,WAAYtF,MAAK,EAAY4D,KAAK5D,OACzDuK,EAAMjF,iBAAiB,QAAStF,MAAK,EAAc4D,KAAK5D,OACxDA,MAAK,EAAiB+F,cAAc/F,MAAK,EAAe4D,KAAK5D,MACjE,CAEA,KACIA,KAAK6K,cACT,CAEA,KACI7K,MAAK,GACT,CAEA,GAAe8H,GACX9H,MAAK,EAAcuB,MAAQuG,EAAOzB,YAClCrG,MAAK,EAAgB8H,EACrB9H,MAAK,GACT,CAEA,KACIA,KAAK6K,cACT,CAEA,GAAWnG,GAKP,OAJI,CAACvC,EAAQyC,GAAIzC,EAAQ0C,MAAMqF,SAASxF,EAAMyF,QAC1CzF,EAAMI,iBACNJ,EAAM0F,4BAEF1F,EAAMC,KACV,KAAKxC,EAAQkI,IACT3F,EAAMI,iBACN9E,MAAK,IACLA,MAAK,EAAcqE,QACnB,MAEJ,KAAKlC,EAAQ4C,MACL/E,MAAK,EAAiBuH,cACtB7C,EAAMoG,kBACF9K,MAAK,EAAiBkH,qBACtBlH,MAAK,EAAiBoH,6BAEtBpH,MAAK,EAAiB+G,QAE9B,MAEJ,KAAK5E,EAAQ0C,KACJ7E,MAAK,EAAiBuH,aACvBvH,MAAK,EAAiB4G,OAC1B5G,MAAK,EAAiBgH,iBACtB,MAEJ,KAAK7E,EAAQyC,GACJ5E,MAAK,EAAiBuH,aACvBvH,MAAK,EAAiB4G,OAC1B5G,MAAK,EAAiBmH,iBAIlC,CAEA,KACInH,MAAK,EAAiB+G,OACtB/G,MAAK,GACT,CAEA,KACQA,MAAK,KAAeA,MAAK,IAAoBA,KAAKuB,QAClDvB,MAAK,EAAkBA,KAAKuB,MAC5BvB,MAAK,EAAWmD,cAAc8B,SAAQd,GAAYA,EAASnE,KAAKuB,SAExE,CAEA,KAKI,OAJIvB,MAAK,EAAcyB,aAAa,cAAgBzB,MAAK,EAAcuB,MACnEvB,MAAK,EAAcG,aAAe,WAElCH,MAAK,EAAcG,aAAe,GAC/BH,MAAK,EAAcI,eAC9B,CAEA,KACI,MAAMoK,EAAoBxK,KAAKyB,aAAa,YAAc,WAAa,GACjEgJ,EAAoBzK,KAAKyB,aAAa,YAAc,WAAa,GACvE,OAAOY,CAAQ;;;yBAGErC,KAAKuD,aAAa;kBACzBiH;kBACAC;;;;kCAKd,CAEA,aAAW9E,GACP,MAAO,cACX,EAGJjC,OAAOkC,eAAeC,OAAO8E,EAAYhF,GAAIgF,GCxJ9B,MAAMI,UAAiBhI,YAClC,GACA,IAAW,EACX,GACA,GAAU,GACV,GAAU,GAEV,GAAkB,IAAIiI,eAAehL,MAAK,GAAqB4D,KAAK5D,OAEpE,GAAa,CACTmD,cAAe,IAGnB,iBAAAE,GACIrD,KAAKsD,UAAYtD,MAAK,IACtBA,MAAK,EAAY,CACbqI,KAAMrI,KAAKC,cAAc,oBACzBgL,MAAOjL,KAAKC,cAAc,qBAC1BsK,MAAOvK,KAAKC,cAAc,eAE9BD,MAAK,IACLA,MAAK,EAAgBkL,QAAQ3F,SAASiD,MACtCxI,MAAK,KACLA,MAAK,IACT,CAEA,oBAAAwD,GACIxD,MAAK,EAAgBmL,UAAU5F,SAASiD,KAC5C,CAEA,KAAAjH,GACI,OAAOvB,MAAK,CAChB,CAEA,QAAAoL,CAAS3D,GACLzH,MAAK,EAAWmD,cAAciB,KAAKqD,EACvC,CAEA,MACI,IAAI4D,EAAMrL,MAAK,EAGf,OAFIA,MAAK,OACLqL,GAAOA,GACJ,GAAGrL,MAAK,IAAUqL,IAAMrL,MAAK,GACxC,CAEA,KACIA,MAAK,EAAUqI,KAAK/C,iBAAiB,QAAStF,MAAK,GAAW4D,KAAK5D,OACnEA,MAAK,EAAUiL,MAAM3F,iBAAiB,QAAStF,MAAK,GAAS4D,KAAK5D,OAClEA,MAAK,EAAUiL,MAAM3F,iBAAiB,UAAWtF,MAAK,EAAW4D,KAAK5D,OACtEA,MAAK,EAAUuK,MAAMnH,QAAQpD,MAAK,EAAS4D,KAAK5D,OAChDA,KAAKsF,iBAAiB,SAAUtF,MAAK,GAAU4D,KAAK5D,OACpDA,KAAKC,cAAc,kBAAkBqF,iBAAiB,SAAUZ,IAC5DA,EAAMoG,iBAAiB,GAE/B,CAEA,MACI9K,MAAK,KACLA,MAAK,KACLA,MAAK,EAAUiL,MAAMK,YACrBtL,MAAK,EAAUuK,MAAMlG,OACzB,CAEA,GAAS9C,EAAOrB,GACZF,MAAK,EAAWE,CACpB,CAEA,MACIF,MAAK,EAAUiL,MAAMM,OACzB,CAEA,MACSvL,MAAK,IAEVA,MAAK,EAAUiL,MAAMM,QACjBvL,MAAK,IAAWA,MAAK,EAAUuK,MAAMhJ,QACrCvB,MAAK,KACLA,MAAK,EAAWmD,cAAc8B,SAAQwC,GAAMA,EAAGzH,KAAKuB,YAE5D,CAEA,GAAWiK,GACPA,EAAIV,kBACAU,EAAI7G,MAAQxC,EAAQ4C,OAAUyG,EAAIxG,QAClChF,MAAK,IACb,CAEA,MACIA,MAAK,EAAUuK,MAAMhJ,MAAQvB,MAAK,CACtC,CAEA,MACIA,MAAK,EAASA,MAAK,EAAUuK,MAAMhJ,MACnCvB,MAAK,EAAUqI,KAAKnE,YAAclE,MAAK,IAC3C,CAEA,MACI,IAAI,IAACyL,EAAG,KAAEpC,GAAQrJ,KAAKmI,wBACvBnI,MAAK,EAAUiL,MAAMpE,MAAM4E,IAAMA,EAAM/H,OAAOgI,QAAU,KACxD1L,MAAK,EAAUiL,MAAMpE,MAAMwC,KAAOA,EAAO3F,OAAOiI,QAAU,IAC9D,CAEA,MACI,MAAqC,WAA9B3L,KAAKuD,aAAa,OAC7B,CAEA,MACQvD,KAAKyB,aAAa,YAClBzB,MAAK,EAAUA,KAAKuD,aAAa,WACjCvD,KAAKyB,aAAa,YAClBzB,MAAK,EAAUA,KAAKuD,aAAa,WACrCvD,MAAK,EAASA,KAAKuD,aAAa,UAAY,EAChD,CAEA,KACI,MAAMqI,EAAe5L,KAAKyB,aAAa,YAAc,WAAa,GAC5DoK,EAAW7L,KAAKuD,aAAa,SAAW,OAC9C,IAAIuI,EAAW,GACX9L,KAAKyB,aAAa,UAClBqK,EAAW,SAAS9L,KAAKuD,aAAa,YAC1C,IAAIwI,EAAU,GACV/L,KAAKyB,aAAa,SAClBsK,EAAU,QAAQ/L,KAAKuD,aAAa,WACxC,IAAIyI,EAAU,GAId,OAHIhM,KAAKyB,aAAa,SAClBuK,EAAU,QAAQhM,KAAKuD,aAAa,WAEjC,0XAOeqI,kCACAE,kCACAC,kCACAC,wCACMH,0CAZd7L,KAAKuD,aAAa,8GAiBpC,CAEA,aAAWoC,GACP,MAAO,WACX,EAGJjC,OAAOkC,eAAeC,OAAOkF,EAASpF,GAAIoF,E","sources":["webpack://@elsci-io/ui-essential/./src/TextInput/TextInputValidityState.js","webpack://@elsci-io/ui-essential/./src/utils.js","webpack://@elsci-io/ui-essential/./src/TextInput/TextInput.js","webpack://@elsci-io/ui-essential/./src/ListBox/ListBox.js","webpack://@elsci-io/ui-essential/./src/TypeAheadInput/TypeAheadInput.js","webpack://@elsci-io/ui-essential/./src/SelectInput/SelectInput.js","webpack://@elsci-io/ui-essential/./src/EditText/EditText.js"],"sourcesContent":["export default class TextInputValidityState {\n\t#textInput;\n\t#inputElement;\n\t#isValid;\n\t#errorMessage;\n\n\tconstructor(textInput) {\n\t\tthis.#textInput = textInput\n\t\tthis.#inputElement = textInput.querySelector('input');\n\t\tthis.#isValid = true;\n\t\tthis.#errorMessage = \"\";\n\t}\n\n\tget isValid() {\n\t\treturn this.#isValid;\n\t}\n\n\tget errorMessage() {\n\t\treturn this.#errorMessage;\n\t}\n\n\tcheckValidity() {\n\t\t// reset custom validity\n\t\tthis.setCustomValidity(\"\");\n\t\tthis.#inputElement.checkValidity();\n\t\t// if the input element is valid, then check custom validity\n\t\tlet validity = this.#inputElement.validity;\n\t\tif (validity.valid) {\n\t\t\tvalidity = this.#getCustomValidity();\n\t\t}\n\t\tthis.#isValid = validity.valid;\n\t\tthis.#errorMessage = this.#getValidationMessage(validity);\n\t\treturn this.isValid;\n\t}\n\n\tsetCustomValidity(message) {\n\t\tthis.#inputElement.setCustomValidity(message);\n\t\tthis.#isValid = this.#inputElement.validity.valid;\n\t\tthis.#errorMessage = message;\n\t}\n\n\t/**\n\t * @see https://developer.mozilla.org/en-US/docs/Web/API/ValidityState\n\t * Here we add our own validation steps, and update the validity state properties.\n\t * - valueMissing: if the input element is required and the trimmed text is empty (contains only whitespaces).\n\t * - rangeUnderflow: if the input element is a number and the value is less than the min attribute.\n\t * - rangeOverflow: if the input element is a number and the value is greater than the max attribute.\n\t */\n\t#getCustomValidity() {\n\t\tconst {badInput, customError, patternMismatch, typeMismatch, valid, rangeOverflow, rangeUnderflow, tooLong,\n\t\t\ttooShort, valueMissing, stepMismatch} = this.#inputElement.validity;\n\t\tconst cv = Object.assign({},\n\t\t\t{badInput, customError, patternMismatch, typeMismatch, valid, rangeOverflow, rangeUnderflow, tooLong,\n\t\t\t\ttooShort, valueMissing, stepMismatch},\n\t\t\tthis.#isBlanknessConstraintViolated(),\n\t\t\tthis.#isRangeConstraintViolated()\n\t\t);\n\t\tcv.valid = !cv.valueMissing && !cv.rangeUnderflow && !cv.rangeOverflow;\n\t\treturn cv;\n\t}\n\n\t/**\n\t * Checks if the input element is required and the trimmed text is empty (contains only whitespaces).\n\t * @returns {{valueMissing: (*|boolean)}}\n\t */\n\t#isBlanknessConstraintViolated() {\n\t\tconst trimmedText = this.#inputElement.value.trim();\n\t\treturn {valueMissing: this.#textInput.hasAttribute(\"required\") && trimmedText === \"\"};\n\t}\n\n\t/**\n\t * This is a workaround for the fact that the browser does not validate decimals properly. It takes only\n\t * first 18 digits of the decimal number and then compares it with the min and max attributes.\n\t * So if the min attribute is 0 and the value is -0.0000000000000000001, then the browser will not\n\t * consider it as a range underflow (after conversion it becomes -0 => 0).\n\t * This is why we have to check the value manually.\n\t */\n\t#isRangeConstraintViolated() {\n\t\tif (this.#inputElement.type !== \"number\")\n\t\t\treturn {rangeUnderflow: false, rangeOverflow: false};\n\t\tconst {min, max, value} = this.#inputElement;\n\t\treturn {rangeUnderflow: (min !== \"\" && +value < +min), rangeOverflow: (max !== \"\" && +value > +max)};\n\t}\n\n\t#getValidationMessage(validityState) {\n\t\tconst isTypeNumber = this.#inputElement.type === \"number\";\n\t\tconst {badInput, rangeOverflow, rangeUnderflow, tooLong, tooShort, valueMissing, stepMismatch} = validityState;\n\t\tif (isTypeNumber && badInput)\n\t\t\treturn \"Invalid number\";\n\t\tif (isTypeNumber && stepMismatch && this.#inputElement.step === \"1\") {\n\t\t\t// Here we validate only floats because if step is 1, then the value must be an integer.\n\t\t\treturn \"Must be an integer\";\n\t\t}\n\t\tif (rangeOverflow)\n\t\t\treturn \"Greater than \" + this.#inputElement.max;\n\t\tif (rangeUnderflow)\n\t\t\treturn \"Less than \" + this.#inputElement.min;\n\t\tif (tooLong)\n\t\t\treturn \"Max length is \" + this.#inputElement.maxLength;\n\t\tif (tooShort)\n\t\t\treturn \"Min length is \" + this.#inputElement.minLength;\n\t\tif (!badInput && valueMissing)\n\t\t\treturn \"Required\";\n\t\treturn this.#inputElement.validationMessage;\n\t}\n}","export const KeyCode = Object.freeze({\n \"Shift\": \"ShiftLeft\",\n \"Esc\": \"Escape\",\n \"Enter\": \"Enter\",\n \"Up\": \"ArrowUp\",\n \"Down\": \"ArrowDown\"\n});\n\n/**\n * @param {string} unsafe\n * @returns {string}\n */\nexport const safeText = (unsafe) => {\n if (!unsafe)\n return ''\n return unsafe\n .replace(/&/g, \"&\")\n .replace(//g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n}\n\n/**\n * To be used when generating HTML via string interpolation e.g. {@code safeHtml`
${variables}
`} -\n * these variables will go through this function and have to be escaped should such string be shown on UI.\n *\n * @param {TemplateStringsArray} strings\n * @param {string[]} values\n * @returns {string}\n */\nexport const safeHtml = (strings, ...values) => {\n let result = strings[0];\n for (let i = 0; i < values.length; i++) {\n result += safeText(String(values[i]));\n result += strings[i + 1];\n }\n return result;\n}\n\n/* @param {String} text */\nexport function getTextWidth(text) {\n const span = document.createElement(\"span\");\n document.body.appendChild(span)\n span.textContent = text;\n span.style.fontSize = '1rem';\n span.style.visibility = 'hidden';\n span.style.position = 'absolute';\n const width = Math.ceil(span.getBoundingClientRect().width) + 1;\n span.remove();\n return width;\n}\n\nfunction getCssStyle(element, prop) {\n return window.getComputedStyle(element, null).getPropertyValue(prop);\n}\n\nexport function isFiniteNumber (value) {\n if (typeof value !== 'undefined' && Number.isFinite(value)) {\n return true\n }\n else return false\n}","// @ts-check\nimport TextInputValidityState from \"./TextInputValidityState.js\";\nimport {isFiniteNumber, KeyCode, safeHtml} from \"../utils.js\"\n\nexport default class TextInput extends HTMLElement {\n static #INPUT_ATTRIBUTES = new Set([\"autocomplete\", \"autofocus\", \"disabled\", \"max\", \"maxlength\",\n \"min\", \"minlength\", \"name\", \"pattern\", \"readonly\", \"step\", \"type\", \"value\"\n /* \"required\" - we do not want to set attribute required when render text-input, because in this case all\n required inputs becomes red, as solution we just leave it in the root element and do this validation manually */]);\n /** @type {HTMLInputElement} */\n #inputElement;\n /** @type {HTMLElement} */\n #errorElement;\n /** @type {TextInputValidityState} */\n #validityState;\n #callbacks = {\n /** @type {Function[]} */\n onTrailingIconClick: [],\n /** @type {Function[]} */\n onChangeValue: [],\n /** @type {Function[]} */\n onInput: []\n };\n /** @type {string} */\n #lastChangedValue;\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"input\");\n this.#errorElement = this.querySelector(\".text-input__error\");\n this.#validityState = new TextInputValidityState(this);\n this.#fillInputAttributes();\n this.#addListeners();\n if (this.hasAttribute(\"value\"))\n this.value = this.getAttribute(\"value\");\n }\n\n disconnectedCallback() {\n // Save value to attribute, because it will be lost after element is removed from DOM and reinserted.\n // The case is happening when user adds new element to the table and then sorts it by reinserting rows.\n this.setAttribute(\"value\", this.value);\n window.removeEventListener(\"visibilitychange\", this.#onVisibilityChange.bind(this), { capture: true });\n }\n\n /**\n * Returns trimmed value of the input.\n * @returns {string}\n */\n get value() {\n return this.rawValue.trim();\n }\n\n /**\n * Returns raw value of the input.\n * @returns {string}\n */\n get rawValue() {\n return this.#inputElement.value;\n }\n\n /** @param {string | null} value */\n set value(value) {\n this.#inputElement.value = (isFiniteNumber(value) || typeof value == \"string\")? value : '';\n this.checkValidity();\n }\n\n checkValidity() {\n const isValid = this.#validityState.checkValidity();\n this.errorMessage = this.#validityState.errorMessage;\n return isValid;\n }\n\n get errorMessage() {\n return this.#errorElement.textContent;\n }\n\n set errorMessage(message) {\n // We reset lastChangedValue because if the same invalid value is entered again, we want to validate this value\n this.#lastChangedValue = null;\n this.#validityState.setCustomValidity(message);\n this.#errorElement.textContent = this.#validityState.errorMessage;\n }\n\n /** @param {Function} callback */\n onTrailingIconClick(callback) {\n this.#callbacks.onTrailingIconClick.push(callback);\n }\n /** @param {Function} callback */\n onInput(callback) {\n this.#callbacks.onInput.push(callback);\n }\n /** @param {Function} callback */\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n // @ts-ignore\n focus(options) {\n this.#inputElement.focus(options)\n }\n\n /** @param {boolean} isDisabled */\n setDisabled(isDisabled) {\n this.toggleAttribute(\"disabled\", isDisabled);\n this.#inputElement.toggleAttribute(\"disabled\", isDisabled);\n }\n\n /** @param {KeyboardEvent} event */\n #onKeyDown(event) {\n if (this.#inputElement.type === \"number\" && (event.key === KeyCode.Up || event.key === KeyCode.Down))\n event.preventDefault();\n if (event.key === KeyCode.Enter && !event.repeat)\n this.#onChange();\n }\n\n #onInput() {\n const isValid = this.checkValidity();\n this.#callbacks.onInput.forEach(callback => callback(this.value, isValid));\n }\n\n #onChange() {\n // We validate if the current value is not equal to the last changed value\n if (this.#lastChangedValue === this.value)\n return;\n this.#lastChangedValue = this.value;\n this.#validateAndNotify();\n }\n\n #onTrailingIconClick() {\n this.#callbacks.onTrailingIconClick.forEach(callback => callback());\n }\n\n #validateAndNotify() {\n this.checkValidity();\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value));\n }\n\n #fillInputAttributes() {\n for (const attribute of this.attributes)\n if (TextInput.#INPUT_ATTRIBUTES.has(attribute.name))\n this.#inputElement.setAttribute(attribute.name, attribute.value)\n // For number inputs, if step is not specified then it is set to 1 by default, and it is not possible to enter\n // decimal w/o validation error. So, if step is not specified, then we set it to \"any\" to allow decimal values.\n if (this.getAttribute(\"type\") === \"number\" && !this.hasAttribute(\"step\"))\n this.#inputElement.setAttribute(\"step\", \"any\");\n }\n\n #addListeners() {\n this.#inputElement.addEventListener(\"keydown\", this.#onKeyDown.bind(this));\n this.#inputElement.addEventListener(\"input\", this.#onInput.bind(this));\n this.#inputElement.addEventListener(\"focusout\", this.#onChange.bind(this));\n this.querySelector('.text-input__trailing-icon').addEventListener(\"click\", this.#onTrailingIconClick.bind(this));\n window.addEventListener(\"visibilitychange\", this.#onVisibilityChange.bind(this), { capture: true });\n }\n\n /**\n * This method is called when user:\n * - closes the tab\n * - closes browser window\n * - refreshes the page\n * - navigates to another page\n * - navigates to another tab\n * - minimizes the browser window\n *\n * It is needed to blur the input element, because if it is focused, then it might be not saved to the database.\n * Blurring the input element will trigger the change event, if the value was changed.\n *\n * Note: If the user closes the tab or browser window, then there is no guarantee that asynchronous requests\n * (XHR or fetch) will be sent. So, if the user closes the tab or browser window, then the value\n * of the input element might not be saved to the database.\n */\n #onVisibilityChange() {\n if (document.activeElement === this.#inputElement)\n this.#inputElement.blur();\n }\n\n #htmlTemplate() {\n const trailingIconName = this.getAttribute(\"data-icon\") || \"\";\n return safeHtml`\n \n ${trailingIconName}\n

`;\n }\n\n static get is() {\n return 'text-input';\n }\n}\n\nwindow.customElements.define(TextInput.is, TextInput);","import {getTextWidth, safeHtml} from \"../utils.js\";\n\nexport default class ListBox extends HTMLElement {\n #listElement;\n #values = [];\n #maxItemWidth = 0;\n #selectedElementIndex = -1;\n #callbacks = {\n onOptionClick: []\n }\n\n /**\n * @returns {{displayName:string}[]}\n */\n get options() {\n return this.#values;\n }\n\n /**\n * @param {{displayName:string}[]}values\n */\n set options(values) {\n this.#setValues(values);\n this.innerHTML = this.#htmlTemplate();\n this.#listElement = this.querySelector(\"ul\");\n this.#updatePosition();\n this.#addListeners();\n }\n\n /**\n * @param {string} filter\n */\n set filter(filter) {\n const searchString = filter.toLowerCase();\n for (const li of this.querySelectorAll(\"li\")) {\n const {displayName} = this.#values[li.dataset.index];\n const indexOf = displayName.toLowerCase().indexOf(searchString);\n li.innerHTML = this.#getMarkedText(displayName, indexOf, searchString.length);\n li.toggleAttribute('hidden', indexOf === -1);\n }\n const selectedElement = this.#getSelectedElement();\n if (selectedElement) {\n if (selectedElement.hasAttribute('hidden'))\n this.#resetCurrentSelection();\n else\n selectedElement.scrollIntoView({block: \"nearest\"});\n }\n }\n\n show() {\n this.style.display = 'block';\n this.#updatePosition();\n }\n\n hide() {\n this.style.display = 'none';\n this.#resetCurrentSelection();\n }\n\n selectNextItem() {\n const visibleElements = this.#getVisibleElements();\n if (!this.hasSelectedElement()) {\n if (visibleElements.length === 0)\n return;\n this.#setSelectedElement(visibleElements[0].dataset.index);\n } else {\n const indexOf = visibleElements.indexOf(this.#getSelectedElement());\n if (visibleElements.length - 1 <= indexOf) // is last item?\n return;\n this.#setSelectedElement(visibleElements[indexOf + 1].dataset.index);\n }\n }\n\n selectPrevItem() {\n const visibleElements = this.#getVisibleElements();\n if (!this.hasSelectedElement()) {\n if (visibleElements.length === 0)\n return;\n this.#setSelectedElement(visibleElements[visibleElements.length - 1].dataset.index);\n } else {\n const indexOf = visibleElements.indexOf(this.#getSelectedElement());\n if (indexOf === 0) // is first item?\n return;\n this.#setSelectedElement(visibleElements[indexOf - 1].dataset.index);\n }\n }\n\n triggerClickOnSelectedItem() {\n if (this.hasSelectedElement())\n this.#getSelectedElement().dispatchEvent(new MouseEvent('mousedown'));\n }\n\n hasSelectedElement() {\n return this.#getSelectedElement() != null;\n }\n\n isVisible() {\n return window.getComputedStyle(this).display !== 'none'\n }\n\n onOptionClick(cb) {\n this.#callbacks.onOptionClick.push(cb);\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#listElement = this.querySelector(\"ul\");\n this.#addListeners();\n }\n\n #setValues(values) {\n this.#values = [...values].sort((a, b) => a.displayName.localeCompare(b.displayName));\n }\n\n #getVisibleElements() {\n return [...this.#listElement.querySelectorAll('li:not([hidden])')];\n }\n\n #addListeners() {\n for (const li of this.querySelectorAll(\"li\")) {\n li.addEventListener('mousedown', () => {\n const option = this.#values[li.dataset.index];\n this.#callbacks.onOptionClick.forEach(cb => cb(option));\n });\n }\n }\n\n #htmlTemplate() {\n return `\n `;\n }\n\n #updatePosition() {\n const parentClientRect = this.parentElement.getBoundingClientRect();\n if (this.#maxItemWidth === 0) // calculate max item width only once\n this.#maxItemWidth = Math.max(...this.#values.map(value => getTextWidth(value.displayName)), 0);\n // if parent element width is greater than max item width, set list width to parent width\n const widthToBe = Math.max(this.#maxItemWidth + 24/*paddings*/ + 22/*scrollbar*/, parentClientRect.width);\n // max allowed width is the distance from the left side of parent element to the right side of the page\n const maxAllowedWidth = document.documentElement.clientWidth - parentClientRect.left\n if (widthToBe > maxAllowedWidth) { // can't fit to the right side, so put it to the left side\n this.#listElement.style.right = 0;\n } else {\n this.#listElement.style.right = null;\n }\n this.#listElement.style.width = `${Math.min(widthToBe, document.documentElement.clientWidth)}px`;\n }\n\n #getSelectedElement() {\n return this.querySelector(`li[data-index=\"${this.#selectedElementIndex}\"]`);\n }\n\n #setSelectedElement(elementIndex) {\n this.#resetCurrentSelection();\n this.#selectedElementIndex = elementIndex;\n const element = this.#getSelectedElement();\n element.classList.add('list-box__item--active');\n element.scrollIntoView({block: \"nearest\"});\n }\n\n #resetCurrentSelection() {\n if (this.#selectedElementIndex >= 0) {\n const selectedElement = this.#getSelectedElement();\n selectedElement.classList.remove('list-box__item--active');\n this.#selectedElementIndex = -1;\n }\n }\n\n #getMarkedText(text, startIndex, length) {\n if (startIndex >= 0) {\n const before = text.substring(0, startIndex);\n const match = text.substring(startIndex, startIndex + length);\n const after = text.substring(startIndex + length);\n // wrap whole text in span to prevent swallowing spaces\n return safeHtml`${before}${match}${after}`;\n } else {\n return text;\n }\n }\n\n static get is() {\n return 'list-box';\n }\n}\n\nwindow.customElements.define(ListBox.is, ListBox);","import '../TextInput/TextInput.js';\nimport '../ListBox/ListBox.js';\nimport { KeyCode, safeHtml } from \"../utils.js\"\n\nexport default class TypeAheadInput extends HTMLElement {\n /**\n * @type {TextInput}\n */\n #inputElement;\n /**\n * @type {ListBox}\n */\n #dropdownElement;\n #currentValue;\n #lastValidValue = null;\n #shouldMatchOptions;\n #callbacks = {\n onChangeValue: []\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"text-input\");\n this.#dropdownElement = this.querySelector(\"list-box\");\n this.#shouldMatchOptions = this.hasAttribute(\"shouldMatchOptions\")\n this.#addListeners();\n }\n\n get value() {\n return this.#currentValue;\n }\n\n get rawValue() {\n return this.#inputElement.value;\n }\n\n set value(value) {\n this.#currentValue = value;\n this.#inputElement.value = value && value.displayName ? value.displayName : \"\";\n }\n\n /**\n * Sets the initial value of the input, as well as the last valid value.\n */\n set initialValue(value) {\n this.value = value;\n this.#lastValidValue = value;\n }\n\n set options(options) {\n this.#dropdownElement.options = options;\n this.#filterDatalist();\n }\n\n set errorMessage(message) {\n this.#inputElement.errorMessage = message;\n }\n\n checkValidity() {\n return this.#validate() && this.#inputElement.checkValidity();\n }\n\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n /** @param {boolean} isDisabled */\n setDisabled(isDisabled) {\n this.toggleAttribute(\"disabled\", isDisabled);\n this.#inputElement.setDisabled(isDisabled);\n }\n\n\n #onInput() {\n this.errorMessage = \"\";\n this.#filterDatalist();\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n }\n\n #onFocus() {\n this.#filterDatalist();\n this.#dropdownElement.show();\n }\n\n #onBlur() {\n this.#hideDropdownAndValidate();\n }\n\n #onOptionClick(option) {\n this.value = option;\n this.#hideDropdownAndValidate();\n }\n\n #onClearIconClick() {\n this.value = {displayName: \"\"};\n this.#inputElement.querySelector('input').focus();\n }\n\n #onKeydown(event) {\n if ([KeyCode.Up, KeyCode.Down].includes(event.code)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n switch (event.key) {\n case KeyCode.Esc: {\n this.#hideDropdownAndValidate();\n break;\n }\n case KeyCode.Enter: {\n if (this.#dropdownElement.isVisible())\n if (this.#dropdownElement.hasSelectedElement())\n this.#dropdownElement.triggerClickOnSelectedItem();\n else\n this.#hideDropdownAndValidate();\n break;\n }\n case KeyCode.Down: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectNextItem();\n break;\n }\n case KeyCode.Up: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectPrevItem();\n break;\n }\n }\n }\n\n #onInputValueChange() {\n this.#validateAndNotify();\n }\n\n #hideDropdownAndValidate() {\n this.#dropdownElement.hide();\n this.#validateAndNotify();\n }\n\n #validateAndNotify() {\n if (this.#validate() && this.#isValueChanged()) {\n this.#lastValidValue = this.value;\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value));\n }\n }\n\n #validate() {\n const inputText = this.#inputElement.value;\n if (inputText === \"\") {\n this.#currentValue = null;\n return true; // assume that value is valid if it is empty, otherwise required attribute should be set\n }\n if (this.value && this.value.displayName === inputText) {\n this.errorMessage = \"\";\n return true; // assume that value is valid if it is the same as the initial value\n }\n if (!this.#shouldMatchOptions) {\n this.errorMessage = \"\";\n this.#currentValue = {displayName: inputText};\n return true; // assume that value is valid if it should not match to any option\n }\n for (const option of this.#dropdownElement.options) {\n if (option.displayName === inputText) {\n this.errorMessage = \"\";\n this.#currentValue = option;\n this.#inputElement.value = option.displayName;\n return true;\n }\n }\n this.#currentValue = null;\n this.errorMessage = \"Select from list\";\n return false;\n }\n\n #filterDatalist() {\n this.#dropdownElement.filter = this.#inputElement.value;\n }\n\n #isValueChanged() {\n return this.#lastValidValue !== this.value;\n }\n\n #addListeners() {\n const input = this.#inputElement.querySelector(\"input\");\n this.addEventListener(\"keydown\", this.#onKeydown.bind(this));\n input.addEventListener(\"input\", this.#onInput.bind(this));\n input.addEventListener(\"blur\", this.#onBlur.bind(this));\n input.addEventListener('focus', this.#onFocus.bind(this));\n this.#inputElement.onTrailingIconClick(this.#onClearIconClick.bind(this));\n this.#inputElement.onChangeValue(this.#onInputValueChange.bind(this));\n this.#dropdownElement.onOptionClick(this.#onOptionClick.bind(this));\n }\n\n #htmlTemplate() {\n const requiredAttribute = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const disabledAttribute = this.hasAttribute(\"disabled\") ? \"disabled\" : \"\";\n const iconName = this.hasAttribute(\"no-icon\") ? \"\" : \"close\";\n return safeHtml`\n \n `;\n }\n\n static get is() {\n return 'typeahead-input';\n }\n}\n\nwindow.customElements.define(TypeAheadInput.is, TypeAheadInput);","import {KeyCode, safeHtml} from \"../utils.js\";\n\nexport default class SelectInput extends HTMLElement {\n #inputElement;\n #dropdownElement;\n #currentValue;\n #lastValidValue = null;\n\n #callbacks = {\n onShowDropdown: [],\n onChangeValue: []\n }\n\n get value() {\n return this.#currentValue;\n }\n\n set value(value) {\n this.#inputElement.value = value && value.displayName ? value.displayName : \"\";\n this.#currentValue = value;\n }\n\n set options(options) {\n this.#dropdownElement.options = options;\n }\n\n showDropdown() {\n this.#dropdownElement.show();\n this.#callbacks.onShowDropdown.forEach(callback => callback());\n }\n\n onShowDropdown(callback) {\n this.#callbacks.onShowDropdown.push(callback);\n }\n\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n checkValidity() {\n return this.#validate();\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"text-input\");\n this.#dropdownElement = this.querySelector(\"list-box\");\n this.#addListeners();\n }\n\n #addListeners() {\n this.addEventListener(\"keydown\", this.#onKeydown.bind(this));\n const input = this.#inputElement.querySelector(\"input\");\n input.addEventListener('focus', this.#onFocus.bind(this));\n input.addEventListener(\"focusout\", this.#onFocusout.bind(this));\n input.addEventListener(\"click\", this.#onInputClick.bind(this));\n this.#dropdownElement.onOptionClick(this.#onOptionClick.bind(this));\n }\n\n #onFocus() {\n this.showDropdown();\n }\n\n #onFocusout() {\n this.#hideDropdownAndValidate();\n }\n\n #onOptionClick(option) {\n this.#inputElement.value = option.displayName;\n this.#currentValue = option;\n this.#hideDropdownAndValidate();\n }\n\n #onInputClick() {\n this.showDropdown();\n }\n\n #onKeydown(event) {\n if ([KeyCode.Up, KeyCode.Down].includes(event.code)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n switch (event.key) {\n case KeyCode.Esc: {\n event.preventDefault();\n this.#hideDropdownAndValidate();\n this.#inputElement.focus();\n break;\n }\n case KeyCode.Enter: {\n if (this.#dropdownElement.isVisible()) {\n event.stopPropagation();\n if (this.#dropdownElement.hasSelectedElement())\n this.#dropdownElement.triggerClickOnSelectedItem();\n else\n this.#dropdownElement.hide();\n }\n break;\n }\n case KeyCode.Down: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectNextItem();\n break;\n }\n case KeyCode.Up: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectPrevItem();\n break;\n }\n }\n }\n\n #hideDropdownAndValidate() {\n this.#dropdownElement.hide();\n this.#validateAndNotify();\n }\n\n #validateAndNotify() {\n if (this.#validate() && this.#lastValidValue !== this.value) {\n this.#lastValidValue = this.value;\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value))\n }\n }\n\n #validate() {\n if (this.#inputElement.hasAttribute(\"required\") && !this.#inputElement.value)\n this.#inputElement.errorMessage = \"Required\";\n else\n this.#inputElement.errorMessage = \"\";\n return this.#inputElement.checkValidity();\n }\n\n #htmlTemplate() {\n const requiredAttribute = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const disabledAttribute = this.hasAttribute(\"disabled\") ? \"disabled\" : \"\";\n return safeHtml`\n \n `;\n }\n\n static get is() {\n return 'select-input';\n }\n}\n\nwindow.customElements.define(SelectInput.is, SelectInput);","import {KeyCode} from \"../utils.js\";\n\nexport default class EditText extends HTMLElement {\n #children;\n #isValid = true;\n #value;\n #suffix = \"\";\n #prefix = \"\";\n\n #resizeObserver = new ResizeObserver(this.#updatePopupPosition.bind(this));\n\n #callbacks = {\n onChangeValue: []\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#children = {\n text: this.querySelector(\".edit-text__text\"),\n popup: this.querySelector(\".edit-text__popup\"),\n input: this.querySelector('text-input')\n };\n this.#addListeners();\n this.#resizeObserver.observe(document.body);\n this.#initAttributes();\n this.#updateTextValue();\n }\n\n disconnectedCallback() {\n this.#resizeObserver.unobserve(document.body);\n }\n\n value() {\n return this.#value;\n }\n\n onChange(cb){\n this.#callbacks.onChangeValue.push(cb);\n }\n\n #getDisplayName(){\n let val = this.#value;\n if (this.#isNumberType())\n val = +val;\n return `${this.#prefix}${val}${this.#suffix}`\n }\n\n #addListeners() {\n this.#children.text.addEventListener(\"click\", this.#showPopup.bind(this));\n this.#children.popup.addEventListener('click', this.#onEnter.bind(this));\n this.#children.popup.addEventListener('keydown', this.#onKeydown.bind(this));\n this.#children.input.onInput(this.#onInput.bind(this));\n this.addEventListener(\"cancel\", this.#onEscape.bind(this));\n this.querySelector(\".popup-content\").addEventListener(\"click\", (event) => {\n event.stopPropagation();\n });\n }\n\n #showPopup() {\n this.#updateInputValue();\n this.#updatePopupPosition();\n this.#children.popup.showModal();\n this.#children.input.focus();\n }\n\n #onInput(value, isValid) {\n this.#isValid = isValid;\n }\n\n #onEscape() {\n this.#children.popup.close();\n }\n\n #onEnter() {\n if (!this.#isValid)\n return;\n this.#children.popup.close();\n if (this.#value !== this.#children.input.value){\n this.#updateTextValue();\n this.#callbacks.onChangeValue.forEach(cb => cb(this.value()));\n }\n }\n\n #onKeydown(evt) {\n evt.stopPropagation();\n if (evt.key === KeyCode.Enter && !evt.repeat)\n this.#onEnter();\n }\n\n #updateInputValue() {\n this.#children.input.value = this.#value;\n }\n\n #updateTextValue() {\n this.#value = this.#children.input.value;\n this.#children.text.textContent = this.#getDisplayName();\n }\n\n #updatePopupPosition() {\n let {top, left} = this.getBoundingClientRect();\n this.#children.popup.style.top = top + window.scrollY + \"px\";\n this.#children.popup.style.left = left + window.scrollX + \"px\";\n }\n\n #isNumberType() {\n return this.getAttribute(\"type\") === \"number\"\n }\n\n #initAttributes(){\n if (this.hasAttribute(\"suffix\"))\n this.#suffix = this.getAttribute(\"suffix\");\n if (this.hasAttribute(\"prefix\"))\n this.#prefix = this.getAttribute(\"prefix\");\n this.#value = this.getAttribute(\"value\") || \"\";\n }\n\n #htmlTemplate() {\n const requiredAttr = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const typeAttr = this.getAttribute(\"type\") || \"text\";\n let stepAttr = \"\";\n if (this.hasAttribute(\"step\"))\n stepAttr = `step=\"${this.getAttribute(\"step\")}\"`\n let minAttr = \"\";\n if (this.hasAttribute(\"min\"))\n minAttr = `min=\"${this.getAttribute(\"min\")}\"`\n let maxAttr = \"\";\n if (this.hasAttribute(\"max\"))\n maxAttr = `max=\"${this.getAttribute(\"max\")}\"`\n const value = this.getAttribute(\"value\");\n return `\n \n
\n \n
\n
`;\n }\n\n static get is() {\n return 'edit-text';\n }\n}\n\nwindow.customElements.define(EditText.is, EditText);\n"],"names":["TextInputValidityState","constructor","textInput","this","querySelector","isValid","errorMessage","checkValidity","setCustomValidity","validity","valid","message","badInput","customError","patternMismatch","typeMismatch","rangeOverflow","rangeUnderflow","tooLong","tooShort","valueMissing","stepMismatch","cv","Object","assign","trimmedText","value","trim","hasAttribute","type","min","max","validityState","isTypeNumber","step","maxLength","minLength","validationMessage","KeyCode","freeze","safeHtml","strings","values","result","i","length","unsafe","String","replace","TextInput","HTMLElement","static","Set","onTrailingIconClick","onChangeValue","onInput","connectedCallback","innerHTML","getAttribute","disconnectedCallback","setAttribute","window","removeEventListener","bind","capture","rawValue","Number","isFinite","isFiniteNumber","textContent","callback","push","focus","options","setDisabled","isDisabled","toggleAttribute","event","key","Up","Down","preventDefault","Enter","repeat","forEach","attribute","attributes","has","name","addEventListener","document","activeElement","blur","trailingIconName","is","customElements","define","ListBox","onOptionClick","filter","searchString","toLowerCase","li","querySelectorAll","displayName","dataset","index","indexOf","selectedElement","scrollIntoView","block","show","style","display","hide","selectNextItem","visibleElements","hasSelectedElement","selectPrevItem","triggerClickOnSelectedItem","dispatchEvent","MouseEvent","isVisible","getComputedStyle","cb","sort","a","b","localeCompare","option","map","join","parentClientRect","parentElement","getBoundingClientRect","Math","text","span","createElement","body","appendChild","fontSize","visibility","position","width","ceil","remove","getTextWidth","widthToBe","maxAllowedWidth","documentElement","clientWidth","left","right","elementIndex","element","classList","add","startIndex","before","substring","match","after","TypeAheadInput","initialValue","includes","code","stopImmediatePropagation","Esc","inputText","input","requiredAttribute","disabledAttribute","iconName","SelectInput","onShowDropdown","showDropdown","stopPropagation","EditText","ResizeObserver","popup","observe","unobserve","onChange","val","showModal","close","evt","top","scrollY","scrollX","requiredAttr","typeAttr","stepAttr","minAttr","maxAttr"],"sourceRoot":""} \ No newline at end of file +{"version":3,"file":"bundle.js","mappings":"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","sources":["webpack://@elsci-io/ui-essential/./src/TextInput/TextInputValidityState.js","webpack://@elsci-io/ui-essential/./src/utils.js","webpack://@elsci-io/ui-essential/./src/TextInput/TextInput.js","webpack://@elsci-io/ui-essential/./src/ListBox/ListBox.js","webpack://@elsci-io/ui-essential/./src/TypeAheadInput/TypeAheadInput.js","webpack://@elsci-io/ui-essential/./src/SelectInput/SelectInput.js","webpack://@elsci-io/ui-essential/./src/EditText/EditText.js"],"sourcesContent":["export default class TextInputValidityState {\n\t#textInput;\n\t#inputElement;\n\t#isValid;\n\t#errorMessage;\n\n\tconstructor(textInput) {\n\t\tthis.#textInput = textInput\n\t\tthis.#inputElement = textInput.querySelector('input');\n\t\tthis.#isValid = true;\n\t\tthis.#errorMessage = \"\";\n\t}\n\n\tget isValid() {\n\t\treturn this.#isValid;\n\t}\n\n\tget errorMessage() {\n\t\treturn this.#errorMessage;\n\t}\n\n\tcheckValidity() {\n\t\t// reset custom validity\n\t\tthis.setCustomValidity(\"\");\n\t\tthis.#inputElement.checkValidity();\n\t\t// if the input element is valid, then check custom validity\n\t\tlet validity = this.#inputElement.validity;\n\t\tif (validity.valid) {\n\t\t\tvalidity = this.#getCustomValidity();\n\t\t}\n\t\tthis.#isValid = validity.valid;\n\t\tthis.#errorMessage = this.#getValidationMessage(validity);\n\t\treturn this.isValid;\n\t}\n\n\tsetCustomValidity(message) {\n\t\tthis.#inputElement.setCustomValidity(message);\n\t\tthis.#isValid = this.#inputElement.validity.valid;\n\t\tthis.#errorMessage = message;\n\t}\n\n\t/**\n\t * @see https://developer.mozilla.org/en-US/docs/Web/API/ValidityState\n\t * Here we add our own validation steps, and update the validity state properties.\n\t * - valueMissing: if the input element is required and the trimmed text is empty (contains only whitespaces).\n\t * - rangeUnderflow: if the input element is a number and the value is less than the min attribute.\n\t * - rangeOverflow: if the input element is a number and the value is greater than the max attribute.\n\t */\n\t#getCustomValidity() {\n\t\tconst {badInput, customError, patternMismatch, typeMismatch, valid, rangeOverflow, rangeUnderflow, tooLong,\n\t\t\ttooShort, valueMissing, stepMismatch} = this.#inputElement.validity;\n\t\tconst cv = Object.assign({},\n\t\t\t{badInput, customError, patternMismatch, typeMismatch, valid, rangeOverflow, rangeUnderflow, tooLong,\n\t\t\t\ttooShort, valueMissing, stepMismatch},\n\t\t\tthis.#isBlanknessConstraintViolated(),\n\t\t\tthis.#isRangeConstraintViolated()\n\t\t);\n\t\tcv.valid = !cv.valueMissing && !cv.rangeUnderflow && !cv.rangeOverflow;\n\t\treturn cv;\n\t}\n\n\t/**\n\t * Checks if the input element is required and the trimmed text is empty (contains only whitespaces).\n\t * @returns {{valueMissing: (*|boolean)}}\n\t */\n\t#isBlanknessConstraintViolated() {\n\t\tconst trimmedText = this.#inputElement.value.trim();\n\t\treturn {valueMissing: this.#textInput.hasAttribute(\"required\") && trimmedText === \"\"};\n\t}\n\n\t/**\n\t * This is a workaround for the fact that the browser does not validate decimals properly. It takes only\n\t * first 18 digits of the decimal number and then compares it with the min and max attributes.\n\t * So if the min attribute is 0 and the value is -0.0000000000000000001, then the browser will not\n\t * consider it as a range underflow (after conversion it becomes -0 => 0).\n\t * This is why we have to check the value manually.\n\t */\n\t#isRangeConstraintViolated() {\n\t\tif (this.#inputElement.type !== \"number\")\n\t\t\treturn {rangeUnderflow: false, rangeOverflow: false};\n\t\tconst {min, max, value} = this.#inputElement;\n\t\treturn {rangeUnderflow: (min !== \"\" && +value < +min), rangeOverflow: (max !== \"\" && +value > +max)};\n\t}\n\n\t#getValidationMessage(validityState) {\n\t\tconst isTypeNumber = this.#inputElement.type === \"number\";\n\t\tconst {badInput, rangeOverflow, rangeUnderflow, tooLong, tooShort, valueMissing, stepMismatch} = validityState;\n\t\tif (isTypeNumber && badInput)\n\t\t\treturn \"Invalid number\";\n\t\tif (isTypeNumber && stepMismatch && this.#inputElement.step === \"1\") {\n\t\t\t// Here we validate only floats because if step is 1, then the value must be an integer.\n\t\t\treturn \"Must be an integer\";\n\t\t}\n\t\tif (rangeOverflow)\n\t\t\treturn \"Greater than \" + this.#inputElement.max;\n\t\tif (rangeUnderflow)\n\t\t\treturn \"Less than \" + this.#inputElement.min;\n\t\tif (tooLong)\n\t\t\treturn \"Max length is \" + this.#inputElement.maxLength;\n\t\tif (tooShort)\n\t\t\treturn \"Min length is \" + this.#inputElement.minLength;\n\t\tif (!badInput && valueMissing)\n\t\t\treturn \"Required\";\n\t\treturn this.#inputElement.validationMessage;\n\t}\n}","export const KeyCode = Object.freeze({\n \"Shift\": \"ShiftLeft\",\n \"Esc\": \"Escape\",\n \"Enter\": \"Enter\",\n \"Up\": \"ArrowUp\",\n \"Down\": \"ArrowDown\"\n});\n\n/**\n * @param {string} unsafe\n * @returns {string}\n */\nexport const safeText = (unsafe) => {\n if (!unsafe)\n return ''\n return unsafe\n .replace(/&/g, \"&\")\n .replace(//g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n}\n\n/**\n * To be used when generating HTML via string interpolation e.g. {@code safeHtml`
${variables}
`} -\n * these variables will go through this function and have to be escaped should such string be shown on UI.\n *\n * @param {TemplateStringsArray} strings\n * @param {string[]} values\n * @returns {string}\n */\nexport const safeHtml = (strings, ...values) => {\n let result = strings[0];\n for (let i = 0; i < values.length; i++) {\n result += safeText(String(values[i]));\n result += strings[i + 1];\n }\n return result;\n}\n\n/* @param {String} text */\nexport function getTextWidth(text) {\n const span = document.createElement(\"span\");\n document.body.appendChild(span)\n span.textContent = text;\n span.style.fontSize = '1rem';\n span.style.visibility = 'hidden';\n span.style.position = 'absolute';\n const width = Math.ceil(span.getBoundingClientRect().width) + 1;\n span.remove();\n return width;\n}\n\nfunction getCssStyle(element, prop) {\n return window.getComputedStyle(element, null).getPropertyValue(prop);\n}\n\nexport function isFiniteNumber (value) {\n if (typeof value !== 'undefined' && Number.isFinite(value)) {\n return true\n }\n else return false\n}","// @ts-check\nimport TextInputValidityState from \"./TextInputValidityState.js\";\nimport {isFiniteNumber, KeyCode, safeHtml} from \"../utils.js\"\n\nexport default class TextInput extends HTMLElement {\n static #INPUT_ATTRIBUTES = new Set([\"autocomplete\", \"autofocus\", \"disabled\", \"max\", \"maxlength\",\n \"min\", \"minlength\", \"name\", \"pattern\", \"readonly\", \"step\", \"type\", \"value\"\n /* \"required\" - we do not want to set attribute required when render text-input, because in this case all\n required inputs becomes red, as solution we just leave it in the root element and do this validation manually */]);\n /** @type {HTMLInputElement} */\n #inputElement;\n /** @type {HTMLElement} */\n #errorElement;\n /** @type {TextInputValidityState} */\n #validityState;\n #callbacks = {\n /** @type {Function[]} */\n onTrailingIconClick: [],\n /** @type {Function[]} */\n onChangeValue: [],\n /** @type {Function[]} */\n onInput: []\n };\n /** @type {string} */\n #lastChangedValue;\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"input\");\n this.#errorElement = this.querySelector(\".text-input__error\");\n this.#validityState = new TextInputValidityState(this);\n this.#fillInputAttributes();\n this.#addListeners();\n if (this.hasAttribute(\"value\"))\n this.value = this.getAttribute(\"value\");\n }\n\n disconnectedCallback() {\n // Save value to attribute, because it will be lost after element is removed from DOM and reinserted.\n // The case is happening when user adds new element to the table and then sorts it by reinserting rows.\n this.setAttribute(\"value\", this.value);\n window.removeEventListener(\"visibilitychange\", this.#onVisibilityChange.bind(this), { capture: true });\n }\n\n /**\n * Returns trimmed value of the input.\n * @returns {string}\n */\n get value() {\n return this.rawValue.trim();\n }\n\n /**\n * Returns raw value of the input.\n * @returns {string}\n */\n get rawValue() {\n return this.#inputElement.value;\n }\n\n /** @param {string | null} value */\n set value(value) {\n this.#inputElement.value = (isFiniteNumber(value) || typeof value == \"string\")? value : '';\n this.checkValidity();\n }\n\n checkValidity() {\n const isValid = this.#validityState.checkValidity();\n this.errorMessage = this.#validityState.errorMessage;\n return isValid;\n }\n\n get errorMessage() {\n return this.#errorElement.textContent;\n }\n\n set errorMessage(message) {\n // We reset lastChangedValue because if the same invalid value is entered again, we want to validate this value\n this.#lastChangedValue = null;\n this.#validityState.setCustomValidity(message);\n this.#errorElement.textContent = this.#validityState.errorMessage;\n }\n\n /** @param {Function} callback */\n onTrailingIconClick(callback) {\n this.#callbacks.onTrailingIconClick.push(callback);\n }\n /** @param {Function} callback */\n onInput(callback) {\n this.#callbacks.onInput.push(callback);\n }\n /** @param {Function} callback */\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n // @ts-ignore\n focus(options) {\n this.#inputElement.focus(options)\n }\n\n /** @param {boolean} isDisabled */\n setDisabled(isDisabled) {\n this.toggleAttribute(\"disabled\", isDisabled);\n this.#inputElement.toggleAttribute(\"disabled\", isDisabled);\n }\n\n /** @param {KeyboardEvent} event */\n #onKeyDown(event) {\n if (this.#inputElement.type === \"number\" && (event.key === KeyCode.Up || event.key === KeyCode.Down))\n event.preventDefault();\n if (event.key === KeyCode.Enter && !event.repeat)\n this.#onChange();\n }\n\n #onInput() {\n const isValid = this.checkValidity();\n this.#callbacks.onInput.forEach(callback => callback(this.value, isValid));\n }\n\n #onChange() {\n // We validate if the current value is not equal to the last changed value\n if (this.#lastChangedValue === this.value)\n return;\n this.#lastChangedValue = this.value;\n this.#validateAndNotify();\n }\n\n #onTrailingIconClick() {\n this.#callbacks.onTrailingIconClick.forEach(callback => callback());\n }\n\n #validateAndNotify() {\n this.checkValidity();\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value));\n }\n\n #fillInputAttributes() {\n for (const attribute of this.attributes)\n if (TextInput.#INPUT_ATTRIBUTES.has(attribute.name))\n this.#inputElement.setAttribute(attribute.name, attribute.value)\n // For number inputs, if step is not specified then it is set to 1 by default, and it is not possible to enter\n // decimal w/o validation error. So, if step is not specified, then we set it to \"any\" to allow decimal values.\n if (this.getAttribute(\"type\") === \"number\" && !this.hasAttribute(\"step\"))\n this.#inputElement.setAttribute(\"step\", \"any\");\n }\n\n #addListeners() {\n this.#inputElement.addEventListener(\"keydown\", this.#onKeyDown.bind(this));\n this.#inputElement.addEventListener(\"input\", this.#onInput.bind(this));\n this.#inputElement.addEventListener(\"focusout\", this.#onChange.bind(this));\n this.querySelector('.text-input__trailing-icon').addEventListener(\"click\", this.#onTrailingIconClick.bind(this));\n window.addEventListener(\"visibilitychange\", this.#onVisibilityChange.bind(this), { capture: true });\n }\n\n /**\n * This method is called when user:\n * - closes the tab\n * - closes browser window\n * - refreshes the page\n * - navigates to another page\n * - navigates to another tab\n * - minimizes the browser window\n *\n * It is needed to blur the input element, because if it is focused, then it might be not saved to the database.\n * Blurring the input element will trigger the change event, if the value was changed.\n *\n * Note: If the user closes the tab or browser window, then there is no guarantee that asynchronous requests\n * (XHR or fetch) will be sent. So, if the user closes the tab or browser window, then the value\n * of the input element might not be saved to the database.\n */\n #onVisibilityChange() {\n if (document.activeElement === this.#inputElement)\n this.#inputElement.blur();\n }\n\n #htmlTemplate() {\n const trailingIconName = this.getAttribute(\"data-icon\") || \"\";\n return safeHtml`\n \n ${trailingIconName}\n

`;\n }\n\n static get is() {\n return 'text-input';\n }\n}\n\nwindow.customElements.define(TextInput.is, TextInput);","import {getTextWidth, safeHtml} from \"../utils.js\";\n\nexport default class ListBox extends HTMLElement {\n #listElement;\n #values = [];\n #maxItemWidth = 0;\n #selectedElementIndex = -1;\n #callbacks = {\n onOptionClick: []\n }\n\n /**\n * @returns {{displayName:string}[]}\n */\n get options() {\n return this.#values;\n }\n\n /**\n * @param {{displayName:string}[]}values\n */\n set options(values) {\n this.#setValues(values);\n this.innerHTML = this.#htmlTemplate();\n this.#listElement = this.querySelector(\"ul\");\n this.#updatePosition();\n this.#addListeners();\n }\n\n /**\n * @param {string} filter\n */\n set filter(filter) {\n const searchString = filter.toLowerCase();\n for (const li of this.querySelectorAll(\"li\")) {\n const {displayName} = this.#values[li.dataset.index];\n const indexOf = displayName.toLowerCase().indexOf(searchString);\n li.innerHTML = this.#getMarkedText(displayName, indexOf, searchString.length);\n li.toggleAttribute('hidden', indexOf === -1);\n }\n const selectedElement = this.#getSelectedElement();\n if (selectedElement) {\n if (selectedElement.hasAttribute('hidden'))\n this.#resetCurrentSelection();\n else\n selectedElement.scrollIntoView({block: \"nearest\"});\n }\n }\n\n show() {\n this.style.display = 'block';\n this.#updatePosition();\n }\n\n hide() {\n this.style.display = 'none';\n this.#resetCurrentSelection();\n }\n\n selectNextItem() {\n const visibleElements = this.#getVisibleElements();\n if (!this.hasSelectedElement()) {\n if (visibleElements.length === 0)\n return;\n this.#setSelectedElement(visibleElements[0].dataset.index);\n } else {\n const indexOf = visibleElements.indexOf(this.#getSelectedElement());\n if (visibleElements.length - 1 <= indexOf) // is last item?\n return;\n this.#setSelectedElement(visibleElements[indexOf + 1].dataset.index);\n }\n }\n\n selectPrevItem() {\n const visibleElements = this.#getVisibleElements();\n if (!this.hasSelectedElement()) {\n if (visibleElements.length === 0)\n return;\n this.#setSelectedElement(visibleElements[visibleElements.length - 1].dataset.index);\n } else {\n const indexOf = visibleElements.indexOf(this.#getSelectedElement());\n if (indexOf === 0) // is first item?\n return;\n this.#setSelectedElement(visibleElements[indexOf - 1].dataset.index);\n }\n }\n\n triggerClickOnSelectedItem() {\n if (this.hasSelectedElement())\n this.#getSelectedElement().dispatchEvent(new MouseEvent('mousedown'));\n }\n\n hasSelectedElement() {\n return this.#getSelectedElement() != null;\n }\n\n isVisible() {\n return window.getComputedStyle(this).display !== 'none'\n }\n\n onOptionClick(cb) {\n this.#callbacks.onOptionClick.push(cb);\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#listElement = this.querySelector(\"ul\");\n this.#addListeners();\n }\n\n #setValues(values) {\n this.#values = [...values].sort((a, b) => a.displayName.localeCompare(b.displayName));\n }\n\n #getVisibleElements() {\n return [...this.#listElement.querySelectorAll('li:not([hidden])')];\n }\n\n #addListeners() {\n for (const li of this.querySelectorAll(\"li\")) {\n li.addEventListener('mousedown', () => {\n const option = this.#values[li.dataset.index];\n this.#callbacks.onOptionClick.forEach(cb => cb(option));\n });\n }\n }\n\n #htmlTemplate() {\n return `\n
    \n ${this.#values.map((value, i) =>\n safeHtml`
  • ${value.displayName}
  • `\n ).join('')}\n
`;\n }\n\n #updatePosition() {\n const parentClientRect = this.parentElement.getBoundingClientRect();\n if (this.#maxItemWidth === 0) // calculate max item width only once\n this.#maxItemWidth = Math.max(...this.#values.map(value => getTextWidth(value.displayName)), 0);\n // if parent element width is greater than max item width, set list width to parent width\n const widthToBe = Math.max(this.#maxItemWidth + 24/*paddings*/ + 22/*scrollbar*/, parentClientRect.width);\n // max allowed width is the distance from the left side of parent element to the right side of the page\n const maxAllowedWidth = document.documentElement.clientWidth - parentClientRect.left\n if (widthToBe > maxAllowedWidth) { // can't fit to the right side, so put it to the left side\n this.#listElement.style.right = 0;\n } else {\n this.#listElement.style.right = null;\n }\n this.#listElement.style.width = `${Math.min(widthToBe, document.documentElement.clientWidth)}px`;\n }\n\n #getSelectedElement() {\n return this.querySelector(`li[data-index=\"${this.#selectedElementIndex}\"]`);\n }\n\n #setSelectedElement(elementIndex) {\n this.#resetCurrentSelection();\n this.#selectedElementIndex = elementIndex;\n const element = this.#getSelectedElement();\n element.classList.add('list-box__item--active');\n element.scrollIntoView({block: \"nearest\"});\n }\n\n #resetCurrentSelection() {\n if (this.#selectedElementIndex >= 0) {\n const selectedElement = this.#getSelectedElement();\n selectedElement.classList.remove('list-box__item--active');\n this.#selectedElementIndex = -1;\n }\n }\n\n #getMarkedText(text, startIndex, length) {\n if (startIndex >= 0) {\n const before = text.substring(0, startIndex);\n const match = text.substring(startIndex, startIndex + length);\n const after = text.substring(startIndex + length);\n // wrap whole text in span to prevent swallowing spaces\n return safeHtml`${before}${match}${after}`;\n } else {\n return text;\n }\n }\n\n static get is() {\n return 'list-box';\n }\n}\n\nwindow.customElements.define(ListBox.is, ListBox);","import '../TextInput/TextInput.js';\nimport '../ListBox/ListBox.js';\nimport { KeyCode, safeHtml } from \"../utils.js\"\n\nexport default class TypeAheadInput extends HTMLElement {\n /**\n * @type {TextInput}\n */\n #inputElement;\n /**\n * @type {ListBox}\n */\n #dropdownElement;\n #currentValue;\n #lastValidValue = null;\n #shouldMatchOptions;\n #callbacks = {\n onChangeValue: []\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"text-input\");\n this.#dropdownElement = this.querySelector(\"list-box\");\n this.#shouldMatchOptions = this.hasAttribute(\"shouldMatchOptions\")\n this.#addListeners();\n }\n\n get value() {\n return this.#currentValue;\n }\n\n get rawValue() {\n return this.#inputElement.value;\n }\n\n set value(value) {\n this.#currentValue = value;\n this.#inputElement.value = value && value.displayName ? value.displayName : \"\";\n }\n\n /**\n * Sets the initial value of the input, as well as the last valid value.\n */\n set initialValue(value) {\n this.value = value;\n this.#lastValidValue = value;\n }\n\n set options(options) {\n this.#dropdownElement.options = options;\n this.#filterDatalist();\n }\n\n set errorMessage(message) {\n this.#inputElement.errorMessage = message;\n }\n\n checkValidity() {\n return this.#validate() && this.#inputElement.checkValidity();\n }\n\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n /** @param {boolean} isDisabled */\n setDisabled(isDisabled) {\n this.toggleAttribute(\"disabled\", isDisabled);\n this.#inputElement.setDisabled(isDisabled);\n }\n\n\n #onInput() {\n this.errorMessage = \"\";\n this.#filterDatalist();\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n }\n\n #onFocus() {\n this.#filterDatalist();\n this.#dropdownElement.show();\n }\n\n #onBlur() {\n this.#hideDropdownAndValidate();\n }\n\n #onOptionClick(option) {\n this.value = option;\n this.#hideDropdownAndValidate();\n }\n\n #onClearIconClick() {\n this.value = {displayName: \"\"};\n this.#inputElement.querySelector('input').focus();\n }\n\n #onKeydown(event) {\n if ([KeyCode.Up, KeyCode.Down].includes(event.code)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n switch (event.key) {\n case KeyCode.Esc: {\n this.#hideDropdownAndValidate();\n break;\n }\n case KeyCode.Enter: {\n if (this.#dropdownElement.isVisible())\n if (this.#dropdownElement.hasSelectedElement())\n this.#dropdownElement.triggerClickOnSelectedItem();\n else\n this.#hideDropdownAndValidate();\n break;\n }\n case KeyCode.Down: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectNextItem();\n break;\n }\n case KeyCode.Up: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectPrevItem();\n break;\n }\n }\n }\n\n #onInputValueChange() {\n this.#validateAndNotify();\n }\n\n #hideDropdownAndValidate() {\n this.#dropdownElement.hide();\n this.#validateAndNotify();\n }\n\n #validateAndNotify() {\n if (this.#validate() && this.#isValueChanged()) {\n this.#lastValidValue = this.value;\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value));\n }\n }\n\n #validate() {\n const inputText = this.#inputElement.value;\n if (inputText === \"\") {\n this.#currentValue = null;\n return true; // assume that value is valid if it is empty, otherwise required attribute should be set\n }\n if (this.value && this.value.displayName === inputText) {\n this.errorMessage = \"\";\n return true; // assume that value is valid if it is the same as the initial value\n }\n if (!this.#shouldMatchOptions) {\n this.errorMessage = \"\";\n this.#currentValue = {displayName: inputText};\n return true; // assume that value is valid if it should not match to any option\n }\n for (const option of this.#dropdownElement.options) {\n if (option.displayName === inputText) {\n this.errorMessage = \"\";\n this.#currentValue = option;\n this.#inputElement.value = option.displayName;\n return true;\n }\n }\n this.#currentValue = null;\n this.errorMessage = \"Select from list\";\n return false;\n }\n\n #filterDatalist() {\n this.#dropdownElement.filter = this.#inputElement.value;\n }\n\n #isValueChanged() {\n return this.#lastValidValue !== this.value;\n }\n\n #addListeners() {\n const input = this.#inputElement.querySelector(\"input\");\n this.addEventListener(\"keydown\", this.#onKeydown.bind(this));\n input.addEventListener(\"input\", this.#onInput.bind(this));\n input.addEventListener(\"blur\", this.#onBlur.bind(this));\n input.addEventListener('focus', this.#onFocus.bind(this));\n this.#inputElement.onTrailingIconClick(this.#onClearIconClick.bind(this));\n this.#inputElement.onChangeValue(this.#onInputValueChange.bind(this));\n this.#dropdownElement.onOptionClick(this.#onOptionClick.bind(this));\n }\n\n #htmlTemplate() {\n const requiredAttribute = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const disabledAttribute = this.hasAttribute(\"disabled\") ? \"disabled\" : \"\";\n const iconName = this.hasAttribute(\"no-icon\") ? \"\" : \"close\";\n return safeHtml`\n \n `;\n }\n\n static get is() {\n return 'typeahead-input';\n }\n}\n\nwindow.customElements.define(TypeAheadInput.is, TypeAheadInput);","import {KeyCode, safeHtml} from \"../utils.js\";\n\nexport default class SelectInput extends HTMLElement {\n #inputElement;\n #dropdownElement;\n #currentValue;\n #lastValidValue = null;\n\n #callbacks = {\n onShowDropdown: [],\n onChangeValue: []\n }\n\n get value() {\n return this.#currentValue;\n }\n\n set value(value) {\n this.#inputElement.value = value && value.displayName ? value.displayName : \"\";\n this.#currentValue = value;\n }\n\n set options(options) {\n this.#dropdownElement.options = options;\n }\n\n showDropdown() {\n this.#dropdownElement.show();\n this.#callbacks.onShowDropdown.forEach(callback => callback());\n }\n\n onShowDropdown(callback) {\n this.#callbacks.onShowDropdown.push(callback);\n }\n\n onChangeValue(callback) {\n this.#callbacks.onChangeValue.push(callback);\n }\n\n checkValidity() {\n return this.#validate();\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#inputElement = this.querySelector(\"text-input\");\n this.#dropdownElement = this.querySelector(\"list-box\");\n this.#addListeners();\n }\n\n #addListeners() {\n this.addEventListener(\"keydown\", this.#onKeydown.bind(this));\n const input = this.#inputElement.querySelector(\"input\");\n input.addEventListener('focus', this.#onFocus.bind(this));\n input.addEventListener(\"focusout\", this.#onFocusout.bind(this));\n input.addEventListener(\"click\", this.#onInputClick.bind(this));\n this.#dropdownElement.onOptionClick(this.#onOptionClick.bind(this));\n }\n\n #onFocus() {\n this.showDropdown();\n }\n\n #onFocusout() {\n this.#hideDropdownAndValidate();\n }\n\n #onOptionClick(option) {\n this.#inputElement.value = option.displayName;\n this.#currentValue = option;\n this.#hideDropdownAndValidate();\n }\n\n #onInputClick() {\n this.showDropdown();\n }\n\n #onKeydown(event) {\n if ([KeyCode.Up, KeyCode.Down].includes(event.code)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n switch (event.key) {\n case KeyCode.Esc: {\n event.preventDefault();\n this.#hideDropdownAndValidate();\n this.#inputElement.focus();\n break;\n }\n case KeyCode.Enter: {\n if (this.#dropdownElement.isVisible()) {\n event.stopPropagation();\n if (this.#dropdownElement.hasSelectedElement())\n this.#dropdownElement.triggerClickOnSelectedItem();\n else\n this.#dropdownElement.hide();\n }\n break;\n }\n case KeyCode.Down: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectNextItem();\n break;\n }\n case KeyCode.Up: {\n if (!this.#dropdownElement.isVisible())\n this.#dropdownElement.show();\n this.#dropdownElement.selectPrevItem();\n break;\n }\n }\n }\n\n #hideDropdownAndValidate() {\n this.#dropdownElement.hide();\n this.#validateAndNotify();\n }\n\n #validateAndNotify() {\n if (this.#validate() && this.#lastValidValue !== this.value) {\n this.#lastValidValue = this.value;\n this.#callbacks.onChangeValue.forEach(callback => callback(this.value))\n }\n }\n\n #validate() {\n if (this.#inputElement.hasAttribute(\"required\") && !this.#inputElement.value)\n this.#inputElement.errorMessage = \"Required\";\n else\n this.#inputElement.errorMessage = \"\";\n return this.#inputElement.checkValidity();\n }\n\n #htmlTemplate() {\n const requiredAttribute = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const disabledAttribute = this.hasAttribute(\"disabled\") ? \"disabled\" : \"\";\n return safeHtml`\n \n `;\n }\n\n static get is() {\n return 'select-input';\n }\n}\n\nwindow.customElements.define(SelectInput.is, SelectInput);","import {KeyCode} from \"../utils.js\";\n\nexport default class EditText extends HTMLElement {\n #children;\n #isValid = true;\n #value;\n #suffix = \"\";\n #prefix = \"\";\n\n #resizeObserver = new ResizeObserver(this.#updatePopupPosition.bind(this));\n\n #callbacks = {\n onChangeValue: []\n }\n\n connectedCallback() {\n this.innerHTML = this.#htmlTemplate();\n this.#children = {\n text: this.querySelector(\".edit-text__text\"),\n popup: this.querySelector(\".edit-text__popup\"),\n input: this.querySelector('text-input')\n };\n this.#addListeners();\n this.#resizeObserver.observe(document.body);\n this.#initAttributes();\n this.#updateTextValue();\n }\n\n disconnectedCallback() {\n this.#resizeObserver.unobserve(document.body);\n }\n\n value() {\n return this.#value;\n }\n\n onChange(cb){\n this.#callbacks.onChangeValue.push(cb);\n }\n\n #getDisplayName(){\n let val = this.#value;\n if (this.#isNumberType())\n val = +val;\n return `${this.#prefix}${val}${this.#suffix}`\n }\n\n #addListeners() {\n this.#children.text.addEventListener(\"click\", this.#showPopup.bind(this));\n this.#children.popup.addEventListener('click', this.#onClickOutsideOfInput.bind(this));\n this.#children.popup.addEventListener('keydown', this.#onKeydown.bind(this));\n this.#children.input.onInput(this.#onInput.bind(this));\n this.addEventListener(\"cancel\", this.#onEscape.bind(this));\n this.querySelector(\".popup-content\").addEventListener(\"click\", (event) => {\n event.stopPropagation();\n });\n }\n\n #showPopup() {\n this.#updateInputValue();\n this.#updatePopupPosition();\n this.#children.popup.showModal();\n this.#children.input.focus();\n }\n\n #onInput(value, isValid) {\n this.#isValid = isValid;\n }\n\n #onEscape() {\n this.#children.popup.close();\n }\n\n #onEnter() {\n if (this.#isValid)\n this.#updateDisplayTextAndNotifyIfChanged();\n }\n\n #onClickOutsideOfInput() {\n this.#children.popup.close();\n this.#onEnter();\n }\n\n #updateDisplayTextAndNotifyIfChanged() {\n if (this.#value !== this.#children.input.value){\n this.#updateTextValue();\n this.#callbacks.onChangeValue.forEach(cb => cb(this.value()));\n }\n }\n\n #onKeydown(evt) {\n evt.stopPropagation();\n if (evt.key === KeyCode.Enter && !evt.repeat)\n this.#onEnter();\n }\n\n #updateInputValue() {\n this.#children.input.value = this.#value;\n }\n\n #updateTextValue() {\n this.#value = this.#children.input.value;\n this.#children.text.textContent = this.#getDisplayName();\n }\n\n #updatePopupPosition() {\n let {top, left} = this.getBoundingClientRect();\n this.#children.popup.style.top = top + window.scrollY + \"px\";\n this.#children.popup.style.left = left + window.scrollX + \"px\";\n }\n\n #isNumberType() {\n return this.getAttribute(\"type\") === \"number\"\n }\n\n #initAttributes(){\n if (this.hasAttribute(\"suffix\"))\n this.#suffix = this.getAttribute(\"suffix\");\n if (this.hasAttribute(\"prefix\"))\n this.#prefix = this.getAttribute(\"prefix\");\n this.#value = this.getAttribute(\"value\") || \"\";\n }\n\n #htmlTemplate() {\n const requiredAttr = this.hasAttribute(\"required\") ? \"required\" : \"\";\n const typeAttr = this.getAttribute(\"type\") || \"text\";\n let stepAttr = \"\";\n if (this.hasAttribute(\"step\"))\n stepAttr = `step=\"${this.getAttribute(\"step\")}\"`\n let minAttr = \"\";\n if (this.hasAttribute(\"min\"))\n minAttr = `min=\"${this.getAttribute(\"min\")}\"`\n let maxAttr = \"\";\n if (this.hasAttribute(\"max\"))\n maxAttr = `max=\"${this.getAttribute(\"max\")}\"`\n const value = this.getAttribute(\"value\");\n return `\n \n
\n \n
\n
`;\n }\n\n static get is() {\n return 'edit-text';\n }\n}\n\nwindow.customElements.define(EditText.is, EditText);\n"],"names":["TextInputValidityState","constructor","textInput","this","querySelector","isValid","errorMessage","checkValidity","setCustomValidity","validity","valid","message","badInput","customError","patternMismatch","typeMismatch","rangeOverflow","rangeUnderflow","tooLong","tooShort","valueMissing","stepMismatch","cv","Object","assign","trimmedText","value","trim","hasAttribute","type","min","max","validityState","isTypeNumber","step","maxLength","minLength","validationMessage","KeyCode","freeze","safeHtml","strings","values","result","i","length","unsafe","String","replace","TextInput","HTMLElement","static","Set","onTrailingIconClick","onChangeValue","onInput","connectedCallback","innerHTML","getAttribute","disconnectedCallback","setAttribute","window","removeEventListener","bind","capture","rawValue","Number","isFinite","isFiniteNumber","textContent","callback","push","focus","options","setDisabled","isDisabled","toggleAttribute","event","key","Up","Down","preventDefault","Enter","repeat","forEach","attribute","attributes","has","name","addEventListener","document","activeElement","blur","trailingIconName","is","customElements","define","ListBox","onOptionClick","filter","searchString","toLowerCase","li","querySelectorAll","displayName","dataset","index","indexOf","selectedElement","scrollIntoView","block","show","style","display","hide","selectNextItem","visibleElements","hasSelectedElement","selectPrevItem","triggerClickOnSelectedItem","dispatchEvent","MouseEvent","isVisible","getComputedStyle","cb","sort","a","b","localeCompare","option","map","join","parentClientRect","parentElement","getBoundingClientRect","Math","text","span","createElement","body","appendChild","fontSize","visibility","position","width","ceil","remove","getTextWidth","widthToBe","maxAllowedWidth","documentElement","clientWidth","left","right","elementIndex","element","classList","add","startIndex","before","substring","match","after","TypeAheadInput","initialValue","includes","code","stopImmediatePropagation","Esc","inputText","input","requiredAttribute","disabledAttribute","iconName","SelectInput","onShowDropdown","showDropdown","stopPropagation","EditText","ResizeObserver","popup","observe","unobserve","onChange","val","showModal","close","evt","top","scrollY","scrollX","requiredAttr","typeAttr","stepAttr","minAttr","maxAttr"],"sourceRoot":""} \ No newline at end of file diff --git a/tmp_tsoutput/EditText/EditText.js b/tmp_tsoutput/EditText/EditText.js index 84afd7e..8565d2d 100644 --- a/tmp_tsoutput/EditText/EditText.js +++ b/tmp_tsoutput/EditText/EditText.js @@ -38,7 +38,7 @@ export default class EditText extends HTMLElement { } #addListeners() { this.#children.text.addEventListener("click", this.#showPopup.bind(this)); - this.#children.popup.addEventListener('click', this.#onEnter.bind(this)); + this.#children.popup.addEventListener('click', this.#onClickOutsideOfInput.bind(this)); this.#children.popup.addEventListener('keydown', this.#onKeydown.bind(this)); this.#children.input.onInput(this.#onInput.bind(this)); this.addEventListener("cancel", this.#onEscape.bind(this)); @@ -59,9 +59,14 @@ export default class EditText extends HTMLElement { this.#children.popup.close(); } #onEnter() { - if (!this.#isValid) - return; + if (this.#isValid) + this.#updateDisplayTextAndNotifyIfChanged(); + } + #onClickOutsideOfInput() { this.#children.popup.close(); + this.#onEnter(); + } + #updateDisplayTextAndNotifyIfChanged() { if (this.#value !== this.#children.input.value) { this.#updateTextValue(); this.#callbacks.onChangeValue.forEach(cb => cb(this.value()));