diff --git a/assets/css/extra.css b/assets/css/extra.css index 3d3438d..ef83835 100644 --- a/assets/css/extra.css +++ b/assets/css/extra.css @@ -363,7 +363,7 @@ select { font-size: large; outline: none; position: relative; - width: 160px; + width: 220px; } #browserInfo { cursor: pointer; diff --git a/assets/css/index.css b/assets/css/index.css index 0c4d6d1..bb6b5d3 100644 --- a/assets/css/index.css +++ b/assets/css/index.css @@ -149,7 +149,7 @@ --blueBtn: #268bd2; --blueBtn-bottom: #2074b1; } -:root[theme = "gruvbox"]{ +:root[theme="gruvbox"] { --background: #242424; --text: #fffefd; --box-main: #32302f; @@ -158,13 +158,12 @@ --box-toggleOn: #458588; --item-bg: #eebd35; --select: #98971a; - --greenBtn:#8ec07c; - --greenBtn-bottom:#689D6A; + --greenBtn: #8ec07c; + --greenBtn-bottom: #689d6a; --redBtn: #fb4934; --redBtn-bottom: #cc241d; --blueBtn: #7fa2ac; --blueBtn-bottom: #458588; - } body { @@ -291,7 +290,9 @@ img { border-radius: 8px; padding: 8px; font-family: "Inter", sans-serif; - transition: border 0.2s, background 0.2s; + transition: + border 0.2s, + background 0.2s; width: 100%; cursor: pointer; } @@ -382,23 +383,22 @@ img { } .custom-progress { - width: 90%; - height: 8px; - background: #e0e0e0; - border-radius: 6px; - overflow: hidden; - display:inline-block; + width: 90%; + height: 8px; + background: #e0e0e0; + border-radius: 6px; + overflow: hidden; + display: inline-block; } .custom-progress-fill { - width: 0%; - height: 100%; - background: var(--blueBtn); - transition: width 0.3s ease; - border-radius: 6px 0 0 6px; + width: 0%; + height: 100%; + background: var(--blueBtn); + transition: width 0.3s ease; + border-radius: 6px 0 0 6px; } - .itemSpeed { padding: 10px 5px 5px 5px; } @@ -534,16 +534,8 @@ img { padding: 10px; } -#videoFormatSelect, -#audioFormatSelect, -#audioForVideoFormatSelect { - font-family: JetBrains, monospace; - font-size: medium; - width: 400px; -} - .formatSelect { - margin-right: 4px; + margin: 2px 4px 2px 0; } label { @@ -1217,3 +1209,170 @@ input[type="range"]::-webkit-slider-thumb:hover { #updateProgress { font-size: 14px; } + +#videoFormatSelectContainer, +#audioFormatSelectContainer, +#audioFormatSelectContainer { + display: inline-block; + width: min(400px, 100%); + padding: 5px 0; +} + +/* SlimeSelect styles */ +.ss-main { + background-color: var(--select); + color: var(--text); + border: none; + border-radius: 12px; + height: 50px; +} + +.ss-arrow path { + stroke: var(--text) !important; + opacity: 0.6; +} + +.ss-search { + padding: 8px 12px !important; + border-bottom: 1px solid var(--select) !important; +} + +.ss-search input { + background-color: var(--box-separation) !important; + color: var(--text) !important; + border-radius: 6px !important; + padding: 8px 12px !important; + font-family: inherit !important; + font-size: 13px !important; + transition: border-color 0.2s !important; +} + +.ss-search input::placeholder { + color: var(--text) !important; + opacity: 0.6; +} + +.ss-content { + background-color: var(--select) !important; + border: transparent !important; + border-radius: 8px !important; +} +.ss-list { + padding: 4px !important; +} + +.ss-list::-webkit-scrollbar { + width: 10px; +} +.ss-list::-webkit-scrollbar-track { + box-shadow: inset 0 0 6px rgba(0, 0, 0, 0.3); +} +.ss-list::-webkit-scrollbar-thumb { + background-color: rgb(79, 78, 78); + border-radius: 5px; +} + +.ss-option { + padding: 8px 12px !important; + border-radius: 6px !important; + color: var(--text); +} +.ss-option:hover, +.ss-selected, +.ss-highlighted { + background-color: var(--box-toggleOn) !important; + color: var(--text) !important; +} + +/* Row Grid structures */ +.modern-option-row { + display: grid; + align-items: center; + width: 100%; + justify-items: center; +} + +.video-grid-extended { + grid-template-columns: 85px 65px 60px 1fr auto; +} + +.video-grid-compact { + grid-template-columns: 85px 65px 1fr auto; +} + +.audio-grid { + grid-template-columns: 200px 60px 1fr; + justify-items: center; +} + +.modern-option-row .main-text { + font-weight: 600; + font-size: 14px; + text-overflow: ellipsis; + overflow: hidden; + opacity: 0.9; + white-space: normal; +} +.modern-option-row .codec-text { + font-size: 12px; + font-family: JetBrains; + opacity: 0.6; +} +.modern-option-row .size-text { + font-size: 13px; + font-weight: 500; + justify-self: end; + margin-right: 12px; + opacity: 0.8; +} + +.badge { + font-size: 11px; + font-weight: 600; + padding: 3px 6px; + border-radius: 4px; + text-transform: uppercase; + width: max-content; + text-align: center; +} +.badge-format { + background-color: var(--box-main); + color: var(--text); +} + +.audio-indicator { + display: inline-flex; + align-items: center; + gap: 4px; + font-size: 11px; + padding: 2px 6px; + border-radius: 4px; + background-color: transparent; + color: #10b981; + font-weight: 500; +} +.audio-indicator svg { + width: 20px; + height: 20px; + fill: currentColor; +} +.audio-placeholder { + width: 53px; +} +/* Resolution */ +.ss-option .main-text { + color: var(--text) !important; + opacity: 0.8; +} + +/* Video codec */ +.ss-option .codec-text { + color: var(--text) !important; + opacity: 0.6; +} + +/* Video/audio size */ +.ss-option .size-text { + color: var(--text) !important; + opacity: 0.8; +} diff --git a/assets/slimselect.css b/assets/slimselect.css new file mode 100644 index 0000000..0acee03 --- /dev/null +++ b/assets/slimselect.css @@ -0,0 +1 @@ +:root{--ss-primary-color: #5897fb;--ss-bg-color: #ffffff;--ss-font-color: #4d4d4d;--ss-placeholder-color: #8d8d8d;--ss-disabled-color: #dcdee2;--ss-border-color: #dcdee2;--ss-highlight-color: #fffb8c;--ss-focus-color: var(--ss-primary-color);--ss-success-color: #00b755;--ss-error-color: #dc3545;--ss-main-height: 40px;--ss-content-height: 300px;--ss-search-height: 40px;--ss-option-height: auto;--ss-spacing-l: 9px;--ss-spacing-m: 7px;--ss-spacing-s: 5px;--ss-animation-timing: 0.2s;--ss-border-radius: 4px}@keyframes ss-valueIn{0%{transform:scale(0);opacity:0}100%{transform:scale(1);opacity:1}}@keyframes ss-valueOut{0%{transform:scale(1);opacity:1}100%{transform:scale(0);opacity:0}}.ss-hide{display:none !important}.ss-main{display:flex;flex-direction:row;position:relative;user-select:none;color:var(--ss-font-color);min-height:var(--ss-main-height);width:100%;padding:var(--ss-spacing-s);cursor:pointer;border:1px solid var(--ss-border-color);border-radius:var(--ss-border-radius);background-color:var(--ss-bg-color);outline:0;box-sizing:border-box;transition:background-color var(--ss-animation-timing);overflow:hidden}.ss-main:focus{box-shadow:0 0 5px var(--ss-focus-color)}.ss-main.ss-disabled{background-color:var(--ss-disabled-color);cursor:not-allowed}.ss-main.ss-disabled .ss-values .ss-disabled{color:var(--ss-font-color)}.ss-main.ss-disabled .ss-values .ss-value .ss-value-delete{cursor:not-allowed}.ss-main.ss-dir-above{border-top-left-radius:0px;border-top-right-radius:0px}.ss-main.ss-dir-below{border-bottom-left-radius:0px;border-bottom-right-radius:0px}.ss-main .ss-values{display:inline-flex;flex-wrap:wrap;gap:var(--ss-spacing-m);flex:1 1 100%;min-width:0;max-width:100%;overflow:hidden}.ss-main .ss-values:has(.ss-multi-string){flex-wrap:nowrap;gap:0;align-items:center}.ss-main .ss-values .ss-placeholder{display:block;width:100%;min-width:0;padding:var(--ss-spacing-s) var(--ss-spacing-m) var(--ss-spacing-s) var(--ss-spacing-m);margin:auto 0px auto 0px;line-height:1em;color:var(--ss-placeholder-color);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.ss-main .ss-values .ss-max{display:flex;user-select:none;align-items:center;width:fit-content;font-size:12px;color:var(--ss-bg-color);line-height:1;padding:var(--ss-spacing-s) var(--ss-spacing-m);background-color:var(--ss-primary-color);border-radius:var(--ss-border-radius)}.ss-main .ss-values .ss-single{display:block;margin:auto 0px auto var(--ss-spacing-s);min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;flex:1 1 auto;max-width:calc(100% - 20px)}.ss-main .ss-values .ss-multi-string{display:block;width:100%;min-width:0;padding:var(--ss-spacing-s) var(--ss-spacing-m) var(--ss-spacing-s) var(--ss-spacing-m);margin:auto 0px auto 0px;line-height:1em;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;flex:1 1 auto;max-width:calc(100% - 20px)}.ss-main .ss-values .ss-value{display:flex;user-select:none;align-items:center;width:fit-content;max-width:100%;background-color:var(--ss-primary-color);border-radius:var(--ss-border-radius);animation-name:ss-valueIn;animation-duration:var(--ss-animation-timing);animation-timing-function:ease-out;animation-fill-mode:both}.ss-main .ss-values .ss-value.ss-value-out{animation-name:ss-valueOut;animation-duration:var(--ss-animation-timing);animation-timing-function:ease-out}.ss-main .ss-values .ss-value .ss-value-text{flex:1;min-width:0;font-size:12px;line-height:1;color:var(--ss-bg-color);padding:var(--ss-spacing-s) var(--ss-spacing-m);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.ss-main .ss-values .ss-value .ss-value-delete{display:flex;align-items:center;height:var(--ss-spacing-l);width:var(--ss-spacing-l);padding:var(--ss-spacing-s) var(--ss-spacing-m);cursor:pointer;border-left:solid 1px var(--ss-bg-color);box-sizing:content-box}.ss-main .ss-values .ss-value .ss-value-delete svg{height:var(--ss-spacing-l);width:var(--ss-spacing-l)}.ss-main .ss-values .ss-value .ss-value-delete svg path{fill:none;stroke:var(--ss-bg-color);stroke-width:18;stroke-linecap:round;stroke-linejoin:round}.ss-main .ss-deselect{flex:0 1 auto;display:flex;align-items:center;justify-content:center;width:fit-content;height:auto;padding:0 var(--ss-spacing-m) 0 var(--ss-spacing-m)}.ss-main .ss-deselect svg{width:8px;height:8px}.ss-main .ss-deselect svg path{fill:none;stroke:var(--ss-font-color);stroke-width:20;stroke-linecap:round;stroke-linejoin:round}.ss-main .ss-arrow{flex:0 1 auto;display:flex;align-items:center;justify-content:flex-end;width:12px;height:12px;margin:auto var(--ss-spacing-m) auto var(--ss-spacing-m)}.ss-main .ss-arrow path{fill:none;stroke:var(--ss-font-color);stroke-width:18;stroke-linecap:round;stroke-linejoin:round;transition-timing-function:ease-out;transition:var(--ss-animation-timing)}.ss-status{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0, 0, 0, 0);white-space:nowrap;border:0}.ss-content{position:absolute;display:flex;height:auto;flex-direction:column;width:auto;max-height:var(--ss-content-height);box-sizing:border-box;border:solid 1px var(--ss-border-color);background-color:var(--ss-bg-color);transition:transform var(--ss-animation-timing),opacity var(--ss-animation-timing);opacity:0;transform:scaleY(0);overflow:hidden;z-index:10000}.ss-content.ss-relative{position:relative;height:100%}.ss-content.ss-fixed{position:fixed}.ss-content.ss-dir-above{transform-origin:center bottom;flex-direction:column-reverse;border-top-left-radius:var(--ss-border-radius);border-top-right-radius:var(--ss-border-radius)}.ss-content.ss-dir-below{transform-origin:center top;border-bottom-left-radius:var(--ss-border-radius);border-bottom-right-radius:var(--ss-border-radius)}.ss-content.ss-open{opacity:1;transform:scaleY(1)}.ss-content .ss-search{flex:0 1 auto;display:flex;flex-direction:row;border-bottom:1px solid var(--ss-border-color)}.ss-content .ss-search input{display:inline-flex;font-size:inherit;line-height:inherit;flex:1 1 auto;width:100%;min-width:0px;height:var(--ss-search-height);padding:var(--ss-spacing-m) var(--ss-spacing-l);margin:0;border:none;background-color:var(--ss-bg-color);outline:0;text-align:left;box-sizing:border-box}.ss-content .ss-search input::placeholder{color:var(--ss-placeholder-color);vertical-align:middle}.ss-content .ss-search input:focus{box-shadow:none}.ss-content .ss-search .ss-addable{display:inline-flex;justify-content:center;align-items:center;cursor:pointer;flex:0 0 auto;height:auto;margin:0 0 0 var(--ss-spacing-m);border:1px solid var(--ss-border-color);border-radius:var(--ss-border-radius)}.ss-content .ss-search .ss-addable svg{display:flex;align-items:center;justify-content:flex-end;flex:0 1 auto;width:12px;height:12px;margin:auto var(--ss-spacing-m) auto var(--ss-spacing-m)}.ss-content .ss-search .ss-addable svg path{fill:none;stroke:var(--ss-font-color);stroke-width:18;stroke-linecap:round;stroke-linejoin:round}.ss-content.ss-dir-above .ss-search{border-bottom:none;border-top:1px solid var(--ss-border-color)}.ss-content .ss-list{flex:1 1 auto;height:auto;overflow-x:hidden;overflow-y:auto}.ss-content .ss-list .ss-error{color:var(--ss-error-color);padding:var(--ss-spacing-l)}.ss-content .ss-list .ss-searching{color:var(--ss-font-color);padding:var(--ss-spacing-l)}.ss-content .ss-list .ss-optgroup .ss-option{transition:max-height var(--ss-animation-timing) ease,opacity var(--ss-animation-timing) ease,padding-top var(--ss-animation-timing) ease,padding-bottom var(--ss-animation-timing) ease,margin-top var(--ss-animation-timing) ease,margin-bottom var(--ss-animation-timing) ease}.ss-content .ss-list .ss-optgroup.ss-open .ss-option{max-height:100px;opacity:1;overflow:visible}.ss-content .ss-list .ss-optgroup.ss-close .ss-option{padding-top:0 !important;padding-bottom:0 !important;margin-top:0 !important;margin-bottom:0 !important;max-height:0;opacity:0;overflow:hidden}.ss-content .ss-list .ss-optgroup .ss-optgroup-label{display:flex;flex-direction:row;align-items:center;justify-content:space-between;padding:var(--ss-spacing-m) var(--ss-spacing-l) var(--ss-spacing-m) var(--ss-spacing-l)}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-label-text{flex:1 1 auto;font-weight:bold;color:var(--ss-font-color)}.ss-content .ss-list .ss-optgroup .ss-optgroup-label:has(.ss-arrow){cursor:pointer}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions{flex:0 1 auto;display:flex;flex-direction:row;align-items:center;justify-content:center;gap:var(--ss-spacing-m)}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall{flex:0 0 auto;display:flex;flex-direction:row;cursor:pointer}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall:hover{opacity:.5}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall.ss-selected svg path{stroke:var(--ss-error-color)}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall span{flex:0 1 auto;display:flex;align-items:center;justify-content:center;font-size:60%;text-align:center;padding:0 var(--ss-spacing-s) 0 0}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall svg{flex:0 1 auto;width:13px;height:13px}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall svg path{fill:none;stroke:var(--ss-success-color);stroke-linecap:round;stroke-linejoin:round}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall svg:first-child{stroke-width:5}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-selectall svg:last-child{stroke-width:11}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-closable{flex:0 1 auto;display:flex;flex-direction:row;cursor:pointer}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-closable .ss-arrow{flex:1 1 auto;width:10px;height:10px}.ss-content .ss-list .ss-optgroup .ss-optgroup-label .ss-optgroup-actions .ss-closable .ss-arrow path{fill:none;stroke:var(--ss-font-color);stroke-width:18;stroke-linecap:round;stroke-linejoin:round;transition-timing-function:ease-out;transition:var(--ss-animation-timing)}.ss-content .ss-list .ss-optgroup .ss-option{padding:var(--ss-spacing-s) var(--ss-spacing-s) var(--ss-spacing-s) calc(var(--ss-spacing-l)*3)}.ss-content .ss-list .ss-option{display:flex;align-items:center;min-height:var(--ss-option-height);padding:var(--ss-spacing-m) var(--ss-spacing-l) var(--ss-spacing-m) var(--ss-spacing-l);white-space:normal;color:var(--ss-font-color);cursor:pointer;user-select:none}.ss-content .ss-list .ss-option:hover:not(.ss-disabled){color:var(--ss-bg-color);background-color:var(--ss-primary-color);border-left:5px solid var(--ss-primary-color);transition:border-left var(--ss-animation-timing) ease}.ss-content .ss-list .ss-option.ss-highlighted,.ss-content .ss-list .ss-option:not(.ss-disabled).ss-selected{color:var(--ss-bg-color);background-color:var(--ss-primary-color)}.ss-content .ss-list .ss-option.ss-disabled{cursor:not-allowed;background-color:var(--ss-disabled-color)}.ss-content .ss-list .ss-option.ss-disabled:hover{color:var(--ss-font-color)}.ss-content .ss-list .ss-option .ss-search-highlight{display:inline-block;background-color:var(--ss-highlight-color)}.ss-content .ss-list .ss-search{display:flex;flex-direction:row;align-items:center;padding:var(--ss-spacing-m) var(--ss-spacing-l) var(--ss-spacing-m) var(--ss-spacing-l)}/*# sourceMappingURL=slimselect.css.map */ diff --git a/assets/slimselect.js b/assets/slimselect.js new file mode 100644 index 0000000..a19dd6b --- /dev/null +++ b/assets/slimselect.js @@ -0,0 +1,2 @@ +(function(e,t){typeof exports==`object`&&typeof module<`u`?module.exports=t():typeof define==`function`&&define.amd?define([],t):(e=typeof globalThis<`u`?globalThis:e||self,e.SlimSelect=t())})(this,function(){var e=Object.defineProperty,t=(t,n)=>{let r={};for(var i in t)e(r,i,{get:t[i],enumerable:!0});return n||e(r,Symbol.toStringTag,{value:`Module`}),r},n=class{main;placeholder;values;single;multiString;max;value;valueText;valueDelete;valueOut;deselect;deselectPath;arrow;arrowClose;arrowOpen;content;contentOpen;dirAbove;dirBelow;search;searchHighlighter;searching;status;addable;addablePath;list;optgroup;optgroupLabel;optgroupLabelText;optgroupActions;optgroupSelectAll;optgroupSelectAllBox;optgroupSelectAllCheck;optgroupClosable;option;optionDelete;highlighted;mainOpen;close;selected;error;disabled;hide;constructor(e){e||={};let t=(e=``,t=``)=>`${e} ${t}`.trim();this.main=t(`ss-main`,e.main),this.placeholder=t(`ss-placeholder`,e.placeholder),this.values=t(`ss-values`,e.values),this.single=t(`ss-single`,e.single),this.multiString=t(`ss-multi-string`,e.multiString),this.max=t(`ss-max`,e.max),this.value=t(`ss-value`,e.value),this.valueText=t(`ss-value-text`,e.valueText),this.valueDelete=t(`ss-value-delete`,e.valueDelete),this.valueOut=t(`ss-value-out`,e.valueOut),this.deselect=t(`ss-deselect`,e.deselect),this.deselectPath=e.deselectPath||`M10,10 L90,90 M10,90 L90,10`,this.arrow=t(`ss-arrow`,e.arrow),this.arrowClose=e.arrowClose||`M10,30 L50,70 L90,30`,this.arrowOpen=e.arrowOpen||`M10,70 L50,30 L90,70`,this.content=t(`ss-content`,e.content),this.contentOpen=t(`ss-open`,e.contentOpen),this.dirAbove=t(`ss-dir-above`,e.dirAbove),this.dirBelow=t(`ss-dir-below`,e.dirBelow),this.search=t(`ss-search`,e.search),this.searchHighlighter=t(`ss-search-highlight`,e.searchHighlighter),this.searching=t(`ss-searching`,e.searching),this.status=t(`ss-status`,e.status),this.addable=t(`ss-addable`,e.addable),this.addablePath=e.addablePath||`M50,10 L50,90 M10,50 L90,50`,this.list=t(`ss-list`,e.list),this.optgroup=t(`ss-optgroup`,e.optgroup),this.optgroupLabel=t(`ss-optgroup-label`,e.optgroupLabel),this.optgroupLabelText=t(`ss-optgroup-label-text`,e.optgroupLabelText),this.optgroupActions=t(`ss-optgroup-actions`,e.optgroupActions),this.optgroupSelectAll=t(`ss-selectall`,e.optgroupSelectAll),this.optgroupSelectAllBox=e.optgroupSelectAllBox||`M60,10 L10,10 L10,90 L90,90 L90,50`,this.optgroupSelectAllCheck=e.optgroupSelectAllCheck||`M30,45 L50,70 L90,10`,this.optgroupClosable=t(`ss-closable`,e.optgroupClosable),this.option=t(`ss-option`,e.option),this.optionDelete=e.optionDelete||`M10,10 L90,90 M10,90 L90,10`,this.highlighted=t(`ss-highlighted`,e.highlighted),this.mainOpen=t(`ss-open`,e.mainOpen),this.close=t(`ss-close`,e.close),this.selected=t(`ss-selected`,e.selected),this.error=t(`ss-error`,e.error),this.disabled=t(`ss-disabled`,e.disabled),this.hide=t(`ss-hide`,e.hide)}getFirst(e){return this[e].split(` `)[0]}};function r(){return Math.random().toString(36).substring(2,10)}function i(e,t){function n(e,n){return n&&e&&e.classList&&e.classList.contains(n)||n&&e&&e.dataset&&e.dataset.id&&e.dataset.id===t?e:null}function r(e,t){return!e||e===document?null:n(e,t)?e:r(e.parentNode,t)}return n(e,t)||r(e,t)}function a(e,t=50,n=!1){let r;return function(...i){let a=self,o=()=>{r=null,n||e.apply(a,i)},s=n&&!r;clearTimeout(r),r=setTimeout(o,t),s&&e.apply(a,i)}}function o(e,t){return JSON.stringify(e)===JSON.stringify(t)}function s(e){let t=e.replace(/[A-Z\u00C0-\u00D6\u00D8-\u00DE]/g,e=>`-`+e.toLowerCase());return e[0]===e[0].toUpperCase()?t.substring(1):t}var c=class{id;value;text;html;defaultSelected;selected;display;disabled;placeholder;class;style;data;mandatory;constructor(e){this.id=!e.id||e.id===``?r():e.id,this.value=e.value===void 0?e.text||``:e.value||``,this.text=e.text||``,this.html=e.html||``,this.defaultSelected=e.defaultSelected===void 0?!1:e.defaultSelected,this.selected=e.selected===void 0?!1:e.selected,this.display=e.display===void 0?!0:e.display,this.disabled=e.disabled===void 0?!1:e.disabled,this.mandatory=e.mandatory===void 0?!1:e.mandatory,this.placeholder=e.placeholder===void 0?!1:e.placeholder,this.class=e.class||``,this.style=e.style||``,this.data=e.data||{}}},l=class{id;label;selectAll;selectAllText;closable;options;constructor(e){if(this.id=!e.id||e.id===``?r():e.id,this.label=e.label||``,this.selectAll=e.selectAll===void 0?!1:e.selectAll,this.selectAllText=e.selectAllText||`Select All`,this.closable=e.closable||`off`,this.options=[],e.options)for(let t of e.options)this.options.push(new c(t))}},u=class{selectType=`single`;data=[];selectedOrder=[];constructor(e,t){this.selectType=e,this.setData(t)}validateDataArray(e){if(!Array.isArray(e))return Error(`Data must be an array`);for(let t of e)if(t)if(t instanceof l||`label`in t){if(!(`label`in t))return Error(`Optgroup must have a label`);if(`options`in t&&t.options)for(let e of t.options){let t=this.validateOption(e);if(t)return t}}else if(t instanceof c||`text`in t){let e=this.validateOption(t);if(e)return e}else return Error(`Data object must be a valid optgroup or option`);return null}validateOption(e){return`text`in e?null:Error(`Option must have a text`)}partialToFullData(e){let t=[];return e.forEach(e=>{if(e){if(e instanceof l||`label`in e){let n=[];`options`in e&&e.options&&e.options.forEach(e=>{n.push(new c(e))}),n.length>0&&t.push(new l(e))}(e instanceof c||`text`in e)&&t.push(new c(e))}}),t}setData(e,t=!1){let n=this.partialToFullData(e),r=[];if(t){r=this.getSelectedOptions();let e=[];r.forEach(t=>{let r=!1;for(let e of n){if(e instanceof c&&e.id===t.id){r=!0;break}if(e instanceof l){for(let n of e.options)if(n.id===t.id){r=!0;break}}}r||e.push(t)}),this.data=[...e,...n]}else this.data=n;if(this.selectType===`single`){let e=t&&r.length===0;this.setSelectedBy(`id`,this.getSelected(),e)}}getData(){return this.filter(null,!0)}getDataOptions(){return this.filter(null,!1)}addOption(e,t=!1){if(t){let t=[new c(e)];this.setData(t.concat(this.getData()))}else this.setData(this.getData().concat(new c(e)))}setSelectedBy(e,t,n=!1){let r=null,i=!1,a=[];for(let n of this.data){if(n instanceof l)for(let o of n.options){r||=o;let n=o[e]||``;o.selected=i?!1:t.includes(n),o.selected&&(a.push(o),this.selectType===`single`&&(i=!0))}n instanceof c&&(r||=n,n.selected=i?!1:t.includes(n[e]),n.selected&&(a.push(n),this.selectType===`single`&&(i=!0)))}this.selectType===`single`&&r&&!i&&!n&&(r.selected=!0,a.push(r));let o=t.map(t=>a.find(n=>n[e]===t)?.id||``);this.selectedOrder=o}getSelected(){return this.getSelectedOptions().map(e=>e.id)}getSelectedValues(){return this.getSelectedOptions().map(e=>e.value)}getSelectedOptions(){return this.filter(e=>e.selected,!1)}getOptgroupByID(e){for(let t of this.data)if(t instanceof l&&t.id===e)return t;return null}getOptionByID(e){let t=this.filter(t=>t.id===e,!1);return t.length?t[0]:null}getSelectType(){return this.selectType}getFirstOption(){let e=null;for(let t of this.data)if(t instanceof l?e=t.options[0]:t instanceof c&&(e=t),e)break;return e}search(e,t){return e=e.trim(),e===``?this.getData():this.filter(n=>t(n,e),!0)}filter(e,t){let n=[];return this.data.forEach(r=>{if(r instanceof l){let i=[];if(r.options.forEach(r=>{(!e||e(r))&&(t?i.push(new c(r)):n.push(new c(r)))}),i.length>0){let e=new l(r);e.options=i,n.push(e)}}r instanceof c&&(!e||e(r))&&n.push(new c(r))}),n}selectedOrderOptions(e){let t=[];return this.selectedOrder.forEach(n=>{let r=e.find(e=>e.id===n);r&&t.push(r)}),e.forEach(e=>{let n=!1;t.forEach(t=>{if(e.id===t.id){n=!0;return}}),n||t.push(e)}),t}},d=class{settings;store;callbacks;lastSelectedOption;lastRenderedOptions;closeAnimationTimeout=null;main;content;classes;constructor(e,t,n,r){this.store=n,this.settings=e,this.classes=t,this.callbacks=r,this.lastSelectedOption=null,this.lastRenderedOptions=[],this.main=this.mainDiv(),this.content=this.contentDiv(),this.updateClassStyles(),this.updateAriaAttributes(),this.settings.contentPosition!==`relative`&&(this.content.main.style.top=`-9999px`,this.content.main.style.left=`-9999px`,this.content.main.style.margin=`0`,this.content.main.style.width=`auto`),this.settings.contentLocation&&this.settings.contentLocation.appendChild(this.content.main)}addClasses(e,t){if(!t||t.trim()===``)return;let n=t.split(` `).filter(e=>e.trim()!==``);for(let t of n)e.classList.add(t.trim())}removeClasses(e,t){if(!t||t.trim()===``)return;let n=t.split(` `).filter(e=>e.trim()!==``);for(let t of n)e.classList.remove(t.trim())}enable(){this.removeClasses(this.main.main,this.classes.disabled),this.main.main.setAttribute(`aria-disabled`,`false`),this.content.search.input.disabled=!1}disable(){this.addClasses(this.main.main,this.classes.disabled),this.main.main.setAttribute(`aria-disabled`,`true`),this.content.search.input.disabled=!0}open(){this.main.arrow.path.setAttribute(`d`,this.classes.arrowOpen),this.main.main.setAttribute(`aria-expanded`,`true`),this.closeAnimationTimeout&&=(clearTimeout(this.closeAnimationTimeout),null);let e=this.settings.openPosition===`up`?this.classes.dirAbove:this.classes.dirBelow;this.addClasses(this.main.main,e),this.addClasses(this.content.main,e),this.addClasses(this.content.main,this.classes.contentOpen),this.content.search.input.removeAttribute(`aria-hidden`),this.moveContent();let t=this.store.getSelectedOptions();if(t.length){let e=t[t.length-1].id,n=this.content.list.querySelector(`[data-id="`+e+`"]`);n&&this.ensureElementInView(this.content.list,n)}}close(){this.main.main.setAttribute(`aria-expanded`,`false`),this.main.arrow.path.setAttribute(`d`,this.classes.arrowClose),this.removeClasses(this.content.main,this.classes.contentOpen),this.content.search.input.setAttribute(`aria-hidden`,`true`),this.main.main.removeAttribute(`aria-activedescendant`);let e=this.getAnimationTiming();this.closeAnimationTimeout=setTimeout(()=>{this.removeClasses(this.main.main,this.classes.dirAbove),this.removeClasses(this.main.main,this.classes.dirBelow),this.removeClasses(this.content.main,this.classes.dirAbove),this.removeClasses(this.content.main,this.classes.dirBelow),this.closeAnimationTimeout=null},e)}getAnimationTiming(){let e=getComputedStyle(this.content.main).getPropertyValue(`--ss-animation-timing`).trim();if(e){if(e.endsWith(`ms`))return parseFloat(e);if(e.endsWith(`s`))return parseFloat(e)*1e3}return 200}updateClassStyles(){if(this.main.main.className=``,this.main.main.removeAttribute(`style`),this.content.main.className=``,this.content.main.removeAttribute(`style`),this.addClasses(this.main.main,this.classes.main),this.addClasses(this.content.main,this.classes.content),this.settings.style!==``&&(this.main.main.style.cssText=this.settings.style,this.content.main.style.cssText=this.settings.style),this.settings.class.length)for(let e of this.settings.class)e.trim()!==``&&(this.main.main.classList.add(e.trim()),this.content.main.classList.add(e.trim()));(this.settings.contentPosition===`relative`||this.settings.contentPosition===`fixed`)&&this.content.main.classList.add(`ss-`+this.settings.contentPosition)}updateAriaAttributes(){let e=this.content.list.id;this.main.main.role=`combobox`,this.main.main.setAttribute(`aria-haspopup`,`listbox`),this.main.main.setAttribute(`aria-controls`,e),this.main.main.setAttribute(`aria-expanded`,`false`),this.content.list.setAttribute(`role`,`listbox`),this.content.list.setAttribute(`aria-label`,this.settings.ariaLabel+` listbox`),this.settings.isMultiple&&this.content.list.setAttribute(`aria-multiselectable`,`true`),this.content.search.input.setAttribute(`aria-controls`,e)}mainDiv(){let e=document.createElement(`div`);e.dataset.id=this.settings.id,e.setAttribute(`aria-label`,this.settings.ariaLabel),e.tabIndex=0,e.onkeydown=e=>{switch(e.key){case`ArrowUp`:case`ArrowDown`:return this.callbacks.open(),e.key===`ArrowDown`?this.highlight(`down`):this.highlight(`up`),!1;case`Tab`:return this.callbacks.close(),!0;case`Enter`:case` `:this.callbacks.open();let t=this.content.list.querySelector(`.`+this.classes.getFirst(`highlighted`));return t&&t.click(),!1;case`Escape`:return this.callbacks.close(),!1}return e.key.length===1&&this.callbacks.open(),!0},e.onclick=e=>{this.settings.disabled||(this.settings.isOpen?this.callbacks.close():this.callbacks.open())};let t=document.createElement(`div`);this.addClasses(t,this.classes.values),e.appendChild(t);let n=document.createElement(`div`);this.addClasses(n,this.classes.deselect),n.setAttribute(`role`,`button`),n.setAttribute(`aria-label`,this.settings.deselectText),n.setAttribute(`tabindex`,`0`);let r=this.store?.getSelectedOptions();!this.settings.allowDeselect||this.settings.isMultiple&&r&&r.length<=0?this.addClasses(n,this.classes.hide):this.removeClasses(n,this.classes.hide),n.onclick=e=>{if(e.stopPropagation(),this.settings.disabled)return;let t=!0,n=this.store.getSelectedOptions();if(this.callbacks.beforeChange&&(t=this.callbacks.beforeChange([],n)===!0),t){if(this.settings.isMultiple)this.callbacks.setSelected([],!1),this.updateDeselectAll();else{let e=this.store.getFirstOption(),t=e?e.id:``;this.callbacks.setSelected(t,!1)}this.settings.closeOnSelect&&this.callbacks.close(),this.callbacks.afterChange&&this.callbacks.afterChange(this.store.getSelectedOptions())}},n.onkeydown=e=>{(e.key===`Enter`||e.key===` `)&&(e.preventDefault(),n.click())};let i=document.createElementNS(`http://www.w3.org/2000/svg`,`svg`);i.setAttribute(`viewBox`,`0 0 100 100`);let a=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);a.setAttribute(`d`,this.classes.deselectPath),i.appendChild(a),n.appendChild(i),e.appendChild(n);let o=document.createElementNS(`http://www.w3.org/2000/svg`,`svg`);this.addClasses(o,this.classes.arrow),o.setAttribute(`viewBox`,`0 0 100 100`);let s=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);return s.setAttribute(`d`,this.classes.arrowClose),this.settings.alwaysOpen&&this.addClasses(o,this.classes.hide),o.appendChild(s),e.appendChild(o),{main:e,values:t,deselect:{main:n,svg:i,path:a},arrow:{main:o,path:s}}}mainFocus(e){e!==`click`&&this.main.main.focus({preventScroll:!0})}placeholder(){let e=this.store.filter(e=>e.placeholder,!1),t=this.settings.placeholderText;e.length&&(e[0].html===``?e[0].text!==``&&(t=e[0].text):t=e[0].html);let n=document.createElement(`div`);return this.addClasses(n,this.classes.placeholder),n.innerHTML=t,n}renderValues(){if(!this.settings.isMultiple){this.renderSingleValue();return}this.renderMultipleValues(),this.updateDeselectAll()}renderSingleValue(){let e=this.store.filter(e=>e.selected&&!e.placeholder,!1),t=e.length>0?e[0]:null;if(!t)this.main.values.innerHTML=this.placeholder().outerHTML;else{let e=document.createElement(`div`);this.addClasses(e,this.classes.single),t.html?e.innerHTML=t.html:e.innerText=t.text,this.main.values.innerHTML=e.outerHTML}!this.settings.allowDeselect||!e.length?this.addClasses(this.main.deselect.main,this.classes.hide):this.removeClasses(this.main.deselect.main,this.classes.hide)}renderMultipleValues(){let e=this.main.values.childNodes,t=this.store.filter(e=>e.selected&&e.display,!1);if(t.length===0){this.main.values.innerHTML=this.placeholder().outerHTML;return}else{let e=this.main.values.querySelector(`.`+this.classes.getFirst(`placeholder`));e&&e.remove()}if(this.settings.multiString){let e=t;this.settings.keepOrder&&(e=this.store.selectedOrderOptions(e));let n=document.createElement(`div`);this.addClasses(n,this.classes.multiString),n.textContent=e.map(e=>e.text).join(`, `),this.settings.showOptionTooltips&&n.setAttribute(`title`,n.textContent),this.main.values.innerHTML=n.outerHTML;return}if(t.length>this.settings.maxValuesShown){let e=document.createElement(`div`);this.addClasses(e,this.classes.max),e.textContent=this.settings.maxValuesMessage.replace(`{number}`,t.length.toString()),this.main.values.innerHTML=e.outerHTML;return}else{let e=this.main.values.querySelector(`.`+this.classes.getFirst(`max`));e&&e.remove()}this.settings.keepOrder&&(t=this.store.selectedOrderOptions(t));let n=[];for(let r=0;re.id===a,!1).length||n.push(i))}for(let e of n)this.addClasses(e,this.classes.valueOut),setTimeout(()=>{this.main.values.hasChildNodes()&&this.main.values.contains(e)&&this.main.values.removeChild(e)},100);e=this.main.values.childNodes;for(let n=0;n{if(t.preventDefault(),t.stopPropagation(),this.settings.disabled)return;let n=!0,r=this.store.getSelectedOptions(),i=r.filter(t=>t.selected&&t.id!==e.id,!0);if(!(this.settings.minSelected&&i.length{e.key===`Enter`&&n.click()}}return t}contentDiv(){let e=document.createElement(`div`);e.dataset.id=this.settings.id;let t=this.searchDiv();e.appendChild(t.main);let n=document.createElement(`div`);this.addClasses(n,this.classes.status),n.setAttribute(`aria-live`,`polite`),n.setAttribute(`aria-atomic`,`true`),n.setAttribute(`role`,`status`),e.appendChild(n);let r=this.listDiv();return e.appendChild(r),{main:e,search:t,status:n,list:r}}announce(e){this.settings.showSearch&&(this.content.status.textContent=e)}moveContent(){if(this.settings.contentPosition===`relative`){this.moveContentBelow();return}if(this.settings.openPosition===`down`){this.moveContentBelow();return}else if(this.settings.openPosition===`up`){this.moveContentAbove();return}this.putContent()===`up`?this.moveContentAbove():this.moveContentBelow()}searchDiv(){let e=document.createElement(`div`),t=document.createElement(`input`),n=document.createElement(`div`);this.addClasses(e,this.classes.search);let r={main:e,input:t};if(this.settings.showSearch||(this.addClasses(e,this.classes.hide),t.readOnly=!0),t.type=`search`,t.placeholder=this.settings.searchPlaceholder,t.tabIndex=-1,t.setAttribute(`aria-label`,this.settings.searchPlaceholder),t.setAttribute(`aria-autocomplete`,`list`),t.setAttribute(`autocapitalize`,`off`),t.setAttribute(`autocomplete`,`off`),t.setAttribute(`autocorrect`,`off`),t.setAttribute(`aria-hidden`,`true`),t.oninput=a(e=>{this.callbacks.search(e.target.value)},100),t.onkeydown=e=>{switch(e.key){case`ArrowUp`:case`ArrowDown`:return e.key===`ArrowDown`?this.highlight(`down`):this.highlight(`up`),!1;case`Tab`:return this.callbacks.close(),!0;case`Escape`:return this.callbacks.close(),!1;case` `:let t=this.content.list.querySelector(`.`+this.classes.getFirst(`highlighted`));return t?(t.click(),!1):!0;case`Enter`:let r=this.content.list.querySelector(`.`+this.classes.getFirst(`highlighted`));return r?(r.click(),!1):this.callbacks.addable?(n.click(),!1):!0}return!0},e.appendChild(t),this.callbacks.addable){this.addClasses(n,this.classes.addable);let t=document.createElementNS(`http://www.w3.org/2000/svg`,`svg`);t.setAttribute(`viewBox`,`0 0 100 100`);let i=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);i.setAttribute(`d`,this.classes.addablePath),t.appendChild(i),n.appendChild(t),n.onclick=e=>{if(e.preventDefault(),e.stopPropagation(),!this.callbacks.addable)return;let t=this.content.search.input.value.trim();if(t===``){this.content.search.input.focus();return}let n=e=>{let t=new c(e);if(this.callbacks.addOption(t),this.settings.isMultiple){let e=this.store.getSelected();e.push(t.id),this.callbacks.setSelected(e,!0)}else this.callbacks.setSelected([t.id],!0);this.callbacks.search(``),this.settings.closeOnSelect&&setTimeout(()=>{this.callbacks.close()},100)},r=this.callbacks.addable(t);r===!1||r==null||(r instanceof Promise?r.then(e=>{typeof e==`string`?n({text:e,value:e}):r instanceof Error?this.renderError(r.message):n(e)}):typeof r==`string`?n({text:r,value:r}):r instanceof Error?this.renderError(r.message):n(r))},e.appendChild(n),r.addable={main:n,svg:t,path:i}}return r}searchFocus(){this.content.search.input.focus({preventScroll:!0})}getOptions(e=!1,t=!1,n=!1){let r=`.`+this.classes.getFirst(`option`);return e&&(r+=`:not(.`+this.classes.getFirst(`placeholder`)+`)`),t&&(r+=`:not(.`+this.classes.getFirst(`disabled`)+`)`),n&&(r+=`:not(.`+this.classes.getFirst(`hide`)+`)`),Array.from(this.content.list.querySelectorAll(r))}highlight(e){let t=this.getOptions(!0,!0,!0);if(t.length===0)return;if(t.length===1&&!t[0].classList.contains(this.classes.getFirst(`highlighted`))){this.addClasses(t[0],this.classes.highlighted);return}let n=!1;for(let e of t)e.classList.contains(this.classes.getFirst(`highlighted`))&&(n=!0);if(!n){for(let e of t)if(e.classList.contains(this.classes.getFirst(`selected`))){this.addClasses(e,this.classes.highlighted);break}}for(let n=0;n=0?n-1:t.length-1];this.addClasses(a,this.classes.highlighted),this.ensureElementInView(this.content.list,a),a.id&&this.main.main.setAttribute(`aria-activedescendant`,a.id);let o=a.parentElement;if(o&&o.classList.contains(this.classes.getFirst(`close`))){let e=o.querySelector(`.`+this.classes.getFirst(`optgroupLabel`));e&&e.click()}return}let r=t[e===`down`?0:t.length-1];this.addClasses(r,this.classes.highlighted),r.id&&this.main.main.setAttribute(`aria-activedescendant`,r.id),this.ensureElementInView(this.content.list,r)}listDiv(){let e=document.createElement(`div`);this.addClasses(e,this.classes.list);let t=this.settings.id+`-list`;return e.id=t,e.dataset.id=t,e}renderError(e){this.content.list.innerHTML=``;let t=document.createElement(`div`);this.addClasses(t,this.classes.error),t.textContent=e,this.content.list.appendChild(t)}renderSearching(){this.content.list.innerHTML=``;let e=document.createElement(`div`);this.addClasses(e,this.classes.searching),e.textContent=this.settings.searchingText,this.content.list.appendChild(e),this.announce(this.settings.searchingText)}renderOptions(e){if(this.lastRenderedOptions=e.map(e=>e instanceof c?[e]:e.options.map(e=>new c(e))).flat(),this.content.list.innerHTML=``,e.length===0){let e=document.createElement(`div`);if(this.addClasses(e,this.classes.search),this.callbacks.addable){let t=this.settings.addableText.replace(`{value}`,this.content.search.input.value);e.innerHTML=t,this.announce(t)}else e.innerHTML=this.settings.searchText,this.announce(this.settings.searchText);this.content.list.appendChild(e);return}this.settings.allowDeselect&&!this.settings.isMultiple&&(this.store.filter(e=>e.placeholder,!1).length||this.store.addOption(new c({text:``,value:``,selected:!1,placeholder:!0}),!0));let t=document.createDocumentFragment();for(let n of e){if(n instanceof l){let e=document.createElement(`div`);this.addClasses(e,this.classes.optgroup);let r=document.createElement(`div`);this.addClasses(r,this.classes.optgroupLabel),e.appendChild(r);let i=document.createElement(`div`);this.addClasses(i,this.classes.optgroupLabelText),i.textContent=n.label,r.appendChild(i);let a=document.createElement(`div`);if(this.addClasses(a,this.classes.optgroupActions),r.appendChild(a),this.settings.isMultiple&&n.selectAll){let e=document.createElement(`div`);this.addClasses(e,this.classes.optgroupSelectAll);let t=!0;for(let e of n.options)if(!e.selected){t=!1;break}t&&this.addClasses(e,this.classes.selected);let r=document.createElement(`span`);r.textContent=n.selectAllText,e.appendChild(r);let i=document.createElementNS(`http://www.w3.org/2000/svg`,`svg`);i.setAttribute(`viewBox`,`0 0 100 100`),e.appendChild(i);let o=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);o.setAttribute(`d`,this.classes.optgroupSelectAllBox),i.appendChild(o);let s=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);s.setAttribute(`d`,this.classes.optgroupSelectAllCheck),i.appendChild(s),e.addEventListener(`click`,e=>{e.preventDefault(),e.stopPropagation();let r=this.store.getSelected();if(t){let e=r.filter(e=>{for(let t of n.options)if(e===t.id)return!1;return!0});this.callbacks.setSelected(e,!0);return}else{let e=n.options.map(e=>e.id).filter(e=>e!==void 0),t=r.concat(e);for(let e of n.options)e.id&&!this.store.getOptionByID(e.id)&&this.callbacks.addOption(new c(e));this.callbacks.setSelected(t,!0);return}}),a.appendChild(e)}if(n.closable!==`off`){let t=document.createElement(`div`);this.addClasses(t,this.classes.optgroupClosable);let i=document.createElementNS(`http://www.w3.org/2000/svg`,`svg`);i.setAttribute(`viewBox`,`0 0 100 100`),this.addClasses(i,this.classes.arrow),t.appendChild(i);let o=document.createElementNS(`http://www.w3.org/2000/svg`,`path`);i.appendChild(o),n.options.some(e=>e.selected)||this.content.search.input.value.trim()!==``?(this.addClasses(t,this.classes.mainOpen),o.setAttribute(`d`,this.classes.arrowOpen)):n.closable===`open`?(this.addClasses(e,this.classes.mainOpen),o.setAttribute(`d`,this.classes.arrowOpen)):n.closable===`close`&&(this.addClasses(e,this.classes.close),o.setAttribute(`d`,this.classes.arrowClose)),r.addEventListener(`click`,t=>{t.preventDefault(),t.stopPropagation(),e.classList.contains(this.classes.getFirst(`close`))?(this.removeClasses(e,this.classes.close),this.addClasses(e,this.classes.mainOpen),o.setAttribute(`d`,this.classes.arrowOpen)):(this.removeClasses(e,this.classes.mainOpen),this.addClasses(e,this.classes.close),o.setAttribute(`d`,this.classes.arrowClose))}),a.appendChild(t)}e.appendChild(r);for(let r of n.options)e.appendChild(this.option(new c(r))),t.appendChild(e)}n instanceof c&&t.appendChild(this.option(n))}this.content.list.appendChild(t),this.announce(this.settings.resultsText.replace(`{count}`,String(this.lastRenderedOptions.length)))}option(e){if(e.placeholder){let e=document.createElement(`div`);return this.addClasses(e,this.classes.option),this.addClasses(e,this.classes.hide),e}let t=document.createElement(`div`);return t.dataset.id=e.id,t.id=this.settings.id+`-`+e.id,this.addClasses(t,this.classes.option),t.setAttribute(`role`,`option`),e.class&&e.class.split(` `).forEach(e=>{t.classList.add(e)}),e.style&&(t.style.cssText=e.style),this.settings.searchHighlight&&this.content.search.input.value.trim()!==``?t.innerHTML=this.highlightText(e.html===``?e.text:e.html,this.content.search.input.value,this.classes.searchHighlighter):e.html===``?t.textContent=e.text:t.innerHTML=e.html,this.settings.showOptionTooltips&&t.textContent&&t.setAttribute(`title`,t.textContent),e.display||this.addClasses(t,this.classes.hide),e.disabled&&this.addClasses(t,this.classes.disabled),e.selected&&this.settings.hideSelected&&this.addClasses(t,this.classes.hide),e.selected?(this.addClasses(t,this.classes.selected),t.setAttribute(`aria-selected`,`true`),this.main.main.setAttribute(`aria-activedescendant`,t.id)):(this.removeClasses(t,this.classes.selected),t.setAttribute(`aria-selected`,`false`)),t.addEventListener(`click`,t=>{t.preventDefault(),t.stopPropagation();let n=this.store.getSelected(),r=t.currentTarget,i=String(r.dataset.id),a=t.ctrlKey||t.metaKey;if(e.disabled||!this.settings.isMultiple&&e.selected&&!this.settings.allowDeselect||e.selected&&e.mandatory||this.settings.isMultiple&&this.settings.maxSelected<=n.length&&!e.selected||this.settings.isMultiple&&this.settings.minSelected>=n.length&&e.selected&&!a)return;let o=!1,s=this.store.getSelectedOptions(),c=[];if(this.settings.isMultiple){let n=s.some(e=>e.id===i);if(t.shiftKey&&this.lastSelectedOption){let t=this.lastRenderedOptions,n=t.findIndex(e=>e.id===this.lastSelectedOption.id),r=t.findIndex(t=>t.id===e.id);if(n>=0&&r>=0){let e=Math.min(n,r),i=Math.max(n,r),a=t.slice(e,i+1).filter(e=>!s.find(t=>t.id===e.id));c=s.length+a.length<=this.settings.maxSelected?s.concat(a):s}else c=s}else c=n?s.filter(e=>e.id!==i):s.concat(e),this.lastSelectedOption=e}if(this.settings.isMultiple||(c=e.selected?[]:[e]),this.callbacks.beforeChange||(o=!0),this.callbacks.beforeChange&&(o=this.callbacks.beforeChange(c,s)!==!1),o){this.store.getOptionByID(i)||this.callbacks.addOption(e),this.callbacks.setSelected(c.map(e=>e.id),!1);let n=t.ctrlKey||t.metaKey||t.shiftKey;this.settings.closeOnSelect&&!(this.settings.isMultiple&&n)&&this.callbacks.close(),this.callbacks.afterChange&&this.callbacks.afterChange(c)}}),t}destroy(){this.closeAnimationTimeout&&=(clearTimeout(this.closeAnimationTimeout),null),this.main.main.remove(),this.content.main.remove()}highlightText(e,t,n){let r=t.trim();if(r===``)return e;let i=r.replace(/[.*+?^${}()|[\]\\]/g,`\\$&`),a=document.createElement(`div`);a.innerHTML=e;let o=e=>{if(e.nodeType===Node.TEXT_NODE){let t=e.textContent||``,r=RegExp(`(`+i+`)`,`i`);if(r.test(t)){let i=document.createElement(`span`);t.split(r).forEach((e,t)=>{if(e&&r.test(e)){let t=document.createElement(`mark`);t.className=n,t.textContent=e,i.appendChild(t)}else e&&i.appendChild(document.createTextNode(e))}),e.parentNode?.replaceChild(i,e)}}else e.nodeType===Node.ELEMENT_NODE&&Array.from(e.childNodes).forEach(e=>o(e))};return Array.from(a.childNodes).forEach(e=>o(e)),a.innerHTML}setContentDirection(e){let t=e===`above`,n=t?this.classes.dirAbove:this.classes.dirBelow,r=t?this.classes.dirBelow:this.classes.dirAbove;if(this.removeClasses(this.main.main,r),this.addClasses(this.main.main,n),this.removeClasses(this.content.main,r),this.addClasses(this.content.main,n),t){let e=this.main.main.offsetHeight,t=this.content.main.offsetHeight;this.content.main.style.margin=`-`+(e+t-1)+`px 0px 0px 0px`}else this.content.main.style.margin=`-1px 0px 0px 0px`}setContentPosition(){if(this.settings.contentPosition===`relative`)return;let e=this.main.main.getBoundingClientRect(),t,n;this.settings.contentPosition===`fixed`?(t=e.top+e.height,n=e.left):(t=e.top+window.scrollY+e.height,n=e.left+window.scrollX),this.content.main.style.top=t+`px`,this.content.main.style.left=n+`px`;let r=this.settings.contentWidth;this.content.main.style.width=``,this.content.main.style.minWidth=``,this.content.main.style.maxWidth=``,r?r.startsWith(`>`)?this.content.main.style.minWidth=r.slice(1):r.startsWith(`<`)?this.content.main.style.maxWidth=r.slice(1):this.content.main.style.width=r:this.content.main.style.width=e.width+`px`;let i=window.innerWidth-20,a=()=>{let e=this.content.main.getBoundingClientRect().right;if(e<=i)return;let t=e-i,n=parseFloat(this.content.main.style.left)||0;if(this.settings.contentPosition===`fixed`){let e=Math.max(20,n-t);this.content.main.style.left=e+`px`}else{let e=Math.max(window.scrollX+20,n-t);this.content.main.style.left=e+`px`}};requestAnimationFrame(()=>{a(),requestAnimationFrame(a)})}moveContentAbove(){this.setContentDirection(`above`),this.setContentPosition()}moveContentBelow(){this.setContentDirection(`below`),this.setContentPosition()}ensureElementInView(e,t){let n=e.scrollTop+e.offsetTop,r=n+e.clientHeight,i=t.offsetTop,a=i+t.clientHeight;ir&&(e.scrollTop+=a-r)}putContent(){let e=this.main.main.offsetHeight,t=this.main.main.getBoundingClientRect(),n=this.content.main.offsetHeight;return window.innerHeight-(t.top+e)<=n&&t.top>n?`up`:`down`}updateDeselectAll(){if(!this.store||!this.settings)return;let e=this.store.getSelectedOptions(),t=e&&e.length>0,n=this.settings.isMultiple,r=this.settings.allowDeselect,i=this.main.deselect.main,a=this.classes.hide;r&&!(n&&!t)?this.removeClasses(i,a):this.addClasses(i,a)}},f=class{select;onValueChange;onClassChange;onDisabledChange;onOptionsChange;onLabelClick;listen=!1;observer=null;isUpdating=!1;pendingOptionsChange=null;preventNativeSelect=null;preventNativeSelectMousedown=null;preventNativeSelectFocus=null;constructor(e){this.select=e,this.valueChange=this.valueChange.bind(this),this.select.addEventListener(`change`,this.valueChange,{passive:!0}),this.observer=new MutationObserver(this.observeCall.bind(this)),this.changeListen(!0)}enable(){this.select.disabled=!1}disable(){this.select.disabled=!0}hideUI(){this.select.tabIndex=-1,this.select.style.position=`absolute`,this.select.style.width=`1px`,this.select.style.height=`1px`,this.select.style.opacity=`0`,this.select.style.overflow=`hidden`,this.select.style.pointerEvents=`none`,this.select.style.margin=`0`,this.select.style.padding=`0`,this.select.style.borderWidth=`0`,this.select.style.clip=`rect(0 0 0 0)`,this.select.setAttribute(`aria-hidden`,`true`),this.preventNativeSelect||(this.preventNativeSelect=e=>{e.preventDefault(),e.stopPropagation(),e.stopImmediatePropagation()},this.preventNativeSelectMousedown=e=>{e.preventDefault(),e.stopPropagation(),e.stopImmediatePropagation()},this.preventNativeSelectFocus=e=>{e.preventDefault(),e.stopPropagation(),e.stopImmediatePropagation()},this.select.addEventListener(`click`,this.preventNativeSelect,{capture:!0,passive:!1}),this.select.addEventListener(`mousedown`,this.preventNativeSelectMousedown,{capture:!0,passive:!1}),this.select.addEventListener(`focus`,this.preventNativeSelectFocus,{capture:!0,passive:!1}))}showUI(){this.select.removeAttribute(`tabindex`),this.select.style.position=``,this.select.style.width=``,this.select.style.height=``,this.select.style.opacity=``,this.select.style.overflow=``,this.select.style.pointerEvents=``,this.select.style.margin=``,this.select.style.padding=``,this.select.style.borderWidth=``,this.select.style.clip=``,this.select.removeAttribute(`aria-hidden`),this.preventNativeSelect&&=(this.select.removeEventListener(`click`,this.preventNativeSelect,{capture:!0}),null),this.preventNativeSelectMousedown&&=(this.select.removeEventListener(`mousedown`,this.preventNativeSelectMousedown,{capture:!0}),null),this.preventNativeSelectFocus&&=(this.select.removeEventListener(`focus`,this.preventNativeSelectFocus,{capture:!0}),null)}changeListen(e){this.listen=e,e&&this.observer&&this.observer.observe(this.select,{subtree:!0,childList:!0,attributes:!0}),e||this.observer&&this.observer.disconnect()}valueChange(e){return this.listen&&this.onValueChange&&this.onValueChange(this.getSelectedOptions()),!0}observeCall(e){if(!this.listen)return;let t=!1,n=!1,r=!1,i=!1;for(let a of e){if(a.target===this.select&&(a.attributeName===`disabled`&&(n=!0),a.attributeName===`class`&&(t=!0),a.type===`childList`)){for(let e of Array.from(a.addedNodes))if(e.nodeName===`OPTION`&&e.value===this.select.value){i=!0;break}r=!0}(a.target.nodeName===`OPTGROUP`||a.target.nodeName===`OPTION`)&&(r=!0)}if(t&&this.onClassChange&&this.onClassChange(this.select.className.split(` `)),n&&this.onDisabledChange&&(this.changeListen(!1),this.onDisabledChange(this.select.disabled),this.changeListen(!0)),r&&this.onOptionsChange){if(this.isUpdating){if(this.select.options.length>0){let e=this.getData();e.length>0&&(this.pendingOptionsChange=e)}i&&this.select.dispatchEvent(new Event(`change`));return}this.changeListen(!1),this.onOptionsChange(this.getData()),this.changeListen(!0)}i&&this.select.dispatchEvent(new Event(`change`))}getData(){let e=[],t=this.select.childNodes;for(let n of t)n.nodeName===`OPTGROUP`&&e.push(this.getDataFromOptgroup(n)),n.nodeName===`OPTION`&&e.push(this.getDataFromOption(n));return e}getDataFromOptgroup(e){let t={id:e.id,label:e.label,selectAll:e.dataset?e.dataset.selectall===`true`:!1,selectAllText:e.dataset?e.dataset.selectalltext:`Select all`,closable:e.dataset?e.dataset.closable:`off`,options:[]},n=e.childNodes;for(let e of n)e.nodeName===`OPTION`&&t.options.push(this.getDataFromOption(e));return t}getDataFromOption(e){return{id:e.id,value:e.value,text:e.text,html:e.dataset&&e.dataset.html?e.dataset.html:``,defaultSelected:e.defaultSelected,selected:e.selected,display:e.style.display!==`none`,disabled:e.disabled,mandatory:e.dataset?e.dataset.mandatory===`true`:!1,placeholder:e.dataset.placeholder===`true`,class:e.className,style:e.style.cssText,data:e.dataset}}getSelectedOptions(){let e=[],t=this.select.childNodes;for(let n of t){if(n.nodeName===`OPTGROUP`){let t=n.childNodes;for(let n of t)if(n.nodeName===`OPTION`){let t=n;t.selected&&e.push(this.getDataFromOption(t))}}if(n.nodeName===`OPTION`){let t=n;t.selected&&e.push(this.getDataFromOption(t))}}return e}getSelectedValues(){return this.getSelectedOptions().map(e=>e.value)}setSelected(e){this.changeListen(!1);let t=this.select.childNodes;for(let n of t){if(n.nodeName===`OPTGROUP`){let t=n.childNodes;for(let n of t)if(n.nodeName===`OPTION`){let t=n;t.selected=e.includes(t.id)}}if(n.nodeName===`OPTION`){let t=n;t.selected=e.includes(t.id)}}this.changeListen(!0)}setSelectedByValue(e){this.changeListen(!1);let t=this.select.childNodes;for(let n of t){if(n.nodeName===`OPTGROUP`){let t=n.childNodes;for(let n of t)if(n.nodeName===`OPTION`){let t=n;t.selected=e.includes(t.value)}}if(n.nodeName===`OPTION`){let t=n;t.selected=e.includes(t.value)}}this.changeListen(!0)}updateSelect(e,t,n){this.changeListen(!1),e&&(this.select.dataset.id=e),t&&(this.select.style.cssText=t),n&&(this.select.className=``,n.forEach(e=>{e.trim()!==``&&this.select.classList.add(e.trim())})),this.changeListen(!0)}updateOptions(e){if(!(!e||e.length===0)){this.isUpdating=!0,this.pendingOptionsChange=null,this.changeListen(!1),this.select.innerHTML=``;for(let t of e)t instanceof l&&this.select.appendChild(this.createOptgroup(t)),t instanceof c&&this.select.appendChild(this.createOption(t));if(this.select.dispatchEvent(new Event(`change`,{bubbles:!0})),this.changeListen(!0),this.isUpdating=!1,this.pendingOptionsChange!==null){let e=this.pendingOptionsChange;e.length>0&&this.onOptionsChange?(this.pendingOptionsChange=null,this.changeListen(!1),this.onOptionsChange(e),this.changeListen(!0)):this.pendingOptionsChange=null}}}createOptgroup(e){let t=document.createElement(`optgroup`);if(t.id=e.id,t.label=e.label,e.selectAll&&(t.dataset.selectAll=`true`),e.closable!==`off`&&(t.dataset.closable=e.closable),e.options)for(let n of e.options)t.appendChild(this.createOption(n));return t}createOption(e){let t=document.createElement(`option`);return t.id=e.id,t.value=e.value,t.textContent=e.text,e.html!==``&&t.setAttribute(`data-html`,e.html),t.defaultSelected=e.defaultSelected,t.selected=e.selected,e.disabled&&(t.disabled=!0),e.display||(t.style.display=`none`),e.placeholder&&t.setAttribute(`data-placeholder`,`true`),e.mandatory&&t.setAttribute(`data-mandatory`,`true`),e.class&&e.class.split(` `).forEach(e=>{t.classList.add(e)}),e.data&&typeof e.data==`object`&&Object.keys(e.data).forEach(n=>{t.setAttribute(`data-`+s(n),e.data[n])}),t}setupLabelHandlers(){let e=[],t=this.select.id;t&&document.querySelectorAll(`label[for="${t}"]`).forEach(t=>e.push(t));let n=this.select.parentElement;for(;n&&n!==document.body;){if(n.tagName===`LABEL`){e.push(n);break}n=n.parentElement}Array.from(new Set(e)).forEach(e=>{if(e.__slimSelectLabelHandler)return;let t=e=>{let t=e.target,n=i(t,this.select.dataset.id);e.preventDefault(),!n&&this.onLabelClick&&this.onLabelClick()};e.__slimSelectLabelHandler=t,e.addEventListener(`click`,t,{capture:!0,passive:!1})})}removeLabelHandlers(){let e=[],t=this.select.id;t&&document.querySelectorAll(`label[for="${t}"]`).forEach(t=>e.push(t));let n=this.select.parentElement;for(;n&&n!==document.body;){if(n.tagName===`LABEL`){e.push(n);break}n=n.parentElement}Array.from(new Set(e)).forEach(e=>{let t=e.__slimSelectLabelHandler;t&&(e.removeEventListener(`click`,t,{capture:!0}),delete e.__slimSelectLabelHandler)})}destroy(){this.changeListen(!1),this.select.removeEventListener(`change`,this.valueChange),this.preventNativeSelect&&=(this.select.removeEventListener(`click`,this.preventNativeSelect,{capture:!0}),null),this.preventNativeSelectMousedown&&=(this.select.removeEventListener(`mousedown`,this.preventNativeSelectMousedown,{capture:!0}),null),this.preventNativeSelectFocus&&=(this.select.removeEventListener(`focus`,this.preventNativeSelectFocus,{capture:!0}),null),this.observer&&=(this.observer.disconnect(),null),this.removeLabelHandlers(),delete this.select.dataset.id,this.showUI()}},p=class{id=``;style=``;class=[];isMultiple=!1;isOpen=!1;isFullOpen=!1;intervalMove=null;disabled;alwaysOpen;showSearch;focusSearch;keepSearch;ariaLabel;searchPlaceholder;searchText;searchingText;resultsText;deselectText;removeText;searchHighlight;closeOnSelect;contentLocation;contentPosition;contentWidth;openPosition;placeholderText;allowDeselect;hideSelected;multiString;keepOrder;showOptionTooltips;minSelected;maxSelected;timeoutDelay;maxValuesShown;maxValuesMessage;addableText;constructor(e){e||={},this.id=`ss-`+r(),this.style=e.style||``,this.class=e.class||[],this.disabled=e.disabled===void 0?!1:e.disabled,this.alwaysOpen=e.alwaysOpen===void 0?!1:e.alwaysOpen,this.showSearch=e.showSearch===void 0?!0:e.showSearch,this.focusSearch=e.focusSearch===void 0?!0:e.focusSearch,this.keepSearch=e.keepSearch===void 0?!1:e.keepSearch,this.ariaLabel=e.ariaLabel||`Combobox`,this.searchPlaceholder=e.searchPlaceholder||`Search...`,this.searchText=e.searchText||`No Results`,this.searchingText=e.searchingText||`Searching...`,this.resultsText=e.resultsText||`{count} results available`,this.deselectText=e.deselectText||`Clear`,this.removeText=e.removeText||`Remove`,this.searchHighlight=e.searchHighlight===void 0?!1:e.searchHighlight,this.closeOnSelect=e.closeOnSelect===void 0?!0:e.closeOnSelect,this.contentLocation=e.contentLocation||document.body,this.contentPosition=e.contentPosition||`absolute`,this.contentWidth=e.contentWidth||``,this.openPosition=e.openPosition||`auto`,this.placeholderText=e.placeholderText===void 0?`Select Value`:e.placeholderText,this.allowDeselect=e.allowDeselect===void 0?!1:e.allowDeselect,this.hideSelected=e.hideSelected===void 0?!1:e.hideSelected,this.multiString=e.multiString===void 0?!1:e.multiString,this.keepOrder=e.keepOrder===void 0?!1:e.keepOrder,this.showOptionTooltips=e.showOptionTooltips===void 0?!1:e.showOptionTooltips,this.minSelected=e.minSelected||0,this.maxSelected=e.maxSelected||1e3,this.timeoutDelay=e.timeoutDelay||200,this.maxValuesShown=e.maxValuesShown||20,this.maxValuesMessage=e.maxValuesMessage||`{number} selected`,this.addableText=e.addableText||`Press "Enter" to add {value}`}},m=t({Optgroup:()=>l,Option:()=>c,Settings:()=>p,default:()=>h}),h=class{selectEl;settings;cssClasses;select;store;render;openTimeout=null;closeTimeout=null;events={search:void 0,searchFilter:(e,t)=>e.text.toLowerCase().indexOf(t.toLowerCase())!==-1,addable:void 0,beforeChange:void 0,afterChange:void 0,beforeOpen:void 0,afterOpen:void 0,beforeClose:void 0,afterClose:void 0};constructor(e){if(this.selectEl=typeof e.select==`string`?document.querySelector(e.select):e.select,!this.selectEl){e.events&&e.events.error&&e.events.error(Error(`Could not find select element`));return}if(this.selectEl.tagName!==`SELECT`){e.events&&e.events.error&&e.events.error(Error(`Element isnt of type select`));return}this.selectEl.dataset.ssid&&this.destroy(),this.settings=new p(e.settings),this.cssClasses=new n(e.cssClasses);let t=[`beforeOpen`,`afterOpen`,`beforeClose`,`afterClose`];for(let n in e.events)e.events.hasOwnProperty(n)&&(t.indexOf(n)===-1?this.events[n]=e.events[n]:this.events[n]=a(e.events[n],100));this.settings.disabled=e.settings?.disabled?e.settings.disabled:this.selectEl.disabled,this.settings.isMultiple=this.selectEl.multiple,this.settings.style=this.selectEl.style.cssText,this.settings.class=this.selectEl.className.split(` `),this.select=new f(this.selectEl),this.selectEl.id||(this.selectEl.id=this.settings.id),this.select.updateSelect(this.settings.id,this.settings.style,this.settings.class),this.select.hideUI(),this.select.onValueChange=e=>{this.setSelected(e.map(e=>e.id))},this.select.onClassChange=e=>{this.settings.class=e,this.render.updateClassStyles()},this.select.onDisabledChange=e=>{e?this.disable():this.enable()},this.select.onOptionsChange=e=>{this.setData(e||[])},this.select.onLabelClick=()=>{this.settings.disabled||(this.settings.isOpen?this.close():this.open())};let r=e.data?e.data:this.select.getData();this.store=new u(this.settings.isMultiple?`multiple`:`single`,r),e.data&&this.select.updateOptions(this.store.getData());let i={open:this.open.bind(this),close:this.close.bind(this),addable:this.events.addable?this.events.addable:void 0,setSelected:this.setSelected.bind(this),addOption:this.addOption.bind(this),search:this.search.bind(this),beforeChange:this.events.beforeChange,afterChange:this.events.afterChange};this.render=new d(this.settings,this.cssClasses,this.store,i),this.render.renderValues(),this.render.renderOptions(this.store.getData());let o=this.selectEl.getAttribute(`aria-label`),s=this.selectEl.getAttribute(`aria-labelledby`);if(o)this.render.main.main.setAttribute(`aria-label`,o);else if(s)this.render.main.main.removeAttribute(`aria-label`),this.render.main.main.setAttribute(`aria-labelledby`,s);else if(this.selectEl.labels&&this.selectEl.labels.length>0){let e=Array.from(this.selectEl.labels).map((e,t)=>(e.id||=`${this.settings.id}-label-${t}`,e.id));this.render.main.main.removeAttribute(`aria-label`),this.render.main.main.setAttribute(`aria-labelledby`,e.join(` `))}this.selectEl.parentNode&&this.selectEl.parentNode.insertBefore(this.render.main.main,this.selectEl.nextSibling),window.addEventListener(`resize`,this.windowResize,!1),this.settings.openPosition===`auto`&&window.addEventListener(`scroll`,this.windowScroll,!1),document.addEventListener(`visibilitychange`,this.windowVisibilityChange),this.settings.disabled&&this.disable(),this.settings.alwaysOpen&&this.open(),this.select.setupLabelHandlers(),this.selectEl.slim=this}enable(){this.settings.disabled=!1,this.select.enable(),this.render.enable()}disable(){this.settings.disabled=!0,this.select.disable(),this.render.disable()}getData(){return this.store.getData()}setData(e){let t=this.store.getSelected(),n=this.store.validateDataArray(e);if(n){this.events.error&&this.events.error(n);return}this.store.setData(e);let r=this.store.getData();this.select.updateOptions(r),this.render.renderValues(),this.render.renderOptions(r),this.events.afterChange&&!o(t,this.store.getSelected())&&this.events.afterChange(this.store.getSelectedOptions())}getSelected(){let e=this.store.getSelectedOptions();return this.settings.keepOrder&&(e=this.store.selectedOrderOptions(e)),e.map(e=>e.value)}setSelected(e,t=!0){let n=this.store.getSelected(),r=this.store.getDataOptions();e=Array.isArray(e)?e:[e];let i=[];for(let t of e){if(r.find(e=>e.id==t)){i.push(t);continue}for(let e of r.filter(e=>e.value==t))i.push(e.id)}this.store.setSelectedBy(`id`,i);let a=this.store.getData();this.select.updateOptions(a),this.render.renderValues(),this.render.content.search.input.value===``?this.render.renderOptions(a):this.search(this.render.content.search.input.value),t&&this.events.afterChange&&!o(n,this.store.getSelected())&&this.events.afterChange(this.store.getSelectedOptions())}addOption(e){let t=this.store.getSelected();this.store.getDataOptions().some(t=>t.value===(e.value??e.text))||this.store.addOption(e);let n=this.store.getData();this.select.updateOptions(n),this.render.renderValues(),this.render.renderOptions(n),this.events.afterChange&&!o(t,this.store.getSelected())&&this.events.afterChange(this.store.getSelectedOptions())}open(){this.settings.disabled||this.settings.isOpen||(this.closeTimeout&&=(clearTimeout(this.closeTimeout),null),this.events.beforeOpen&&this.events.beforeOpen(),this.render.open(),this.settings.showSearch&&this.settings.focusSearch&&this.render.searchFocus(),this.settings.isOpen=!0,this.openTimeout=setTimeout(()=>{this.events.afterOpen&&this.events.afterOpen(),this.settings.isOpen&&(this.settings.isFullOpen=!0),document.addEventListener(`click`,this.documentClick)},this.settings.timeoutDelay),this.settings.contentPosition===`absolute`&&(this.settings.intervalMove&&clearInterval(this.settings.intervalMove),this.settings.intervalMove=setInterval(this.render.moveContent.bind(this.render),500)))}close(e=null){!this.settings.isOpen||this.settings.alwaysOpen||(this.openTimeout&&=(clearTimeout(this.openTimeout),null),this.events.beforeClose&&this.events.beforeClose(),this.render.close(),!this.settings.keepSearch&&this.render.content.search.input.value!==``&&this.search(``),this.render.mainFocus(e),this.settings.isOpen=!1,this.settings.isFullOpen=!1,this.closeTimeout=setTimeout(()=>{this.events.afterClose&&this.events.afterClose(),document.removeEventListener(`click`,this.documentClick)},this.settings.timeoutDelay),this.settings.intervalMove&&clearInterval(this.settings.intervalMove))}search(e){if(this.render.content.search.input.value!==e&&(this.render.content.search.input.value=e),e===``){this.render.renderOptions(this.store.getData());return}if(!this.events.search){let t=e===``?this.store.getData():this.store.search(e,this.events.searchFilter);this.render.renderOptions(t);return}this.render.renderSearching();let t=this.events.search(e,this.store.getSelectedOptions());if(t instanceof Promise){t.then(e=>{this.store.setData(e,!0),this.select.updateOptions(this.store.getData()),this.render.renderOptions(this.store.getData())}).catch(e=>{this.render.renderError(typeof e==`string`?e:e.message)});return}else Array.isArray(t)?(this.store.setData(t,!0),this.select.updateOptions(this.store.getData()),this.render.renderOptions(this.store.getData())):this.render.renderError(`Search event must return a promise or an array of data`)}destroy(){this.openTimeout&&=(clearTimeout(this.openTimeout),null),this.closeTimeout&&=(clearTimeout(this.closeTimeout),null),this.settings.intervalMove&&(clearInterval(this.settings.intervalMove),this.settings.intervalMove=null),document.removeEventListener(`click`,this.documentClick),window.removeEventListener(`resize`,this.windowResize,!1),this.settings.openPosition===`auto`&&window.removeEventListener(`scroll`,this.windowScroll,!1),document.removeEventListener(`visibilitychange`,this.windowVisibilityChange),this.store.setData([]),this.render.destroy(),this.select.destroy()}windowResize=a(()=>{!this.settings.isOpen&&!this.settings.isFullOpen||this.render.moveContent()});windowScroll=a(()=>{!this.settings.isOpen&&!this.settings.isFullOpen||this.render.moveContent()});documentClick=e=>{this.settings.isOpen&&e.target&&!i(e.target,this.settings.id)&&this.close(e.type)};windowVisibilityChange=()=>{document.hidden&&this.close()}};return Object.assign(h,m),h}); +//# sourceMappingURL=slimselect.js.map \ No newline at end of file diff --git a/html/index.html b/html/index.html index f1b2463..6ca9aa6 100644 --- a/html/index.html +++ b/html/index.html @@ -7,6 +7,10 @@ YtDownloader + + + + @@ -70,8 +74,9 @@ - - + + @@ -119,8 +124,11 @@

