class VTUtils{static random(t,e){let a=Math.random();if(void 0===t)return a;if(void 0===e)return t instanceof Array?t[Math.floor(a*t.length)]:a*t;if(t>e){let a=t;t=e,e=a}return a*(e-t)+t}static randomInt(t,e){return Math.floor(VTUtils.random(t,e))}static normalize(t,e,a){return(t-a)/(e-a)}static distance(t,e,a,i){let s=t-a,r=e-i;return Math.sqrt(s*s+r*r)}static map(t,e,a,i,s,r){let l=(t-e)/(a-e)*(s-i)+i;return r?i{let i=t.target;if(i.matches(e))a(t,i);else{let s=i.closest(e);s&&a(t,s)}})},Node.prototype.hasClass=function(t){return this.classList.contains(t)},Node.prototype.addClass=function(t){return this.classList.add(t)},Node.prototype.removeClass=function(t){return this.classList.remove(t)};class Template{constructor(){this.tpl={}}async loadTemplate(t){let e=this;this.tpl[t]||await fetch(templateDir+t+".tpl").then(t=>t.text()).then(a=>{e.tpl[t]=a})}async loadArray(t){for(let e of t)await this.loadTemplate(e)}parseTemplate(t,e){if(!this.tpl[t])return"";let a,i=this.tpl[t];for(;null!==(a=templateEx.exec(i));){a.index===templateEx.lastIndex&&templateEx.lastIndex++;let t=a[0];i=i.replace(t,e[a[1]]||"")}return i}parseFromAPI(t,e,a){fetch(t).then(t=>t.json()).then(t=>{a(this.parseTemplate(e,t))}).catch(console.error)}}const templateEx=/\$(.*?)\$/gm,templateDir="out/tpl/";class ShaderHandler{constructor(t){this.gl=t,this.shaderNames=[],this.shaders={},this.programs={}}setGL(t){this.gl=t}async loadShader(t,e){this.shaderNames.push(t),await this.load(t,e+t+".vert",this.gl.VERTEX_SHADER),await this.load(t,e+t+".frag",this.gl.FRAGMENT_SHADER)}async load(t,e,a){let i=t+"_"+a;if(!this.shaders[i]){let t=await fetch(e),s=this.createShader(await t.text(),a);s&&(this.shaders[i]=s)}return!!this.shaders[i]}getShader(t,e){let a=t+"_"+e;return this.shaders[a]}getAllShaders(){return this.shaderNames}async createProgramForEach(t){t=t||this.shaderNames;for(let e=0;ee&&(a=0),this.index=a,t[a]}getPrevious(){let t=this.isShuffle?this.shuffled:this.list,e=t.length-1,a=this.index-1;return a<0&&(a=e),this.index=a,t[a]}getCurrent(){return(this.isShuffle?this.shuffled:this.list)[this.index]}getFile(t){return(this.isShuffle?this.shuffled:this.list)[t]}setPlaylist(t){this.index=0,this.list=t,this.shuffle()}handlePagination(t,e){e.hasClass("inactive")||(e.hasClass("next-site")?this.renderPagination(this.page+1):this.renderPagination(this.page-1))}renderPagination(t){let e=this.list.length,a=Math.ceil(e/50)-1;t<0&&(t=0),t>a&&(t=a);let i=50*t,s=i+50,r="";if(this.page=t,s>=e&&(s=e),e>0){let t=this.isShuffle?this.shuffled:this.list;for(let e=i;e1&&t0?"active":"inactive",nextActive:l?"active":"inactive",page:t+1+" / "+parseInt(a+1)}))}changeFiles(t,e){let a=[],i=0;for(let t of e.files)if(t&&-1!==t.type.indexOf("audio")&&null===t.name.match(".m3u")){let e=t.name.split(".");e.pop(),e=e.join("."),a.push({file:t,name:e,index:i++})}this.setPlaylist(a),a.length>0?this.renderPagination(0):alert("No Valid AudioFiles found!")}}class GUI{async init(){this.data={},this.modal=new Modal,await this.loadForVis(),await template.loadArray(["playlist-item","playlist","playlist-footer"]),this.initDropZone()}async loadForVis(){let t=visual.c;null==this.data[t]&&(this.data[t]=await fetch("out/gui/"+t+".json").then(t=>t.json()))}renderModal(t,e){let a=$("#modal"),i=a.parentNode,s=$("header .headline",a),r=$("modal-content",a);s.innerHTML=e,r.innerHTML=t,i.classList.remove("hide")}initDropZone(){"drag dragstart dragend dragover dragenter dragleave drop".split(" ").forEach(t=>{window.addEventListener(t,async t=>{t.preventDefault(),t.stopPropagation(),"drop"===t.type&&(t.dataTransfer.files.length>0?player.playlist.changeFiles(t,t.dataTransfer):alert("Sorry you need to upload files!"))})})}}class Modal{constructor(){this.currentModal="",this.modal=$("#modal"),this.parent=this.modal.parentNode,this.modal.addDelegatedEventListener("click","header .close",this.closeModal.bind(this))}resetModal(){this.renderModal("","","")}renderModal(t,e,a){this.currentModal=t,this.renderHeader(t),this.renderContent(e),this.renderFooter(a),this.showModal()}renderHeader(t){$("header .headline",this.modal).innerHTML=t}renderContent(t){$("modal-content",this.modal).innerHTML=t}renderFooter(t){$("modal-footer",this.modal).innerHTML=t}closeModal(){this.parent.addClass("hide")}isCurrent(t){return t===this.currentModal}showModal(){this.parent.removeClass("hide")}}class Visual{constructor(){this.data=[],this.dataArray=[]}updateData(){}draw(){}setup(){}}class VisualDrawer{constructor(){this.visuals={sphere:new Sphere,wave:new Wave,water:new Water},this.c="wave"}init(){this.visuals[this.c].setup(),this.updateLoop()}switch(t){null!=this.visuals[t]&&(this.c=t,this.visuals[this.c].setup())}updateLoop(){let t=shaderHandler.use(this.c),e=this.visuals[this.c];e.updateData(),e.draw(t),requestAnimationFrame(this.updateLoop.bind(this))}}class Config{constructor(){this.config={},this.name=""}loadConfigByName(t){this.saveConfig(),this.name="config-"+t,this.config=JSON.parse(this.name)}saveConfig(){""!==this.name&&localStorage.setItem(this.name,JSON.stringify(this.config))}addItem(t,e){this.config[t]=e}removeItem(t){delete this.config[t]}getItem(t,e){let a=this.config[t];return null==a&&(this.config[t]=e,a=e),a}}class Sphere extends Visual{draw(){}setup(){}}class Wave extends Visual{updateData(){this.data=[];let t=audioHandler.getFloatArray(),e=2/t.length,a=-1;for(let i=0;i{player.playlist.renderPagination(player.playlist.page)}),t.addDelegatedEventListener("click",".playlist-item",(t,e)=>{let a=e.dataset.index;player.playByID(parseInt(a)),togglePlayButton("pause")}),t.addDelegatedEventListener("click",".controls button",(t,e)=>{switch(e.id){case"previous":player.prevSong();break;case"next":player.nextSong();break;case"play":player.playStop()}togglePlayButton(audioHandler.audioFile.paused?"play":"pause")})}function togglePlayButton(t){$$("#play .icon").forEach(e=>{e.dataset.name===t?e.removeClass("hide"):e.addClass("hide")})}const shaderHandler=new ShaderHandler(null),audioHandler=new AudioHandler,gui=new GUI,visual=new VisualDrawer,template=new Template,player=new Player,config=new Config;let c=null,gl=null;async function startUP(){if(c=document.body.querySelector("#c"),gl=c.getContext("webgl2"),!gl)return alert("SORRY THE BROWSER DOESN'T SUPPORT WEBGL2"),!1;shaderHandler.setGL(gl),await shaderHandler.loadArray(["wave","sphere","water"],"shaders/"),await audioHandler.init(),await player.init(),await visual.init(),await gui.init(),await initHandler()}startUP().then(t=>{setTimeout(t=>{$(".loading-screen").remove()},100)});