aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorQube <qchinious@gmail.com>2018-07-20 00:32:31 +0700
committerQube <qchinious@gmail.com>2018-07-20 00:32:31 +0700
commite2b70d9457ead36007b6b512496cf9ff532bf025 (patch)
tree98b911f62e3488dde26951582d019f9fb0bf5e0a
parent67d1e2252b8f46605d49a6c95c80475b890ec3b8 (diff)
Fix handleBN
-rw-r--r--webAO/client.b.js2
-rw-r--r--webAO/client.b.js.map2
-rw-r--r--webAO/client.js4
3 files changed, 4 insertions, 4 deletions
diff --git a/webAO/client.b.js b/webAO/client.b.js
index 09267a0..df378d7 100644
--- a/webAO/client.b.js
+++ b/webAO/client.b.js
@@ -1,2 +1,2 @@
-!function(e){var t={};function n(i){if(t[i])return t[i].exports;var c=t[i]={i:i,l:!1,exports:{}};return e[i].call(c.exports,c,c.exports,n),c.l=!0,c.exports}n.m=e,n.c=t,n.d=function(e,t,i){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:i})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var i=Object.create(null);if(n.r(i),Object.defineProperty(i,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var c in e)n.d(i,c,function(t){return e[t]}.bind(null,c));return i},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=3)}({3:function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var i=function(){function e(e,t){for(var n=0;n<t.length;n++){var i=t[n];i.enumerable=i.enumerable||!1,i.configurable=!0,"value"in i&&(i.writable=!0),Object.defineProperty(e,i.key,i)}}return function(t,n,i){return n&&e(t.prototype,n),i&&e(t,i),t}}();function c(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}t.onOOCEnter=v,t.onEnter=_,t.musiclist_click=E,t.area_click=I,t.changeMusicVolume=b,t.changeSFXVolume=B,t.changeBlipVolume=k,t.changeCharacter=w,t.imgError=C,t.demoError=x,t.ReconnectButton=N,t.RetryButton=O,t.pickchar=L,t.pickemotion=A,t.pickevidence=P,t.addevidence=D,t.editevidence=H,t.delevidence=j,t.cancelevidence=R,t.getIndexFromSelect=V,t.updateEvidenceIcon=F,t.changeBackgroundOOC=U,t.updateBackgroundPreview=z,t.toggleaffect=X,t.toggleflip=G,t.togglepresent=q,t.togglemenu=K,t.toggleshout=W;var a={};location.search.substr(1).split("&").forEach(function(e){a[e.split("=")[0]]=e.split("=")[1]});var o=a.ip,s=a.mode,l=a.asset||"http://assets.aceattorneyonline.com/base/",d=l+"sounds/music/",r=!1;/Android|webOS|iPhone|iPad|iPod|BlackBerry|BB|PlayBook|IEMobile|Windows Phone|Kindle|Silk|Opera Mini/i.test(navigator.userAgent)&&(r=!0);var u=0,m=1,h=0,g=new Date(0),p=function(){function e(t){var n=this;c(this,e),this.serv=new WebSocket("ws://"+t),this.serv.onopen=function(e){return n.onOpen(e)},this.serv.onclose=function(e){return n.onClose(e)},this.serv.onmessage=function(e){return n.onMessage(e)},this.serv.onerror=function(e){return n.onError(e)},this.flip=!1,this.presentable=!1,this.playerID=1,this.charID=-1,this.chars=[],this.emotes=[],this.evidences=[],this.selectedEmote=-1,this.selectedEvidence=0,this.checkUpdater=null,this.musicList=Object(),this.handlers={MS:function(e){return n.handleMS(e)},CT:function(e){return n.handleCT(e)},MC:function(e){return n.handleMC(e)},RMC:function(e){return n.handleRMC(e)},CI:function(e){return n.handleCI(e)},SC:function(e){return n.handleSC(e)},EI:function(e){return n.handleEI(e)},LE:function(e){return n.handleLE(e)},EM:function(e){return n.handleEM(e)},SM:function(e){return n.handleSM(e)},music:function(e){return n.handlemusic(e)},DONE:function(e){return n.handleDONE(e)},BN:function(e){return n.handleBN(e)},NBG:function(e){return n.handleNBG(e)},HP:function(e){return n.handleHP(e)},ID:function(e){return n.handleID(e)},PN:function(e){return n.handlePN(e)},SI:function(e){return n.handleSI(e)},CharsCheck:function(e){return n.handleCharsCheck(e)},PV:function(e){return n.handlePV(e)},CHECK:function(e){}},this._lastTimeICReceived=new Date(0)}return i(e,[{key:"me",value:function(){return this.chars[this.charID]}},{key:"myEmote",value:function(){return this.emotes[this.selectedEmote]}},{key:"myEvidence",value:function(){return this.presentable?this.selectedEvidence:0}},{key:"sendOOC",value:function(e){this.serv.send("CT#web"+this.playerID+"#"+J(Y(e))+"#%")}},{key:"sendIC",value:function(e,t,n,i,c,a,o,s,l,d,r,u,m){this.serv.send("MS#chat#"+e+"#"+t+"#"+n+"#"+J(Y(i))+"#"+c+"#"+a+"#"+o+"#"+this.charID+"#"+s+"#"+h+"#"+d+"#"+r+"#"+u+"#"+m+"#%")}},{key:"sendPE",value:function(e,t,n){this.serv.send("PE#"+J(Y(e))+"#"+J(Y(t))+"#"+n+"#%")}},{key:"sendEE",value:function(e,t,n,i){this.serv.send("EE#"+e+"#"+J(Y(t))+"#"+J(Y(n))+"#"+i+"#%")}},{key:"sendDE",value:function(e,t,n,i){this.serv.send("DE#"+e+"#%")}},{key:"sendMusicChange",value:function(e){this.serv.send("MC#"+e+"#"+this.charID+"#%")}},{key:"sendLeaveRoom",value:function(){this.serv.send("FC#%")}},{key:"joinServer",value:function(){var e=this;this.serv.send("HI#"+navigator.userAgent.hashCode()+"#%"),this.serv.send("ID#webAO#2.4.5#%"),this.checkUpdater=setInterval(function(){return e.sendCheck()},5e3)}},{key:"loadResources",value:function(){var e=document.getElementById("evi_select");e.add(new Option("Custom",0));for(var t=1;t<=evidence_arr.length;t++)e.add(new Option(evidence_arr[t-1]));var n=document.getElementById("bg_select");n.add(new Option("Custom",0));for(var i=1;i<=background_arr.length;i++)n.add(new Option(background_arr[i-1]))}},{key:"initialObservBBCode",value:function(){var e=document.getElementById("client_inner_chat");new MutationObserver(function(e){e.forEach(function(e){var t=e.addedNodes;null!==t&&t.forEach(function(e){"C"==e.tagName?e.style.color=e.getAttribute("a"):"M"==e.tagName&&(e.hasAttribute("a")?e.style.backgroundColor=e.getAttribute("a"):(e.style.backgroundColor="yellow",e.style.color="black"))})})}).observe(e,{attributes:!0,childList:!0})}},{key:"sendCharacter",value:function(e){this.serv.send("CC#"+this.playerID+"#"+e+"#web#%")}},{key:"sendMusic",value:function(e){this.serv.send("MC#"+e)}},{key:"sendCheck",value:function(){this.serv.send("CH#"+this.charID+"#%")}},{key:"onOpen",value:function(e){"watch"===s?(document.getElementById("client_loading").style.display="none",document.getElementById("client_charselect").style.display="none"):te.joinServer()}},{key:"onClose",value:function(e){console.error("The connection was closed: "+e.reason+" ("+e.code+")"),1001!==e.code&&(document.getElementById("client_error").style.display="block",document.getElementById("error_id").textContent=e.code,this.cleanup())}},{key:"onMessage",value:function(e){var t=e.data;console.debug(t);var n=t.split("%")[0].split("#"),i=n[0],c=this.handlers[i];void 0!==c?c(n):console.warn("Invalid packet header "+i)}},{key:"onError",value:function(e){console.error("A network error occurred: "+e.reason+" ("+e.code+")"),document.getElementById("client_error").style.display="block",document.getElementById("error_id").textContent=e.code,this.cleanup()}},{key:"cleanup",value:function(){try{this.serv.close(1001)}catch(e){}clearInterval(this.checkUpdater)}},{key:"handleMS",value:function(e){if(e[4]!=ne.chatmsg.content){document.getElementById("client_inner_chat").innerHTML="";for(var t={character:-1,preanim:escape(e[2]),nameplate:e[3],name:e[3],speaking:"(b)"+escape(e[4]),silent:"(a)"+escape(e[4]),content:function(e){return e.replace(/\\n/g,"<br>").replace(/\[(\/?)b\]/g,"<$1b>").replace(/\[(\/?)i\]/g,"<$1i>").replace(/\[(\/?)del\]/g,"<$1del>").replace(/\[(\/?)u\]/g,"<$1ins>").replace(/\[(\/?)sub\]/g,"<$1sub>").replace(/\[(\/?)sup\]/g,"<$1sup>").replace(/\[m=([#a-zA-Z0-9]+)\]/g,'<m a="$1">').replace(/\[(\/?)m\]/g,"<$1m>").replace(/\[c=?([#a-zA-Z0-9]+)\]/g,'<c a="$1">').replace(/\[\/c\]/g,"</c>")}(Z(ee(Q(e[5])))),side:e[6],sound:escape(e[7]),type:e[8],snddelay:e[10],objection:e[11],evidence:e[12],flip:e[13],flash:e[14],color:e[15],isnew:!0},n=0;n<this.chars.length;n++)if(this.chars[n].name==e[3]){t.character=n;break}t.character==this.charID&&function(){document.getElementById("client_inputbox").value="",u&&(document.getElementById("button_effect_"+u).className="client_button",u=0);h&&(document.getElementById("button_"+h).className="client_button",h=0)}(),ne.say(t)}}},{key:"handleCT",value:function(e){var t=document.getElementById("client_ooclog");t.innerHTML+=ee(Q(e[1]))+": "+ee(Q(e[2]))+"\r\n",t.scrollTop>t.scrollHeight-60&&(t.scrollTop=t.scrollHeight)}},{key:"handleMC",value:function(e){var t=ne.music;(t.pause(),t.src=d+e[1],t.play(),e[2]>=0)?S(this.chars[e[2]].name+" changed music to "+e[1]):S("The music was changed to "+e[1])}},{key:"handleRMC",value:function(e){ne.music.pause(),ne.music=new Audio(this.musicList[e[1]]);var t=ne.music;t.totime=e[1],t.offset=(new Date).getTime()/1e3,t.addEventListener("loadedmetadata",function(){t.currentTime+=parseFloat(t.totime+((new Date).getTime()/1e3-t.offset)).toFixed(3),t.play()},!1)}},{key:"handleCI",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Character "+e[1],this.serv.send("AN#"+(e[1]/10+1)+"#%");for(var t=2;t<e.length-1;t++)if(t%2==0){var n=e[t].split("&");this.chars[e[t-1]]={name:n[0],desc:n[1],evidence:n[3],icon:l+"characters/"+escape(n[0])+"/char_icon.png"}}}},{key:"handleSC",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Characters";for(var t=1;t<e.length-1;t++){var n=e[t].split("&");this.chars[t-1]={name:n[0],desc:n[1],evidence:n[3],icon:l+"characters/"+escape(n[0])+"/char_icon.png"}}this.serv.send("RM#%")}},{key:"handleEI",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Evidence "+e[1],this.serv.send("RM#%")}},{key:"handleLE",value:function(e){this.evidences=[];for(var t=1;t<e.length-1;t++){var n=e[t].split("&");this.evidences[t-1]={name:Z(ee(Q(n[0]))),desc:Z(ee(Q(n[1]))),filename:escape(n[2]),icon:l+"evidence/"+escape(n[2])}}var i=document.getElementById("evidences");i.innerHTML="";for(var c=1;c<=this.evidences.length;c++)i.innerHTML+='<img src="'+this.evidences[c-1].icon+'" id="evi_'+c+'" alt="'+this.evidences[c-1].name+'" class="client_button" onclick="pickevidence('+c+')">'}},{key:"handleEM",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Music "+e[1],this.serv.send("AM#"+(e[1]/10+1)+"#%");for(var t=document.getElementById("client_musiclist"),n=2;n<e.length-1;n++)if(n%2==0){var i=document.createElement("OPTION");i.text=e[n],t.options.add(i)}}},{key:"handleSM",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Music ";for(var t=document.getElementById("client_musiclist"),n=!1,i=1;i<e.length-1;i++)if(/\.(?:wav|mp3|mp4|ogg|mid)$/i.test(e[i])&&!n&&(n=!0),n){var c=document.createElement("OPTION");c.text=e[i],t.options.add(c)}else{var a=document.createElement("SPAN");a.className="location-box",a.textContent=e[i],a.onclick=function(){I(this)},document.getElementById("areas").appendChild(a)}var o=document.getElementById("areas"),s=document.createElement("OPTION");s.text=o.lastChild.textContent,t.insertBefore(s,t.firstChild),o.removeChild(o.lastChild),this.serv.send("RD#%")}},{key:"handlemusic",value:function(e){for(var t=0;t<e.length/2;t++)this.musicList[e[2*t]]=e[2*t+1]}},{key:"handleDONE",value:function(e){document.getElementById("client_loading").style.display="none",document.getElementById("client_charselect").style.display="block"}},{key:"handleBN",value:function(e){ne.bgname=escape(e[1]);var t=V("bg_select",escape(e[1]));document.getElementById("bg_select").selectedIndex=t,z(),t>0&&(document.getElementById("bg_filename").value=escape(e[1])),document.getElementById("bg_preview").src=l+"background/"+escape(e[1])+"/defenseempty.png"}},{key:"handleNBG",value:function(e){}},{key:"handleHP",value:function(e){1==e[1]?document.getElementById("client_defense_hp").style.clip="rect(0px,"+90*e[2]/10+"px,20px,0px)":document.getElementById("client_prosecutor_hp").style.clip="rect(0px,"+90*e[2]/10+"px,20px,0px)"}},{key:"handleID",value:function(e){this.playerID=e[1]}},{key:"handlePN",value:function(e){this.serv.send("askchaa#%")}},{key:"handleSI",value:function(e){r?this.serv.send("askchar2#%"):this.serv.send("RC#%")}},{key:"handleCharsCheck",value:function(e){document.getElementById("client_chartable").innerHTML="";for(var t=0;t<this.chars.length;t++){if(t%8==0)var n=document.createElement("TR");var i=document.createElement("TD"),c=void 0,a=this.chars[t].icon;c="-1"==e[t+1]?" dark":"",i.innerHTML="<img class='demothing"+c+"' id='demo_"+t+"' src='"+a+"' alt='"+this.chars[t].name+"' onclick='pickchar("+t+")' onerror='demoError(this);'>",n.appendChild(i),t%8==0&&document.getElementById("client_chartable").appendChild(n)}M("def")}},{key:"handlePV",value:function(e){this.charID=e[3],document.getElementById("client_charselect").style.display="none";var t=this.me(),n=this.emotes,i=new XMLHttpRequest;i.open("GET",l+"characters/"+escape(this.me().name)+"/char.ini",!0),i.responseType="text",i.onload=function(e){if(200==this.status){var i=this.responseText,c=y.parse(i);t.side=c.Options.side;for(var a=1;a<c.Emotions.number;a++){var o=c.Emotions[a].split("#"),s="0",d="0";void 0!==c.SoundN&&(s=c.SoundN[a]),void 0!==c.SoundT&&(d=c.SoundT[a]),n[a]={desc:o[0],speaking:o[1],silent:o[2],zoom:o[3],sfx:s,sfxdelay:d,button_off:l+"characters/"+escape(t.name)+"/emotions/button"+a+"_off.png",button_on:l+"characters/"+escape(t.name)+"/emotions/button"+a+"_on.png"},document.getElementById("client_emo").innerHTML+="<img src='"+n[a].button_off+"' id='emo_"+a+"' alt='"+n[a].desc+"' class='client_button' onclick='pickemotion("+a+")'>"}A(1)}},i.send()}}]),e}(),f=function(){function e(){c(this,e),this.textnow="",this.chatmsg={isnew:!1,content:"",objection:"0",sound:"",startpreanim:!1,startspeaking:!1,side:null,color:"0",snddelay:0,preanimdelay:0},this.blip=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.blip.volume=.5,this.blipChannels=new Array(6);for(var t=0;t<this.blipChannels.length;t++)this.blipChannels[t]=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.blipChannels[t].volume=.5;this.currentBlipChannel=0,this.sfxaudio=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.sfxplayed=0,this.music=new Audio,this.music.play(),this.updater=null,this.bgname="gs4",this.shoutTimer=0,this.textTimer=0,this._animating=!1}return i(e,[{key:"isAnimating",value:function(){return this._animating}},{key:"setBlipVolume",value:function(e){for(var t=0;t<this.blipChannels.length;t++)this.blipChannels[t].volume=e}},{key:"bgFolder",value:function(){return l+"background/"+this.bgname+"/"}},{key:"say",value:function(e){this.chatmsg=e,S(e.content,e.nameplate),M(e.side),this.textnow="",this.sfxplayed=0,this.textTimer=0,this._animating=!0,clearTimeout(this.updater),"-"!=e.preanim?e.preanimdelay=this.getAnimLength(l+"characters/"+escape(e.name)+"/"+e.preanim+".gif",this.initUpdater):this.initUpdater(0)}},{key:"initUpdater",value:function(e){ne.chatmsg.preanimdelay=parseInt(e),ne.updater=setTimeout(function(){return ne.updateText()},65)}},{key:"getAnimLength",value:function(e,t){var n=new XMLHttpRequest;n.open("GET",e,!0),n.responseType="arraybuffer",n.addEventListener("load",function(){for(var e=new Uint8Array(n.response),i=0,c=0;c<e.length;c++)if(String.fromCharCode(e[c]),33==e[c]&&249==e[c+1]&&4==e[c+2]&&0==e[c+7]){var a=e[c+5]<<8|255&e[c+4];i+=a<2?10:a}t(10*i)}),n.send()}},{key:"updateText",value:function(){var e=this;if(1==this.chatmsg.flip?document.getElementById("client_char").style.transform="scaleX(-1)":document.getElementById("client_char").style.transform="scaleX(1)",this._animating&&(this.updater=setTimeout(function(){return e.updateText()},65)),this.chatmsg.isnew){document.getElementById("client_background").style.backgroundColor="transparent",document.getElementById("client_name").style.display="none",document.getElementById("client_chat").style.display="none",document.getElementById("client_evi").style.opacity="0",document.getElementById("client_evi").style.height="0%";var t={1:"holdit",2:"objection",3:"takethat"}[this.chatmsg.objection];void 0!==t?(document.getElementById("client_shout").src=l+"misc/"+t+".gif",new Audio(l+"/characters/"+this.chatmsg.name+"/"+t+".wav").play(),this.shoutTimer=850):this.shoutTimer=0,this.chatmsg.isnew=!1,this.chatmsg.startpreanim=!0}if(this.textTimer>=this.shoutTimer&&this.chatmsg.startpreanim)2==this.chatmsg.flash?(this.sfxaudio.pause(),this.sfxplayed=1,this.sfxaudio.src=l+"sounds/general/sfx-stab.wav",this.sfxaudio.play(),$("#client_gamewindow").effect("shake",{direction:"up"})):1==this.chatmsg.flash&&(document.getElementById("client_background").style.backgroundColor="white",this.sfxaudio.pause(),this.sfxplayed=1,this.sfxaudio.src=l+"sounds/general/sfx-realization.wav",this.sfxaudio.play(),$("#client_gamewindow").effect("pulsate")),this.chatmsg.preanimdelay>0&&(document.getElementById("client_shout").src="misc/placeholder.gif",M(this.chatmsg.side),document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.preanim+".gif"),this.chatmsg.startpreanim=!1,this.chatmsg.startspeaking=!0;else if(this.textTimer>=this.shoutTimer+this.chatmsg.preanimdelay&&!this.chatmsg.startpreanim)if(this.chatmsg.startspeaking){this.chatmsg.evidence>0&&(document.getElementById("client_evi").style.backgroundImage="url('"+te.evidences[this.chatmsg.evidence-1].icon+"')","def"==this.chatmsg.side?(document.getElementById("client_evi").style.right="1.5em",document.getElementById("client_evi").style.left="initial",$("#client_evi").animate({height:"30%",opacity:1,marginLeft:"10.6in"},250)):(document.getElementById("client_evi").style.right="initial",document.getElementById("client_evi").style.left="1.5em",$("#client_evi").animate({height:"30%",opacity:1,marginRight:"10.6in"},250))),$("#client_name").toggle("fade"),$("#client_chat").toggle("drop",{direction:"down"}),0==this.chatmsg.preanimdelay&&(document.getElementById("client_shout").src="misc/placeholder.gif",M(this.chatmsg.side)),document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.speaking+".gif",document.getElementById("client_name").style.fontSize=.7*document.getElementById("client_name").offsetHeight+"px",document.getElementById("client_chat").style.fontSize=.25*document.getElementById("client_chat").offsetHeight+"px",document.getElementById("client_name").innerHTML="<p>"+Z(this.chatmsg.nameplate)+"</p>";var n="color: "+({0:"#ffffff",1:"#00ff00",2:"#ff0000",3:"#ffaa00",4:"#0000ff",5:"#ffff00",6:"#aa00aa"}[this.chatmsg.color]||"#ffffff");document.getElementById("client_inner_chat").style=n,this.chatmsg.startspeaking=!1,this.textnow==this.chatmsg.content&&(document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.silent+".gif",this._animating=!1,clearTimeout(this.updater))}else this.textnow!=this.chatmsg.content&&(" "!=this.chatmsg.content.charAt(this.textnow.length)&&(this.blipChannels[this.currentBlipChannel].play(),this.currentBlipChannel++,this.currentBlipChannel%=this.blipChannels.length),this.textnow=this.chatmsg.content.substring(0,this.textnow.length+1),document.getElementById("client_inner_chat").innerHTML=this.textnow,this.textnow==this.chatmsg.content&&(this.textTimer=0,this._animating=!1,document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.silent+".gif",clearTimeout(this.updater)));!this.sfxplayed&&this.chatmsg.snddelay+this.shoutTimer>=this.textTimer&&(this.sfxaudio.pause(),this.sfxplayed=1,"0"!=this.chatmsg.sound&&"1"!=this.chatmsg.sound&&(this.sfxaudio.src=l+"sounds/general/"+escape(this.chatmsg.sound)+".wav",this.sfxaudio.play())),this.textTimer=this.textTimer+65}}]),e}(),y=function(){function e(){c(this,e)}return i(e,null,[{key:"parse",value:function(e){var t={section:/^\s*\[\s*([^\]]*)\s*\]\s*$/,param:/^\s*([\w\.\-\_]+)\s*=\s*(.*?)\s*$/,comment:/^\s*;.*$/},n={},i=null;return e.split(/\r\n|\r|\n/).forEach(function(e){if(!t.comment.test(e)&&0!=e.length)if(t.param.test(e)){var c=e.match(t.param);i?n[i][c[1]]=c[2]:n[c[1]]=c[2]}else if(t.section.test(e)){var a=e.match(t.section);n[a[1]]={},i=a[1]}}),n}}]),e}();function v(e){13==e.keyCode&&(te.sendOOC(document.getElementById("client_oocinputbox").value),document.getElementById("client_oocinputbox").value="")}function _(e){if(13==e.keyCode){var t=te.me(),n=te.myEmote(),i=te.myEvidence(),c=te.flip?1:0,a=document.getElementById("textcolor").value,o="0",s="0";document.getElementById("sendsfx").checked&&(o=n.sfx,s=n.sfxdelay),te.sendIC(n.speaking,t.name,n.silent,document.getElementById("client_inputbox").value,t.side,o,n.zoom,s,h,i,c,u,a)}}function E(e){var t=document.getElementById("client_musiclist").value;te.sendMusicChange(t)}function I(e){var t=e.textContent;te.sendMusicChange(t)}function b(){ne.music.volume=document.getElementById("client_mvolume").value/100}function B(){ne.sfxaudio.volume=document.getElementById("client_svolume").value/100}function k(){ne.setBlipVolume(document.getElementById("client_bvolume").value/100)}function w(e){te.sendLeaveRoom(),document.getElementById("client_charselect").style.display="block",document.getElementById("client_emo").innerHTML=""}function C(e){return e.onerror="",e.src="misc/placeholder.gif",!0}function x(e){return e.onerror="",e.src="/misc/placeholder.png",!0}function T(e){var t=new Image;return t.src=e,0!=t.height}function M(e){var t,n=ne.bgFolder();switch(document.getElementById("client_fg").style.display="none",document.getElementById("client_bench").style.display="none",e){case"def":document.getElementById("client_court").src=n+"defenseempty.png",document.getElementById("client_bench").style.display="block",T(n+"defensedesk.png")?document.getElementById("client_bench").src=n+"defensedesk.png":document.getElementById("client_bench").src=n+"bancodefensa.png",t="defense";break;case"pro":document.getElementById("client_court").src=n+"prosecutorempty.png",document.getElementById("client_bench").style.display="block",T(n+"defensedesk.png")?document.getElementById("client_bench").src=n+"prosecutiondesk.png":document.getElementById("client_bench").src=n+"bancoacusacion.png",t="prosecution";break;case"hld":document.getElementById("client_court").src=n+"helperstand.png",t="defense";break;case"hlp":document.getElementById("client_court").src=n+"prohelperstand.png",t="prosecution";break;case"wit":document.getElementById("client_court").src=n+"witnessempty.png",document.getElementById("client_bench").style.display="block",document.getElementById("client_bench").src=n+"estrado.png",t="prosecution";break;case"jud":document.getElementById("client_court").src=n+"judgestand.png",t="prosecution"}5==ne.chatmsg.type&&(document.getElementById("client_bench").style.display="none",document.getElementById("client_court").src=l+"themes/default/"+t+"_speedlines.gif")}function N(){te.cleanup(),(te=new p(o))&&(s="join",document.getElementById("client_error").style.display="none")}function O(){te.joinServer()}function S(e){var t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"",n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:new Date,i=document.createElement("p"),c=document.createElement("span");if(c.id="iclog_name",c.appendChild(document.createTextNode(t)),i.appendChild(c),i.appendChild(document.createTextNode(e)),g.getMinutes()!==n.getMinutes()){var a=document.createElement("span");a.id="iclog_time",a.innerText=n.toLocaleTimeString(void 0,{hour:"numeric",minute:"2-digit"}),i.appendChild(a)}var o=document.getElementById("client_log");o.appendChild(i),o.scrollTop>o.scrollHeight-600&&(o.scrollTop=o.scrollHeight),g=new Date}function L(e){e<1e3?te.sendCharacter(e):(document.getElementById("client_charselect").style.display="none",document.getElementById("client_inputbox").style.display="none",document.getElementById("client_emo").style.display="none")}function A(e){-1!=te.selectedEmote&&(document.getElementById("emo_"+te.selectedEmote).src=te.myEmote().button_off),te.selectedEmote=e,document.getElementById("emo_"+e).src=te.myEmote().button_on}function P(e){if(te.selectedEvidence!=e){te.selectedEvidence>0&&(document.getElementById("evi_"+te.selectedEvidence).className="client_button"),document.getElementById("evi_"+e).className="client_button dark",te.selectedEvidence=e,document.getElementById("evi_name").value=te.evidences[e-1].name,document.getElementById("evi_desc").value=te.evidences[e-1].desc;var t=V("evi_select",te.evidences[e-1].filename);document.getElementById("evi_select").selectedIndex=t,0==t&&(document.getElementById("evi_filename").value=te.evidences[e-1].filename),F(),document.getElementById("evi_add").className="client_button hover_button inactive",document.getElementById("evi_edit").className="client_button hover_button",document.getElementById("evi_cancel").className="client_button hover_button",document.getElementById("evi_del").className="client_button hover_button"}else R()}function D(){var e=document.getElementById("evi_select");te.sendPE(document.getElementById("evi_name").value,document.getElementById("evi_desc").value,0==e.selectedIndex?document.getElementById("evi_filename").value:e.options[e.selectedIndex].text),R()}function H(){var e=document.getElementById("evi_select"),t=parseInt(te.selectedEvidence)-1;te.sendEE(t,document.getElementById("evi_name").value,document.getElementById("evi_desc").value,0==e.selectedIndex?document.getElementById("evi_filename").value:e.options[e.selectedIndex].text),R()}function j(){var e=parseInt(te.selectedEvidence)-1;te.sendDE(e),R()}function R(){te.selectedEvidence>0&&(document.getElementById("evi_"+te.selectedEvidence).className="client_button"),te.selectedEvidence=0,document.getElementById("evi_select").selectedIndex=0,F(),document.getElementById("evi_filename").value="",document.getElementById("evi_name").value="",document.getElementById("evi_desc").value="",document.getElementById("evi_icon").style.backgroundImage="url('misc/empty.png')",document.getElementById("evi_add").className="client_button hover_button",document.getElementById("evi_edit").className="client_button hover_button inactive",document.getElementById("evi_cancel").className="client_button hover_button inactive",document.getElementById("evi_del").className="client_button hover_button inactive"}function V(e,t){for(var n=document.getElementById(e),i=1;i<n.length;++i)if(n.options[i].value==t)return i;return 0}function F(){var e=document.getElementById("evi_select"),t=document.getElementById("evi_filename"),n=document.getElementById("evi_icon");0==e.selectedIndex?(t.style.display="initial",n.style.backgroundImage="url('"+l+"evidence/"+t.value+"')"):(t.style.display="none",n.style.backgroundImage="url('"+l+"evidence/"+e.value+"')")}function U(){var e="",t=document.getElementById("bg_select"),n=document.getElementById("bg_command").value;e=0==t.selectedIndex?document.getElementById("bg_filename").value:t.value,te.sendOOC("/"+n.replace("$1",e))}function z(){var e=document.getElementById("bg_select"),t=document.getElementById("bg_filename"),n=document.getElementById("bg_preview");0==e.selectedIndex?(t.style.display="initial",n.src=l+"background/"+t.value+"/defenseempty.png"):(t.style.display="none",n.src=l+"background/"+e.value+"/defenseempty.png")}function X(e){e==u?(document.getElementById("button_effect_"+e).className="client_button",u=0):(document.getElementById("button_effect_"+e).className="client_button dark",u&&(document.getElementById("button_effect_"+u).className="client_button"),u=e)}function G(){te.flip?document.getElementById("button_flip").className="client_button":document.getElementById("button_flip").className="client_button dark",te.flip=!te.flip}function q(){te.presentable?document.getElementById("button_present").className="client_button":document.getElementById("button_present").className="client_button dark",te.presentable=!te.presentable}function K(e){e!=m&&(document.getElementById("menu_"+e).className="menu_icon active",document.getElementById("content_"+e).className="menu_content active",document.getElementById("menu_"+m).className="menu_icon",document.getElementById("content_"+m).className="menu_content",m=e)}function W(e){e==h?(document.getElementById("button_"+e).className="client_button",h=0):(document.getElementById("button_"+e).className="client_button dark",h&&(document.getElementById("button_"+h).className="client_button"),h=e)}function Z(e){return e.replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/"/g,"&quot;").replace(/'/g,"&#039;")}function J(e){return e.replace(/#/g,"<pound>").replace(/&/g,"<and>").replace(/%/g,"<percent>").replace(/\$/g,"<dollar>")}function Q(e){return e.replace(/<pound>/g,"#").replace(/<and>/g,"&").replace(/<percent>/g,"%").replace(/<dollar>/g,"$")}function Y(e){var t=document.getElementById("client_encoding").value;if("unicode"==t)return e.replace(/[^\0-~]/g,function(e){return"\\u"+("000"+e.charCodeAt().toString(16)).slice(-4)});if("utf16"==t){for(var n=new ArrayBuffer(2*e.length),i=new Uint16Array(n),c=0,a=e.length;c<a;c++)i[c]=e.charCodeAt(c);return String(i)}return e}function ee(e){var t=document.getElementById("client_decoding").value;return"unicode"==t?e.replace(/\\u([\d\w]{1,})/gi,function(e,t){return String.fromCharCode(parseInt(t,16))}):"utf16"==t?String.fromCharCode.apply(null,new Uint16Array(e.split(","))):e}window.onOOCEnter=v,window.onEnter=_,window.musiclist_click=E,window.area_click=I,window.changeMusicVolume=b,window.changeSFXVolume=B,window.changeBlipVolume=k,window.changeCharacter=w,window.imgError=C,window.demoError=x,window.ReconnectButton=N,window.RetryButton=O,window.pickchar=L,window.pickemotion=A,window.pickevidence=P,window.addevidence=D,window.editevidence=H,window.delevidence=j,window.cancelevidence=R,window.getIndexFromSelect=V,window.updateEvidenceIcon=F,window.changeBackgroundOOC=U,window.updateBackgroundPreview=z,window.toggleaffect=X,window.toggleflip=G,window.togglepresent=q,window.togglemenu=K,window.toggleshout=W,void 0===String.prototype.trim&&(String.prototype.trim=function(){return String(this).replace(/^\s+|\s+$/g,"")}),String.prototype.hashCode=function(){var e,t=0;if(0===this.length)return t;for(e=0;e<this.length;e++)t=(t<<5)-t+this.charCodeAt(e),t|=0;return t};var te=new p(o),ne=new f;$(document).ready(function(){te.initialObservBBCode(),te.loadResources()})}});
+!function(e){var t={};function n(i){if(t[i])return t[i].exports;var c=t[i]={i:i,l:!1,exports:{}};return e[i].call(c.exports,c,c.exports,n),c.l=!0,c.exports}n.m=e,n.c=t,n.d=function(e,t,i){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:i})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var i=Object.create(null);if(n.r(i),Object.defineProperty(i,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var c in e)n.d(i,c,function(t){return e[t]}.bind(null,c));return i},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=3)}({3:function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var i=function(){function e(e,t){for(var n=0;n<t.length;n++){var i=t[n];i.enumerable=i.enumerable||!1,i.configurable=!0,"value"in i&&(i.writable=!0),Object.defineProperty(e,i.key,i)}}return function(t,n,i){return n&&e(t.prototype,n),i&&e(t,i),t}}();function c(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}t.onOOCEnter=v,t.onEnter=_,t.musiclist_click=E,t.area_click=I,t.changeMusicVolume=b,t.changeSFXVolume=B,t.changeBlipVolume=k,t.changeCharacter=w,t.imgError=C,t.demoError=x,t.ReconnectButton=N,t.RetryButton=O,t.pickchar=L,t.pickemotion=A,t.pickevidence=P,t.addevidence=D,t.editevidence=H,t.delevidence=j,t.cancelevidence=R,t.getIndexFromSelect=V,t.updateEvidenceIcon=F,t.changeBackgroundOOC=U,t.updateBackgroundPreview=z,t.toggleaffect=X,t.toggleflip=G,t.togglepresent=q,t.togglemenu=K,t.toggleshout=W;var a={};location.search.substr(1).split("&").forEach(function(e){a[e.split("=")[0]]=e.split("=")[1]});var o=a.ip,s=a.mode,l=a.asset||"http://assets.aceattorneyonline.com/base/",d=l+"sounds/music/",r=!1;/Android|webOS|iPhone|iPad|iPod|BlackBerry|BB|PlayBook|IEMobile|Windows Phone|Kindle|Silk|Opera Mini/i.test(navigator.userAgent)&&(r=!0);var u=0,m=1,h=0,g=new Date(0),p=function(){function e(t){var n=this;c(this,e),this.serv=new WebSocket("ws://"+t),this.serv.onopen=function(e){return n.onOpen(e)},this.serv.onclose=function(e){return n.onClose(e)},this.serv.onmessage=function(e){return n.onMessage(e)},this.serv.onerror=function(e){return n.onError(e)},this.flip=!1,this.presentable=!1,this.playerID=1,this.charID=-1,this.chars=[],this.emotes=[],this.evidences=[],this.selectedEmote=-1,this.selectedEvidence=0,this.checkUpdater=null,this.musicList=Object(),this.handlers={MS:function(e){return n.handleMS(e)},CT:function(e){return n.handleCT(e)},MC:function(e){return n.handleMC(e)},RMC:function(e){return n.handleRMC(e)},CI:function(e){return n.handleCI(e)},SC:function(e){return n.handleSC(e)},EI:function(e){return n.handleEI(e)},LE:function(e){return n.handleLE(e)},EM:function(e){return n.handleEM(e)},SM:function(e){return n.handleSM(e)},music:function(e){return n.handlemusic(e)},DONE:function(e){return n.handleDONE(e)},BN:function(e){return n.handleBN(e)},NBG:function(e){return n.handleNBG(e)},HP:function(e){return n.handleHP(e)},ID:function(e){return n.handleID(e)},PN:function(e){return n.handlePN(e)},SI:function(e){return n.handleSI(e)},CharsCheck:function(e){return n.handleCharsCheck(e)},PV:function(e){return n.handlePV(e)},CHECK:function(e){}},this._lastTimeICReceived=new Date(0)}return i(e,[{key:"me",value:function(){return this.chars[this.charID]}},{key:"myEmote",value:function(){return this.emotes[this.selectedEmote]}},{key:"myEvidence",value:function(){return this.presentable?this.selectedEvidence:0}},{key:"sendOOC",value:function(e){this.serv.send("CT#web"+this.playerID+"#"+J(Y(e))+"#%")}},{key:"sendIC",value:function(e,t,n,i,c,a,o,s,l,d,r,u,m){this.serv.send("MS#chat#"+e+"#"+t+"#"+n+"#"+J(Y(i))+"#"+c+"#"+a+"#"+o+"#"+this.charID+"#"+s+"#"+h+"#"+d+"#"+r+"#"+u+"#"+m+"#%")}},{key:"sendPE",value:function(e,t,n){this.serv.send("PE#"+J(Y(e))+"#"+J(Y(t))+"#"+n+"#%")}},{key:"sendEE",value:function(e,t,n,i){this.serv.send("EE#"+e+"#"+J(Y(t))+"#"+J(Y(n))+"#"+i+"#%")}},{key:"sendDE",value:function(e,t,n,i){this.serv.send("DE#"+e+"#%")}},{key:"sendMusicChange",value:function(e){this.serv.send("MC#"+e+"#"+this.charID+"#%")}},{key:"sendLeaveRoom",value:function(){this.serv.send("FC#%")}},{key:"joinServer",value:function(){var e=this;this.serv.send("HI#"+navigator.userAgent.hashCode()+"#%"),this.serv.send("ID#webAO#2.4.5#%"),this.checkUpdater=setInterval(function(){return e.sendCheck()},5e3)}},{key:"loadResources",value:function(){var e=document.getElementById("evi_select");e.add(new Option("Custom",0));for(var t=1;t<=evidence_arr.length;t++)e.add(new Option(evidence_arr[t-1]));var n=document.getElementById("bg_select");n.add(new Option("Custom",0));for(var i=1;i<=background_arr.length;i++)n.add(new Option(background_arr[i-1]))}},{key:"initialObservBBCode",value:function(){var e=document.getElementById("client_inner_chat");new MutationObserver(function(e){e.forEach(function(e){var t=e.addedNodes;null!==t&&t.forEach(function(e){"C"==e.tagName?e.style.color=e.getAttribute("a"):"M"==e.tagName&&(e.hasAttribute("a")?e.style.backgroundColor=e.getAttribute("a"):(e.style.backgroundColor="yellow",e.style.color="black"))})})}).observe(e,{attributes:!0,childList:!0})}},{key:"sendCharacter",value:function(e){this.serv.send("CC#"+this.playerID+"#"+e+"#web#%")}},{key:"sendMusic",value:function(e){this.serv.send("MC#"+e)}},{key:"sendCheck",value:function(){this.serv.send("CH#"+this.charID+"#%")}},{key:"onOpen",value:function(e){"watch"===s?(document.getElementById("client_loading").style.display="none",document.getElementById("client_charselect").style.display="none"):te.joinServer()}},{key:"onClose",value:function(e){console.error("The connection was closed: "+e.reason+" ("+e.code+")"),1001!==e.code&&(document.getElementById("client_error").style.display="block",document.getElementById("error_id").textContent=e.code,this.cleanup())}},{key:"onMessage",value:function(e){var t=e.data;console.debug(t);var n=t.split("%")[0].split("#"),i=n[0],c=this.handlers[i];void 0!==c?c(n):console.warn("Invalid packet header "+i)}},{key:"onError",value:function(e){console.error("A network error occurred: "+e.reason+" ("+e.code+")"),document.getElementById("client_error").style.display="block",document.getElementById("error_id").textContent=e.code,this.cleanup()}},{key:"cleanup",value:function(){try{this.serv.close(1001)}catch(e){}clearInterval(this.checkUpdater)}},{key:"handleMS",value:function(e){if(e[4]!=ne.chatmsg.content){document.getElementById("client_inner_chat").innerHTML="";for(var t={character:-1,preanim:escape(e[2]),nameplate:e[3],name:e[3],speaking:"(b)"+escape(e[4]),silent:"(a)"+escape(e[4]),content:function(e){return e.replace(/\\n/g,"<br>").replace(/\[(\/?)b\]/g,"<$1b>").replace(/\[(\/?)i\]/g,"<$1i>").replace(/\[(\/?)del\]/g,"<$1del>").replace(/\[(\/?)u\]/g,"<$1ins>").replace(/\[(\/?)sub\]/g,"<$1sub>").replace(/\[(\/?)sup\]/g,"<$1sup>").replace(/\[m=([#a-zA-Z0-9]+)\]/g,'<m a="$1">').replace(/\[(\/?)m\]/g,"<$1m>").replace(/\[c=?([#a-zA-Z0-9]+)\]/g,'<c a="$1">').replace(/\[\/c\]/g,"</c>")}(Z(ee(Q(e[5])))),side:e[6],sound:escape(e[7]),type:e[8],snddelay:e[10],objection:e[11],evidence:e[12],flip:e[13],flash:e[14],color:e[15],isnew:!0},n=0;n<this.chars.length;n++)if(this.chars[n].name==e[3]){t.character=n;break}t.character==this.charID&&function(){document.getElementById("client_inputbox").value="",u&&(document.getElementById("button_effect_"+u).className="client_button",u=0);h&&(document.getElementById("button_"+h).className="client_button",h=0)}(),ne.say(t)}}},{key:"handleCT",value:function(e){var t=document.getElementById("client_ooclog");t.innerHTML+=ee(Q(e[1]))+": "+ee(Q(e[2]))+"\r\n",t.scrollTop>t.scrollHeight-60&&(t.scrollTop=t.scrollHeight)}},{key:"handleMC",value:function(e){var t=ne.music;(t.pause(),t.src=d+e[1],t.play(),e[2]>=0)?S(this.chars[e[2]].name+" changed music to "+e[1]):S("The music was changed to "+e[1])}},{key:"handleRMC",value:function(e){ne.music.pause(),ne.music=new Audio(this.musicList[e[1]]);var t=ne.music;t.totime=e[1],t.offset=(new Date).getTime()/1e3,t.addEventListener("loadedmetadata",function(){t.currentTime+=parseFloat(t.totime+((new Date).getTime()/1e3-t.offset)).toFixed(3),t.play()},!1)}},{key:"handleCI",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Character "+e[1],this.serv.send("AN#"+(e[1]/10+1)+"#%");for(var t=2;t<e.length-1;t++)if(t%2==0){var n=e[t].split("&");this.chars[e[t-1]]={name:n[0],desc:n[1],evidence:n[3],icon:l+"characters/"+escape(n[0])+"/char_icon.png"}}}},{key:"handleSC",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Characters";for(var t=1;t<e.length-1;t++){var n=e[t].split("&");this.chars[t-1]={name:n[0],desc:n[1],evidence:n[3],icon:l+"characters/"+escape(n[0])+"/char_icon.png"}}this.serv.send("RM#%")}},{key:"handleEI",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Evidence "+e[1],this.serv.send("RM#%")}},{key:"handleLE",value:function(e){this.evidences=[];for(var t=1;t<e.length-1;t++){var n=e[t].split("&");this.evidences[t-1]={name:Z(ee(Q(n[0]))),desc:Z(ee(Q(n[1]))),filename:escape(n[2]),icon:l+"evidence/"+escape(n[2])}}var i=document.getElementById("evidences");i.innerHTML="";for(var c=1;c<=this.evidences.length;c++)i.innerHTML+='<img src="'+this.evidences[c-1].icon+'" id="evi_'+c+'" alt="'+this.evidences[c-1].name+'" class="client_button" onclick="pickevidence('+c+')">'}},{key:"handleEM",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Music "+e[1],this.serv.send("AM#"+(e[1]/10+1)+"#%");for(var t=document.getElementById("client_musiclist"),n=2;n<e.length-1;n++)if(n%2==0){var i=document.createElement("OPTION");i.text=e[n],t.options.add(i)}}},{key:"handleSM",value:function(e){document.getElementById("client_loadingtext").innerHTML="Loading Music ";for(var t=document.getElementById("client_musiclist"),n=!1,i=1;i<e.length-1;i++)if(/\.(?:wav|mp3|mp4|ogg|mid)$/i.test(e[i])&&!n&&(n=!0),n){var c=document.createElement("OPTION");c.text=e[i],t.options.add(c)}else{var a=document.createElement("SPAN");a.className="location-box",a.textContent=e[i],a.onclick=function(){I(this)},document.getElementById("areas").appendChild(a)}var o=document.getElementById("areas"),s=document.createElement("OPTION");s.text=o.lastChild.textContent,t.insertBefore(s,t.firstChild),o.removeChild(o.lastChild),this.serv.send("RD#%")}},{key:"handlemusic",value:function(e){for(var t=0;t<e.length/2;t++)this.musicList[e[2*t]]=e[2*t+1]}},{key:"handleDONE",value:function(e){document.getElementById("client_loading").style.display="none",document.getElementById("client_charselect").style.display="block"}},{key:"handleBN",value:function(e){ne.bgname=escape(e[1]);var t=V("bg_select",escape(e[1]));document.getElementById("bg_select").selectedIndex=t,z(),0==t&&(document.getElementById("bg_filename").value=escape(e[1])),document.getElementById("bg_preview").src=l+"background/"+escape(e[1])+"/defenseempty.png"}},{key:"handleNBG",value:function(e){}},{key:"handleHP",value:function(e){1==e[1]?document.getElementById("client_defense_hp").style.clip="rect(0px,"+90*e[2]/10+"px,20px,0px)":document.getElementById("client_prosecutor_hp").style.clip="rect(0px,"+90*e[2]/10+"px,20px,0px)"}},{key:"handleID",value:function(e){this.playerID=e[1]}},{key:"handlePN",value:function(e){this.serv.send("askchaa#%")}},{key:"handleSI",value:function(e){r?this.serv.send("askchar2#%"):this.serv.send("RC#%")}},{key:"handleCharsCheck",value:function(e){document.getElementById("client_chartable").innerHTML="";for(var t=0;t<this.chars.length;t++){if(t%8==0)var n=document.createElement("TR");var i=document.createElement("TD"),c=void 0,a=this.chars[t].icon;c="-1"==e[t+1]?" dark":"",i.innerHTML="<img class='demothing"+c+"' id='demo_"+t+"' src='"+a+"' alt='"+this.chars[t].name+"' onclick='pickchar("+t+")' onerror='demoError(this);'>",n.appendChild(i),t%8==0&&document.getElementById("client_chartable").appendChild(n)}M("def")}},{key:"handlePV",value:function(e){this.charID=e[3],document.getElementById("client_charselect").style.display="none";var t=this.me(),n=this.emotes,i=new XMLHttpRequest;i.open("GET",l+"characters/"+escape(this.me().name)+"/char.ini",!0),i.responseType="text",i.onload=function(e){if(200==this.status){var i=this.responseText,c=y.parse(i);t.side=c.Options.side;for(var a=1;a<c.Emotions.number;a++){var o=c.Emotions[a].split("#"),s="0",d="0";void 0!==c.SoundN&&(s=c.SoundN[a]),void 0!==c.SoundT&&(d=c.SoundT[a]),n[a]={desc:o[0],speaking:o[1],silent:o[2],zoom:o[3],sfx:s,sfxdelay:d,button_off:l+"characters/"+escape(t.name)+"/emotions/button"+a+"_off.png",button_on:l+"characters/"+escape(t.name)+"/emotions/button"+a+"_on.png"},document.getElementById("client_emo").innerHTML+="<img src='"+n[a].button_off+"' id='emo_"+a+"' alt='"+n[a].desc+"' class='client_button' onclick='pickemotion("+a+")'>"}A(1)}},i.send()}}]),e}(),f=function(){function e(){c(this,e),this.textnow="",this.chatmsg={isnew:!1,content:"",objection:"0",sound:"",startpreanim:!1,startspeaking:!1,side:null,color:"0",snddelay:0,preanimdelay:0},this.blip=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.blip.volume=.5,this.blipChannels=new Array(6);for(var t=0;t<this.blipChannels.length;t++)this.blipChannels[t]=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.blipChannels[t].volume=.5;this.currentBlipChannel=0,this.sfxaudio=new Audio(l+"sounds/general/sfx-blipmale.wav"),this.sfxplayed=0,this.music=new Audio,this.music.play(),this.updater=null,this.bgname="gs4",this.shoutTimer=0,this.textTimer=0,this._animating=!1}return i(e,[{key:"isAnimating",value:function(){return this._animating}},{key:"setBlipVolume",value:function(e){for(var t=0;t<this.blipChannels.length;t++)this.blipChannels[t].volume=e}},{key:"bgFolder",value:function(){return l+"background/"+this.bgname+"/"}},{key:"say",value:function(e){this.chatmsg=e,S(e.content,e.nameplate),M(e.side),this.textnow="",this.sfxplayed=0,this.textTimer=0,this._animating=!0,clearTimeout(this.updater),"-"!=e.preanim?e.preanimdelay=this.getAnimLength(l+"characters/"+escape(e.name)+"/"+e.preanim+".gif",this.initUpdater):this.initUpdater(0)}},{key:"initUpdater",value:function(e){ne.chatmsg.preanimdelay=parseInt(e),ne.updater=setTimeout(function(){return ne.updateText()},65)}},{key:"getAnimLength",value:function(e,t){var n=new XMLHttpRequest;n.open("GET",e,!0),n.responseType="arraybuffer",n.addEventListener("load",function(){for(var e=new Uint8Array(n.response),i=0,c=0;c<e.length;c++)if(String.fromCharCode(e[c]),33==e[c]&&249==e[c+1]&&4==e[c+2]&&0==e[c+7]){var a=e[c+5]<<8|255&e[c+4];i+=a<2?10:a}t(10*i)}),n.send()}},{key:"updateText",value:function(){var e=this;if(1==this.chatmsg.flip?document.getElementById("client_char").style.transform="scaleX(-1)":document.getElementById("client_char").style.transform="scaleX(1)",this._animating&&(this.updater=setTimeout(function(){return e.updateText()},65)),this.chatmsg.isnew){document.getElementById("client_background").style.backgroundColor="transparent",document.getElementById("client_name").style.display="none",document.getElementById("client_chat").style.display="none",document.getElementById("client_evi").style.opacity="0",document.getElementById("client_evi").style.height="0%";var t={1:"holdit",2:"objection",3:"takethat"}[this.chatmsg.objection];void 0!==t?(document.getElementById("client_shout").src=l+"misc/"+t+".gif",new Audio(l+"/characters/"+this.chatmsg.name+"/"+t+".wav").play(),this.shoutTimer=850):this.shoutTimer=0,this.chatmsg.isnew=!1,this.chatmsg.startpreanim=!0}if(this.textTimer>=this.shoutTimer&&this.chatmsg.startpreanim)2==this.chatmsg.flash?(this.sfxaudio.pause(),this.sfxplayed=1,this.sfxaudio.src=l+"sounds/general/sfx-stab.wav",this.sfxaudio.play(),$("#client_gamewindow").effect("shake",{direction:"up"})):1==this.chatmsg.flash&&(document.getElementById("client_background").style.backgroundColor="white",this.sfxaudio.pause(),this.sfxplayed=1,this.sfxaudio.src=l+"sounds/general/sfx-realization.wav",this.sfxaudio.play(),$("#client_gamewindow").effect("pulsate")),this.chatmsg.preanimdelay>0&&(document.getElementById("client_shout").src="misc/placeholder.gif",M(this.chatmsg.side),document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.preanim+".gif"),this.chatmsg.startpreanim=!1,this.chatmsg.startspeaking=!0;else if(this.textTimer>=this.shoutTimer+this.chatmsg.preanimdelay&&!this.chatmsg.startpreanim)if(this.chatmsg.startspeaking){this.chatmsg.evidence>0&&(document.getElementById("client_evi").style.backgroundImage="url('"+te.evidences[this.chatmsg.evidence-1].icon+"')","def"==this.chatmsg.side?(document.getElementById("client_evi").style.right="1.5em",document.getElementById("client_evi").style.left="initial",$("#client_evi").animate({height:"30%",opacity:1,marginLeft:"10.6in"},250)):(document.getElementById("client_evi").style.right="initial",document.getElementById("client_evi").style.left="1.5em",$("#client_evi").animate({height:"30%",opacity:1,marginRight:"10.6in"},250))),$("#client_name").toggle("fade"),$("#client_chat").toggle("drop",{direction:"down"}),0==this.chatmsg.preanimdelay&&(document.getElementById("client_shout").src="misc/placeholder.gif",M(this.chatmsg.side)),document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.speaking+".gif",document.getElementById("client_name").style.fontSize=.7*document.getElementById("client_name").offsetHeight+"px",document.getElementById("client_chat").style.fontSize=.25*document.getElementById("client_chat").offsetHeight+"px",document.getElementById("client_name").innerHTML="<p>"+Z(this.chatmsg.nameplate)+"</p>";var n="color: "+({0:"#ffffff",1:"#00ff00",2:"#ff0000",3:"#ffaa00",4:"#0000ff",5:"#ffff00",6:"#aa00aa"}[this.chatmsg.color]||"#ffffff");document.getElementById("client_inner_chat").style=n,this.chatmsg.startspeaking=!1,this.textnow==this.chatmsg.content&&(document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.silent+".gif",this._animating=!1,clearTimeout(this.updater))}else this.textnow!=this.chatmsg.content&&(" "!=this.chatmsg.content.charAt(this.textnow.length)&&(this.blipChannels[this.currentBlipChannel].play(),this.currentBlipChannel++,this.currentBlipChannel%=this.blipChannels.length),this.textnow=this.chatmsg.content.substring(0,this.textnow.length+1),document.getElementById("client_inner_chat").innerHTML=this.textnow,this.textnow==this.chatmsg.content&&(this.textTimer=0,this._animating=!1,document.getElementById("client_char").src=l+"characters/"+escape(this.chatmsg.name)+"/"+this.chatmsg.silent+".gif",clearTimeout(this.updater)));!this.sfxplayed&&this.chatmsg.snddelay+this.shoutTimer>=this.textTimer&&(this.sfxaudio.pause(),this.sfxplayed=1,"0"!=this.chatmsg.sound&&"1"!=this.chatmsg.sound&&(this.sfxaudio.src=l+"sounds/general/"+escape(this.chatmsg.sound)+".wav",this.sfxaudio.play())),this.textTimer=this.textTimer+65}}]),e}(),y=function(){function e(){c(this,e)}return i(e,null,[{key:"parse",value:function(e){var t={section:/^\s*\[\s*([^\]]*)\s*\]\s*$/,param:/^\s*([\w\.\-\_]+)\s*=\s*(.*?)\s*$/,comment:/^\s*;.*$/},n={},i=null;return e.split(/\r\n|\r|\n/).forEach(function(e){if(!t.comment.test(e)&&0!=e.length)if(t.param.test(e)){var c=e.match(t.param);i?n[i][c[1]]=c[2]:n[c[1]]=c[2]}else if(t.section.test(e)){var a=e.match(t.section);n[a[1]]={},i=a[1]}}),n}}]),e}();function v(e){13==e.keyCode&&(te.sendOOC(document.getElementById("client_oocinputbox").value),document.getElementById("client_oocinputbox").value="")}function _(e){if(13==e.keyCode){var t=te.me(),n=te.myEmote(),i=te.myEvidence(),c=te.flip?1:0,a=document.getElementById("textcolor").value,o="0",s="0";document.getElementById("sendsfx").checked&&(o=n.sfx,s=n.sfxdelay),te.sendIC(n.speaking,t.name,n.silent,document.getElementById("client_inputbox").value,t.side,o,n.zoom,s,h,i,c,u,a)}}function E(e){var t=document.getElementById("client_musiclist").value;te.sendMusicChange(t)}function I(e){var t=e.textContent;te.sendMusicChange(t)}function b(){ne.music.volume=document.getElementById("client_mvolume").value/100}function B(){ne.sfxaudio.volume=document.getElementById("client_svolume").value/100}function k(){ne.setBlipVolume(document.getElementById("client_bvolume").value/100)}function w(e){te.sendLeaveRoom(),document.getElementById("client_charselect").style.display="block",document.getElementById("client_emo").innerHTML=""}function C(e){return e.onerror="",e.src="misc/placeholder.gif",!0}function x(e){return e.onerror="",e.src="/misc/placeholder.png",!0}function T(e){var t=new Image;return t.src=e,0!=t.height}function M(e){var t,n=ne.bgFolder();switch(document.getElementById("client_fg").style.display="none",document.getElementById("client_bench").style.display="none",e){case"def":document.getElementById("client_court").src=n+"defenseempty.png",document.getElementById("client_bench").style.display="block",T(n+"defensedesk.png")?document.getElementById("client_bench").src=n+"defensedesk.png":document.getElementById("client_bench").src=n+"bancodefensa.png",t="defense";break;case"pro":document.getElementById("client_court").src=n+"prosecutorempty.png",document.getElementById("client_bench").style.display="block",T(n+"defensedesk.png")?document.getElementById("client_bench").src=n+"prosecutiondesk.png":document.getElementById("client_bench").src=n+"bancoacusacion.png",t="prosecution";break;case"hld":document.getElementById("client_court").src=n+"helperstand.png",t="defense";break;case"hlp":document.getElementById("client_court").src=n+"prohelperstand.png",t="prosecution";break;case"wit":document.getElementById("client_court").src=n+"witnessempty.png",document.getElementById("client_bench").style.display="block",document.getElementById("client_bench").src=n+"estrado.png",t="prosecution";break;case"jud":document.getElementById("client_court").src=n+"judgestand.png",t="prosecution"}5==ne.chatmsg.type&&(document.getElementById("client_bench").style.display="none",document.getElementById("client_court").src=l+"themes/default/"+t+"_speedlines.gif")}function N(){te.cleanup(),(te=new p(o))&&(s="join",document.getElementById("client_error").style.display="none")}function O(){te.joinServer()}function S(e){var t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"",n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:new Date,i=document.createElement("p"),c=document.createElement("span");if(c.id="iclog_name",c.appendChild(document.createTextNode(t)),i.appendChild(c),i.appendChild(document.createTextNode(e)),g.getMinutes()!==n.getMinutes()){var a=document.createElement("span");a.id="iclog_time",a.innerText=n.toLocaleTimeString(void 0,{hour:"numeric",minute:"2-digit"}),i.appendChild(a)}var o=document.getElementById("client_log");o.appendChild(i),o.scrollTop>o.scrollHeight-600&&(o.scrollTop=o.scrollHeight),g=new Date}function L(e){e<1e3?te.sendCharacter(e):(document.getElementById("client_charselect").style.display="none",document.getElementById("client_inputbox").style.display="none",document.getElementById("client_emo").style.display="none")}function A(e){-1!=te.selectedEmote&&(document.getElementById("emo_"+te.selectedEmote).src=te.myEmote().button_off),te.selectedEmote=e,document.getElementById("emo_"+e).src=te.myEmote().button_on}function P(e){if(te.selectedEvidence!=e){te.selectedEvidence>0&&(document.getElementById("evi_"+te.selectedEvidence).className="client_button"),document.getElementById("evi_"+e).className="client_button dark",te.selectedEvidence=e,document.getElementById("evi_name").value=te.evidences[e-1].name,document.getElementById("evi_desc").value=te.evidences[e-1].desc;var t=V("evi_select",te.evidences[e-1].filename);document.getElementById("evi_select").selectedIndex=t,0==t&&(document.getElementById("evi_filename").value=te.evidences[e-1].filename),F(),document.getElementById("evi_add").className="client_button hover_button inactive",document.getElementById("evi_edit").className="client_button hover_button",document.getElementById("evi_cancel").className="client_button hover_button",document.getElementById("evi_del").className="client_button hover_button"}else R()}function D(){var e=document.getElementById("evi_select");te.sendPE(document.getElementById("evi_name").value,document.getElementById("evi_desc").value,0==e.selectedIndex?document.getElementById("evi_filename").value:e.options[e.selectedIndex].text),R()}function H(){var e=document.getElementById("evi_select"),t=parseInt(te.selectedEvidence)-1;te.sendEE(t,document.getElementById("evi_name").value,document.getElementById("evi_desc").value,0==e.selectedIndex?document.getElementById("evi_filename").value:e.options[e.selectedIndex].text),R()}function j(){var e=parseInt(te.selectedEvidence)-1;te.sendDE(e),R()}function R(){te.selectedEvidence>0&&(document.getElementById("evi_"+te.selectedEvidence).className="client_button"),te.selectedEvidence=0,document.getElementById("evi_select").selectedIndex=0,F(),document.getElementById("evi_filename").value="",document.getElementById("evi_name").value="",document.getElementById("evi_desc").value="",document.getElementById("evi_icon").style.backgroundImage="url('misc/empty.png')",document.getElementById("evi_add").className="client_button hover_button",document.getElementById("evi_edit").className="client_button hover_button inactive",document.getElementById("evi_cancel").className="client_button hover_button inactive",document.getElementById("evi_del").className="client_button hover_button inactive"}function V(e,t){for(var n=document.getElementById(e),i=1;i<n.length;++i)if(n.options[i].value==t)return i;return 0}function F(){var e=document.getElementById("evi_select"),t=document.getElementById("evi_filename"),n=document.getElementById("evi_icon");0==e.selectedIndex?(t.style.display="initial",n.style.backgroundImage="url('"+l+"evidence/"+t.value+"')"):(t.style.display="none",n.style.backgroundImage="url('"+l+"evidence/"+e.value+"')")}function U(){var e="",t=document.getElementById("bg_select"),n=document.getElementById("bg_command").value;e=0==t.selectedIndex?document.getElementById("bg_filename").value:t.value,te.sendOOC("/"+n.replace("$1",e))}function z(){var e=document.getElementById("bg_select"),t=document.getElementById("bg_filename"),n=document.getElementById("bg_preview");0==e.selectedIndex?(t.style.display="initial",n.src=l+"background/"+t.value+"/defenseempty.png"):(t.style.display="none",n.src=l+"background/"+e.value+"/defenseempty.png")}function X(e){e==u?(document.getElementById("button_effect_"+e).className="client_button",u=0):(document.getElementById("button_effect_"+e).className="client_button dark",u&&(document.getElementById("button_effect_"+u).className="client_button"),u=e)}function G(){te.flip?document.getElementById("button_flip").className="client_button":document.getElementById("button_flip").className="client_button dark",te.flip=!te.flip}function q(){te.presentable?document.getElementById("button_present").className="client_button":document.getElementById("button_present").className="client_button dark",te.presentable=!te.presentable}function K(e){e!=m&&(document.getElementById("menu_"+e).className="menu_icon active",document.getElementById("content_"+e).className="menu_content active",document.getElementById("menu_"+m).className="menu_icon",document.getElementById("content_"+m).className="menu_content",m=e)}function W(e){e==h?(document.getElementById("button_"+e).className="client_button",h=0):(document.getElementById("button_"+e).className="client_button dark",h&&(document.getElementById("button_"+h).className="client_button"),h=e)}function Z(e){return e.replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/"/g,"&quot;").replace(/'/g,"&#039;")}function J(e){return e.replace(/#/g,"<pound>").replace(/&/g,"<and>").replace(/%/g,"<percent>").replace(/\$/g,"<dollar>")}function Q(e){return e.replace(/<pound>/g,"#").replace(/<and>/g,"&").replace(/<percent>/g,"%").replace(/<dollar>/g,"$")}function Y(e){var t=document.getElementById("client_encoding").value;if("unicode"==t)return e.replace(/[^\0-~]/g,function(e){return"\\u"+("000"+e.charCodeAt().toString(16)).slice(-4)});if("utf16"==t){for(var n=new ArrayBuffer(2*e.length),i=new Uint16Array(n),c=0,a=e.length;c<a;c++)i[c]=e.charCodeAt(c);return String(i)}return e}function ee(e){var t=document.getElementById("client_decoding").value;return"unicode"==t?e.replace(/\\u([\d\w]{1,})/gi,function(e,t){return String.fromCharCode(parseInt(t,16))}):"utf16"==t?String.fromCharCode.apply(null,new Uint16Array(e.split(","))):e}window.onOOCEnter=v,window.onEnter=_,window.musiclist_click=E,window.area_click=I,window.changeMusicVolume=b,window.changeSFXVolume=B,window.changeBlipVolume=k,window.changeCharacter=w,window.imgError=C,window.demoError=x,window.ReconnectButton=N,window.RetryButton=O,window.pickchar=L,window.pickemotion=A,window.pickevidence=P,window.addevidence=D,window.editevidence=H,window.delevidence=j,window.cancelevidence=R,window.getIndexFromSelect=V,window.updateEvidenceIcon=F,window.changeBackgroundOOC=U,window.updateBackgroundPreview=z,window.toggleaffect=X,window.toggleflip=G,window.togglepresent=q,window.togglemenu=K,window.toggleshout=W,void 0===String.prototype.trim&&(String.prototype.trim=function(){return String(this).replace(/^\s+|\s+$/g,"")}),String.prototype.hashCode=function(){var e,t=0;if(0===this.length)return t;for(e=0;e<this.length;e++)t=(t<<5)-t+this.charCodeAt(e),t|=0;return t};var te=new p(o),ne=new f;$(document).ready(function(){te.initialObservBBCode(),te.loadResources()})}});
//# sourceMappingURL=client.b.js.map \ No newline at end of file
diff --git a/webAO/client.b.js.map b/webAO/client.b.js.map
index b6efd58..1f14ef6 100644
--- a/webAO/client.b.js.map
+++ b/webAO/client.b.js.map
@@ -1 +1 @@
-{"version":3,"sources":["webpack:///webpack/bootstrap","webpack:///./webAO/client.js"],"names":["installedModules","__webpack_require__","moduleId","exports","module","i","l","modules","call","m","c","d","name","getter","o","Object","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","prototype","hasOwnProperty","p","s","onOOCEnter","onEnter","musiclist_click","area_click","changeMusicVolume","changeSFXVolume","changeBlipVolume","changeCharacter","imgError","demoError","ReconnectButton","RetryButton","pickchar","pickemotion","pickevidence","addevidence","editevidence","delevidence","cancelevidence","getIndexFromSelect","updateEvidenceIcon","changeBackgroundOOC","updateBackgroundPreview","toggleaffect","toggleflip","togglepresent","togglemenu","toggleshout","queryDict","location","search","substr","split","forEach","item","serverIP","ip","AO_HOST","asset","MUSIC_HOST","oldLoading","test","navigator","userAgent","selectedEffect","selectedMenu","selectedShout","lastICMessageTime","Date","Client","address","_this","this","_classCallCheck","serv","WebSocket","onopen","evt","onOpen","onclose","onClose","onmessage","onMessage","onerror","onError","flip","presentable","playerID","charID","chars","emotes","evidences","selectedEmote","selectedEvidence","checkUpdater","musicList","handlers","MS","args","handleMS","CT","handleCT","MC","handleMC","RMC","handleRMC","CI","handleCI","SC","handleSC","EI","handleEI","LE","handleLE","EM","handleEM","SM","handleSM","music","handlemusic","DONE","handleDONE","BN","handleBN","NBG","handleNBG","HP","handleHP","ID","handleID","PN","handlePN","SI","handleSI","CharsCheck","handleCharsCheck","PV","handlePV","CHECK","_lastTimeICReceived","message","send","escapeChat","encodeChat","speaking","silent","side","ssfxname","zoom","ssfxdelay","objection","evidence","flash","color","desc","img","id","track","_this2","hashCode","setInterval","sendCheck","evidence_select","document","getElementById","add","Option","evidence_arr","length","background_select","background_arr","target","MutationObserver","mutations","mutation","children","addedNodes","node","tagName","style","getAttribute","hasAttribute","backgroundColor","observe","attributes","childList","character","song","e","display","client","joinServer","console","error","reason","code","textContent","cleanup","msg","data","debug","header","handler","warn","close","clearInterval","viewport","chatmsg","content","innerHTML","preanim","escape","nameplate","estring","replace","decodeBBCode","escapeHtml","decodeChat","unescapeChat","sound","type","snddelay","isnew","className","resetICParams","say","oocLog","scrollTop","scrollHeight","pause","src","play","appendICLog","Audio","totime","offset","getTime","addEventListener","currentTime","parseFloat","toFixed","chargs","icon","arg","filename","evidence_box","hmusiclist","newentry","createElement","text","options","flagAudio","newarea","onclick","appendChild","area_box","audio_title","lastChild","insertBefore","firstChild","removeChild","bgname","bg_index","selectedIndex","clip","tr","td","icon_chosen","thispick","changeBackground","me","xhr","XMLHttpRequest","open","responseType","onload","status","linifile","responseText","pinifile","INI","parse","Options","Emotions","number","emoteinfo","esfx","esfxd","SoundN","SoundT","sfx","sfxdelay","button_off","button_on","Viewport","textnow","startpreanim","startspeaking","preanimdelay","blip","volume","blipChannels","Array","currentBlipChannel","sfxaudio","sfxplayed","updater","shoutTimer","textTimer","_animating","clearTimeout","getAnimLength","initUpdater","animdelay","parseInt","setTimeout","updateText","callback","request","arr","Uint8Array","response","duration","String","fromCharCode","delay","_this3","transform","opacity","height","shout","1","2","3","$","effect","direction","backgroundImage","right","left","animate","marginLeft","marginRight","toggle","fontSize","offsetHeight","stylecolor","0","4","5","6","charAt","substring","regex","section","param","comment","line","match","event","keyCode","sendOOC","mychar","myemo","myEmote","myevi","myEvidence","myflip","mycolor","checked","sendIC","playtrack","sendMusicChange","el","setBlipVolume","sendLeaveRoom","image","ImageExist","url","Image","position","standname","bgfolder","bgFolder","toadd","arguments","undefined","time","entry","nameField","createTextNode","getMinutes","timeStamp","innerText","toLocaleTimeString","hour","minute","clientLog","ccharacter","sendCharacter","emo","icon_id","sendPE","sendEE","sendDE","select_box","select_element","evidence_filename","evidence_iconbox","bg_command","background_filename","background_preview","menu","unsafe","selectedEncoding","ch","charCodeAt","toString","slice","buffer","ArrayBuffer","result","Uint16Array","strLen","selectedDecoding","group","apply","window","trim","hash","ready","initialObservBBCode","loadResources"],"mappings":"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","file":"client.b.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = 3);\n","/*\r\n * Glorious webAO\r\n * made by sD, refactored by oldmud0\r\n * credits to aleks for original idea and source\r\n*/\r\n\r\nlet queryDict = {};\r\nlocation.search.substr(1).split(\"&\").forEach(function(item) {\r\n\tqueryDict[item.split(\"=\")[0]] = item.split(\"=\")[1]\r\n});\r\n\r\n/* Server magic */\r\n\r\nconst serverIP = queryDict.ip;\r\nlet mode = queryDict.mode;\r\n\r\nconst AO_HOST = queryDict.asset || \"http://assets.aceattorneyonline.com/base/\";\r\nconst MUSIC_HOST = AO_HOST + \"sounds/music/\";\r\nconst BAR_WIDTH = 90;\r\nconst BAR_HEIGHT = 20;\r\nconst CHAR_SELECT_WIDTH = 8;\r\nconst UPDATE_INTERVAL = 65;\r\n\r\nlet oldLoading = false;\r\nif (/Android|webOS|iPhone|iPad|iPod|BlackBerry|BB|PlayBook|IEMobile|Windows Phone|Kindle|Silk|Opera Mini/i.test(navigator.userAgent)) {\r\n\toldLoading = true;\r\n}\r\n\r\nlet selectedEffect = 0;\r\nlet selectedMenu = 1;\r\nlet selectedShout = 0;\r\nlet lastICMessageTime = new Date(0);\r\n\r\nclass Client {\r\n\tconstructor(address) {\r\n\t\tthis.serv = new WebSocket(\"ws://\" + address);\r\n\r\n\t\tthis.serv.onopen = (evt) => this.onOpen(evt);\r\n\t\tthis.serv.onclose = (evt) => this.onClose(evt);\r\n\t\tthis.serv.onmessage = (evt) => this.onMessage(evt);\r\n\t\tthis.serv.onerror = (evt) => this.onError(evt);\r\n\t\t\r\n\t\tthis.flip = false;\r\n\t\tthis.presentable = false;\r\n\r\n\t\tthis.playerID = 1;\r\n\t\tthis.charID = -1;\r\n\r\n\t\tthis.chars = [];\r\n\t\tthis.emotes = [];\t\t\r\n\t\tthis.evidences = [];\r\n\r\n\t\tthis.selectedEmote = -1;\r\n\t\tthis.selectedEvidence = 0;\r\n\r\n\t\tthis.checkUpdater = null;\r\n\r\n\t\t// Only used for RMC/`music` packets, not EM/SM/MC packets.\r\n\t\tthis.musicList = Object();\r\n\r\n\t\tthis.handlers = {\r\n\t\t\t\"MS\": (args) => this.handleMS(args),\r\n\t\t\t\"CT\": (args) => this.handleCT(args),\r\n\t\t\t\"MC\": (args) => this.handleMC(args),\r\n\t\t\t\"RMC\": (args) => this.handleRMC(args),\r\n\t\t\t\"CI\": (args) => this.handleCI(args),\r\n\t\t\t\"SC\": (args) => this.handleSC(args),\r\n\t\t\t\"EI\": (args) => this.handleEI(args),\r\n\t\t\t\"LE\": (args) => this.handleLE(args),\r\n\t\t\t\"EM\": (args) => this.handleEM(args),\r\n\t\t\t\"SM\": (args) => this.handleSM(args),\r\n\t\t\t\"music\": (args) => this.handlemusic(args),\r\n\t\t\t\"DONE\": (args) => this.handleDONE(args),\r\n\t\t\t\"BN\": (args) => this.handleBN(args),\r\n\t\t\t\"NBG\": (args) => this.handleNBG(args),\r\n\t\t\t\"HP\": (args) => this.handleHP(args),\r\n\t\t\t\"ID\": (args) => this.handleID(args),\r\n\t\t\t\"PN\": (args) => this.handlePN(args),\r\n\t\t\t\"SI\": (args) => this.handleSI(args),\r\n\t\t\t\"CharsCheck\": (args) => this.handleCharsCheck(args),\r\n\t\t\t\"PV\": (args) => this.handlePV(args),\r\n\t\t\t\"CHECK\": (args) => {}\r\n\t\t}\r\n\r\n\t\tthis._lastTimeICReceived = new Date(0);\r\n\t}\r\n\r\n\t/**\r\n\t * Gets the current player's character.\r\n\t */\r\n\tme() {\r\n\t\treturn this.chars[this.charID];\r\n\t}\r\n\r\n\t/**\r\n\t * Gets the player's currently selected emote.\r\n\t */\r\n\tmyEmote() {\r\n\t\treturn this.emotes[this.selectedEmote];\r\n\t}\r\n\t\r\n\t/**\r\n\t * Gets the player's currently selected evidence if presentable.\r\n\t */\r\n\tmyEvidence() {\r\n\t\treturn (this.presentable)? this.selectedEvidence : 0;\r\n\t}\r\n\r\n\t/**\r\n\t * Sends an out-of-character chat message.\r\n\t * @param {string} message the message to send\r\n\t */\r\n\tsendOOC(message) {\r\n\t\tthis.serv.send(`CT#web${this.playerID}#${escapeChat(encodeChat(message))}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Sends an in-character chat message.\r\n\t * @param {string} speaking who is speaking\r\n\t * @param {string} name the name of the current character\r\n\t * @param {string} silent whether or not it's silent\r\n\t * @param {string} message the message to be sent\r\n\t * @param {string} side the name of the side in the background\r\n\t * @param {string} ssfxname the name of the sound effect\r\n\t * @param {string} zoom whether or not to zoom\r\n\t * @param {string} ssfxdelay the delay (in milliseconds) to play the sound effect\r\n\t * @param {string} objection the number of the shout to play\r\n\t */\r\n\tsendIC(speaking, name, silent, message, side, ssfxname, zoom, ssfxdelay, objection, evidence, flip, flash, color) {\r\n\t\tthis.serv.send(\r\n\t\t\t`MS#chat#${speaking}#${name}#${silent}` +\r\n\t\t\t`#${escapeChat(encodeChat(message))}#${side}#${ssfxname}#${zoom}` +\r\n\t\t\t`#${this.charID}#${ssfxdelay}#${selectedShout}#${evidence}#${flip}#${flash}#${color}#%`\r\n\t\t);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends add evidence command.\r\n\t * @param {string} evidence name\r\n\t * @param {string} evidence description\r\n\t * @param {string} evidence image filename\r\n\t */\r\n\tsendPE(name, desc, img) {\r\n\t\tthis.serv.send(`PE#${escapeChat(encodeChat(name))}#${escapeChat(encodeChat(desc))}#${img}#%`);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends edit evidence command.\r\n\t * @param {string} evidence id\r\n\t * @param {string} evidence name\r\n\t * @param {string} evidence description\r\n\t * @param {string} evidence image filename\r\n\t */\r\n\tsendEE(id, name, desc, img) {\r\n\t\tthis.serv.send(`EE#${id}#${escapeChat(encodeChat(name))}#${escapeChat(encodeChat(desc))}#${img}#%`);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends delete evidence command.\r\n\t * @param {string} evidence id\r\n\t */\r\n\tsendDE(id, name, desc, img) {\r\n\t\tthis.serv.send(`DE#${id}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to change the music to the specified track.\r\n\t * @param {string} track the track ID\r\n\t */\r\n\tsendMusicChange(track) {\r\n\t\tthis.serv.send(`MC#${track}#${this.charID}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to leave the room and free the character slot.\r\n\t * \r\n\t * Note: This packet is undocumented. It is not implemented by\r\n\t * either the AO2 client or tsuserver.\r\n\t */\r\n\tsendLeaveRoom() {\r\n\t\tthis.serv.send(\"FC#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Begins the handshake process by sending an identifier\r\n\t * to the server.\r\n\t */\r\n\tjoinServer() {\r\n\t\tthis.serv.send(`HI#${navigator.userAgent.hashCode()}#%`);\r\n\t\tthis.serv.send(\"ID#webAO#2.4.5#%\");\r\n\t\tthis.checkUpdater = setInterval(() => this.sendCheck(), 5000);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Load game resources.\r\n\t */\r\n\tloadResources() {\r\n\t\t// Load evidence array to select\r\n\t\tvar evidence_select = document.getElementById(\"evi_select\");\r\n\t\tevidence_select.add(new Option(\"Custom\", 0));\r\n\t\tfor(let i = 1; i <= evidence_arr.length; i++) {\r\n\t\t evidence_select.add(new Option(evidence_arr[i - 1]));\r\n\t\t}\t\t\r\n\t\t// Load background array to select\r\n\t\tvar background_select = document.getElementById(\"bg_select\");\r\n\t\tbackground_select.add(new Option(\"Custom\", 0));\r\n\t\tfor(let i = 1; i <= background_arr.length; i++) {\r\n\t\t background_select.add(new Option(background_arr[i - 1]));\r\n\t\t}\r\n\t\t// TODO: Cache some resources\r\n\t\t\r\n\t}\r\n\t\r\n\t/**\r\n\t * Create observer to detect BBCode elements\r\n\t * then manipulate them.\r\n\t */\r\n\tinitialObservBBCode() {\r\n\t\tvar target = document.getElementById(\"client_inner_chat\");\r\n\t\tvar observer = new MutationObserver(function(mutations) {\r\n\t\t mutations.forEach(function(mutation) {\r\n\t\t\tvar children = mutation.addedNodes;\r\n\t\t\tif (children !== null) {\r\n\t\t\t\tchildren.forEach( function(node) {\r\n\t\t\t\t\tif (node.tagName == \"C\") {\r\n\t\t\t\t\t\tnode.style.color = node.getAttribute(\"a\");\r\n\t\t\t\t\t} else if(node.tagName == \"M\"){\r\n\t\t\t\t\t\tif (node.hasAttribute('a')) {\r\n\t\t\t\t\t\t\tnode.style.backgroundColor = node.getAttribute(\"a\");\r\n\t\t\t\t\t\t} else {\r\n\t\t\t\t\t\t\tnode.style.backgroundColor = \"yellow\";\r\n\t\t\t\t\t\t\tnode.style.color = \"black\";\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t});\r\n\t\t\t}\r\n\t\t }); \r\n\t\t});\r\n\t\tvar config = {attributes: true,childList: true};\r\n\t\tobserver.observe(target,config);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to play as a specified character.\r\n\t * @param {number} character the character ID\r\n\t */\r\n\tsendCharacter(character) {\r\n\t\tthis.serv.send(`CC#${this.playerID}#${character}#web#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to select a music track.\r\n\t * @param {number?} song the song to be played\r\n\t */\r\n\tsendMusic(song) {\r\n\t\tthis.serv.send(`MC#${song}`);\r\n\t}\r\n\r\n\t/**\r\n\t * Sends a keepalive packet.\r\n\t */\r\n\tsendCheck() {\r\n\t\tthis.serv.send(`CH#${this.charID}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when a connection is established to the server.\r\n\t */\r\n\tonOpen(e) {\r\n\t\t// XXX: Why does watching mean just SITTING there and doing nothing?\r\n\t\tif (mode === \"watch\") {\r\n\t\t\tdocument.getElementById(\"client_loading\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\t} else {\r\n\t\t\tclient.joinServer();\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when the connection to the server closes.\r\n\t * @param {CloseEvent} e\r\n\t */\r\n\tonClose(e) {\r\n\t\tconsole.error(`The connection was closed: ${e.reason} (${e.code})`);\r\n\t\tif (e.code !== 1001) {\r\n\t\t\tdocument.getElementById(\"client_error\").style.display = \"block\";\r\n\t\t\tdocument.getElementById(\"error_id\").textContent = e.code;\r\n\t\t\tthis.cleanup();\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when a packet is received from the server.\r\n\t * @param {MessageEvent} e\r\n\t */\r\n\tonMessage(e) {\r\n\t\tlet msg = e.data;\r\n\t\tconsole.debug(msg);\r\n\t\tlet lines = msg.split('%');\r\n\t\tlet args = lines[0].split('#');\r\n\t\tlet header = args[0];\r\n\t\tlet handler = this.handlers[header];\r\n\t\tif (typeof handler !== \"undefined\") {\r\n\t\t\thandler(args);\r\n\t\t} else {\r\n\t\t\tconsole.warn(`Invalid packet header ${header}`);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when an network error occurs.\r\n\t * @param {ErrorEvent} e \r\n\t */\r\n\tonError(e) {\r\n\t\tconsole.error(`A network error occurred: ${e.reason} (${e.code})`);\r\n\t\tdocument.getElementById(\"client_error\").style.display = \"block\";\r\n\t\tdocument.getElementById(\"error_id\").textContent = e.code;\r\n\t\tthis.cleanup();\r\n\t}\r\n\r\n\tcleanup() {\r\n\t\ttry {\r\n\t\t\tthis.serv.close(1001);\r\n\t\t} catch (e) {\r\n\t\t\t// I don't care if this errors\r\n\t\t}\r\n\t\tclearInterval(this.checkUpdater);\r\n\t}\r\n\r\n\t/**\r\n\t * Handles an in-character chat message.\r\n\t * @param {*} args packet arguments\r\n\t */\r\n\thandleMS(args) {\r\n\t\t// TODO: this if-statement might be a bug.\r\n\t\tif (args[4] != viewport.chatmsg.content) {\r\n\t\t\tdocument.getElementById(\"client_inner_chat\").innerHTML = \"\";\r\n\t\t\tlet chatmsg = {\r\n\t\t\t\t// pre: escape(args[2]),\r\n\t\t\t\tcharacter: -1, // Will do a linear search\r\n\t\t\t\tpreanim: escape(args[2]), // XXX: why again?\r\n\t\t\t\tnameplate: args[3], // TODO: parse INI to get this info\r\n\t\t\t\tname: args[3],\r\n\t\t\t\tspeaking: \"(b)\" + escape(args[4]),\r\n\t\t\t\tsilent: \"(a)\" + escape(args[4]),\r\n\t\t\t\tcontent: decodeBBCode(escapeHtml(decodeChat(unescapeChat(args[5])))), // Escape HTML tag, Use BBCode Only!\r\n\t\t\t\tside: args[6],\r\n\t\t\t\tsound: escape(args[7]),\r\n\t\t\t\ttype: args[8],\r\n\t\t\t\t// charid: args[9],\r\n\t\t\t\tsnddelay: args[10],\r\n\t\t\t\tobjection: args[11],\r\n\t\t\t\tevidence: args[12],\r\n\t\t\t\tflip: args[13],\r\n\t\t\t\tflash: args[14],\r\n\t\t\t\tcolor: args[15],\r\n\t\t\t\tisnew: true,\r\n\t\t\t};\r\n\r\n\t\t\t// The dreaded linear search...\r\n\t\t\tfor (let i = 0; i < this.chars.length; i++) {\r\n\t\t\t\tif (this.chars[i].name == args[3]) {\r\n\t\t\t\t\tchatmsg.character = i;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (chatmsg.character == this.charID) {\r\n\t\t\t\tresetICParams();\r\n\t\t\t}\r\n\r\n\t\t\tviewport.say(chatmsg);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles an out-of-character chat message.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCT(args) {\r\n\t\tconst oocLog = document.getElementById(\"client_ooclog\");\r\n\t\toocLog.innerHTML += `${decodeChat(unescapeChat(args[1]))}: ${decodeChat(unescapeChat(args[2]))}\\r\\n`;\r\n\t\tif (oocLog.scrollTop > oocLog.scrollHeight - 60) {\r\n\t\t\toocLog.scrollTop = oocLog.scrollHeight;\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a music change to an arbitrary resource.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleMC(args) {\r\n\t\tconst music = viewport.music;\r\n\t\tmusic.pause();\r\n\t\tmusic.src = MUSIC_HOST + args[1];\r\n\t\tmusic.play();\r\n\t\tif (args[2] >= 0) {\r\n\t\t\tlet musicname = this.chars[args[2]].name;\r\n\t\t\tappendICLog(`${musicname} changed music to ${args[1]}`);\r\n\t\t} else {\r\n\t\t\tappendICLog(`The music was changed to ${args[1]}`);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a music change to an arbitrary resource, with an offset in seconds.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleRMC(args) {\r\n\t\tviewport.music.pause();\r\n\t\tviewport.music = new Audio(this.musicList[args[1]]);\r\n\t\tconst music = viewport.music;\r\n\t\t// Music offset + drift from song loading\r\n\t\tmusic.totime = args[1];\r\n\t\tmusic.offset = new Date().getTime() / 1000;\r\n\t\tmusic.addEventListener('loadedmetadata', function() {\r\n\t\t\tmusic.currentTime += parseFloat(music.totime + (new Date().getTime() / 1000 - music.offset)).toFixed(3);\r\n\t\t\tmusic.play();\r\n\t\t}, false);\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming character information, bundling multiple characters\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCI(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Character \" + args[1];\r\n\t\tthis.serv.send(\"AN#\" + ((args[1] / 10) + 1) + \"#%\");\r\n\t\tfor (let i = 2; i < args.length - 1; i++) {\r\n\t\t\tif (i % 2 == 0) {\r\n\t\t\t\tlet chargs = args[i].split(\"&\");\r\n\t\t\t\tthis.chars[args[i - 1]] = {\r\n\t\t\t\t\t\"name\": chargs[0],\r\n\t\t\t\t\t\"desc\": chargs[1],\r\n\t\t\t\t\t\"evidence\": chargs[3],\r\n\t\t\t\t\t\"icon\": AO_HOST + \"characters/\" + escape(chargs[0]) + \"/char_icon.png\"\r\n\t\t\t\t};\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming character information, containing only one character\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSC(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Characters\";\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\tlet chargs = args[i].split(\"&\");\r\n\t\t\tthis.chars[i - 1] = {\r\n\t\t\t\t\"name\": chargs[0],\r\n\t\t\t\t\"desc\": chargs[1],\r\n\t\t\t\t\"evidence\": chargs[3],\r\n\t\t\t\t\"icon\": AO_HOST + \"characters/\" + escape(chargs[0]) + \"/char_icon.png\"\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.serv.send(\"RM#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming evidence information, containing only one evidence\r\n\t * item per packet.\r\n\t * \r\n\t * Mostly unimplemented in webAO.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleEI(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Evidence \" + args[1];\r\n\t\t//serv.send(\"AE#\" + (args[1] + 1) + \"#%\");\r\n\t\tthis.serv.send(\"RM#%\");\r\n\t}\r\n\t\r\n\t/**\r\n\t * Handles incoming evidence list, all evidences at once\r\n\t * item per packet.\r\n\t * \r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleLE(args) {\r\n\t\tthis.evidences = [];\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\tvar arg = args[i].split(\"&\");\r\n\t\t\tthis.evidences[i - 1] = {\r\n\t\t\t\t\"name\": escapeHtml(decodeChat(unescapeChat(arg[0]))),\r\n\t\t\t\t\"desc\": escapeHtml(decodeChat(unescapeChat(arg[1]))),\r\n\t\t\t\t\"filename\": escape(arg[2]),\r\n\t\t\t\t\"icon\": AO_HOST + \"evidence/\" + escape(arg[2])\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\tvar evidence_box = document.getElementById(\"evidences\");\r\n\t\tevidence_box.innerHTML = \"\";\r\n\t\tfor(let i = 1; i <= this.evidences.length; i++){\r\n\t\t\tevidence_box.innerHTML += '<img src=\"' + this.evidences[i - 1].icon + \r\n\t\t\t\t'\" id=\"evi_' + i +'\" alt=\"' + this.evidences[i - 1].name +\r\n\t\t\t\t'\" class=\"client_button\" ' +\r\n\t\t\t\t'onclick=\"pickevidence('+ i +')\">';\t\t\t\t\t\t\t\t\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing multiple entries\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleEM(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Music \" + args[1];\r\n\t\tthis.serv.send(\"AM#\" + ((args[1] / 10) + 1) + \"#%\");\r\n\t\tlet hmusiclist = document.getElementById(\"client_musiclist\");\r\n\t\tfor (let i = 2; i < args.length - 1; i++) {\r\n\t\t\tif (i % 2 == 0) {\r\n\t\t\t\tlet newentry = document.createElement(\"OPTION\");\r\n\t\t\t\tnewentry.text = args[i];\r\n\t\t\t\thmusiclist.options.add(newentry);\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing only one entry\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSM(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Music \";\r\n\t\tlet hmusiclist = document.getElementById(\"client_musiclist\"), flagAudio = false;\r\n\t\t\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\t// Check when found the song for the first time\r\n\t\t\tif(/\\.(?:wav|mp3|mp4|ogg|mid)$/i.test(args[i]) && !flagAudio){\r\n\t\t\t\tflagAudio = true;\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tif(flagAudio) {\r\n\t\t\t\t// After reached the audio put everything in the music list\r\n\t\t\t\tlet newentry = document.createElement(\"OPTION\");\r\n\t\t\t\tnewentry.text = args[i];\r\n\t\t\t\thmusiclist.options.add(newentry);\r\n\t\t\t\r\n\t\t\t} else {\r\n\t\t\t\t// Create area button\r\n\t\t\t\tlet newarea = document.createElement(\"SPAN\");\r\n\t\t\t\tnewarea.className = \"location-box\";\r\n\t\t\t\tnewarea.textContent = args[i]; \r\n\t\t\t\tnewarea.onclick = function(){ area_click(this) };\r\n\t\t\t\tdocument.getElementById(\"areas\").appendChild(newarea);\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\t// Move first audio title from area box to music list\r\n\t\tlet area_box = document.getElementById(\"areas\");\r\n\t\tlet audio_title = document.createElement(\"OPTION\");\r\n\t\taudio_title.text = area_box.lastChild.textContent;\r\n\t\thmusiclist.insertBefore(audio_title, hmusiclist.firstChild);\r\n\t\tarea_box.removeChild(area_box.lastChild); // Remove from arae box\r\n\t\t\t\t\r\n\t\tthis.serv.send(\"RD#%\");\t\t\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing all entries\r\n\t * in the same packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandlemusic(args) {\r\n\t\tfor (let i = 0; i < args.length / 2; i++) {\r\n\t\t\tthis.musicList[args[2 * i]] = args[2 * i + 1];\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the handshake completion packet, meaning the player\r\n\t * is ready to select a character.\r\n\t * \r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleDONE(args) {\r\n\t\tdocument.getElementById(\"client_loading\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"block\";\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a background change.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleBN(args) {\r\n\t\tviewport.bgname = escape(args[1]);\r\n\t\tlet bg_index = getIndexFromSelect(\"bg_select\", escape(args[1]));\r\n\t\tdocument.getElementById(\"bg_select\").selectedIndex = bg_index;\r\n\t\tupdateBackgroundPreview();\r\n\t\tif(bg_index > 0){\r\n\t\t\tdocument.getElementById(\"bg_filename\").value = escape(args[1]);\r\n\t\t}\r\n\t\tdocument.getElementById(\"bg_preview\").src = AO_HOST + 'background/' + escape(args[1]) + \"/defenseempty.png\";\r\n\t\t\t\t\r\n\t}\r\n\r\n\thandleNBG(args) {\r\n\t\t// TODO (set by sD)\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a change in the health bars' states.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleHP(args) {\r\n\t\t// TODO (set by sD)\r\n\t\t// Also, this is broken.\r\n\t\tif (args[1] == 1) {\r\n\t\t\tdocument.getElementById(\"client_defense_hp\").style.clip = \"rect(0px,\" + BAR_WIDTH * args[2] / 10 + \"px,\" + BAR_HEIGHT + \"px,0px)\";\r\n\t\t} else {\r\n\t\t\tdocument.getElementById(\"client_prosecutor_hp\").style.clip = \"rect(0px,\" + BAR_WIDTH * args[2] / 10 + \"px,\" + BAR_HEIGHT + \"px,0px)\";\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Handles the issuance of a player ID by the server.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleID(args) {\r\n\t\tthis.playerID = args[1];\r\n\t}\r\n\r\n\thandlePN(args) {\r\n\t\tthis.serv.send(\"askchaa#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Received when the server announces its server info,\r\n\t * but we use it as a cue to begin retrieving characters.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSI(args) {\r\n\t\tif (oldLoading) {\r\n\t\t\tthis.serv.send(\"askchar2#%\");\r\n\t\t} else {\r\n\t\t\tthis.serv.send(\"RC#%\");\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the list of all used and vacant characters.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCharsCheck(args) {\r\n\t\tdocument.getElementById(\"client_chartable\").innerHTML = \"\";\r\n\t\tfor (let i = 0; i < this.chars.length; i++) {\r\n\t\t\tif (i % CHAR_SELECT_WIDTH == 0) {\r\n\t\t\t\tvar tr = document.createElement('TR');\r\n\t\t\t}\r\n\t\t\tlet td = document.createElement('TD');\r\n\t\t\tlet icon_chosen;\r\n\t\t\tlet thispick = this.chars[i].icon;\r\n\t\t\tif (args[i + 1] == \"-1\") {\r\n\t\t\t\ticon_chosen = \" dark\";\r\n\t\t\t} else {\r\n\t\t\t\ticon_chosen = \"\";\r\n\t\t\t}\r\n\t\t\ttd.innerHTML = `<img class='demothing${icon_chosen}' id='demo_${i}' ` +\r\n\t\t\t\t`src='${thispick}' alt='${this.chars[i].name}' onclick='pickchar(${i})' ` +\r\n\t\t\t\t`onerror='demoError(this);'>`;\r\n\t\t\ttr.appendChild(td);\r\n\t\t\tif (i % CHAR_SELECT_WIDTH == 0) {\r\n\t\t\t\tdocument.getElementById(\"client_chartable\").appendChild(tr);\r\n\t\t\t}\r\n\t\t}\r\n\t\tchangeBackground(\"def\");\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the server's assignment of a character for the player to use.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandlePV(args) {\r\n\t\tthis.charID = args[3];\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\tlet me = this.me();\r\n\t\tlet emotes = this.emotes;\r\n\t\tlet xhr = new XMLHttpRequest();\r\n\t\txhr.open('GET', AO_HOST + 'characters/' + escape(this.me().name) + '/char.ini', true);\r\n\t\txhr.responseType = 'text';\r\n\t\txhr.onload = function (e) {\r\n\t\t\tif (this.status == 200) {\r\n\t\t\t\tlet linifile = this.responseText;\r\n\t\t\t\tlet pinifile = INI.parse(linifile);\r\n\t\t\t\tme.side = pinifile.Options.side;\r\n\t\t\t\tfor (let i = 1; i < pinifile.Emotions.number; i++) {\r\n\t\t\t\t\tlet emoteinfo = pinifile.Emotions[i].split('#');\r\n\t\t\t\t\tlet esfx = \"0\";\r\n\t\t\t\t\tlet esfxd = \"0\";\r\n\t\t\t\t\tif (typeof pinifile.SoundN !== 'undefined') {\r\n\t\t\t\t\t\tesfx = pinifile.SoundN[i];\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (typeof pinifile.SoundT !== 'undefined') {\r\n\t\t\t\t\t\tesfxd = pinifile.SoundT[i];\r\n\t\t\t\t\t}\r\n\t\t\t\t\temotes[i] = {\r\n\t\t\t\t\t\tdesc: emoteinfo[0],\r\n\t\t\t\t\t\tspeaking: emoteinfo[1],\r\n\t\t\t\t\t\tsilent: emoteinfo[2],\r\n\t\t\t\t\t\tzoom: emoteinfo[3],\r\n\t\t\t\t\t\tsfx: esfx,\r\n\t\t\t\t\t\tsfxdelay: esfxd,\r\n\t\t\t\t\t\tbutton_off: AO_HOST + 'characters/' + escape(me.name) + '/emotions/button' + i + '_off.png',\r\n\t\t\t\t\t\tbutton_on: AO_HOST + 'characters/' + escape(me.name) + '/emotions/button' + i + '_on.png'\r\n\t\t\t\t\t};\r\n\t\t\t\t\tdocument.getElementById(\"client_emo\").innerHTML += \"<img src='\" + emotes[i].button_off + \"' id='emo_\" + i + \"' alt='\" + emotes[i].desc + \"' class='client_button' onclick='pickemotion(\" + i + \")'>\";\r\n\t\t\t\t}\r\n\t\t\t\tpickemotion(1);\r\n\t\t\t}\r\n\t\t};\r\n\t\txhr.send();\r\n\t}\t\t\r\n}\r\n\r\nclass Viewport {\r\n\tconstructor() {\r\n\t\tthis.textnow = \"\";\r\n\t\tthis.chatmsg = {\r\n\t\t\t\"isnew\": false,\r\n\t\t\t\"content\": \"\",\r\n\t\t\t\"objection\": \"0\",\r\n\t\t\t\"sound\": \"\",\r\n\t\t\t\"startpreanim\": false,\r\n\t\t\t\"startspeaking\": false,\r\n\t\t\t\"side\": null,\r\n\t\t\t\"color\": \"0\",\r\n\t\t\t\"snddelay\": 0,\r\n\t\t\t\"preanimdelay\": 0\r\n\t\t};\r\n\t\tthis.blip = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\tthis.blip.volume = 0.5;\r\n\r\n\t\t// Allocate multiple blip audio channels to make blips less jittery\r\n\r\n\t\t// TODO: read blip type (\"gender\") from ini\r\n\t\tthis.blipChannels = new Array(6);\r\n\t\tfor (let i = 0; i < this.blipChannels.length; i++) {\r\n\t\t\tthis.blipChannels[i] = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\t\tthis.blipChannels[i].volume = 0.5;\r\n\t\t}\r\n\t\tthis.currentBlipChannel = 0;\r\n\r\n\t\tthis.sfxaudio = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\tthis.sfxplayed = 0;\r\n\r\n\t\tthis.music = new Audio();\r\n\t\tthis.music.play();\r\n\r\n\t\tthis.updater = null;\r\n\r\n\t\tthis.bgname = \"gs4\";\r\n\r\n\t\tthis.shoutTimer = 0;\r\n\t\tthis.textTimer = 0;\r\n\r\n\t\tthis._animating = false;\r\n\t}\r\n\r\n\t/**\r\n\t * Returns whether or not the viewport is busy\r\n\t * performing a task (animating).\r\n\t */\r\n\tisAnimating() {\r\n\t\treturn this._animating;\r\n\t}\r\n\r\n\t/**\r\n\t * Sets the volume of the blip sound.\r\n\t * @param {number} volume\r\n\t */\r\n\tsetBlipVolume(volume) {\r\n\t\tfor (let i = 0; i < this.blipChannels.length; i++) {\r\n\t\t\tthis.blipChannels[i].volume = volume;\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Returns the path which the background is located in.\r\n\t */\r\n\tbgFolder() {\r\n\t\treturn `${AO_HOST}background/${this.bgname}/`;\r\n\t}\r\n\r\n\t/**\r\n\t * Sets a new emote.\r\n\t * @param {object} chatmsg the new chat message\r\n\t */\r\n\tsay(chatmsg) {\r\n\t\tthis.chatmsg = chatmsg;\r\n\t\tappendICLog(chatmsg.content, chatmsg.nameplate);\r\n\t\tchangeBackground(chatmsg.side);\r\n\t\tthis.textnow = '';\r\n\t\tthis.sfxplayed = 0;\r\n\t\tthis.textTimer = 0;\r\n\t\tthis._animating = true;\r\n\t\tclearTimeout(this.updater);\r\n\t\t//If preanim existed then determine the length\r\n\t\tif (chatmsg.preanim != \"-\") {\r\n\t\t\tchatmsg.preanimdelay = this.getAnimLength(AO_HOST + 'characters/' + escape(chatmsg.name) + '/' + chatmsg.preanim + '.gif',this.initUpdater);\r\n\t\t} else {\r\n\t\t\tthis.initUpdater(0)\r\n\t\t}\t\r\n\t}\r\n\t\r\n\t/**\r\n\t * Intialize updater\r\n\t * @param {int} animdelay the length of pre-animation \r\n\t */\r\n\tinitUpdater(animdelay){\r\n\t\tviewport.chatmsg.preanimdelay = parseInt(animdelay); \r\n\t\tviewport.updater = setTimeout(() => viewport.updateText(), UPDATE_INTERVAL);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Gets animation length.\r\n\t * @param {string} filename the animation file name\r\n\t * @param {function} callback the callback function\r\n\t */\r\n\tgetAnimLength(filename,callback) {\r\n\t\t//Source (Thanks to Ryman): https://codepen.io/Ryman/pen/wzioA\r\n\t\tvar request = new XMLHttpRequest();\r\n\t\trequest.open('GET', filename, true);\r\n\t\trequest.responseType = 'arraybuffer';\r\n\t\trequest.addEventListener('load', function () {\r\n\t\t\tvar arr = new Uint8Array(request.response),\r\n\t\t\t// Thanks to http://justinsomnia.org/2006/10/gif-animation-duration-calculation/\r\n\t\t\t// And http://www.w3.org/Graphics/GIF/spec-gif89a.txt\r\n\t\t\tbin = '', \r\n\t\t\tduration = 0;\r\n\t\t\t\r\n\t\t\tfor (var i = 0; i < arr.length; i++) {\t\t\t\t\r\n\t\t\t\tbin += String.fromCharCode( arr[i] )\r\n\r\n\t\t\t\t// Find a Graphic Control Extension hex(21F904__ ____ __00)\r\n\t\t\t\tif (arr[i] == 0x21 \r\n\t\t\t\t && arr[i + 1] == 0xF9 \r\n\t\t\t\t && arr[i + 2] == 0x04 \r\n\t\t\t\t && arr[i + 7] == 0x00) {\r\n\t\t\t\t // Swap 5th and 6th bytes to get the delay per frame\r\n\t\t\t\t let delay = (arr[i + 5] << 8) | (arr[i + 4] & 0xFF)\r\n\t\t\t\t \r\n\t\t\t\t // Should be aware browsers have a minimum frame delay \r\n\t\t\t\t // e.g. 6ms for IE, 2ms modern browsers (50fps)\r\n\t\t\t\t duration += delay < 2 ? 10 : (delay)\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\t// Return animation length\r\n\t\t\tcallback(duration * 10);\r\n\t\t});\r\n\t\trequest.send();\r\n\t}\r\n\r\n\t/**\r\n\t * Updates the chatbox based on the given text.\r\n\t * \r\n\t * XXX: This relies on a global variable `this.chatmsg`!\r\n\t */\r\n\tupdateText() {\r\n\t\t// Flip the character\r\n\t\tif (this.chatmsg.flip == 1){\r\n\t\t\tdocument.getElementById(\"client_char\").style.transform = \"scaleX(-1)\"; \r\n\t\t} else {\r\n\t\t\tdocument.getElementById(\"client_char\").style.transform = \"scaleX(1)\";\r\n\t\t}\r\n\t\t\t\r\n\t\tif (this._animating) {\r\n\t\t\tthis.updater = setTimeout(() => this.updateText(), UPDATE_INTERVAL);\r\n\t\t}\r\n\r\n\t\tif (this.chatmsg.isnew) {\r\n\t\t\t// Reset screen background\r\n\t\t\tdocument.getElementById(\"client_background\").style.backgroundColor = \"transparent\";\r\n\t\t\t//Hide message and evidence window\r\n\t\t\tdocument.getElementById(\"client_name\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_chat\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_evi\").style.opacity = \"0\";\r\n\t\t\tdocument.getElementById(\"client_evi\").style.height = \"0%\";\r\n\t\t\tconst shouts = {\r\n\t\t\t\t\"1\": \"holdit\",\r\n\t\t\t\t\"2\": \"objection\",\r\n\t\t\t\t\"3\": \"takethat\"\r\n\t\t\t};\r\n\r\n\t\t\tlet shout = shouts[this.chatmsg.objection];\r\n\t\t\tif (typeof shout !== \"undefined\") {\r\n\t\t\t\tdocument.getElementById(\"client_shout\").src = AO_HOST + \"misc/\" + shout + \".gif\";\r\n\t\t\t\t(new Audio(`${AO_HOST}/characters/${this.chatmsg.name}/${shout}.wav`)).play();\r\n\t\t\t\tthis.shoutTimer = 850;\r\n\t\t\t} else {\r\n\t\t\t\tthis.shoutTimer = 0;\r\n\t\t\t}\r\n\r\n\t\t\tthis.chatmsg.isnew = false;\r\n\t\t\tthis.chatmsg.startpreanim = true;\r\n\t\t}\r\n\r\n\t\tif(this.textTimer >= this.shoutTimer && this.chatmsg.startpreanim) {\r\n\t\t\t// Effect stuff\r\n\t\t\tif (this.chatmsg.flash == 2){\r\n\t\t\t\t//Shake screen\r\n\t\t\t\tthis.sfxaudio.pause();\r\n\t\t\t\tthis.sfxplayed = 1;\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/sfx-stab.wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t\t$('#client_gamewindow').effect( \"shake\",{\"direction\":\"up\"});\r\n\t\t\t} else if (this.chatmsg.flash == 1) {\r\n\t\t\t\t//Flash screen\r\n\t\t\t\tdocument.getElementById(\"client_background\").style.backgroundColor = \"white\";\r\n\t\t\t\tthis.sfxaudio.pause();\r\n\t\t\t\tthis.sfxplayed = 1;\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/sfx-realization.wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t\t$('#client_gamewindow').effect(\"pulsate\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t//Pre-animation stuff\r\n\t\t\tif(this.chatmsg.preanimdelay > 0){\r\n\t\t\t\tdocument.getElementById(\"client_shout\").src = \"misc/placeholder.gif\";\r\n\t\t\t\tchangeBackground(this.chatmsg.side);\r\n\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.preanim + \".gif\";\r\n\t\t\t}\r\n\t\t\tthis.chatmsg.startpreanim = false;\r\n\t\t\tthis.chatmsg.startspeaking = true;\r\n\t\t} else if (this.textTimer >= this.shoutTimer + this.chatmsg.preanimdelay && !this.chatmsg.startpreanim) {\r\n\t\t\tif (this.chatmsg.startspeaking) {\r\n\t\t\t\tif(this.chatmsg.evidence > 0){\r\n\t\t\t\t\t// Prepare evidence\r\n\t\t\t\t\tdocument.getElementById(\"client_evi\").style.backgroundImage = \"url('\"+ client.evidences[this.chatmsg.evidence - 1].icon +\"')\";\r\n\t\t\t\t\r\n\t\t\t\t\tif (this.chatmsg.side == 'def'){\r\n\t\t\t\t\t\t// Only def show evidence on right\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.right = \"1.5em\";\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.left = \"initial\";\r\n\t\t\t\t\t\t$( \"#client_evi\" ).animate({\r\n\t\t\t\t\t\t\theight: \"30%\",\r\n\t\t\t\t\t\t\topacity: 1,\r\n\t\t\t\t\t\t\tmarginLeft: \"10.6in\"\r\n\t\t\t\t\t\t}, 250 );\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.right = \"initial\";\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.left = \"1.5em\";\r\n\t\t\t\t\t\t$( \"#client_evi\" ).animate({\r\n\t\t\t\t\t\t\theight: \"30%\",\r\n\t\t\t\t\t\t\topacity: 1,\r\n\t\t\t\t\t\t\tmarginRight: \"10.6in\"\r\n\t\t\t\t\t\t}, 250 );\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\t\r\n\t\t\t\t$(\"#client_name\").toggle( \"fade\" );\r\n\t\t\t\t$(\"#client_chat\").toggle(\"drop\",{\"direction\":\"down\"});\r\n\t\t\t\tif(this.chatmsg.preanimdelay == 0){\r\n\t\t\t\t\tdocument.getElementById(\"client_shout\").src = \"misc/placeholder.gif\";\r\n\t\t\t\t\tchangeBackground(this.chatmsg.side);\r\n\t\t\t\t}\r\n\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.speaking + \".gif\";\r\n\t\t\t\tdocument.getElementById(\"client_name\").style.fontSize = (document.getElementById(\"client_name\").offsetHeight * 0.7) + \"px\";\r\n\t\t\t\tdocument.getElementById(\"client_chat\").style.fontSize = (document.getElementById(\"client_chat\").offsetHeight * 0.25) + \"px\";\r\n\t\t\t\tdocument.getElementById(\"client_name\").innerHTML = \"<p>\" + escapeHtml(this.chatmsg.nameplate) + \"</p>\";\r\n\r\n\t\t\t\tconst colors = {\r\n\t\t\t\t\t\"0\": \"#ffffff\",\r\n\t\t\t\t\t\"1\": \"#00ff00\",\r\n\t\t\t\t\t\"2\": \"#ff0000\",\r\n\t\t\t\t\t\"3\": \"#ffaa00\",\r\n\t\t\t\t\t\"4\": \"#0000ff\",\r\n\t\t\t\t\t\"5\": \"#ffff00\",\r\n\t\t\t\t\t\"6\": \"#aa00aa\"\r\n\t\t\t\t}\r\n\t\t\t\tlet stylecolor = \"color: \" + (colors[this.chatmsg.color] || \"#ffffff\");\r\n\t\t\t\tdocument.getElementById(\"client_inner_chat\").style = stylecolor;\r\n\t\t\t\tthis.chatmsg.startspeaking = false;\r\n\r\n\t\t\t\tif (this.textnow == this.chatmsg.content) {\r\n\t\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.silent + \".gif\";\r\n\t\t\t\t\tthis._animating = false;\r\n\t\t\t\t\tclearTimeout(this.updater);\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\tif (this.textnow != this.chatmsg.content) {\r\n\t\t\t\t\tif (this.chatmsg.content.charAt(this.textnow.length) != \" \") {\r\n\t\t\t\t\t\tthis.blipChannels[this.currentBlipChannel].play();\r\n\t\t\t\t\t\tthis.currentBlipChannel++;\r\n\t\t\t\t\t\tthis.currentBlipChannel %= this.blipChannels.length;\r\n\t\t\t\t\t}\r\n\t\t\t\t\tthis.textnow = this.chatmsg.content.substring(0, this.textnow.length + 1);\r\n\t\t\t\t\tdocument.getElementById(\"client_inner_chat\").innerHTML = this.textnow;\r\n\t\t\t\t\tif (this.textnow == this.chatmsg.content) {\r\n\t\t\t\t\t\tthis.textTimer = 0;\r\n\t\t\t\t\t\tthis._animating = false;\r\n\t\t\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.silent + \".gif\";\r\n\t\t\t\t\t\tclearTimeout(this.updater);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\tif (!this.sfxplayed && this.chatmsg.snddelay + this.shoutTimer >= this.textTimer) {\r\n\t\t\tthis.sfxaudio.pause();\r\n\t\t\tthis.sfxplayed = 1;\r\n\t\t\tif (this.chatmsg.sound != \"0\" && this.chatmsg.sound != \"1\") {\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/\" + escape(this.chatmsg.sound) + \".wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.textTimer = this.textTimer + UPDATE_INTERVAL;\r\n\t}\r\n}\r\n\r\nclass INI {\r\n\tstatic parse(data) {\r\n\t\tlet regex = {\r\n\t\t\tsection: /^\\s*\\[\\s*([^\\]]*)\\s*\\]\\s*$/,\r\n\t\t\tparam: /^\\s*([\\w\\.\\-\\_]+)\\s*=\\s*(.*?)\\s*$/,\r\n\t\t\tcomment: /^\\s*;.*$/\r\n\t\t};\r\n\t\tlet value = {};\r\n\t\tlet lines = data.split(/\\r\\n|\\r|\\n/);\r\n\t\tlet section = null;\r\n\t\tlines.forEach(function(line) {\r\n\t\t\tif (regex.comment.test(line)) {\r\n\t\t\t\treturn;\r\n\t\t\t} else if (line.length == 0) {\r\n\t\t\t\treturn;\r\n\t\t\t} else if (regex.param.test(line)) {\r\n\t\t\t\tlet match = line.match(regex.param);\r\n\t\t\t\tif (section) {\r\n\t\t\t\t\tvalue[section][match[1]] = match[2];\r\n\t\t\t\t} else {\r\n\t\t\t\t\tvalue[match[1]] = match[2];\r\n\t\t\t\t}\r\n\t\t\t} else if (regex.section.test(line)) {\r\n\t\t\t\tlet match = line.match(regex.section);\r\n\t\t\t\tvalue[match[1]] = {};\r\n\t\t\t\tsection = match[1];\r\n\t\t\t};\r\n\t\t});\r\n\t\treturn value;\r\n\t}\r\n}\r\n\r\n/**\r\n * Triggered when the Return key is pressed on the out-of-character chat input box.\r\n * @param {KeyboardEvent} event\r\n */\r\nexport function onOOCEnter(event) {\r\n\tif (event.keyCode == 13) {\r\n\t\tclient.sendOOC(document.getElementById(\"client_oocinputbox\").value);\r\n\t\tdocument.getElementById(\"client_oocinputbox\").value = \"\";\r\n\t}\r\n}\r\nwindow.onOOCEnter = onOOCEnter;\r\n\r\n/**\r\n * Triggered when the Return key is pressed on the in-character chat input box.\r\n * @param {KeyboardEvent} event\r\n */\r\nexport function onEnter(event) {\r\n\tif (event.keyCode == 13) {\r\n\t\tlet mychar = client.me();\r\n\t\tlet myemo = client.myEmote();\r\n\t\tlet myevi = client.myEvidence();\r\n\t\tlet myflip = ((client.flip)? 1:0);\r\n\t\tlet mycolor = document.getElementById(\"textcolor\").value;\r\n\t\tlet ssfxname = \"0\";\r\n\t\tlet ssfxdelay = \"0\";\r\n\t\tif (document.getElementById(\"sendsfx\").checked) {\r\n\t\t\tssfxname = myemo.sfx;\r\n\t\t\tssfxdelay = myemo.sfxdelay;\r\n\t\t}\r\n\t\tclient.sendIC(myemo.speaking, mychar.name, myemo.silent, document.getElementById(\"client_inputbox\").value, mychar.side, ssfxname, myemo.zoom, ssfxdelay, selectedShout, myevi, myflip, selectedEffect, mycolor);\r\n\t}\r\n}\r\nwindow.onEnter = onEnter;\r\n\r\n/**\r\n * Resets the IC parameters for the player to enter a new chat message.\r\n * This should only be called when the player's previous chat message\r\n * was successfully sent/presented.\r\n */\r\nfunction resetICParams() {\r\n\tdocument.getElementById(\"client_inputbox\").value = \"\";\r\n\tif (selectedEffect) {\r\n\t\tdocument.getElementById(\"button_effect_\" + selectedEffect).className = \"client_button\";\r\n\t\tselectedEffect = 0;\r\n\t}\r\n\tif (selectedShout) {\r\n\t\tdocument.getElementById(\"button_\" + selectedShout).className = \"client_button\";\r\n\t\tselectedShout = 0;\r\n\t}\t\t\r\n}\r\n\r\n/**\r\n * Triggered when an item on the music list is clicked.\r\n * @param {MouseEvent} event\r\n */\r\nexport function musiclist_click(event) {\r\n\tlet playtrack = document.getElementById(\"client_musiclist\").value;\r\n\tclient.sendMusicChange(playtrack);\r\n}\r\nwindow.musiclist_click = musiclist_click;\r\n\r\n/**\r\n * Triggered when an item on the music list is clicked.\r\n * @param {MouseEvent} event\r\n */\r\nexport function area_click(el) {\r\n\tlet playtrack = el.textContent;\r\n\tclient.sendMusicChange(playtrack);\r\n}\r\nwindow.area_click = area_click;\r\n\r\n/**\r\n * Triggered by the music volume slider.\r\n */\r\nexport function changeMusicVolume() {\r\n\tviewport.music.volume = document.getElementById(\"client_mvolume\").value / 100;\r\n}\r\nwindow.changeMusicVolume = changeMusicVolume;\r\n\r\n/**\r\n * Triggered by the sound effect volume slider.\r\n */\r\nexport function changeSFXVolume() {\r\n\tviewport.sfxaudio.volume = document.getElementById(\"client_svolume\").value / 100;\r\n}\r\nwindow.changeSFXVolume = changeSFXVolume;\r\n\r\n/**\r\n * Triggered by the blip volume slider.\r\n */\r\nexport function changeBlipVolume() {\r\n\tviewport.setBlipVolume(document.getElementById(\"client_bvolume\").value / 100);\r\n}\r\nwindow.changeBlipVolume = changeBlipVolume;\r\n\r\n/**\r\n * Triggered when a character icon is clicked in the character selection menu.\r\n * @param {MouseEvent} event\r\n */\r\nexport function changeCharacter(event) {\r\n\tclient.sendLeaveRoom();\r\n\tdocument.getElementById(\"client_charselect\").style.display = \"block\";\r\n\tdocument.getElementById(\"client_emo\").innerHTML = \"\";\r\n}\r\nwindow.changeCharacter = changeCharacter;\r\n\r\n/**\r\n * Triggered when there was an error loading a character sprite.\r\n * @param {HTMLImageElement} image the element containing the missing image\r\n */\r\nexport function imgError(image) {\r\n\timage.onerror = \"\";\r\n\timage.src = \"misc/placeholder.gif\";\r\n\treturn true;\r\n}\r\nwindow.imgError = imgError;\r\n\r\n/**\r\n * Triggered when there was an error loading a character icon.\r\n * @param {HTMLImageElement} image the element containing the missing image\r\n */\r\nexport function demoError(image) {\r\n\timage.onerror = \"\";\r\n\timage.src = \"/misc/placeholder.png\";\r\n\treturn true;\r\n}\r\nwindow.demoError = demoError;\r\n\r\n/**\r\n * Checks if an image exists at the specified URI.\r\n * @param {string} url the URI to be checked\r\n */\r\nfunction ImageExist(url) {\r\n\tvar img = new Image();\r\n\timg.src = url;\r\n\treturn img.height != 0;\r\n}\r\n\r\n/**\r\n * Changes the viewport background based on a given position.\r\n * \r\n * Valid positions: `def, pro, hld, hlp, wit, jud`\r\n * @param {string} position the position to change into\r\n */\r\nfunction changeBackground(position) {\r\n\tvar standname;\r\n\tlet bgfolder = viewport.bgFolder();\r\n\tdocument.getElementById(\"client_fg\").style.display = \"none\";\r\n\tdocument.getElementById(\"client_bench\").style.display = \"none\";\r\n\tswitch (position) {\r\n\t\tcase \"def\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"defenseempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\";\r\n\t\t\tif(ImageExist(bgfolder + \"defensedesk.png\")){\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"defensedesk.png\"\r\n\t\t\t}else{\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"bancodefensa.png\"\r\n\t\t\t}\r\n\t\t\tstandname = \"defense\";\r\n\t\t\tbreak;\r\n\t\tcase \"pro\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"prosecutorempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\"\r\n\t\t\tif(ImageExist(bgfolder + \"defensedesk.png\")){\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"prosecutiondesk.png\"\r\n\t\t\t} else {\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"bancoacusacion.png\"\r\n\t\t\t}\t\t\t\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"hld\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"helperstand.png\"\r\n\t\t\tstandname = \"defense\";\r\n\t\t\tbreak;\r\n\t\tcase \"hlp\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"prohelperstand.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"wit\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"witnessempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\"\r\n\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"estrado.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"jud\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"judgestand.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t}\r\n\tif (viewport.chatmsg.type == 5) {\r\n\t\tdocument.getElementById(\"client_bench\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_court\").src = AO_HOST + \"themes/default/\" + standname + \"_speedlines.gif\";\r\n\t}\r\n}\r\n\r\n/**\r\n * Triggered when the reconnect button is pushed.\r\n */\r\nexport function ReconnectButton() {\r\n\tclient.cleanup();\r\n\tclient = new Client(serverIP);\r\n\tif (client) {\r\n\t\tmode = \"join\"; // HACK: see client.onOpen\r\n\t\tdocument.getElementById(\"client_error\").style.display = \"none\";\r\n\t}\r\n}\r\nwindow.ReconnectButton = ReconnectButton;\r\n\r\n/**\r\n * Triggered when the retry button is pushed (during the loading process).\r\n */\r\nexport function RetryButton() {\r\n\tclient.joinServer();\r\n}\r\nwindow.RetryButton = RetryButton;\r\n\r\n/**\r\n * Appends a message to the in-character chat log.\r\n * @param {string} toadd the string to be added\r\n * @param {string} name the name of the sender\r\n */\r\nfunction appendICLog(toadd, name = \"\", time = new Date()) {\r\n\tconst entry = document.createElement(\"p\");\r\n\tconst nameField = document.createElement(\"span\");\r\n\tnameField.id = \"iclog_name\";\r\n\tnameField.appendChild(document.createTextNode(name));\r\n\tentry.appendChild(nameField);\r\n\tentry.appendChild(document.createTextNode(toadd));\r\n\r\n\t// Only put a timestamp if the minute has changed.\r\n\tif (lastICMessageTime.getMinutes() !== time.getMinutes()) {\r\n\t\tconst timeStamp = document.createElement(\"span\");\r\n\t\ttimeStamp.id = \"iclog_time\";\r\n\t\ttimeStamp.innerText = time.toLocaleTimeString(undefined, {\r\n\t\t\thour: \"numeric\",\r\n\t\t\tminute: \"2-digit\"\r\n\t\t});\r\n\t\tentry.appendChild(timeStamp);\r\n\t}\r\n\r\n\tconst clientLog = document.getElementById(\"client_log\");\r\n\tclientLog.appendChild(entry);\r\n\r\n\tif (clientLog.scrollTop > clientLog.scrollHeight - 600) {\r\n\t\tclientLog.scrollTop = clientLog.scrollHeight;\r\n\t}\r\n\r\n\tlastICMessageTime = new Date();\r\n}\r\n\r\n/**\r\n * Requests to play as a character.\r\n * @param {number} ccharacter the character ID; if this is a large number, then spectator is chosen instead.\r\n */\r\nexport function pickchar(ccharacter) {\r\n\tif (ccharacter < 1000) {\r\n\t\tclient.sendCharacter(ccharacter);\r\n\t} else {\r\n\t\t// Spectator\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_inputbox\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_emo\").style.display = \"none\";\r\n\t}\r\n}\r\nwindow.pickchar = pickchar;\r\n\r\n/**\r\n * Highlights and selects an emotion for in-character chat.\r\n * @param {string} emo the new emotion to be selected\r\n */\r\nexport function pickemotion(emo) {\r\n\tif (client.selectedEmote != -1) {\r\n\t\tdocument.getElementById(\"emo_\" + client.selectedEmote).src = client.myEmote().button_off;\r\n\t}\r\n\tclient.selectedEmote = emo\r\n\tdocument.getElementById(\"emo_\" + emo).src = client.myEmote().button_on;\r\n}\r\nwindow.pickemotion = pickemotion;\r\n\r\n/**\r\n * Highlights and selects an evidence for in-character chat.\r\n * @param {string} evidence the evidence to be presented\r\n */\r\nexport function pickevidence(evidence) {\r\n\tif (client.selectedEvidence != evidence) {\r\n\t\t//Update selected evidence\t\t\r\n\t\tif(client.selectedEvidence > 0){\r\n\t\t\tdocument.getElementById(\"evi_\" + client.selectedEvidence).className = \"client_button\";\r\n\t\t}\r\n\t\tdocument.getElementById(\"evi_\" + evidence).className = \"client_button dark\";\r\n\t\tclient.selectedEvidence = evidence;\r\n\t\t\r\n\t\t// Show evidence on information window\r\n\t\tdocument.getElementById(\"evi_name\").value = client.evidences[evidence - 1].name;\r\n\t\tdocument.getElementById(\"evi_desc\").value = client.evidences[evidence - 1].desc;\r\n\r\n\t\t//Update Icon\r\n\t\tlet icon_id = getIndexFromSelect(\"evi_select\", client.evidences[evidence - 1].filename);\r\n\t\tdocument.getElementById(\"evi_select\").selectedIndex = icon_id;\r\n\t\tif (icon_id == 0){\t\t\t\r\n\t\t\tdocument.getElementById(\"evi_filename\").value = client.evidences[evidence - 1].filename;\r\n\t\t}\r\n\t\tupdateEvidenceIcon();\r\n\t\t\r\n\t\t// Update button\r\n\t\tdocument.getElementById(\"evi_add\").className = \"client_button hover_button inactive\";\r\n\t\tdocument.getElementById(\"evi_edit\").className = \"client_button hover_button\";\r\n\t\tdocument.getElementById(\"evi_cancel\").className = \"client_button hover_button\";\r\n\t\tdocument.getElementById(\"evi_del\").className = \"client_button hover_button\";\r\n\t} else {\r\n\t\tcancelevidence();\r\n\t}\r\n}\r\nwindow.pickevidence = pickevidence;\r\n\r\n/**\r\n * Add evidence.\r\n */\r\nexport function addevidence() {\r\n\tlet evidence_select = document.getElementById('evi_select');\r\n\tclient.sendPE( document.getElementById('evi_name').value,\r\n\t\tdocument.getElementById('evi_desc').value,\r\n\t\t(evidence_select.selectedIndex == 0)? \r\n\t\t\tdocument.getElementById('evi_filename').value : \r\n\t\t\tevidence_select.options[evidence_select.selectedIndex].text \r\n\t\t);\r\n\tcancelevidence();\r\n}\r\nwindow.addevidence = addevidence;\r\n\r\n/**\r\n * Edit selected evidence.\r\n */\r\nexport function editevidence() {\r\n\tlet evidence_select = document.getElementById('evi_select');\r\n\tlet id = parseInt(client.selectedEvidence) - 1;\r\n\tclient.sendEE( id, \r\n\t\tdocument.getElementById('evi_name').value,\r\n\t\tdocument.getElementById('evi_desc').value,\r\n\t\t(evidence_select.selectedIndex == 0)? \r\n\t\t\tdocument.getElementById('evi_filename').value : \r\n\t\t\tevidence_select.options[evidence_select.selectedIndex].text \r\n\t\t);\r\n\tcancelevidence();\r\n}\r\nwindow.editevidence = editevidence;\r\n\r\n/**\r\n * Delete selected evidence.\r\n */\r\nexport function delevidence() {\r\n\tlet id = parseInt(client.selectedEvidence) - 1;\r\n\tclient.sendDE(id);\r\n\tcancelevidence();\r\n}\r\nwindow.delevidence = delevidence;\r\n\r\n/**\r\n * Cancel evidence selection.\r\n */\r\nexport function cancelevidence() {\r\n\t//Clear evidence data\r\n\tif(client.selectedEvidence > 0){\r\n\t\tdocument.getElementById(\"evi_\" + client.selectedEvidence).className = \"client_button\";\r\n\t}\r\n\tclient.selectedEvidence = 0;\r\n\t\r\n\t// Clear evidence on information window\r\n\tdocument.getElementById(\"evi_select\").selectedIndex = 0;\r\n\tupdateEvidenceIcon(); // Update icon widget\r\n\tdocument.getElementById(\"evi_filename\").value = \"\";\r\n\tdocument.getElementById(\"evi_name\").value = \"\";\r\n\tdocument.getElementById(\"evi_desc\").value = \"\";\r\n\tdocument.getElementById(\"evi_icon\").style.backgroundImage = \"url('misc/empty.png')\"; //Clear icon\r\n\t\r\n\t// Update button\r\n\tdocument.getElementById(\"evi_add\").className = \"client_button hover_button\";\r\n\tdocument.getElementById(\"evi_edit\").className = \"client_button hover_button inactive\";\r\n\tdocument.getElementById(\"evi_cancel\").className = \"client_button hover_button inactive\";\r\n\tdocument.getElementById(\"evi_del\").className = \"client_button hover_button inactive\";\r\n}\r\nwindow.cancelevidence = cancelevidence;\r\n\r\n/**\r\n * Find index of anything in select box.\r\n * @param {string} select_box the select element name\r\n * @param {string} value the value that need to be compared\r\n */\r\nexport function getIndexFromSelect(select_box, value) {\r\n\t\t//Find if icon alraedy existed in select box\r\n\t\tlet select_element = document.getElementById(select_box);\r\n\t\tfor (let i = 1; i < select_element.length; ++i){\r\n\t\t\tif (select_element.options[i].value == value){\r\n\t\t\t\treturn i;\r\n\t\t\t}\r\n\t\t}\r\n\t\treturn 0;\r\n}\r\nwindow.getIndexFromSelect = getIndexFromSelect;\r\n\r\n/**\r\n * Update evidence icon.\r\n */\r\nexport function updateEvidenceIcon() {\r\n\tlet evidence_select = document.getElementById(\"evi_select\");\r\n\tlet evidence_filename = document.getElementById(\"evi_filename\");\r\n\tlet evidence_iconbox = document.getElementById(\"evi_icon\");\r\n\t\r\n\tif (evidence_select.selectedIndex == 0) {\r\n\t\tevidence_filename.style.display = \"initial\";\r\n\t\tevidence_iconbox.style.backgroundImage = \"url('\" + AO_HOST + 'evidence/' + evidence_filename.value + \"')\";\r\n\t} else {\t\t\r\n\t\tevidence_filename.style.display = \"none\";\r\n\t\tevidence_iconbox.style.backgroundImage = \"url('\" + AO_HOST + 'evidence/' + evidence_select.value + \"')\" ;\r\n\t}\r\n}\r\nwindow.updateEvidenceIcon = updateEvidenceIcon;\r\n\r\n/**\r\n * Change background.\r\n */\r\nexport function changeBackgroundOOC() {\r\n\tlet filename = \"\", background_select = document.getElementById(\"bg_select\")\r\n\t\t, bg_command = document.getElementById(\"bg_command\").value;\r\n\tif (background_select.selectedIndex == 0) {\r\n\t\tfilename = document.getElementById(\"bg_filename\").value; \r\n\t} else{\r\n\t\tfilename = background_select.value;\r\n\t}\r\n\tclient.sendOOC(\"/\" + bg_command.replace(\"$1\",filename));\r\n}\r\nwindow.changeBackgroundOOC = changeBackgroundOOC;\r\n\r\n/**\r\n * Update background preview.\r\n */\r\nexport function updateBackgroundPreview() {\r\n\tlet background_select = document.getElementById(\"bg_select\");\r\n\tlet background_filename = document.getElementById(\"bg_filename\");\r\n\tlet background_preview = document.getElementById(\"bg_preview\");\r\n\t\r\n\tif (background_select.selectedIndex == 0) {\r\n\t\tbackground_filename.style.display = \"initial\";\r\n\t\tbackground_preview.src = AO_HOST + 'background/' + background_filename.value + \"/defenseempty.png\";\r\n\t} else {\r\n\t\tbackground_filename.style.display = \"none\";\r\n\t\tbackground_preview.src = AO_HOST + 'background/' + background_select.value + \"/defenseempty.png\";\r\n\t}\r\n}\r\nwindow.updateBackgroundPreview = updateBackgroundPreview;\r\n\r\n/**\r\n * Highlights and selects an effect for in-character chat.\r\n * If the same effect button is selected, then the effect is canceled.\r\n * @param {string} effect the new effect to be selected\r\n */\r\nexport function toggleaffect(effect) {\r\n\tif (effect == selectedEffect) {\r\n\t\tdocument.getElementById(\"button_effect_\" + effect).className = \"client_button\";\r\n\t\tselectedEffect = 0;\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_effect_\" + effect).className = \"client_button dark\";\r\n\t\tif (selectedEffect) {\r\n\t\t\tdocument.getElementById(\"button_effect_\" + selectedEffect).className = \"client_button\";\r\n\t\t}\r\n\t\tselectedEffect = effect;\r\n\t}\r\n}\r\nwindow.toggleaffect = toggleaffect;\r\n\r\n/**\r\n * Toggle flip for in-character chat.\r\n */\r\nexport function toggleflip() {\r\n\tif (client.flip) {\r\n\t\tdocument.getElementById(\"button_flip\").className = \"client_button\";\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_flip\").className = \"client_button dark\";\r\n\t}\r\n\tclient.flip = !client.flip;\r\n}\r\nwindow.toggleflip = toggleflip;\r\n\r\n/**\r\n * Toggle presentable for presenting evidence in-character chat.\r\n */\r\nexport function togglepresent() {\r\n\tif (client.presentable) {\r\n\t\tdocument.getElementById(\"button_present\").className = \"client_button\";\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_present\").className = \"client_button dark\";\r\n\t}\r\n\tclient.presentable = !client.presentable;\r\n}\r\nwindow.togglepresent = togglepresent;\r\n\r\n/**\r\n * Highlights and selects a menu.\r\n * @param {string} menu the menu to be selected\r\n */\r\nexport function togglemenu(menu) {\r\n\tif (menu != selectedMenu) {\r\n\t\tdocument.getElementById(\"menu_\" + menu).className = \"menu_icon active\";\r\n\t\tdocument.getElementById(\"content_\" + menu).className = \"menu_content active\";\r\n\t\tdocument.getElementById(\"menu_\" + selectedMenu).className = \"menu_icon\";\r\n\t\tdocument.getElementById(\"content_\" + selectedMenu).className = \"menu_content\";\r\n\t\tselectedMenu = menu;\r\n\t}\r\n}\r\nwindow.togglemenu = togglemenu;\r\n\r\n/**\r\n * Highlights and selects a shout for in-character chat.\r\n * If the same shout button is selected, then the shout is canceled.\r\n * @param {string} shout the new shout to be selected\r\n */\r\nexport function toggleshout(shout) {\r\n\tif (shout == selectedShout) {\r\n\t\tdocument.getElementById(\"button_\" + shout).className = \"client_button\";\r\n\t\tselectedShout = 0;\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_\" + shout).className = \"client_button dark\";\r\n\t\tif (selectedShout) {\r\n\t\t\tdocument.getElementById(\"button_\" + selectedShout).className = \"client_button\";\r\n\t\t}\r\n\t\tselectedShout = shout;\r\n\t}\r\n}\r\nwindow.toggleshout = toggleshout;\r\n\r\n/**\r\n * Escapes a string to be HTML-safe.\r\n * \r\n * XXX: This is unnecessary if we use `createTextNode` instead!\r\n * @param {string} unsafe an unsanitized string\r\n */\r\nfunction escapeHtml(unsafe) {\r\n\treturn unsafe\r\n\t\t.replace(/&/g, \"&amp;\")\r\n\t\t.replace(/</g, \"&lt;\")\r\n\t\t.replace(/>/g, \"&gt;\")\r\n\t\t.replace(/\"/g, \"&quot;\")\r\n\t\t.replace(/'/g, \"&#039;\");\r\n}\r\n\r\n/**\r\n * Escapes a string to AO1 escape codes.\r\n * @param {string} estring the string to be escaped\r\n */\r\nfunction escapeChat(estring) {\r\n\treturn estring\r\n\t\t.replace(/#/g, \"<pound>\")\r\n\t\t.replace(/&/g, \"<and>\")\r\n\t\t.replace(/%/g, \"<percent>\")\r\n\t\t.replace(/\\$/g, \"<dollar>\");\r\n}\r\n\r\n/**\r\n * Unescapes a string to AO1 escape codes.\r\n * @param {string} estring the string to be unescaped\r\n */\r\nfunction unescapeChat(estring) {\r\n\treturn estring\r\n\t\t.replace(/<pound>/g, \"#\")\r\n\t\t.replace(/<and>/g, \"&\")\r\n\t\t.replace(/<percent>/g, \"%\")\r\n\t\t.replace(/<dollar>/g, \"$\");\r\n}\r\n\r\n/**\r\n * Encoding text on client side.\r\n * @param {string} estring the string to be encoded\r\n */\r\nfunction encodeChat(estring) {\r\n\tlet selectedEncoding = document.getElementById(\"client_encoding\").value;\r\n\tif (selectedEncoding == \"unicode\") {\r\n\t\t//Source: https://gist.github.com/mathiasbynens/1243213\r\n\t\treturn estring.replace(/[^\\0-~]/g, function(ch) {\r\n\t\t\treturn \"\\\\u\" + (\"000\" + ch.charCodeAt().toString(16)).slice(-4); });\r\n\t} else if (selectedEncoding == \"utf16\"){\r\n\t\t//Source: https://developers.google.com/web/updates/2012/06/How-to-convert-ArrayBuffer-to-and-from-String\r\n\t\tvar buffer = new ArrayBuffer(estring.length*2);\r\n\t\tvar result = new Uint16Array(buffer);\r\n\t\tfor (var i=0, strLen=estring.length; i < strLen; i++) {\r\n\t\t\tresult[i] = estring.charCodeAt(i);\r\n\t\t}\r\n\t\treturn String(result);\r\n\t} else {\r\n\t\treturn estring;\r\n\t}\r\n}\r\n\r\n/**\r\n * Decoding text on client side.\r\n * @param {string} estring the string to be decoded\r\n */\r\nfunction decodeChat(estring) {\r\n\tlet selectedDecoding = document.getElementById(\"client_decoding\").value;\r\n\tif (selectedDecoding == \"unicode\") {\r\n\t\t//Source: https://stackoverflow.com/questions/7885096/how-do-i-decode-a-string-with-escaped-unicode\r\n return estring.replace(/\\\\u([\\d\\w]{1,})/gi, function (match, group) {\r\n\t\t\treturn String.fromCharCode(parseInt(group, 16)); } );\r\n\t} else if (selectedDecoding == \"utf16\"){\t\r\n\t\t//Source: https://developers.google.com/web/updates/2012/06/How-to-convert-ArrayBuffer-to-and-from-String\r\n\t\treturn String.fromCharCode.apply(null, new Uint16Array(estring.split(\",\")));\r\n\t} else {\r\n\t\treturn estring;\r\n\t}\r\n}\r\n\r\n/**\r\n * Decoding text on client side.\r\n * @param {string} estring the string to be decoded\r\n */\r\nfunction decodeBBCode(estring) {\r\n\treturn estring\r\n\t\t.replace(/\\\\n/g, \"<br>\") // Newline \\n\r\n\t\t.replace(/\\[(\\/?)b\\]/g, \"<$1b>\") // Bold [b][/b]\r\n\t\t.replace(/\\[(\\/?)i\\]/g, \"<$1i>\") // Italic [i][/i]\r\n\t\t.replace(/\\[(\\/?)del\\]/g, \"<$1del>\") // Deleted [del][/del]\r\n\t\t.replace(/\\[(\\/?)u\\]/g, \"<$1ins>\") // Underline [u][/u]\r\n\t\t.replace(/\\[(\\/?)sub\\]/g, \"<$1sub>\") // Subscript [sub][/sub]\r\n\t\t.replace(/\\[(\\/?)sup\\]/g, \"<$1sup>\") // Superscript [sup][/sup]\r\n\t\t.replace(/\\[m=([#a-zA-Z0-9]+)\\]/g, '<m a=\"$1\">') // Markup [m=#0ff]\r\n\t\t.replace(/\\[(\\/?)m\\]/g, '<$1m>') // [m][/m]\r\n\t\t.replace(/\\[c=?([#a-zA-Z0-9]+)\\]/g, '<c a=\"$1\">') // Color [c=red]\r\n\t\t.replace(/\\[\\/c\\]/g, '</c>'); // [/c]\r\n}\r\n\r\n\r\n// TODO: Possibly safe to remove, since we are using a transpiler.\r\nif (typeof(String.prototype.trim) === \"undefined\")\r\n{\r\n String.prototype.trim = function() \r\n {\r\n return String(this).replace(/^\\s+|\\s+$/g, '');\r\n };\r\n}\r\n\r\n// Used for HDID calculation.\r\nString.prototype.hashCode = function() {\r\n\tvar hash = 0, i, chr;\r\n\tif (this.length === 0) return hash;\r\n\tfor (i = 0; i < this.length; i++) {\r\n\t chr = this.charCodeAt(i);\r\n\t hash = ((hash << 5) - hash) + chr;\r\n\t hash |= 0; // Convert to 32bit integer\r\n\t}\r\n\treturn hash;\r\n};\r\n\r\n\r\n//\r\n// Client code\r\n//\r\n\r\nlet client = new Client(serverIP);\r\nlet viewport = new Viewport();\r\n\r\n$(document).ready(function(){\r\n\tclient.initialObservBBCode();\r\n\tclient.loadResources(); \r\n});\r\n"],"sourceRoot":""} \ No newline at end of file
+{"version":3,"sources":["webpack:///webpack/bootstrap","webpack:///./webAO/client.js"],"names":["installedModules","__webpack_require__","moduleId","exports","module","i","l","modules","call","m","c","d","name","getter","o","Object","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","prototype","hasOwnProperty","p","s","onOOCEnter","onEnter","musiclist_click","area_click","changeMusicVolume","changeSFXVolume","changeBlipVolume","changeCharacter","imgError","demoError","ReconnectButton","RetryButton","pickchar","pickemotion","pickevidence","addevidence","editevidence","delevidence","cancelevidence","getIndexFromSelect","updateEvidenceIcon","changeBackgroundOOC","updateBackgroundPreview","toggleaffect","toggleflip","togglepresent","togglemenu","toggleshout","queryDict","location","search","substr","split","forEach","item","serverIP","ip","AO_HOST","asset","MUSIC_HOST","oldLoading","test","navigator","userAgent","selectedEffect","selectedMenu","selectedShout","lastICMessageTime","Date","Client","address","_this","this","_classCallCheck","serv","WebSocket","onopen","evt","onOpen","onclose","onClose","onmessage","onMessage","onerror","onError","flip","presentable","playerID","charID","chars","emotes","evidences","selectedEmote","selectedEvidence","checkUpdater","musicList","handlers","MS","args","handleMS","CT","handleCT","MC","handleMC","RMC","handleRMC","CI","handleCI","SC","handleSC","EI","handleEI","LE","handleLE","EM","handleEM","SM","handleSM","music","handlemusic","DONE","handleDONE","BN","handleBN","NBG","handleNBG","HP","handleHP","ID","handleID","PN","handlePN","SI","handleSI","CharsCheck","handleCharsCheck","PV","handlePV","CHECK","_lastTimeICReceived","message","send","escapeChat","encodeChat","speaking","silent","side","ssfxname","zoom","ssfxdelay","objection","evidence","flash","color","desc","img","id","track","_this2","hashCode","setInterval","sendCheck","evidence_select","document","getElementById","add","Option","evidence_arr","length","background_select","background_arr","target","MutationObserver","mutations","mutation","children","addedNodes","node","tagName","style","getAttribute","hasAttribute","backgroundColor","observe","attributes","childList","character","song","e","display","client","joinServer","console","error","reason","code","textContent","cleanup","msg","data","debug","header","handler","warn","close","clearInterval","viewport","chatmsg","content","innerHTML","preanim","escape","nameplate","estring","replace","decodeBBCode","escapeHtml","decodeChat","unescapeChat","sound","type","snddelay","isnew","className","resetICParams","say","oocLog","scrollTop","scrollHeight","pause","src","play","appendICLog","Audio","totime","offset","getTime","addEventListener","currentTime","parseFloat","toFixed","chargs","icon","arg","filename","evidence_box","hmusiclist","newentry","createElement","text","options","flagAudio","newarea","onclick","appendChild","area_box","audio_title","lastChild","insertBefore","firstChild","removeChild","bgname","bg_index","selectedIndex","clip","tr","td","icon_chosen","thispick","changeBackground","me","xhr","XMLHttpRequest","open","responseType","onload","status","linifile","responseText","pinifile","INI","parse","Options","Emotions","number","emoteinfo","esfx","esfxd","SoundN","SoundT","sfx","sfxdelay","button_off","button_on","Viewport","textnow","startpreanim","startspeaking","preanimdelay","blip","volume","blipChannels","Array","currentBlipChannel","sfxaudio","sfxplayed","updater","shoutTimer","textTimer","_animating","clearTimeout","getAnimLength","initUpdater","animdelay","parseInt","setTimeout","updateText","callback","request","arr","Uint8Array","response","duration","String","fromCharCode","delay","_this3","transform","opacity","height","shout","1","2","3","$","effect","direction","backgroundImage","right","left","animate","marginLeft","marginRight","toggle","fontSize","offsetHeight","stylecolor","0","4","5","6","charAt","substring","regex","section","param","comment","line","match","event","keyCode","sendOOC","mychar","myemo","myEmote","myevi","myEvidence","myflip","mycolor","checked","sendIC","playtrack","sendMusicChange","el","setBlipVolume","sendLeaveRoom","image","ImageExist","url","Image","position","standname","bgfolder","bgFolder","toadd","arguments","undefined","time","entry","nameField","createTextNode","getMinutes","timeStamp","innerText","toLocaleTimeString","hour","minute","clientLog","ccharacter","sendCharacter","emo","icon_id","sendPE","sendEE","sendDE","select_box","select_element","evidence_filename","evidence_iconbox","bg_command","background_filename","background_preview","menu","unsafe","selectedEncoding","ch","charCodeAt","toString","slice","buffer","ArrayBuffer","result","Uint16Array","strLen","selectedDecoding","group","apply","window","trim","hash","ready","initialObservBBCode","loadResources"],"mappings":"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","file":"client.b.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = 3);\n","/*\r\n * Glorious webAO\r\n * made by sD, refactored by oldmud0\r\n * credits to aleks for original idea and source\r\n*/\r\n\r\nlet queryDict = {};\r\nlocation.search.substr(1).split(\"&\").forEach(function(item) {\r\n\tqueryDict[item.split(\"=\")[0]] = item.split(\"=\")[1]\r\n});\r\n\r\n/* Server magic */\r\n\r\nconst serverIP = queryDict.ip;\r\nlet mode = queryDict.mode;\r\n\r\nconst AO_HOST = queryDict.asset || \"http://assets.aceattorneyonline.com/base/\";\r\nconst MUSIC_HOST = AO_HOST + \"sounds/music/\";\r\nconst BAR_WIDTH = 90;\r\nconst BAR_HEIGHT = 20;\r\nconst CHAR_SELECT_WIDTH = 8;\r\nconst UPDATE_INTERVAL = 65;\r\n\r\nlet oldLoading = false;\r\nif (/Android|webOS|iPhone|iPad|iPod|BlackBerry|BB|PlayBook|IEMobile|Windows Phone|Kindle|Silk|Opera Mini/i.test(navigator.userAgent)) {\r\n\toldLoading = true;\r\n}\r\n\r\nlet selectedEffect = 0;\r\nlet selectedMenu = 1;\r\nlet selectedShout = 0;\r\nlet lastICMessageTime = new Date(0);\r\n\r\nclass Client {\r\n\tconstructor(address) {\r\n\t\tthis.serv = new WebSocket(\"ws://\" + address);\r\n\r\n\t\tthis.serv.onopen = (evt) => this.onOpen(evt);\r\n\t\tthis.serv.onclose = (evt) => this.onClose(evt);\r\n\t\tthis.serv.onmessage = (evt) => this.onMessage(evt);\r\n\t\tthis.serv.onerror = (evt) => this.onError(evt);\r\n\t\t\r\n\t\tthis.flip = false;\r\n\t\tthis.presentable = false;\r\n\r\n\t\tthis.playerID = 1;\r\n\t\tthis.charID = -1;\r\n\r\n\t\tthis.chars = [];\r\n\t\tthis.emotes = [];\t\t\r\n\t\tthis.evidences = [];\r\n\r\n\t\tthis.selectedEmote = -1;\r\n\t\tthis.selectedEvidence = 0;\r\n\r\n\t\tthis.checkUpdater = null;\r\n\r\n\t\t// Only used for RMC/`music` packets, not EM/SM/MC packets.\r\n\t\tthis.musicList = Object();\r\n\r\n\t\tthis.handlers = {\r\n\t\t\t\"MS\": (args) => this.handleMS(args),\r\n\t\t\t\"CT\": (args) => this.handleCT(args),\r\n\t\t\t\"MC\": (args) => this.handleMC(args),\r\n\t\t\t\"RMC\": (args) => this.handleRMC(args),\r\n\t\t\t\"CI\": (args) => this.handleCI(args),\r\n\t\t\t\"SC\": (args) => this.handleSC(args),\r\n\t\t\t\"EI\": (args) => this.handleEI(args),\r\n\t\t\t\"LE\": (args) => this.handleLE(args),\r\n\t\t\t\"EM\": (args) => this.handleEM(args),\r\n\t\t\t\"SM\": (args) => this.handleSM(args),\r\n\t\t\t\"music\": (args) => this.handlemusic(args),\r\n\t\t\t\"DONE\": (args) => this.handleDONE(args),\r\n\t\t\t\"BN\": (args) => this.handleBN(args),\r\n\t\t\t\"NBG\": (args) => this.handleNBG(args),\r\n\t\t\t\"HP\": (args) => this.handleHP(args),\r\n\t\t\t\"ID\": (args) => this.handleID(args),\r\n\t\t\t\"PN\": (args) => this.handlePN(args),\r\n\t\t\t\"SI\": (args) => this.handleSI(args),\r\n\t\t\t\"CharsCheck\": (args) => this.handleCharsCheck(args),\r\n\t\t\t\"PV\": (args) => this.handlePV(args),\r\n\t\t\t\"CHECK\": (args) => {}\r\n\t\t}\r\n\r\n\t\tthis._lastTimeICReceived = new Date(0);\r\n\t}\r\n\r\n\t/**\r\n\t * Gets the current player's character.\r\n\t */\r\n\tme() {\r\n\t\treturn this.chars[this.charID];\r\n\t}\r\n\r\n\t/**\r\n\t * Gets the player's currently selected emote.\r\n\t */\r\n\tmyEmote() {\r\n\t\treturn this.emotes[this.selectedEmote];\r\n\t}\r\n\t\r\n\t/**\r\n\t * Gets the player's currently selected evidence if presentable.\r\n\t */\r\n\tmyEvidence() {\r\n\t\treturn (this.presentable)? this.selectedEvidence : 0;\r\n\t}\r\n\r\n\t/**\r\n\t * Sends an out-of-character chat message.\r\n\t * @param {string} message the message to send\r\n\t */\r\n\tsendOOC(message) {\r\n\t\tthis.serv.send(`CT#web${this.playerID}#${escapeChat(encodeChat(message))}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Sends an in-character chat message.\r\n\t * @param {string} speaking who is speaking\r\n\t * @param {string} name the name of the current character\r\n\t * @param {string} silent whether or not it's silent\r\n\t * @param {string} message the message to be sent\r\n\t * @param {string} side the name of the side in the background\r\n\t * @param {string} ssfxname the name of the sound effect\r\n\t * @param {string} zoom whether or not to zoom\r\n\t * @param {string} ssfxdelay the delay (in milliseconds) to play the sound effect\r\n\t * @param {string} objection the number of the shout to play\r\n\t */\r\n\tsendIC(speaking, name, silent, message, side, ssfxname, zoom, ssfxdelay, objection, evidence, flip, flash, color) {\r\n\t\tthis.serv.send(\r\n\t\t\t`MS#chat#${speaking}#${name}#${silent}` +\r\n\t\t\t`#${escapeChat(encodeChat(message))}#${side}#${ssfxname}#${zoom}` +\r\n\t\t\t`#${this.charID}#${ssfxdelay}#${selectedShout}#${evidence}#${flip}#${flash}#${color}#%`\r\n\t\t);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends add evidence command.\r\n\t * @param {string} evidence name\r\n\t * @param {string} evidence description\r\n\t * @param {string} evidence image filename\r\n\t */\r\n\tsendPE(name, desc, img) {\r\n\t\tthis.serv.send(`PE#${escapeChat(encodeChat(name))}#${escapeChat(encodeChat(desc))}#${img}#%`);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends edit evidence command.\r\n\t * @param {string} evidence id\r\n\t * @param {string} evidence name\r\n\t * @param {string} evidence description\r\n\t * @param {string} evidence image filename\r\n\t */\r\n\tsendEE(id, name, desc, img) {\r\n\t\tthis.serv.send(`EE#${id}#${escapeChat(encodeChat(name))}#${escapeChat(encodeChat(desc))}#${img}#%`);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Sends delete evidence command.\r\n\t * @param {string} evidence id\r\n\t */\r\n\tsendDE(id, name, desc, img) {\r\n\t\tthis.serv.send(`DE#${id}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to change the music to the specified track.\r\n\t * @param {string} track the track ID\r\n\t */\r\n\tsendMusicChange(track) {\r\n\t\tthis.serv.send(`MC#${track}#${this.charID}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to leave the room and free the character slot.\r\n\t * \r\n\t * Note: This packet is undocumented. It is not implemented by\r\n\t * either the AO2 client or tsuserver.\r\n\t */\r\n\tsendLeaveRoom() {\r\n\t\tthis.serv.send(\"FC#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Begins the handshake process by sending an identifier\r\n\t * to the server.\r\n\t */\r\n\tjoinServer() {\r\n\t\tthis.serv.send(`HI#${navigator.userAgent.hashCode()}#%`);\r\n\t\tthis.serv.send(\"ID#webAO#2.4.5#%\");\r\n\t\tthis.checkUpdater = setInterval(() => this.sendCheck(), 5000);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Load game resources.\r\n\t */\r\n\tloadResources() {\r\n\t\t// Load evidence array to select\r\n\t\tvar evidence_select = document.getElementById(\"evi_select\");\r\n\t\tevidence_select.add(new Option(\"Custom\", 0));\r\n\t\tfor(let i = 1; i <= evidence_arr.length; i++) {\r\n\t\t evidence_select.add(new Option(evidence_arr[i - 1]));\r\n\t\t}\t\t\r\n\t\t// Load background array to select\r\n\t\tvar background_select = document.getElementById(\"bg_select\");\r\n\t\tbackground_select.add(new Option(\"Custom\", 0));\r\n\t\tfor(let i = 1; i <= background_arr.length; i++) {\r\n\t\t background_select.add(new Option(background_arr[i - 1]));\r\n\t\t}\r\n\t\t// TODO: Cache some resources\r\n\t\t\r\n\t}\r\n\t\r\n\t/**\r\n\t * Create observer to detect BBCode elements\r\n\t * then manipulate them.\r\n\t */\r\n\tinitialObservBBCode() {\r\n\t\tvar target = document.getElementById(\"client_inner_chat\");\r\n\t\tvar observer = new MutationObserver(function(mutations) {\r\n\t\t mutations.forEach(function(mutation) {\r\n\t\t\tvar children = mutation.addedNodes;\r\n\t\t\tif (children !== null) {\r\n\t\t\t\tchildren.forEach( function(node) {\r\n\t\t\t\t\tif (node.tagName == \"C\") {\r\n\t\t\t\t\t\tnode.style.color = node.getAttribute(\"a\");\r\n\t\t\t\t\t} else if(node.tagName == \"M\"){\r\n\t\t\t\t\t\tif (node.hasAttribute('a')) {\r\n\t\t\t\t\t\t\tnode.style.backgroundColor = node.getAttribute(\"a\");\r\n\t\t\t\t\t\t} else {\r\n\t\t\t\t\t\t\tnode.style.backgroundColor = \"yellow\";\r\n\t\t\t\t\t\t\tnode.style.color = \"black\";\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t});\r\n\t\t\t}\r\n\t\t }); \r\n\t\t});\r\n\t\tvar config = {attributes: true,childList: true};\r\n\t\tobserver.observe(target,config);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to play as a specified character.\r\n\t * @param {number} character the character ID\r\n\t */\r\n\tsendCharacter(character) {\r\n\t\tthis.serv.send(`CC#${this.playerID}#${character}#web#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Requests to select a music track.\r\n\t * @param {number?} song the song to be played\r\n\t */\r\n\tsendMusic(song) {\r\n\t\tthis.serv.send(`MC#${song}`);\r\n\t}\r\n\r\n\t/**\r\n\t * Sends a keepalive packet.\r\n\t */\r\n\tsendCheck() {\r\n\t\tthis.serv.send(`CH#${this.charID}#%`);\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when a connection is established to the server.\r\n\t */\r\n\tonOpen(e) {\r\n\t\t// XXX: Why does watching mean just SITTING there and doing nothing?\r\n\t\tif (mode === \"watch\") {\r\n\t\t\tdocument.getElementById(\"client_loading\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\t} else {\r\n\t\t\tclient.joinServer();\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when the connection to the server closes.\r\n\t * @param {CloseEvent} e\r\n\t */\r\n\tonClose(e) {\r\n\t\tconsole.error(`The connection was closed: ${e.reason} (${e.code})`);\r\n\t\tif (e.code !== 1001) {\r\n\t\t\tdocument.getElementById(\"client_error\").style.display = \"block\";\r\n\t\t\tdocument.getElementById(\"error_id\").textContent = e.code;\r\n\t\t\tthis.cleanup();\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when a packet is received from the server.\r\n\t * @param {MessageEvent} e\r\n\t */\r\n\tonMessage(e) {\r\n\t\tlet msg = e.data;\r\n\t\tconsole.debug(msg);\r\n\t\tlet lines = msg.split('%');\r\n\t\tlet args = lines[0].split('#');\r\n\t\tlet header = args[0];\r\n\t\tlet handler = this.handlers[header];\r\n\t\tif (typeof handler !== \"undefined\") {\r\n\t\t\thandler(args);\r\n\t\t} else {\r\n\t\t\tconsole.warn(`Invalid packet header ${header}`);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Triggered when an network error occurs.\r\n\t * @param {ErrorEvent} e \r\n\t */\r\n\tonError(e) {\r\n\t\tconsole.error(`A network error occurred: ${e.reason} (${e.code})`);\r\n\t\tdocument.getElementById(\"client_error\").style.display = \"block\";\r\n\t\tdocument.getElementById(\"error_id\").textContent = e.code;\r\n\t\tthis.cleanup();\r\n\t}\r\n\r\n\tcleanup() {\r\n\t\ttry {\r\n\t\t\tthis.serv.close(1001);\r\n\t\t} catch (e) {\r\n\t\t\t// I don't care if this errors\r\n\t\t}\r\n\t\tclearInterval(this.checkUpdater);\r\n\t}\r\n\r\n\t/**\r\n\t * Handles an in-character chat message.\r\n\t * @param {*} args packet arguments\r\n\t */\r\n\thandleMS(args) {\r\n\t\t// TODO: this if-statement might be a bug.\r\n\t\tif (args[4] != viewport.chatmsg.content) {\r\n\t\t\tdocument.getElementById(\"client_inner_chat\").innerHTML = \"\";\r\n\t\t\tlet chatmsg = {\r\n\t\t\t\t// pre: escape(args[2]),\r\n\t\t\t\tcharacter: -1, // Will do a linear search\r\n\t\t\t\tpreanim: escape(args[2]), // XXX: why again?\r\n\t\t\t\tnameplate: args[3], // TODO: parse INI to get this info\r\n\t\t\t\tname: args[3],\r\n\t\t\t\tspeaking: \"(b)\" + escape(args[4]),\r\n\t\t\t\tsilent: \"(a)\" + escape(args[4]),\r\n\t\t\t\tcontent: decodeBBCode(escapeHtml(decodeChat(unescapeChat(args[5])))), // Escape HTML tag, Use BBCode Only!\r\n\t\t\t\tside: args[6],\r\n\t\t\t\tsound: escape(args[7]),\r\n\t\t\t\ttype: args[8],\r\n\t\t\t\t// charid: args[9],\r\n\t\t\t\tsnddelay: args[10],\r\n\t\t\t\tobjection: args[11],\r\n\t\t\t\tevidence: args[12],\r\n\t\t\t\tflip: args[13],\r\n\t\t\t\tflash: args[14],\r\n\t\t\t\tcolor: args[15],\r\n\t\t\t\tisnew: true,\r\n\t\t\t};\r\n\r\n\t\t\t// The dreaded linear search...\r\n\t\t\tfor (let i = 0; i < this.chars.length; i++) {\r\n\t\t\t\tif (this.chars[i].name == args[3]) {\r\n\t\t\t\t\tchatmsg.character = i;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (chatmsg.character == this.charID) {\r\n\t\t\t\tresetICParams();\r\n\t\t\t}\r\n\r\n\t\t\tviewport.say(chatmsg);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles an out-of-character chat message.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCT(args) {\r\n\t\tconst oocLog = document.getElementById(\"client_ooclog\");\r\n\t\toocLog.innerHTML += `${decodeChat(unescapeChat(args[1]))}: ${decodeChat(unescapeChat(args[2]))}\\r\\n`;\r\n\t\tif (oocLog.scrollTop > oocLog.scrollHeight - 60) {\r\n\t\t\toocLog.scrollTop = oocLog.scrollHeight;\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a music change to an arbitrary resource.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleMC(args) {\r\n\t\tconst music = viewport.music;\r\n\t\tmusic.pause();\r\n\t\tmusic.src = MUSIC_HOST + args[1];\r\n\t\tmusic.play();\r\n\t\tif (args[2] >= 0) {\r\n\t\t\tlet musicname = this.chars[args[2]].name;\r\n\t\t\tappendICLog(`${musicname} changed music to ${args[1]}`);\r\n\t\t} else {\r\n\t\t\tappendICLog(`The music was changed to ${args[1]}`);\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a music change to an arbitrary resource, with an offset in seconds.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleRMC(args) {\r\n\t\tviewport.music.pause();\r\n\t\tviewport.music = new Audio(this.musicList[args[1]]);\r\n\t\tconst music = viewport.music;\r\n\t\t// Music offset + drift from song loading\r\n\t\tmusic.totime = args[1];\r\n\t\tmusic.offset = new Date().getTime() / 1000;\r\n\t\tmusic.addEventListener('loadedmetadata', function() {\r\n\t\t\tmusic.currentTime += parseFloat(music.totime + (new Date().getTime() / 1000 - music.offset)).toFixed(3);\r\n\t\t\tmusic.play();\r\n\t\t}, false);\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming character information, bundling multiple characters\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCI(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Character \" + args[1];\r\n\t\tthis.serv.send(\"AN#\" + ((args[1] / 10) + 1) + \"#%\");\r\n\t\tfor (let i = 2; i < args.length - 1; i++) {\r\n\t\t\tif (i % 2 == 0) {\r\n\t\t\t\tlet chargs = args[i].split(\"&\");\r\n\t\t\t\tthis.chars[args[i - 1]] = {\r\n\t\t\t\t\t\"name\": chargs[0],\r\n\t\t\t\t\t\"desc\": chargs[1],\r\n\t\t\t\t\t\"evidence\": chargs[3],\r\n\t\t\t\t\t\"icon\": AO_HOST + \"characters/\" + escape(chargs[0]) + \"/char_icon.png\"\r\n\t\t\t\t};\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming character information, containing only one character\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSC(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Characters\";\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\tlet chargs = args[i].split(\"&\");\r\n\t\t\tthis.chars[i - 1] = {\r\n\t\t\t\t\"name\": chargs[0],\r\n\t\t\t\t\"desc\": chargs[1],\r\n\t\t\t\t\"evidence\": chargs[3],\r\n\t\t\t\t\"icon\": AO_HOST + \"characters/\" + escape(chargs[0]) + \"/char_icon.png\"\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.serv.send(\"RM#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming evidence information, containing only one evidence\r\n\t * item per packet.\r\n\t * \r\n\t * Mostly unimplemented in webAO.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleEI(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Evidence \" + args[1];\r\n\t\t//serv.send(\"AE#\" + (args[1] + 1) + \"#%\");\r\n\t\tthis.serv.send(\"RM#%\");\r\n\t}\r\n\t\r\n\t/**\r\n\t * Handles incoming evidence list, all evidences at once\r\n\t * item per packet.\r\n\t * \r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleLE(args) {\r\n\t\tthis.evidences = [];\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\tvar arg = args[i].split(\"&\");\r\n\t\t\tthis.evidences[i - 1] = {\r\n\t\t\t\t\"name\": escapeHtml(decodeChat(unescapeChat(arg[0]))),\r\n\t\t\t\t\"desc\": escapeHtml(decodeChat(unescapeChat(arg[1]))),\r\n\t\t\t\t\"filename\": escape(arg[2]),\r\n\t\t\t\t\"icon\": AO_HOST + \"evidence/\" + escape(arg[2])\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\tvar evidence_box = document.getElementById(\"evidences\");\r\n\t\tevidence_box.innerHTML = \"\";\r\n\t\tfor(let i = 1; i <= this.evidences.length; i++){\r\n\t\t\tevidence_box.innerHTML += '<img src=\"' + this.evidences[i - 1].icon + \r\n\t\t\t\t'\" id=\"evi_' + i +'\" alt=\"' + this.evidences[i - 1].name +\r\n\t\t\t\t'\" class=\"client_button\" ' +\r\n\t\t\t\t'onclick=\"pickevidence('+ i +')\">';\t\t\t\t\t\t\t\t\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing multiple entries\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleEM(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Music \" + args[1];\r\n\t\tthis.serv.send(\"AM#\" + ((args[1] / 10) + 1) + \"#%\");\r\n\t\tlet hmusiclist = document.getElementById(\"client_musiclist\");\r\n\t\tfor (let i = 2; i < args.length - 1; i++) {\r\n\t\t\tif (i % 2 == 0) {\r\n\t\t\t\tlet newentry = document.createElement(\"OPTION\");\r\n\t\t\t\tnewentry.text = args[i];\r\n\t\t\t\thmusiclist.options.add(newentry);\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing only one entry\r\n\t * per packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSM(args) {\r\n\t\tdocument.getElementById(\"client_loadingtext\").innerHTML = \"Loading Music \";\r\n\t\tlet hmusiclist = document.getElementById(\"client_musiclist\"), flagAudio = false;\r\n\t\t\r\n\t\tfor (let i = 1; i < args.length - 1; i++) {\r\n\t\t\t// Check when found the song for the first time\r\n\t\t\tif(/\\.(?:wav|mp3|mp4|ogg|mid)$/i.test(args[i]) && !flagAudio){\r\n\t\t\t\tflagAudio = true;\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tif(flagAudio) {\r\n\t\t\t\t// After reached the audio put everything in the music list\r\n\t\t\t\tlet newentry = document.createElement(\"OPTION\");\r\n\t\t\t\tnewentry.text = args[i];\r\n\t\t\t\thmusiclist.options.add(newentry);\r\n\t\t\t\r\n\t\t\t} else {\r\n\t\t\t\t// Create area button\r\n\t\t\t\tlet newarea = document.createElement(\"SPAN\");\r\n\t\t\t\tnewarea.className = \"location-box\";\r\n\t\t\t\tnewarea.textContent = args[i]; \r\n\t\t\t\tnewarea.onclick = function(){ area_click(this) };\r\n\t\t\t\tdocument.getElementById(\"areas\").appendChild(newarea);\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\t// Move first audio title from area box to music list\r\n\t\tlet area_box = document.getElementById(\"areas\");\r\n\t\tlet audio_title = document.createElement(\"OPTION\");\r\n\t\taudio_title.text = area_box.lastChild.textContent;\r\n\t\thmusiclist.insertBefore(audio_title, hmusiclist.firstChild);\r\n\t\tarea_box.removeChild(area_box.lastChild); // Remove from arae box\r\n\t\t\t\t\r\n\t\tthis.serv.send(\"RD#%\");\t\t\r\n\t}\r\n\r\n\t/**\r\n\t * Handles incoming music information, containing all entries\r\n\t * in the same packet.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandlemusic(args) {\r\n\t\tfor (let i = 0; i < args.length / 2; i++) {\r\n\t\t\tthis.musicList[args[2 * i]] = args[2 * i + 1];\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the handshake completion packet, meaning the player\r\n\t * is ready to select a character.\r\n\t * \r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleDONE(args) {\r\n\t\tdocument.getElementById(\"client_loading\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"block\";\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a background change.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleBN(args) {\r\n\t\tviewport.bgname = escape(args[1]);\r\n\t\tlet bg_index = getIndexFromSelect(\"bg_select\", escape(args[1]));\r\n\t\tdocument.getElementById(\"bg_select\").selectedIndex = bg_index;\r\n\t\tupdateBackgroundPreview();\r\n\t\tif(bg_index == 0){\r\n\t\t\tdocument.getElementById(\"bg_filename\").value = escape(args[1]);\r\n\t\t}\r\n\t\tdocument.getElementById(\"bg_preview\").src = AO_HOST + 'background/' + escape(args[1]) + \"/defenseempty.png\";\r\n\t\t\t\t\r\n\t}\r\n\r\n\thandleNBG(args) {\r\n\t\t// TODO (set by sD)\r\n\t}\r\n\r\n\t/**\r\n\t * Handles a change in the health bars' states.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleHP(args) {\r\n\t\t// TODO (set by sD)\r\n\t\t// Also, this is broken.\r\n\t\tif (args[1] == 1) {\r\n\t\t\tdocument.getElementById(\"client_defense_hp\").style.clip = \"rect(0px,\" + BAR_WIDTH * args[2] / 10 + \"px,\" + BAR_HEIGHT + \"px,0px)\";\r\n\t\t} else {\r\n\t\t\tdocument.getElementById(\"client_prosecutor_hp\").style.clip = \"rect(0px,\" + BAR_WIDTH * args[2] / 10 + \"px,\" + BAR_HEIGHT + \"px,0px)\";\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Handles the issuance of a player ID by the server.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleID(args) {\r\n\t\tthis.playerID = args[1];\r\n\t}\r\n\r\n\thandlePN(args) {\r\n\t\tthis.serv.send(\"askchaa#%\");\r\n\t}\r\n\r\n\t/**\r\n\t * Received when the server announces its server info,\r\n\t * but we use it as a cue to begin retrieving characters.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleSI(args) {\r\n\t\tif (oldLoading) {\r\n\t\t\tthis.serv.send(\"askchar2#%\");\r\n\t\t} else {\r\n\t\t\tthis.serv.send(\"RC#%\");\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the list of all used and vacant characters.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandleCharsCheck(args) {\r\n\t\tdocument.getElementById(\"client_chartable\").innerHTML = \"\";\r\n\t\tfor (let i = 0; i < this.chars.length; i++) {\r\n\t\t\tif (i % CHAR_SELECT_WIDTH == 0) {\r\n\t\t\t\tvar tr = document.createElement('TR');\r\n\t\t\t}\r\n\t\t\tlet td = document.createElement('TD');\r\n\t\t\tlet icon_chosen;\r\n\t\t\tlet thispick = this.chars[i].icon;\r\n\t\t\tif (args[i + 1] == \"-1\") {\r\n\t\t\t\ticon_chosen = \" dark\";\r\n\t\t\t} else {\r\n\t\t\t\ticon_chosen = \"\";\r\n\t\t\t}\r\n\t\t\ttd.innerHTML = `<img class='demothing${icon_chosen}' id='demo_${i}' ` +\r\n\t\t\t\t`src='${thispick}' alt='${this.chars[i].name}' onclick='pickchar(${i})' ` +\r\n\t\t\t\t`onerror='demoError(this);'>`;\r\n\t\t\ttr.appendChild(td);\r\n\t\t\tif (i % CHAR_SELECT_WIDTH == 0) {\r\n\t\t\t\tdocument.getElementById(\"client_chartable\").appendChild(tr);\r\n\t\t\t}\r\n\t\t}\r\n\t\tchangeBackground(\"def\");\r\n\t}\r\n\r\n\t/**\r\n\t * Handles the server's assignment of a character for the player to use.\r\n\t * @param {Array} args packet arguments\r\n\t */\r\n\thandlePV(args) {\r\n\t\tthis.charID = args[3];\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\tlet me = this.me();\r\n\t\tlet emotes = this.emotes;\r\n\t\tlet xhr = new XMLHttpRequest();\r\n\t\txhr.open('GET', AO_HOST + 'characters/' + escape(this.me().name) + '/char.ini', true);\r\n\t\txhr.responseType = 'text';\r\n\t\txhr.onload = function (e) {\r\n\t\t\tif (this.status == 200) {\r\n\t\t\t\tlet linifile = this.responseText;\r\n\t\t\t\tlet pinifile = INI.parse(linifile);\r\n\t\t\t\tme.side = pinifile.Options.side;\r\n\t\t\t\tfor (let i = 1; i < pinifile.Emotions.number; i++) {\r\n\t\t\t\t\tlet emoteinfo = pinifile.Emotions[i].split('#');\r\n\t\t\t\t\tlet esfx = \"0\";\r\n\t\t\t\t\tlet esfxd = \"0\";\r\n\t\t\t\t\tif (typeof pinifile.SoundN !== 'undefined') {\r\n\t\t\t\t\t\tesfx = pinifile.SoundN[i];\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (typeof pinifile.SoundT !== 'undefined') {\r\n\t\t\t\t\t\tesfxd = pinifile.SoundT[i];\r\n\t\t\t\t\t}\r\n\t\t\t\t\temotes[i] = {\r\n\t\t\t\t\t\tdesc: emoteinfo[0],\r\n\t\t\t\t\t\tspeaking: emoteinfo[1],\r\n\t\t\t\t\t\tsilent: emoteinfo[2],\r\n\t\t\t\t\t\tzoom: emoteinfo[3],\r\n\t\t\t\t\t\tsfx: esfx,\r\n\t\t\t\t\t\tsfxdelay: esfxd,\r\n\t\t\t\t\t\tbutton_off: AO_HOST + 'characters/' + escape(me.name) + '/emotions/button' + i + '_off.png',\r\n\t\t\t\t\t\tbutton_on: AO_HOST + 'characters/' + escape(me.name) + '/emotions/button' + i + '_on.png'\r\n\t\t\t\t\t};\r\n\t\t\t\t\tdocument.getElementById(\"client_emo\").innerHTML += \"<img src='\" + emotes[i].button_off + \"' id='emo_\" + i + \"' alt='\" + emotes[i].desc + \"' class='client_button' onclick='pickemotion(\" + i + \")'>\";\r\n\t\t\t\t}\r\n\t\t\t\tpickemotion(1);\r\n\t\t\t}\r\n\t\t};\r\n\t\txhr.send();\r\n\t}\t\t\r\n}\r\n\r\nclass Viewport {\r\n\tconstructor() {\r\n\t\tthis.textnow = \"\";\r\n\t\tthis.chatmsg = {\r\n\t\t\t\"isnew\": false,\r\n\t\t\t\"content\": \"\",\r\n\t\t\t\"objection\": \"0\",\r\n\t\t\t\"sound\": \"\",\r\n\t\t\t\"startpreanim\": false,\r\n\t\t\t\"startspeaking\": false,\r\n\t\t\t\"side\": null,\r\n\t\t\t\"color\": \"0\",\r\n\t\t\t\"snddelay\": 0,\r\n\t\t\t\"preanimdelay\": 0\r\n\t\t};\r\n\t\tthis.blip = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\tthis.blip.volume = 0.5;\r\n\r\n\t\t// Allocate multiple blip audio channels to make blips less jittery\r\n\r\n\t\t// TODO: read blip type (\"gender\") from ini\r\n\t\tthis.blipChannels = new Array(6);\r\n\t\tfor (let i = 0; i < this.blipChannels.length; i++) {\r\n\t\t\tthis.blipChannels[i] = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\t\tthis.blipChannels[i].volume = 0.5;\r\n\t\t}\r\n\t\tthis.currentBlipChannel = 0;\r\n\r\n\t\tthis.sfxaudio = new Audio(AO_HOST + 'sounds/general/sfx-blipmale.wav');\r\n\t\tthis.sfxplayed = 0;\r\n\r\n\t\tthis.music = new Audio();\r\n\t\tthis.music.play();\r\n\r\n\t\tthis.updater = null;\r\n\r\n\t\tthis.bgname = \"gs4\";\r\n\r\n\t\tthis.shoutTimer = 0;\r\n\t\tthis.textTimer = 0;\r\n\r\n\t\tthis._animating = false;\r\n\t}\r\n\r\n\t/**\r\n\t * Returns whether or not the viewport is busy\r\n\t * performing a task (animating).\r\n\t */\r\n\tisAnimating() {\r\n\t\treturn this._animating;\r\n\t}\r\n\r\n\t/**\r\n\t * Sets the volume of the blip sound.\r\n\t * @param {number} volume\r\n\t */\r\n\tsetBlipVolume(volume) {\r\n\t\tfor (let i = 0; i < this.blipChannels.length; i++) {\r\n\t\t\tthis.blipChannels[i].volume = volume;\r\n\t\t}\r\n\t}\r\n\r\n\t/**\r\n\t * Returns the path which the background is located in.\r\n\t */\r\n\tbgFolder() {\r\n\t\treturn `${AO_HOST}background/${this.bgname}/`;\r\n\t}\r\n\r\n\t/**\r\n\t * Sets a new emote.\r\n\t * @param {object} chatmsg the new chat message\r\n\t */\r\n\tsay(chatmsg) {\r\n\t\tthis.chatmsg = chatmsg;\r\n\t\tappendICLog(chatmsg.content, chatmsg.nameplate);\r\n\t\tchangeBackground(chatmsg.side);\r\n\t\tthis.textnow = '';\r\n\t\tthis.sfxplayed = 0;\r\n\t\tthis.textTimer = 0;\r\n\t\tthis._animating = true;\r\n\t\tclearTimeout(this.updater);\r\n\t\t//If preanim existed then determine the length\r\n\t\tif (chatmsg.preanim != \"-\") {\r\n\t\t\tchatmsg.preanimdelay = this.getAnimLength(AO_HOST + 'characters/' + escape(chatmsg.name) + '/' + chatmsg.preanim + '.gif',this.initUpdater);\r\n\t\t} else {\r\n\t\t\tthis.initUpdater(0)\r\n\t\t}\t\r\n\t}\r\n\t\r\n\t/**\r\n\t * Intialize updater\r\n\t * @param {int} animdelay the length of pre-animation \r\n\t */\r\n\tinitUpdater(animdelay){\r\n\t\tviewport.chatmsg.preanimdelay = parseInt(animdelay); \r\n\t\tviewport.updater = setTimeout(() => viewport.updateText(), UPDATE_INTERVAL);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Gets animation length.\r\n\t * @param {string} filename the animation file name\r\n\t * @param {function} callback the callback function\r\n\t */\r\n\tgetAnimLength(filename,callback) {\r\n\t\t//Source (Thanks to Ryman): https://codepen.io/Ryman/pen/wzioA\r\n\t\tvar request = new XMLHttpRequest();\r\n\t\trequest.open('GET', filename, true);\r\n\t\trequest.responseType = 'arraybuffer';\r\n\t\trequest.addEventListener('load', function () {\r\n\t\t\tvar arr = new Uint8Array(request.response),\r\n\t\t\t// Thanks to http://justinsomnia.org/2006/10/gif-animation-duration-calculation/\r\n\t\t\t// And http://www.w3.org/Graphics/GIF/spec-gif89a.txt\r\n\t\t\tbin = '', \r\n\t\t\tduration = 0;\r\n\t\t\t\r\n\t\t\tfor (var i = 0; i < arr.length; i++) {\t\t\t\t\r\n\t\t\t\tbin += String.fromCharCode( arr[i] )\r\n\r\n\t\t\t\t// Find a Graphic Control Extension hex(21F904__ ____ __00)\r\n\t\t\t\tif (arr[i] == 0x21 \r\n\t\t\t\t && arr[i + 1] == 0xF9 \r\n\t\t\t\t && arr[i + 2] == 0x04 \r\n\t\t\t\t && arr[i + 7] == 0x00) {\r\n\t\t\t\t // Swap 5th and 6th bytes to get the delay per frame\r\n\t\t\t\t let delay = (arr[i + 5] << 8) | (arr[i + 4] & 0xFF)\r\n\t\t\t\t \r\n\t\t\t\t // Should be aware browsers have a minimum frame delay \r\n\t\t\t\t // e.g. 6ms for IE, 2ms modern browsers (50fps)\r\n\t\t\t\t duration += delay < 2 ? 10 : (delay)\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\t// Return animation length\r\n\t\t\tcallback(duration * 10);\r\n\t\t});\r\n\t\trequest.send();\r\n\t}\r\n\r\n\t/**\r\n\t * Updates the chatbox based on the given text.\r\n\t * \r\n\t * XXX: This relies on a global variable `this.chatmsg`!\r\n\t */\r\n\tupdateText() {\r\n\t\t// Flip the character\r\n\t\tif (this.chatmsg.flip == 1){\r\n\t\t\tdocument.getElementById(\"client_char\").style.transform = \"scaleX(-1)\"; \r\n\t\t} else {\r\n\t\t\tdocument.getElementById(\"client_char\").style.transform = \"scaleX(1)\";\r\n\t\t}\r\n\t\t\t\r\n\t\tif (this._animating) {\r\n\t\t\tthis.updater = setTimeout(() => this.updateText(), UPDATE_INTERVAL);\r\n\t\t}\r\n\r\n\t\tif (this.chatmsg.isnew) {\r\n\t\t\t// Reset screen background\r\n\t\t\tdocument.getElementById(\"client_background\").style.backgroundColor = \"transparent\";\r\n\t\t\t//Hide message and evidence window\r\n\t\t\tdocument.getElementById(\"client_name\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_chat\").style.display = \"none\";\r\n\t\t\tdocument.getElementById(\"client_evi\").style.opacity = \"0\";\r\n\t\t\tdocument.getElementById(\"client_evi\").style.height = \"0%\";\r\n\t\t\tconst shouts = {\r\n\t\t\t\t\"1\": \"holdit\",\r\n\t\t\t\t\"2\": \"objection\",\r\n\t\t\t\t\"3\": \"takethat\"\r\n\t\t\t};\r\n\r\n\t\t\tlet shout = shouts[this.chatmsg.objection];\r\n\t\t\tif (typeof shout !== \"undefined\") {\r\n\t\t\t\tdocument.getElementById(\"client_shout\").src = AO_HOST + \"misc/\" + shout + \".gif\";\r\n\t\t\t\t(new Audio(`${AO_HOST}/characters/${this.chatmsg.name}/${shout}.wav`)).play();\r\n\t\t\t\tthis.shoutTimer = 850;\r\n\t\t\t} else {\r\n\t\t\t\tthis.shoutTimer = 0;\r\n\t\t\t}\r\n\r\n\t\t\tthis.chatmsg.isnew = false;\r\n\t\t\tthis.chatmsg.startpreanim = true;\r\n\t\t}\r\n\r\n\t\tif(this.textTimer >= this.shoutTimer && this.chatmsg.startpreanim) {\r\n\t\t\t// Effect stuff\r\n\t\t\tif (this.chatmsg.flash == 2){\r\n\t\t\t\t//Shake screen\r\n\t\t\t\tthis.sfxaudio.pause();\r\n\t\t\t\tthis.sfxplayed = 1;\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/sfx-stab.wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t\t$('#client_gamewindow').effect( \"shake\",{\"direction\":\"up\"});\r\n\t\t\t} else if (this.chatmsg.flash == 1) {\r\n\t\t\t\t//Flash screen\r\n\t\t\t\tdocument.getElementById(\"client_background\").style.backgroundColor = \"white\";\r\n\t\t\t\tthis.sfxaudio.pause();\r\n\t\t\t\tthis.sfxplayed = 1;\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/sfx-realization.wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t\t$('#client_gamewindow').effect(\"pulsate\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t//Pre-animation stuff\r\n\t\t\tif(this.chatmsg.preanimdelay > 0){\r\n\t\t\t\tdocument.getElementById(\"client_shout\").src = \"misc/placeholder.gif\";\r\n\t\t\t\tchangeBackground(this.chatmsg.side);\r\n\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.preanim + \".gif\";\r\n\t\t\t}\r\n\t\t\tthis.chatmsg.startpreanim = false;\r\n\t\t\tthis.chatmsg.startspeaking = true;\r\n\t\t} else if (this.textTimer >= this.shoutTimer + this.chatmsg.preanimdelay && !this.chatmsg.startpreanim) {\r\n\t\t\tif (this.chatmsg.startspeaking) {\r\n\t\t\t\tif(this.chatmsg.evidence > 0){\r\n\t\t\t\t\t// Prepare evidence\r\n\t\t\t\t\tdocument.getElementById(\"client_evi\").style.backgroundImage = \"url('\"+ client.evidences[this.chatmsg.evidence - 1].icon +\"')\";\r\n\t\t\t\t\r\n\t\t\t\t\tif (this.chatmsg.side == 'def'){\r\n\t\t\t\t\t\t// Only def show evidence on right\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.right = \"1.5em\";\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.left = \"initial\";\r\n\t\t\t\t\t\t$( \"#client_evi\" ).animate({\r\n\t\t\t\t\t\t\theight: \"30%\",\r\n\t\t\t\t\t\t\topacity: 1,\r\n\t\t\t\t\t\t\tmarginLeft: \"10.6in\"\r\n\t\t\t\t\t\t}, 250 );\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.right = \"initial\";\r\n\t\t\t\t\t\tdocument.getElementById(\"client_evi\").style.left = \"1.5em\";\r\n\t\t\t\t\t\t$( \"#client_evi\" ).animate({\r\n\t\t\t\t\t\t\theight: \"30%\",\r\n\t\t\t\t\t\t\topacity: 1,\r\n\t\t\t\t\t\t\tmarginRight: \"10.6in\"\r\n\t\t\t\t\t\t}, 250 );\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\t\r\n\t\t\t\t$(\"#client_name\").toggle( \"fade\" );\r\n\t\t\t\t$(\"#client_chat\").toggle(\"drop\",{\"direction\":\"down\"});\r\n\t\t\t\tif(this.chatmsg.preanimdelay == 0){\r\n\t\t\t\t\tdocument.getElementById(\"client_shout\").src = \"misc/placeholder.gif\";\r\n\t\t\t\t\tchangeBackground(this.chatmsg.side);\r\n\t\t\t\t}\r\n\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.speaking + \".gif\";\r\n\t\t\t\tdocument.getElementById(\"client_name\").style.fontSize = (document.getElementById(\"client_name\").offsetHeight * 0.7) + \"px\";\r\n\t\t\t\tdocument.getElementById(\"client_chat\").style.fontSize = (document.getElementById(\"client_chat\").offsetHeight * 0.25) + \"px\";\r\n\t\t\t\tdocument.getElementById(\"client_name\").innerHTML = \"<p>\" + escapeHtml(this.chatmsg.nameplate) + \"</p>\";\r\n\r\n\t\t\t\tconst colors = {\r\n\t\t\t\t\t\"0\": \"#ffffff\",\r\n\t\t\t\t\t\"1\": \"#00ff00\",\r\n\t\t\t\t\t\"2\": \"#ff0000\",\r\n\t\t\t\t\t\"3\": \"#ffaa00\",\r\n\t\t\t\t\t\"4\": \"#0000ff\",\r\n\t\t\t\t\t\"5\": \"#ffff00\",\r\n\t\t\t\t\t\"6\": \"#aa00aa\"\r\n\t\t\t\t}\r\n\t\t\t\tlet stylecolor = \"color: \" + (colors[this.chatmsg.color] || \"#ffffff\");\r\n\t\t\t\tdocument.getElementById(\"client_inner_chat\").style = stylecolor;\r\n\t\t\t\tthis.chatmsg.startspeaking = false;\r\n\r\n\t\t\t\tif (this.textnow == this.chatmsg.content) {\r\n\t\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.silent + \".gif\";\r\n\t\t\t\t\tthis._animating = false;\r\n\t\t\t\t\tclearTimeout(this.updater);\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\tif (this.textnow != this.chatmsg.content) {\r\n\t\t\t\t\tif (this.chatmsg.content.charAt(this.textnow.length) != \" \") {\r\n\t\t\t\t\t\tthis.blipChannels[this.currentBlipChannel].play();\r\n\t\t\t\t\t\tthis.currentBlipChannel++;\r\n\t\t\t\t\t\tthis.currentBlipChannel %= this.blipChannels.length;\r\n\t\t\t\t\t}\r\n\t\t\t\t\tthis.textnow = this.chatmsg.content.substring(0, this.textnow.length + 1);\r\n\t\t\t\t\tdocument.getElementById(\"client_inner_chat\").innerHTML = this.textnow;\r\n\t\t\t\t\tif (this.textnow == this.chatmsg.content) {\r\n\t\t\t\t\t\tthis.textTimer = 0;\r\n\t\t\t\t\t\tthis._animating = false;\r\n\t\t\t\t\t\tdocument.getElementById(\"client_char\").src = AO_HOST + \"characters/\" + escape(this.chatmsg.name) + \"/\" + this.chatmsg.silent + \".gif\";\r\n\t\t\t\t\t\tclearTimeout(this.updater);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\tif (!this.sfxplayed && this.chatmsg.snddelay + this.shoutTimer >= this.textTimer) {\r\n\t\t\tthis.sfxaudio.pause();\r\n\t\t\tthis.sfxplayed = 1;\r\n\t\t\tif (this.chatmsg.sound != \"0\" && this.chatmsg.sound != \"1\") {\r\n\t\t\t\tthis.sfxaudio.src = AO_HOST + \"sounds/general/\" + escape(this.chatmsg.sound) + \".wav\";\r\n\t\t\t\tthis.sfxaudio.play();\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.textTimer = this.textTimer + UPDATE_INTERVAL;\r\n\t}\r\n}\r\n\r\nclass INI {\r\n\tstatic parse(data) {\r\n\t\tlet regex = {\r\n\t\t\tsection: /^\\s*\\[\\s*([^\\]]*)\\s*\\]\\s*$/,\r\n\t\t\tparam: /^\\s*([\\w\\.\\-\\_]+)\\s*=\\s*(.*?)\\s*$/,\r\n\t\t\tcomment: /^\\s*;.*$/\r\n\t\t};\r\n\t\tlet value = {};\r\n\t\tlet lines = data.split(/\\r\\n|\\r|\\n/);\r\n\t\tlet section = null;\r\n\t\tlines.forEach(function(line) {\r\n\t\t\tif (regex.comment.test(line)) {\r\n\t\t\t\treturn;\r\n\t\t\t} else if (line.length == 0) {\r\n\t\t\t\treturn;\r\n\t\t\t} else if (regex.param.test(line)) {\r\n\t\t\t\tlet match = line.match(regex.param);\r\n\t\t\t\tif (section) {\r\n\t\t\t\t\tvalue[section][match[1]] = match[2];\r\n\t\t\t\t} else {\r\n\t\t\t\t\tvalue[match[1]] = match[2];\r\n\t\t\t\t}\r\n\t\t\t} else if (regex.section.test(line)) {\r\n\t\t\t\tlet match = line.match(regex.section);\r\n\t\t\t\tvalue[match[1]] = {};\r\n\t\t\t\tsection = match[1];\r\n\t\t\t};\r\n\t\t});\r\n\t\treturn value;\r\n\t}\r\n}\r\n\r\n/**\r\n * Triggered when the Return key is pressed on the out-of-character chat input box.\r\n * @param {KeyboardEvent} event\r\n */\r\nexport function onOOCEnter(event) {\r\n\tif (event.keyCode == 13) {\r\n\t\tclient.sendOOC(document.getElementById(\"client_oocinputbox\").value);\r\n\t\tdocument.getElementById(\"client_oocinputbox\").value = \"\";\r\n\t}\r\n}\r\nwindow.onOOCEnter = onOOCEnter;\r\n\r\n/**\r\n * Triggered when the Return key is pressed on the in-character chat input box.\r\n * @param {KeyboardEvent} event\r\n */\r\nexport function onEnter(event) {\r\n\tif (event.keyCode == 13) {\r\n\t\tlet mychar = client.me();\r\n\t\tlet myemo = client.myEmote();\r\n\t\tlet myevi = client.myEvidence();\r\n\t\tlet myflip = ((client.flip)? 1:0);\r\n\t\tlet mycolor = document.getElementById(\"textcolor\").value;\r\n\t\tlet ssfxname = \"0\";\r\n\t\tlet ssfxdelay = \"0\";\r\n\t\tif (document.getElementById(\"sendsfx\").checked) {\r\n\t\t\tssfxname = myemo.sfx;\r\n\t\t\tssfxdelay = myemo.sfxdelay;\r\n\t\t}\r\n\t\tclient.sendIC(myemo.speaking, mychar.name, myemo.silent, document.getElementById(\"client_inputbox\").value, mychar.side, ssfxname, myemo.zoom, ssfxdelay, selectedShout, myevi, myflip, selectedEffect, mycolor);\r\n\t}\r\n}\r\nwindow.onEnter = onEnter;\r\n\r\n/**\r\n * Resets the IC parameters for the player to enter a new chat message.\r\n * This should only be called when the player's previous chat message\r\n * was successfully sent/presented.\r\n */\r\nfunction resetICParams() {\r\n\tdocument.getElementById(\"client_inputbox\").value = \"\";\r\n\tif (selectedEffect) {\r\n\t\tdocument.getElementById(\"button_effect_\" + selectedEffect).className = \"client_button\";\r\n\t\tselectedEffect = 0;\r\n\t}\r\n\tif (selectedShout) {\r\n\t\tdocument.getElementById(\"button_\" + selectedShout).className = \"client_button\";\r\n\t\tselectedShout = 0;\r\n\t}\t\t\r\n}\r\n\r\n/**\r\n * Triggered when an item on the music list is clicked.\r\n * @param {MouseEvent} event\r\n */\r\nexport function musiclist_click(event) {\r\n\tlet playtrack = document.getElementById(\"client_musiclist\").value;\r\n\tclient.sendMusicChange(playtrack);\r\n}\r\nwindow.musiclist_click = musiclist_click;\r\n\r\n/**\r\n * Triggered when an item on the music list is clicked.\r\n * @param {MouseEvent} event\r\n */\r\nexport function area_click(el) {\r\n\tlet playtrack = el.textContent;\r\n\tclient.sendMusicChange(playtrack);\r\n}\r\nwindow.area_click = area_click;\r\n\r\n/**\r\n * Triggered by the music volume slider.\r\n */\r\nexport function changeMusicVolume() {\r\n\tviewport.music.volume = document.getElementById(\"client_mvolume\").value / 100;\r\n}\r\nwindow.changeMusicVolume = changeMusicVolume;\r\n\r\n/**\r\n * Triggered by the sound effect volume slider.\r\n */\r\nexport function changeSFXVolume() {\r\n\tviewport.sfxaudio.volume = document.getElementById(\"client_svolume\").value / 100;\r\n}\r\nwindow.changeSFXVolume = changeSFXVolume;\r\n\r\n/**\r\n * Triggered by the blip volume slider.\r\n */\r\nexport function changeBlipVolume() {\r\n\tviewport.setBlipVolume(document.getElementById(\"client_bvolume\").value / 100);\r\n}\r\nwindow.changeBlipVolume = changeBlipVolume;\r\n\r\n/**\r\n * Triggered when a character icon is clicked in the character selection menu.\r\n * @param {MouseEvent} event\r\n */\r\nexport function changeCharacter(event) {\r\n\tclient.sendLeaveRoom();\r\n\tdocument.getElementById(\"client_charselect\").style.display = \"block\";\r\n\tdocument.getElementById(\"client_emo\").innerHTML = \"\";\r\n}\r\nwindow.changeCharacter = changeCharacter;\r\n\r\n/**\r\n * Triggered when there was an error loading a character sprite.\r\n * @param {HTMLImageElement} image the element containing the missing image\r\n */\r\nexport function imgError(image) {\r\n\timage.onerror = \"\";\r\n\timage.src = \"misc/placeholder.gif\";\r\n\treturn true;\r\n}\r\nwindow.imgError = imgError;\r\n\r\n/**\r\n * Triggered when there was an error loading a character icon.\r\n * @param {HTMLImageElement} image the element containing the missing image\r\n */\r\nexport function demoError(image) {\r\n\timage.onerror = \"\";\r\n\timage.src = \"/misc/placeholder.png\";\r\n\treturn true;\r\n}\r\nwindow.demoError = demoError;\r\n\r\n/**\r\n * Checks if an image exists at the specified URI.\r\n * @param {string} url the URI to be checked\r\n */\r\nfunction ImageExist(url) {\r\n\tvar img = new Image();\r\n\timg.src = url;\r\n\treturn img.height != 0;\r\n}\r\n\r\n/**\r\n * Changes the viewport background based on a given position.\r\n * \r\n * Valid positions: `def, pro, hld, hlp, wit, jud`\r\n * @param {string} position the position to change into\r\n */\r\nfunction changeBackground(position) {\r\n\tvar standname;\r\n\tlet bgfolder = viewport.bgFolder();\r\n\tdocument.getElementById(\"client_fg\").style.display = \"none\";\r\n\tdocument.getElementById(\"client_bench\").style.display = \"none\";\r\n\tswitch (position) {\r\n\t\tcase \"def\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"defenseempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\";\r\n\t\t\tif(ImageExist(bgfolder + \"defensedesk.png\")){\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"defensedesk.png\"\r\n\t\t\t}else{\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"bancodefensa.png\"\r\n\t\t\t}\r\n\t\t\tstandname = \"defense\";\r\n\t\t\tbreak;\r\n\t\tcase \"pro\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"prosecutorempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\"\r\n\t\t\tif(ImageExist(bgfolder + \"defensedesk.png\")){\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"prosecutiondesk.png\"\r\n\t\t\t} else {\r\n\t\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"bancoacusacion.png\"\r\n\t\t\t}\t\t\t\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"hld\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"helperstand.png\"\r\n\t\t\tstandname = \"defense\";\r\n\t\t\tbreak;\r\n\t\tcase \"hlp\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"prohelperstand.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"wit\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"witnessempty.png\"\r\n\t\t\tdocument.getElementById(\"client_bench\").style.display = \"block\"\r\n\t\t\tdocument.getElementById(\"client_bench\").src = bgfolder + \"estrado.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t\tcase \"jud\":\r\n\t\t\tdocument.getElementById(\"client_court\").src = bgfolder + \"judgestand.png\"\r\n\t\t\tstandname = \"prosecution\";\r\n\t\t\tbreak;\r\n\t}\r\n\tif (viewport.chatmsg.type == 5) {\r\n\t\tdocument.getElementById(\"client_bench\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_court\").src = AO_HOST + \"themes/default/\" + standname + \"_speedlines.gif\";\r\n\t}\r\n}\r\n\r\n/**\r\n * Triggered when the reconnect button is pushed.\r\n */\r\nexport function ReconnectButton() {\r\n\tclient.cleanup();\r\n\tclient = new Client(serverIP);\r\n\tif (client) {\r\n\t\tmode = \"join\"; // HACK: see client.onOpen\r\n\t\tdocument.getElementById(\"client_error\").style.display = \"none\";\r\n\t}\r\n}\r\nwindow.ReconnectButton = ReconnectButton;\r\n\r\n/**\r\n * Triggered when the retry button is pushed (during the loading process).\r\n */\r\nexport function RetryButton() {\r\n\tclient.joinServer();\r\n}\r\nwindow.RetryButton = RetryButton;\r\n\r\n/**\r\n * Appends a message to the in-character chat log.\r\n * @param {string} toadd the string to be added\r\n * @param {string} name the name of the sender\r\n */\r\nfunction appendICLog(toadd, name = \"\", time = new Date()) {\r\n\tconst entry = document.createElement(\"p\");\r\n\tconst nameField = document.createElement(\"span\");\r\n\tnameField.id = \"iclog_name\";\r\n\tnameField.appendChild(document.createTextNode(name));\r\n\tentry.appendChild(nameField);\r\n\tentry.appendChild(document.createTextNode(toadd));\r\n\r\n\t// Only put a timestamp if the minute has changed.\r\n\tif (lastICMessageTime.getMinutes() !== time.getMinutes()) {\r\n\t\tconst timeStamp = document.createElement(\"span\");\r\n\t\ttimeStamp.id = \"iclog_time\";\r\n\t\ttimeStamp.innerText = time.toLocaleTimeString(undefined, {\r\n\t\t\thour: \"numeric\",\r\n\t\t\tminute: \"2-digit\"\r\n\t\t});\r\n\t\tentry.appendChild(timeStamp);\r\n\t}\r\n\r\n\tconst clientLog = document.getElementById(\"client_log\");\r\n\tclientLog.appendChild(entry);\r\n\r\n\tif (clientLog.scrollTop > clientLog.scrollHeight - 600) {\r\n\t\tclientLog.scrollTop = clientLog.scrollHeight;\r\n\t}\r\n\r\n\tlastICMessageTime = new Date();\r\n}\r\n\r\n/**\r\n * Requests to play as a character.\r\n * @param {number} ccharacter the character ID; if this is a large number, then spectator is chosen instead.\r\n */\r\nexport function pickchar(ccharacter) {\r\n\tif (ccharacter < 1000) {\r\n\t\tclient.sendCharacter(ccharacter);\r\n\t} else {\r\n\t\t// Spectator\r\n\t\tdocument.getElementById(\"client_charselect\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_inputbox\").style.display = \"none\";\r\n\t\tdocument.getElementById(\"client_emo\").style.display = \"none\";\r\n\t}\r\n}\r\nwindow.pickchar = pickchar;\r\n\r\n/**\r\n * Highlights and selects an emotion for in-character chat.\r\n * @param {string} emo the new emotion to be selected\r\n */\r\nexport function pickemotion(emo) {\r\n\tif (client.selectedEmote != -1) {\r\n\t\tdocument.getElementById(\"emo_\" + client.selectedEmote).src = client.myEmote().button_off;\r\n\t}\r\n\tclient.selectedEmote = emo\r\n\tdocument.getElementById(\"emo_\" + emo).src = client.myEmote().button_on;\r\n}\r\nwindow.pickemotion = pickemotion;\r\n\r\n/**\r\n * Highlights and selects an evidence for in-character chat.\r\n * @param {string} evidence the evidence to be presented\r\n */\r\nexport function pickevidence(evidence) {\r\n\tif (client.selectedEvidence != evidence) {\r\n\t\t//Update selected evidence\t\t\r\n\t\tif(client.selectedEvidence > 0){\r\n\t\t\tdocument.getElementById(\"evi_\" + client.selectedEvidence).className = \"client_button\";\r\n\t\t}\r\n\t\tdocument.getElementById(\"evi_\" + evidence).className = \"client_button dark\";\r\n\t\tclient.selectedEvidence = evidence;\r\n\t\t\r\n\t\t// Show evidence on information window\r\n\t\tdocument.getElementById(\"evi_name\").value = client.evidences[evidence - 1].name;\r\n\t\tdocument.getElementById(\"evi_desc\").value = client.evidences[evidence - 1].desc;\r\n\r\n\t\t//Update Icon\r\n\t\tlet icon_id = getIndexFromSelect(\"evi_select\", client.evidences[evidence - 1].filename);\r\n\t\tdocument.getElementById(\"evi_select\").selectedIndex = icon_id;\r\n\t\tif (icon_id == 0){\t\t\t\r\n\t\t\tdocument.getElementById(\"evi_filename\").value = client.evidences[evidence - 1].filename;\r\n\t\t}\r\n\t\tupdateEvidenceIcon();\r\n\t\t\r\n\t\t// Update button\r\n\t\tdocument.getElementById(\"evi_add\").className = \"client_button hover_button inactive\";\r\n\t\tdocument.getElementById(\"evi_edit\").className = \"client_button hover_button\";\r\n\t\tdocument.getElementById(\"evi_cancel\").className = \"client_button hover_button\";\r\n\t\tdocument.getElementById(\"evi_del\").className = \"client_button hover_button\";\r\n\t} else {\r\n\t\tcancelevidence();\r\n\t}\r\n}\r\nwindow.pickevidence = pickevidence;\r\n\r\n/**\r\n * Add evidence.\r\n */\r\nexport function addevidence() {\r\n\tlet evidence_select = document.getElementById('evi_select');\r\n\tclient.sendPE( document.getElementById('evi_name').value,\r\n\t\tdocument.getElementById('evi_desc').value,\r\n\t\t(evidence_select.selectedIndex == 0)? \r\n\t\t\tdocument.getElementById('evi_filename').value : \r\n\t\t\tevidence_select.options[evidence_select.selectedIndex].text \r\n\t\t);\r\n\tcancelevidence();\r\n}\r\nwindow.addevidence = addevidence;\r\n\r\n/**\r\n * Edit selected evidence.\r\n */\r\nexport function editevidence() {\r\n\tlet evidence_select = document.getElementById('evi_select');\r\n\tlet id = parseInt(client.selectedEvidence) - 1;\r\n\tclient.sendEE( id, \r\n\t\tdocument.getElementById('evi_name').value,\r\n\t\tdocument.getElementById('evi_desc').value,\r\n\t\t(evidence_select.selectedIndex == 0)? \r\n\t\t\tdocument.getElementById('evi_filename').value : \r\n\t\t\tevidence_select.options[evidence_select.selectedIndex].text \r\n\t\t);\r\n\tcancelevidence();\r\n}\r\nwindow.editevidence = editevidence;\r\n\r\n/**\r\n * Delete selected evidence.\r\n */\r\nexport function delevidence() {\r\n\tlet id = parseInt(client.selectedEvidence) - 1;\r\n\tclient.sendDE(id);\r\n\tcancelevidence();\r\n}\r\nwindow.delevidence = delevidence;\r\n\r\n/**\r\n * Cancel evidence selection.\r\n */\r\nexport function cancelevidence() {\r\n\t//Clear evidence data\r\n\tif(client.selectedEvidence > 0){\r\n\t\tdocument.getElementById(\"evi_\" + client.selectedEvidence).className = \"client_button\";\r\n\t}\r\n\tclient.selectedEvidence = 0;\r\n\t\r\n\t// Clear evidence on information window\r\n\tdocument.getElementById(\"evi_select\").selectedIndex = 0;\r\n\tupdateEvidenceIcon(); // Update icon widget\r\n\tdocument.getElementById(\"evi_filename\").value = \"\";\r\n\tdocument.getElementById(\"evi_name\").value = \"\";\r\n\tdocument.getElementById(\"evi_desc\").value = \"\";\r\n\tdocument.getElementById(\"evi_icon\").style.backgroundImage = \"url('misc/empty.png')\"; //Clear icon\r\n\t\r\n\t// Update button\r\n\tdocument.getElementById(\"evi_add\").className = \"client_button hover_button\";\r\n\tdocument.getElementById(\"evi_edit\").className = \"client_button hover_button inactive\";\r\n\tdocument.getElementById(\"evi_cancel\").className = \"client_button hover_button inactive\";\r\n\tdocument.getElementById(\"evi_del\").className = \"client_button hover_button inactive\";\r\n}\r\nwindow.cancelevidence = cancelevidence;\r\n\r\n/**\r\n * Find index of anything in select box.\r\n * @param {string} select_box the select element name\r\n * @param {string} value the value that need to be compared\r\n */\r\nexport function getIndexFromSelect(select_box, value) {\r\n\t\t//Find if icon alraedy existed in select box\r\n\t\tlet select_element = document.getElementById(select_box);\r\n\t\tfor (let i = 1; i < select_element.length; ++i){\r\n\t\t\tif (select_element.options[i].value == value){\r\n\t\t\t\treturn i;\r\n\t\t\t}\r\n\t\t}\r\n\t\treturn 0;\r\n}\r\nwindow.getIndexFromSelect = getIndexFromSelect;\r\n\r\n/**\r\n * Update evidence icon.\r\n */\r\nexport function updateEvidenceIcon() {\r\n\tlet evidence_select = document.getElementById(\"evi_select\");\r\n\tlet evidence_filename = document.getElementById(\"evi_filename\");\r\n\tlet evidence_iconbox = document.getElementById(\"evi_icon\");\r\n\t\r\n\tif (evidence_select.selectedIndex == 0) {\r\n\t\tevidence_filename.style.display = \"initial\";\r\n\t\tevidence_iconbox.style.backgroundImage = \"url('\" + AO_HOST + 'evidence/' + evidence_filename.value + \"')\";\r\n\t} else {\t\t\r\n\t\tevidence_filename.style.display = \"none\";\r\n\t\tevidence_iconbox.style.backgroundImage = \"url('\" + AO_HOST + 'evidence/' + evidence_select.value + \"')\" ;\r\n\t}\r\n}\r\nwindow.updateEvidenceIcon = updateEvidenceIcon;\r\n\r\n/**\r\n * Change background.\r\n */\r\nexport function changeBackgroundOOC() {\r\n\tlet filename = \"\", background_select = document.getElementById(\"bg_select\")\r\n\t\t, bg_command = document.getElementById(\"bg_command\").value;\r\n\tif (background_select.selectedIndex == 0) {\r\n\t\tfilename = document.getElementById(\"bg_filename\").value; \r\n\t} else{\r\n\t\tfilename = background_select.value;\r\n\t}\r\n\tclient.sendOOC(\"/\" + bg_command.replace(\"$1\",filename));\r\n}\r\nwindow.changeBackgroundOOC = changeBackgroundOOC;\r\n\r\n/**\r\n * Update background preview.\r\n */\r\nexport function updateBackgroundPreview() {\r\n\tlet background_select = document.getElementById(\"bg_select\");\r\n\tlet background_filename = document.getElementById(\"bg_filename\");\r\n\tlet background_preview = document.getElementById(\"bg_preview\");\r\n\t\r\n\tif (background_select.selectedIndex == 0) {\r\n\t\tbackground_filename.style.display = \"initial\";\r\n\t\tbackground_preview.src = AO_HOST + 'background/' + background_filename.value + \"/defenseempty.png\";\r\n\t} else {\r\n\t\tbackground_filename.style.display = \"none\";\r\n\t\tbackground_preview.src = AO_HOST + 'background/' + background_select.value + \"/defenseempty.png\";\r\n\t}\r\n}\r\nwindow.updateBackgroundPreview = updateBackgroundPreview;\r\n\r\n/**\r\n * Highlights and selects an effect for in-character chat.\r\n * If the same effect button is selected, then the effect is canceled.\r\n * @param {string} effect the new effect to be selected\r\n */\r\nexport function toggleaffect(effect) {\r\n\tif (effect == selectedEffect) {\r\n\t\tdocument.getElementById(\"button_effect_\" + effect).className = \"client_button\";\r\n\t\tselectedEffect = 0;\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_effect_\" + effect).className = \"client_button dark\";\r\n\t\tif (selectedEffect) {\r\n\t\t\tdocument.getElementById(\"button_effect_\" + selectedEffect).className = \"client_button\";\r\n\t\t}\r\n\t\tselectedEffect = effect;\r\n\t}\r\n}\r\nwindow.toggleaffect = toggleaffect;\r\n\r\n/**\r\n * Toggle flip for in-character chat.\r\n */\r\nexport function toggleflip() {\r\n\tif (client.flip) {\r\n\t\tdocument.getElementById(\"button_flip\").className = \"client_button\";\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_flip\").className = \"client_button dark\";\r\n\t}\r\n\tclient.flip = !client.flip;\r\n}\r\nwindow.toggleflip = toggleflip;\r\n\r\n/**\r\n * Toggle presentable for presenting evidence in-character chat.\r\n */\r\nexport function togglepresent() {\r\n\tif (client.presentable) {\r\n\t\tdocument.getElementById(\"button_present\").className = \"client_button\";\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_present\").className = \"client_button dark\";\r\n\t}\r\n\tclient.presentable = !client.presentable;\r\n}\r\nwindow.togglepresent = togglepresent;\r\n\r\n/**\r\n * Highlights and selects a menu.\r\n * @param {string} menu the menu to be selected\r\n */\r\nexport function togglemenu(menu) {\r\n\tif (menu != selectedMenu) {\r\n\t\tdocument.getElementById(\"menu_\" + menu).className = \"menu_icon active\";\r\n\t\tdocument.getElementById(\"content_\" + menu).className = \"menu_content active\";\r\n\t\tdocument.getElementById(\"menu_\" + selectedMenu).className = \"menu_icon\";\r\n\t\tdocument.getElementById(\"content_\" + selectedMenu).className = \"menu_content\";\r\n\t\tselectedMenu = menu;\r\n\t}\r\n}\r\nwindow.togglemenu = togglemenu;\r\n\r\n/**\r\n * Highlights and selects a shout for in-character chat.\r\n * If the same shout button is selected, then the shout is canceled.\r\n * @param {string} shout the new shout to be selected\r\n */\r\nexport function toggleshout(shout) {\r\n\tif (shout == selectedShout) {\r\n\t\tdocument.getElementById(\"button_\" + shout).className = \"client_button\";\r\n\t\tselectedShout = 0;\r\n\t} else {\r\n\t\tdocument.getElementById(\"button_\" + shout).className = \"client_button dark\";\r\n\t\tif (selectedShout) {\r\n\t\t\tdocument.getElementById(\"button_\" + selectedShout).className = \"client_button\";\r\n\t\t}\r\n\t\tselectedShout = shout;\r\n\t}\r\n}\r\nwindow.toggleshout = toggleshout;\r\n\r\n/**\r\n * Escapes a string to be HTML-safe.\r\n * \r\n * XXX: This is unnecessary if we use `createTextNode` instead!\r\n * @param {string} unsafe an unsanitized string\r\n */\r\nfunction escapeHtml(unsafe) {\r\n\treturn unsafe\r\n\t\t.replace(/&/g, \"&amp;\")\r\n\t\t.replace(/</g, \"&lt;\")\r\n\t\t.replace(/>/g, \"&gt;\")\r\n\t\t.replace(/\"/g, \"&quot;\")\r\n\t\t.replace(/'/g, \"&#039;\");\r\n}\r\n\r\n/**\r\n * Escapes a string to AO1 escape codes.\r\n * @param {string} estring the string to be escaped\r\n */\r\nfunction escapeChat(estring) {\r\n\treturn estring\r\n\t\t.replace(/#/g, \"<pound>\")\r\n\t\t.replace(/&/g, \"<and>\")\r\n\t\t.replace(/%/g, \"<percent>\")\r\n\t\t.replace(/\\$/g, \"<dollar>\");\r\n}\r\n\r\n/**\r\n * Unescapes a string to AO1 escape codes.\r\n * @param {string} estring the string to be unescaped\r\n */\r\nfunction unescapeChat(estring) {\r\n\treturn estring\r\n\t\t.replace(/<pound>/g, \"#\")\r\n\t\t.replace(/<and>/g, \"&\")\r\n\t\t.replace(/<percent>/g, \"%\")\r\n\t\t.replace(/<dollar>/g, \"$\");\r\n}\r\n\r\n/**\r\n * Encoding text on client side.\r\n * @param {string} estring the string to be encoded\r\n */\r\nfunction encodeChat(estring) {\r\n\tlet selectedEncoding = document.getElementById(\"client_encoding\").value;\r\n\tif (selectedEncoding == \"unicode\") {\r\n\t\t//Source: https://gist.github.com/mathiasbynens/1243213\r\n\t\treturn estring.replace(/[^\\0-~]/g, function(ch) {\r\n\t\t\treturn \"\\\\u\" + (\"000\" + ch.charCodeAt().toString(16)).slice(-4); });\r\n\t} else if (selectedEncoding == \"utf16\"){\r\n\t\t//Source: https://developers.google.com/web/updates/2012/06/How-to-convert-ArrayBuffer-to-and-from-String\r\n\t\tvar buffer = new ArrayBuffer(estring.length*2);\r\n\t\tvar result = new Uint16Array(buffer);\r\n\t\tfor (var i=0, strLen=estring.length; i < strLen; i++) {\r\n\t\t\tresult[i] = estring.charCodeAt(i);\r\n\t\t}\r\n\t\treturn String(result);\r\n\t} else {\r\n\t\treturn estring;\r\n\t}\r\n}\r\n\r\n/**\r\n * Decoding text on client side.\r\n * @param {string} estring the string to be decoded\r\n */\r\nfunction decodeChat(estring) {\r\n\tlet selectedDecoding = document.getElementById(\"client_decoding\").value;\r\n\tif (selectedDecoding == \"unicode\") {\r\n\t\t//Source: https://stackoverflow.com/questions/7885096/how-do-i-decode-a-string-with-escaped-unicode\r\n return estring.replace(/\\\\u([\\d\\w]{1,})/gi, function (match, group) {\r\n\t\t\treturn String.fromCharCode(parseInt(group, 16)); } );\r\n\t} else if (selectedDecoding == \"utf16\"){\t\r\n\t\t//Source: https://developers.google.com/web/updates/2012/06/How-to-convert-ArrayBuffer-to-and-from-String\r\n\t\treturn String.fromCharCode.apply(null, new Uint16Array(estring.split(\",\")));\r\n\t} else {\r\n\t\treturn estring;\r\n\t}\r\n}\r\n\r\n/**\r\n * Decoding text on client side.\r\n * @param {string} estring the string to be decoded\r\n */\r\nfunction decodeBBCode(estring) {\r\n\treturn estring\r\n\t\t.replace(/\\\\n/g, \"<br>\") // Newline \\n\r\n\t\t.replace(/\\[(\\/?)b\\]/g, \"<$1b>\") // Bold [b][/b]\r\n\t\t.replace(/\\[(\\/?)i\\]/g, \"<$1i>\") // Italic [i][/i]\r\n\t\t.replace(/\\[(\\/?)del\\]/g, \"<$1del>\") // Deleted [del][/del]\r\n\t\t.replace(/\\[(\\/?)u\\]/g, \"<$1ins>\") // Underline [u][/u]\r\n\t\t.replace(/\\[(\\/?)sub\\]/g, \"<$1sub>\") // Subscript [sub][/sub]\r\n\t\t.replace(/\\[(\\/?)sup\\]/g, \"<$1sup>\") // Superscript [sup][/sup]\r\n\t\t.replace(/\\[m=([#a-zA-Z0-9]+)\\]/g, '<m a=\"$1\">') // Markup [m=#0ff]\r\n\t\t.replace(/\\[(\\/?)m\\]/g, '<$1m>') // [m][/m]\r\n\t\t.replace(/\\[c=?([#a-zA-Z0-9]+)\\]/g, '<c a=\"$1\">') // Color [c=red]\r\n\t\t.replace(/\\[\\/c\\]/g, '</c>'); // [/c]\r\n}\r\n\r\n\r\n// TODO: Possibly safe to remove, since we are using a transpiler.\r\nif (typeof(String.prototype.trim) === \"undefined\")\r\n{\r\n String.prototype.trim = function() \r\n {\r\n return String(this).replace(/^\\s+|\\s+$/g, '');\r\n };\r\n}\r\n\r\n// Used for HDID calculation.\r\nString.prototype.hashCode = function() {\r\n\tvar hash = 0, i, chr;\r\n\tif (this.length === 0) return hash;\r\n\tfor (i = 0; i < this.length; i++) {\r\n\t chr = this.charCodeAt(i);\r\n\t hash = ((hash << 5) - hash) + chr;\r\n\t hash |= 0; // Convert to 32bit integer\r\n\t}\r\n\treturn hash;\r\n};\r\n\r\n\r\n//\r\n// Client code\r\n//\r\n\r\nlet client = new Client(serverIP);\r\nlet viewport = new Viewport();\r\n\r\n$(document).ready(function(){\r\n\tclient.initialObservBBCode();\r\n\tclient.loadResources(); \r\n});\r\n"],"sourceRoot":""} \ No newline at end of file
diff --git a/webAO/client.js b/webAO/client.js
index b2be1e6..145a83b 100644
--- a/webAO/client.js
+++ b/webAO/client.js
@@ -590,8 +590,8 @@ class Client {
let bg_index = getIndexFromSelect("bg_select", escape(args[1]));
document.getElementById("bg_select").selectedIndex = bg_index;
updateBackgroundPreview();
- if(bg_index > 0){
- document.getElementById("bg_filename").value = escape(args[1]);
+ if(bg_index == 0){
+ document.getElementById("bg_filename").value = args[1];
}
document.getElementById("bg_preview").src = AO_HOST + 'background/' + escape(args[1]) + "/defenseempty.png";