Video

- +
+ +
+
@@ -128,8 +136,13 @@

Audio

- + + +
+ +
+
@@ -146,9 +159,13 @@
- -
+ +
+ +
+ +

+ + + \ No newline at end of file diff --git a/src/renderer.js b/src/renderer.js index 0d91ff9..8b6d6e2 100644 --- a/src/renderer.js +++ b/src/renderer.js @@ -201,7 +201,7 @@ class YtDownloaderApp { } const savedPath = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.DOWNLOAD_PATH + CONSTANTS.LOCAL_STORAGE_KEYS.DOWNLOAD_PATH, ); if (savedPath) { try { @@ -209,12 +209,12 @@ class YtDownloaderApp { this.state.downloadDir = savedPath; } catch { console.warn( - `Cannot write to saved path "${savedPath}". Falling back to default.` + `Cannot write to saved path "${savedPath}". Falling back to default.`, ); this.state.downloadDir = defaultDownloadDir; localStorage.setItem( CONSTANTS.LOCAL_STORAGE_KEYS.DOWNLOAD_PATH, - defaultDownloadDir + defaultDownloadDir, ); } } else { @@ -272,7 +272,7 @@ class YtDownloaderApp { window.i18n.translatePage(); resolve(); }, - {once: true} + {once: true}, ); }); } @@ -296,7 +296,7 @@ class YtDownloaderApp { executablePath = process.env.YTDOWNLOADER_YTDLP_PATH; } else { throw new Error( - "YTDOWNLOADER_YTDLP_PATH is set, but no file exists there." + "YTDOWNLOADER_YTDLP_PATH is set, but no file exists there.", ); } } @@ -325,7 +325,7 @@ class YtDownloaderApp { executablePath = execSync("which yt-dlp").toString().trim(); } catch { throw new Error( - "No yt-dlp found in PATH on FreeBSD. Please install it." + "No yt-dlp found in PATH on FreeBSD. Please install it.", ); } } @@ -336,7 +336,7 @@ class YtDownloaderApp { // app-managed binary so YouTube fixes arrive fastest. const source = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_SOURCE + CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_SOURCE, ) || CONSTANTS.YT_DLP_SOURCE.NIGHTLY; // "system": use yt-dlp from PATH (apt/pip/etc.). Falls back to the @@ -366,7 +366,7 @@ class YtDownloaderApp { // binary. A stored path is reused; otherwise it is downloaded. if (!executablePath) { const storedPath = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_PATH + CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_PATH, ); if ( @@ -378,16 +378,15 @@ class YtDownloaderApp { } // Download if missing else { - executablePath = await this.ensureYtDlpBinary( - defaultYtDlpPath - ); + executablePath = + await this.ensureYtDlpBinary(defaultYtDlpPath); } } } localStorage.setItem( CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_PATH, - executablePath + executablePath, ); // Auto update @@ -411,10 +410,10 @@ class YtDownloaderApp { const brewUpdate = spawn(brewExec, ["upgrade", "yt-dlp"]); brewUpdate.on("error", (err) => - console.error("Failed to run 'brew upgrade yt-dlp':", err) + console.error("Failed to run 'brew upgrade yt-dlp':", err), ); brewUpdate.stdout.on("data", (data) => - console.log("yt-dlp brew update:", data.toString()) + console.log("yt-dlp brew update:", data.toString()), ); } else { // Only self-update binaries we manage in ~/.ytDownloader. @@ -423,7 +422,7 @@ class YtDownloaderApp { const hiddenDir = join(homedir(), ".ytDownloader"); if (!executablePath.startsWith(hiddenDir)) { console.log( - "Using system yt-dlp; skipping self-update (-U)." + "Using system yt-dlp; skipping self-update (-U).", ); return; } @@ -438,8 +437,8 @@ class YtDownloaderApp { updateProc.on("error", (err) => console.error( "Failed to run background yt-dlp update:", - err - ) + err, + ), ); updateProc.stdout.on("data", (data) => { @@ -479,7 +478,7 @@ class YtDownloaderApp { $(CONSTANTS.DOM_IDS.POPUP_BOX).style.display = "block"; $(CONSTANTS.DOM_IDS.POPUP_SVG).style.display = "inline"; document.querySelector("#popupBox p").textContent = i18n.__( - "downloadingNecessaryFilesWait" + "downloadingNecessaryFilesWait", ); try { @@ -489,18 +488,18 @@ class YtDownloaderApp { undefined, (progress, _d, _t) => { $( - CONSTANTS.DOM_IDS.YTDLP_DOWNLOAD_PROGRESS + CONSTANTS.DOM_IDS.YTDLP_DOWNLOAD_PROGRESS, ).textContent = i18n.__("progress") + `: ${(progress * 100).toFixed(2)}%`; - } + }, ); $(CONSTANTS.DOM_IDS.POPUP_BOX).style.display = "none"; localStorage.setItem( CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_PATH, - defaultYtDlpPath + defaultYtDlpPath, ); return defaultYtDlpPath; @@ -510,7 +509,7 @@ class YtDownloaderApp { console.error("Failed to download yt-dlp:", downloadError); document.querySelector("#popupBox p").textContent = i18n.__( - "errorFailedFileDownload" + "errorFailedFileDownload", ); $(CONSTANTS.DOM_IDS.POPUP_SVG).style.display = "none"; @@ -539,7 +538,7 @@ class YtDownloaderApp { return process.env.YTDOWNLOADER_FFMPEG_PATH; } throw new Error( - "YTDOWNLOADER_FFMPEG_PATH is set, but no file exists there." + "YTDOWNLOADER_FFMPEG_PATH is set, but no file exists there.", ); } @@ -549,7 +548,7 @@ class YtDownloaderApp { return execSync("which ffmpeg").toString().trim(); } catch { throw new Error( - "No ffmpeg found in PATH on FreeBSD. App may not work correctly." + "No ffmpeg found in PATH on FreeBSD. App may not work correctly.", ); } } @@ -647,35 +646,37 @@ class YtDownloaderApp { prefs.videoQuality = Number( localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_VIDEO_QUALITY - ) + CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_VIDEO_QUALITY, + ), ) || 1080; prefs.audioQuality = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_AUDIO_QUALITY + CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_AUDIO_QUALITY, ) || ""; prefs.videoCodec = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_VIDEO_CODEC + CONSTANTS.LOCAL_STORAGE_KEYS.PREFERRED_VIDEO_CODEC, ) || "avc1"; prefs.showMoreFormats = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.SHOW_MORE_FORMATS + CONSTANTS.LOCAL_STORAGE_KEYS.SHOW_MORE_FORMATS, ) === "true"; prefs.proxy = localStorage.getItem(CONSTANTS.LOCAL_STORAGE_KEYS.PROXY) || ""; prefs.browserForCookies = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.BROWSER_COOKIES + CONSTANTS.LOCAL_STORAGE_KEYS.BROWSER_COOKIES, ) || ""; prefs.customYtDlpArgs = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_CUSTOM_ARGS + CONSTANTS.LOCAL_STORAGE_KEYS.YT_DLP_CUSTOM_ARGS, ) || ""; - prefs.configPath = localStorage.getItem(CONSTANTS.LOCAL_STORAGE_KEYS.CONFIG_PATH) || ""; + prefs.configPath = + localStorage.getItem(CONSTANTS.LOCAL_STORAGE_KEYS.CONFIG_PATH) || + ""; const maxDownloads = Number( - localStorage.getItem(CONSTANTS.LOCAL_STORAGE_KEYS.MAX_DOWNLOADS) + localStorage.getItem(CONSTANTS.LOCAL_STORAGE_KEYS.MAX_DOWNLOADS), ); this.state.maxActiveDownloads = maxDownloads >= 1 ? maxDownloads : 5; @@ -683,7 +684,7 @@ class YtDownloaderApp { $(CONSTANTS.DOM_IDS.CUSTOM_ARGS_INPUT).value = prefs.customYtDlpArgs; const downloadDir = localStorage.getItem( - CONSTANTS.LOCAL_STORAGE_KEYS.DOWNLOAD_PATH + CONSTANTS.LOCAL_STORAGE_KEYS.DOWNLOAD_PATH, ); if (downloadDir) { @@ -697,7 +698,7 @@ class YtDownloaderApp { */ _addEventListeners() { $(CONSTANTS.DOM_IDS.PASTE_URL_BTN).addEventListener("click", () => - this.pasteAndGetInfo() + this.pasteAndGetInfo(), ); document.addEventListener("keydown", (event) => { if ( @@ -712,7 +713,7 @@ class YtDownloaderApp { setTimeout(() => { $(CONSTANTS.DOM_IDS.PASTE_URL_BTN).classList.remove( - "active" + "active", ); }, 150); @@ -722,24 +723,24 @@ class YtDownloaderApp { // Download buttons $(CONSTANTS.DOM_IDS.VIDEO_DOWNLOAD_BTN).addEventListener("click", () => - this.handleDownloadRequest("video") + this.handleDownloadRequest("video"), ); $(CONSTANTS.DOM_IDS.AUDIO_DOWNLOAD_BTN).addEventListener("click", () => - this.handleDownloadRequest("audio") + this.handleDownloadRequest("audio"), ); $(CONSTANTS.DOM_IDS.EXTRACT_BTN).addEventListener("click", () => - this.handleDownloadRequest("extract") + this.handleDownloadRequest("extract"), ); // UI controls $(CONSTANTS.DOM_IDS.CLOSE_HIDDEN_BTN).addEventListener("click", () => - this._hideInfoPanel() + this._hideInfoPanel(), ); $(CONSTANTS.DOM_IDS.SELECT_LOCATION_BTN).addEventListener("click", () => - ipcRenderer.send("select-location-main", "") + ipcRenderer.send("select-location-main", ""), ); $(CONSTANTS.DOM_IDS.CLEAR_BTN).addEventListener("click", () => - this._clearAllDownloaded() + this._clearAllDownloaded(), ); // Error details @@ -813,19 +814,19 @@ class YtDownloaderApp { const maxSlider = $(CONSTANTS.DOM_IDS.MAX_SLIDER); minSlider.addEventListener("input", () => - this._updateSliderUI(minSlider) + this._updateSliderUI(minSlider), ); maxSlider.addEventListener("input", () => - this._updateSliderUI(maxSlider) + this._updateSliderUI(maxSlider), ); $(CONSTANTS.DOM_IDS.START_TIME).addEventListener( "change", - this._handleTimeInputChange + this._handleTimeInputChange, ); $(CONSTANTS.DOM_IDS.END_TIME).addEventListener( "change", - this._handleTimeInputChange + this._handleTimeInputChange, ); this._updateSliderUI(null); @@ -899,7 +900,7 @@ class YtDownloaderApp { uiSnapshot: { videoFormat: $(CONSTANTS.DOM_IDS.VIDEO_FORMAT_SELECT).value, audioForVideoFormat: $( - CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT + CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT, ).value, audioFormat: $(CONSTANTS.DOM_IDS.AUDIO_FORMAT_SELECT).value, extractFormat: $(CONSTANTS.DOM_IDS.EXTRACT_SELECTION).value, @@ -944,9 +945,9 @@ class YtDownloaderApp { const process = this.state.ytDlp.exec(args, {shell: true}); console.log( - "Spawned yt-dlp with args:", - process.ytDlpProcess.spawnargs.join(" ") - ); + "Spawned yt-dlp with args:", + process.ytDlpProcess.spawnargs.join(" "), + ); let stdout = ""; let stderr = ""; @@ -964,15 +965,15 @@ class YtDownloaderApp { reject( new Error( "Failed to parse yt-dlp JSON output: " + - (stderr || e.message) - ) + (stderr || e.message), + ), ); } } else { reject( new Error( - stderr || `yt-dlp exited with a non-zero code.` - ) + stderr || `yt-dlp exited with a non-zero code.`, + ), ); } }); @@ -1005,7 +1006,7 @@ class YtDownloaderApp { console.log( "Spawned yt-dlp with args:", - downloadProcess.ytDlpProcess.spawnargs.join(" ") + downloadProcess.ytDlpProcess.spawnargs.join(" "), ); // Attach event listeners @@ -1026,7 +1027,7 @@ class YtDownloaderApp { randomId, finalFilename, finalExt, - job.thumbnail + job.thumbnail, ); }) .once("error", (error) => { @@ -1051,7 +1052,7 @@ class YtDownloaderApp { job.thumbnail || "../assets/images/thumb.png" }" alt="thumbnail" class="itemIcon" crossorigin="anonymous"> ${i18n.__( - job.type === "video" ? "video" : "audio" + job.type === "video" ? "video" : "audio", )}
@@ -1061,7 +1062,7 @@ class YtDownloaderApp {
`; $(CONSTANTS.DOM_IDS.DOWNLOAD_LIST).insertAdjacentHTML( "beforeend", - itemHTML + itemHTML, ); } @@ -1146,7 +1147,7 @@ class YtDownloaderApp { const outputPath = `"${join( this.state.downloadDir, - `${finalFilename}.${ext}` + `${finalFilename}.${ext}`, )}"`; const baseArgs = [ @@ -1198,7 +1199,7 @@ class YtDownloaderApp { if (rangeOption) downloadArgs.push(rangeOption, rangeCmd); const customArgsString = $( - CONSTANTS.DOM_IDS.CUSTOM_ARGS_INPUT + CONSTANTS.DOM_IDS.CUSTOM_ARGS_INPUT, ).value.trim(); if (customArgsString) { const customArgs = customArgsString.split(/\s+/); @@ -1225,7 +1226,7 @@ class YtDownloaderApp { // code is null if aborted, so only show error if it's a real exit code this._handleDownloadError( new Error(`Download process exited with code ${code}.`), - randomId + randomId, ); } @@ -1247,7 +1248,7 @@ class YtDownloaderApp { console.log(`Download ${randomId} was aborted.`); this.state.currentDownloads = Math.max( 0, - this.state.currentDownloads - 1 + this.state.currentDownloads - 1, ); this.state.downloadControllers.delete(randomId); this._processQueue(); @@ -1309,9 +1310,8 @@ class YtDownloaderApp { $(CONSTANTS.DOM_IDS.VIDEO_FORMAT_SELECT).innerHTML = ""; $(CONSTANTS.DOM_IDS.AUDIO_FORMAT_SELECT).innerHTML = ""; const noAudioTxt = i18n.__("noAudio"); - $( - CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT - ).innerHTML = ``; + $(CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT).innerHTML = + ``; } /** @@ -1319,48 +1319,18 @@ class YtDownloaderApp { * @param {Array} formats The formats array from yt-dlp metadata. */ _populateFormatSelectors(formats) { - const videoSelect = $(CONSTANTS.DOM_IDS.VIDEO_FORMAT_SELECT); - const audioSelect = $(CONSTANTS.DOM_IDS.AUDIO_FORMAT_SELECT); - const audioForVideoSelect = $( - CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT - ); - - const NBSP = " "; - - let maxVideoQualityLen = 0; - let maxAudioQualityLen = 0; - - formats.forEach((format) => { - if (format.video_ext !== "none" && format.vcodec !== "none") { - const quality = `${format.height || "???"}p${ - format.fps === 60 ? "60" : "" - }`; - if (quality.length > maxVideoQualityLen) { - maxVideoQualityLen = quality.length; - } - } else if ( - format.acodec !== "none" && - format.video_ext === "none" - ) { - const formatNote = - i18n.__(format.format_note) || i18n.__("unknownQuality"); - if (formatNote.length > maxAudioQualityLen) { - maxAudioQualityLen = formatNote.length; - } - } - }); - - const videoQualityPadding = maxVideoQualityLen; - const audioQualityPadding = maxAudioQualityLen; - - const extPadding = 5; // "mp4", "webm" - const vcodecPadding = 5; // "avc1", "vp9" - const filesizePadding = 10; // "12.48 MB" + const videoSelectId = CONSTANTS.DOM_IDS.VIDEO_FORMAT_SELECT; + const audioSelectId = CONSTANTS.DOM_IDS.AUDIO_FORMAT_SELECT; + const audioForVideoSelectId = + CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT; const {videoQuality, videoCodec, showMoreFormats} = this.state.preferences; let bestMatchHeight = 0; + const speakerIconSvg = ``; + + // Find the ideal match height boundary formats.forEach((f) => { if ( f.height && @@ -1373,19 +1343,24 @@ class YtDownloaderApp { }); if (bestMatchHeight === 0 && formats.length > 0) { bestMatchHeight = Math.max( - ...formats.filter((f) => f.height).map((f) => f.height) + ...formats.filter((f) => f.height).map((f) => f.height), ); } + const availableCodecs = new Set( formats .filter((f) => f.height === bestMatchHeight && f.vcodec) - .map((f) => f.vcodec.split(".")[0]) + .map((f) => f.vcodec.split(".")[0]), ); const finalCodec = availableCodecs.has(videoCodec) ? videoCodec : [...availableCodecs].pop(); + let isAVideoSelected = false; + const videoOptions = []; + const audioOptions = []; + formats.forEach((format) => { let sizeInMB = null; let isApprox = false; @@ -1411,7 +1386,9 @@ class YtDownloaderApp { ) { return; } + let isSelected = false; + if ( !isAVideoSelected && format.height === bestMatchHeight && @@ -1421,31 +1398,44 @@ class YtDownloaderApp { isAVideoSelected = true; } - const quality = `${format.height || "???"}p${ - format.fps === 60 ? "60" : "" - }`; - const hasAudio = format.acodec !== "none" ? " 🔊" : ""; - - const col1 = quality.padEnd(videoQualityPadding + 1, NBSP); - const col2 = format.ext.padEnd(extPadding, NBSP); - const col4 = displaySize.padEnd(filesizePadding, NBSP); - - let optionText; - if (showMoreFormats) { - const vcodec = format.vcodec?.split(".")[0] || ""; - const col3 = vcodec.padEnd(vcodecPadding, NBSP); - optionText = `${col1} | ${col2} | ${col3} | ${col4}${hasAudio}`; - } else { - optionText = `${col1} | ${col2} | ${col4}${hasAudio}`; - } - - const option = ``; + const quality = `${format.height || "???"}p${format.fps === 60 ? "60" : ""}`; + const vcodecText = format.vcodec?.split(".")[0] || ""; + + const audioMarkup = + format.acodec !== "none" + ? `
${speakerIconSvg}
` + : `
`; + + const codecHtml = showMoreFormats + ? `${vcodecText}` + : ""; + + const gridClass = showMoreFormats + ? "video-grid-extended" + : "video-grid-compact"; + + const optionTextFallback = showMoreFormats + ? `${quality} ${format.ext} ${vcodecText} ${displaySize}` + : `${quality} ${format.ext} ${displaySize}`; + + const htmlContent = ` +
+ ${quality} + ${format.ext} + ${codecHtml} + ${displaySize} + ${audioMarkup} +
+ `; + + videoOptions.push({ + text: optionTextFallback, + value: `${format.format_id}|${format.ext}|${format.height}|${format.vcodec}`, + selected: isSelected, + html: htmlContent, + }); - videoSelect.innerHTML += option; + // PROCESS AUDIO ONLY CHANNELS } else if ( format.acodec !== "none" && format.video_ext === "none" @@ -1456,31 +1446,82 @@ class YtDownloaderApp { const formatNote = i18n.__(format.format_note) || i18n.__("unknownQuality"); - const audioExtPadded = audioExt.padEnd(extPadding, NBSP); + // HTML for Audio Grid + const htmlContent = ` +
+ ${formatNote} + ${audioExt} + ${displaySize} +
+ `; + + audioOptions.push({ + text: `${formatNote} ${audioExt} ${displaySize}`, + value: `${format.format_id}|${audioExt}`, + html: htmlContent, + }); + } + }); + + const hasAudioTrack = formats.some( + (f) => f.acodec !== "none" && f.acodec !== undefined && f.vcodec === "none", + ); + const audioSection = $(CONSTANTS.DOM_IDS.AUDIO_PRESENT_SECTION); - const audioQualityPadded = formatNote.padEnd( - audioQualityPadding, - NBSP - ); - const audioSizePadded = displaySize.padEnd( - filesizePadding, - NBSP - ); + if (audioSection) { + audioSection.style.display = hasAudioTrack ? "block" : "none"; + } + + const videoSelectEl = $(CONSTANTS.DOM_IDS.VIDEO_FORMAT_SELECT); + const audioSelectEl = $(CONSTANTS.DOM_IDS.AUDIO_FORMAT_SELECT); + const audioForVideoSelectEl = $( + CONSTANTS.DOM_IDS.AUDIO_FOR_VIDEO_FORMAT_SELECT, + ); - const option_audio = ``; + const mountSlimSelect = (domElement, optionsData) => { + if (!domElement) return; - audioSelect.innerHTML += option_audio; - audioForVideoSelect.innerHTML += option_audio; + if (domElement.slim) { + domElement.slim.destroy(); } - }); - if ( - formats.every((f) => f.acodec === "none" || f.acodec === undefined) - ) { - $(CONSTANTS.DOM_IDS.AUDIO_PRESENT_SECTION).style.display = "none"; - } else { - $(CONSTANTS.DOM_IDS.AUDIO_PRESENT_SECTION).style.display = "block"; + domElement.slim = new SlimSelect({ + select: domElement, + data: optionsData, + settings: { + showSearch: true, + contentLocation: document.body, + }, + }); + }; + + if (videoOptions.length > 0) { + mountSlimSelect(videoSelectEl, videoOptions); + } + + if (audioOptions.length > 0) { + mountSlimSelect(audioSelectEl, audioOptions); + + mountSlimSelect( + audioForVideoSelectEl, + JSON.parse(JSON.stringify(audioOptions)), + ); } + + const audioForVideoOptions = JSON.parse(JSON.stringify(audioOptions)); + const noAudioTxt = i18n.__("noAudio") || "No Audio"; + + audioForVideoOptions.push({ + text: noAudioTxt, + value: "none|none", + html: ` +
+ ${noAudioTxt} +
+ `, + }); + + mountSlimSelect(audioForVideoSelectEl, audioForVideoOptions); } /** @@ -1501,7 +1542,7 @@ class YtDownloaderApp { type: "text", value: `${info.title} [${info.id}]`, onchange: (e) => (this.state.videoInfo.title = e.target.value), - }) + }), ); document @@ -1526,7 +1567,7 @@ class YtDownloaderApp { job.thumbnail || "../assets/images/thumb.png" }" alt="thumbnail" class="itemIcon" crossorigin="anonymous"> ${i18n.__( - job.type === "video" ? "video" : "audio" + job.type === "video" ? "video" : "audio", )}
@@ -1534,17 +1575,17 @@ class YtDownloaderApp {
${job.title}
${i18n.__( - "preparing" - )}
+ "preparing", + )} `; $(CONSTANTS.DOM_IDS.DOWNLOAD_LIST).insertAdjacentHTML( "beforeend", - itemHTML + itemHTML, ); $(`${randomId}_close`).addEventListener("click", () => - this._cancelDownload(randomId) + this._cancelDownload(randomId), ); } @@ -1633,7 +1674,7 @@ class YtDownloaderApp { duration: this.state.videoInfo.duration, }) .catch((err) => - console.error("Error adding to history:", err) + console.error("Error adding to history:", err), ); }) .catch((error) => console.error("Error saving to history:", error)); @@ -1710,7 +1751,7 @@ class YtDownloaderApp { $(CONSTANTS.DOM_IDS.MENU).style.opacity = "0"; setTimeout( () => ($(CONSTANTS.DOM_IDS.MENU).style.display = "none"), - 500 + 500, ); } @@ -1725,7 +1766,7 @@ class YtDownloaderApp { } // If it's in the queue this.state.downloadQueue = this.state.downloadQueue.filter( - (job) => job.queueId !== id + (job) => job.queueId !== id, ); // If it has been downloaded, remove from the set @@ -1888,7 +1929,7 @@ class YtDownloaderApp { if (isNaN(newSeconds)) { input.value = this._formatTime( - input.id === "min-time" ? minSlider.value : maxSlider.value + input.id === "min-time" ? minSlider.value : maxSlider.value, ); return; } @@ -1901,7 +1942,7 @@ class YtDownloaderApp { if (newSeconds >= parseInt(maxSlider.value)) { newSeconds = Math.max( minSliderVal, - parseInt(maxSlider.value) - 1 + parseInt(maxSlider.value) - 1, ); } minSlider.value = newSeconds; @@ -1909,7 +1950,7 @@ class YtDownloaderApp { if (newSeconds <= parseInt(minSlider.value)) { newSeconds = Math.min( maxSliderVal, - parseInt(minSlider.value) + 1 + parseInt(minSlider.value) + 1, ); } maxSlider.value = newSeconds; @@ -1928,7 +1969,7 @@ class YtDownloaderApp { if (typeof duration !== "number" || duration < 1) { console.error( - "Invalid duration provided to setVideoLength. Must be a number greater than 0." + "Invalid duration provided to setVideoLength. Must be a number greater than 0.", ); minSlider.max = 0;