@chronodivide/game-api 0.73.0 → 0.74.0-dev.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +63 -11
- package/dist/index.js +15 -1
- package/dist/res/ra2cd.mix +0 -0
- package/package.json +6 -5
package/dist/index.js
CHANGED
|
@@ -1 +1,15 @@
|
|
|
1
|
-
import*as __WEBPACK_EXTERNAL_MODULE_fetch_blob_71f8024a__ from"fetch-blob";import*as __WEBPACK_EXTERNAL_MODULE_three__ from"three";import*as __WEBPACK_EXTERNAL_MODULE_websocket_polyfill_8396782d__ from"websocket-polyfill";import{createRequire as __WEBPACK_EXTERNAL_createRequire}from"module";import*as __WEBPACK_EXTERNAL_MODULE_es_dirname_044d89a0__ from"es-dirname";import*as __WEBPACK_EXTERNAL_MODULE_file_system_access_58c08c7f__ from"file-system-access";import*as __WEBPACK_EXTERNAL_MODULE_file_system_access_lib_adapters_node_js_b1c03fd5__ from"file-system-access/lib/adapters/node.js";var __webpack_modules__={251:(e,t,i)=>{i.r(t),i.d(t,{default:()=>s});const s=function(){"use strict";var i=new function(){this.blockSize=131072,this.minNewSize=this.blockSize,this.maxSize=0,this.OK=0,this.INPUT_OVERRUN=-4,this.OUTPUT_OVERRUN=-5,this.LOOKBEHIND_OVERRUN=-6,this.EOF_FOUND=-999,this.ret=0,this.buf=null,this.buf32=null,this.out=new Uint8Array(262144),this.cbl=0,this.ip_end=0,this.op_end=0,this.t=0,this.ip=0,this.op=0,this.m_pos=0,this.m_len=0,this.m_off=0,this.dv_hi=0,this.dv_lo=0,this.dindex=0,this.ii=0,this.jj=0,this.tt=0,this.v=0,this.dict=new Uint32Array(16384),this.emptyDict=new Uint32Array(16384),this.skipToFirstLiteralFun=!1,this.returnNewBuffers=!0,this.setBlockSize=function(e){return"number"==typeof e&&!isNaN(e)&&0<parseInt(e)&&(this.blockSize=parseInt(e),!0)},this.setOutputSize=function(e){return"number"==typeof e&&!isNaN(e)&&0<parseInt(e)&&(this.out=new Uint8Array(parseInt(e)),!0)},this.setReturnNewBuffers=function(e){this.returnNewBuffers=!!e},this.applyConfig=function(e){void 0!==e&&(void 0!==e.outputSize&&i.setOutputSize(e.outputSize),void 0!==e.blockSize&&i.setBlockSize(e.blockSize))},this.ctzl=function(e){var t;return 1&e?t=0:(t=1,0==(65535&e)&&(e>>=16,t+=16),0==(255&e)&&(e>>=8,t+=8),0==(15&e)&&(e>>=4,t+=4),0==(3&e)&&(e>>=2,t+=2),t-=1&e),t},this.extendBuffer=function(){var e=new Uint8Array(this.minNewSize+(this.blockSize-this.minNewSize%this.blockSize));e.set(this.out),this.out=e,this.cbl=this.out.length},this.match_next=function(){this.minNewSize=this.op+3,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.buf[this.ip++],1<this.t&&(this.out[this.op++]=this.buf[this.ip++],2<this.t&&(this.out[this.op++]=this.buf[this.ip++])),this.t=this.buf[this.ip++]},this.match_done=function(){return this.t=3&this.buf[this.ip-2],this.t},this.copy_match=function(){for(this.t+=2,this.minNewSize=this.op+this.t,this.minNewSize>this.cbl&&this.extendBuffer();this.out[this.op++]=this.out[this.m_pos++],0<--this.t;);},this.copy_from_buf=function(){for(this.minNewSize=this.op+this.t,this.minNewSize>this.cbl&&this.extendBuffer();this.out[this.op++]=this.buf[this.ip++],0<--this.t;);},this.match=function(){for(;;){if(64<=this.t)this.m_pos=this.op-1-(this.t>>2&7)-(this.buf[this.ip++]<<3),this.t=(this.t>>5)-1,this.copy_match();else if(32<=this.t){if(this.t&=31,0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=31+this.buf[this.ip++]}this.m_pos=this.op-1-(this.buf[this.ip]>>2)-(this.buf[this.ip+1]<<6),this.ip+=2,this.copy_match()}else if(16<=this.t){if(this.m_pos=this.op-((8&this.t)<<11),this.t&=7,0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=7+this.buf[this.ip++]}if(this.m_pos-=(this.buf[this.ip]>>2)+(this.buf[this.ip+1]<<6),this.ip+=2,this.m_pos===this.op)return this.state.outputBuffer=!0===this.returnNewBuffers?new Uint8Array(this.out.subarray(0,this.op)):this.out.subarray(0,this.op),this.EOF_FOUND;this.m_pos-=16384,this.copy_match()}else this.m_pos=this.op-1-(this.t>>2)-(this.buf[this.ip++]<<2),this.minNewSize=this.op+2,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos];if(0===this.match_done())return this.OK;this.match_next()}},this.decompress=function(e){if(this.state=e,this.buf=this.state.inputBuffer,this.cbl=this.out.length,this.ip_end=this.buf.length,this.t=0,this.ip=0,this.op=0,this.m_pos=0,this.skipToFirstLiteralFun=!1,17<this.buf[this.ip])if(this.t=this.buf[this.ip++]-17,this.t<4){if(this.match_next(),this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret}else this.copy_from_buf(),this.skipToFirstLiteralFun=!0;for(;;){if(this.skipToFirstLiteralFun)this.skipToFirstLiteralFun=!1;else{if(this.t=this.buf[this.ip++],16<=this.t){if(this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret;continue}if(0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=15+this.buf[this.ip++]}this.t+=3,this.copy_from_buf()}if(this.t=this.buf[this.ip++],this.t<16){if(this.m_pos=this.op-2049,this.m_pos-=this.t>>2,this.m_pos-=this.buf[this.ip++]<<2,this.minNewSize=this.op+3,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos],0===this.match_done())continue;this.match_next()}if(this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret}return this.OK},this._compressCore=function(){for(this.ip_start=this.ip,this.ip_end=this.ip+this.ll-20,this.jj=this.ip,this.ti=this.t,this.ip+=this.ti<4?4-this.ti:0,this.ip+=1+(this.ip-this.jj>>5);!(this.ip>=this.ip_end);)if(this.dv_lo=this.buf[this.ip]|this.buf[this.ip+1]<<8,this.dv_hi=this.buf[this.ip+2]|this.buf[this.ip+3]<<8,this.dindex=((17053*this.dv_lo>>>16)+17053*this.dv_hi+6180*this.dv_lo&65535)>>>2,this.m_pos=this.ip_start+this.dict[this.dindex],this.dict[this.dindex]=this.ip-this.ip_start,(this.dv_hi<<16)+this.dv_lo==(this.buf[this.m_pos]|this.buf[this.m_pos+1]<<8|this.buf[this.m_pos+2]<<16|this.buf[this.m_pos+3]<<24)){if(this.jj-=this.ti,this.ti=0,this.v=this.ip-this.jj,0!==this.v)if(this.v<=3)for(this.out[this.op-2]|=this.v;this.out[this.op++]=this.buf[this.jj++],0<--this.v;);else{if(this.v<=18)this.out[this.op++]=this.v-3;else{for(this.tt=this.v-18,this.out[this.op++]=0;255<this.tt;)this.tt-=255,this.out[this.op++]=0;this.out[this.op++]=this.tt}for(;this.out[this.op++]=this.buf[this.jj++],0<--this.v;);}if(this.m_len=4,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len])for(;this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&!(this.ip+this.m_len>=this.ip_end)&&this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]))))))););if(this.m_off=this.ip-this.m_pos,this.ip+=this.m_len,this.jj=this.ip,this.m_len<=8&&this.m_off<=2048)--this.m_off,this.out[this.op++]=this.m_len-1<<5|(7&this.m_off)<<2,this.out[this.op++]=this.m_off>>3;else if(this.m_off<=16384){if(--this.m_off,this.m_len<=33)this.out[this.op++]=32|this.m_len-2;else{for(this.m_len-=33,this.out[this.op++]=32;255<this.m_len;)this.m_len-=255,this.out[this.op++]=0;this.out[this.op++]=this.m_len}this.out[this.op++]=this.m_off<<2,this.out[this.op++]=this.m_off>>6}else{if(this.m_off-=16384,this.m_len<=9)this.out[this.op++]=16|this.m_off>>11&8|this.m_len-2;else{for(this.m_len-=9,this.out[this.op++]=16|this.m_off>>11&8;255<this.m_len;)this.m_len-=255,this.out[this.op++]=0;this.out[this.op++]=this.m_len}this.out[this.op++]=this.m_off<<2,this.out[this.op++]=this.m_off>>6}}else this.ip+=1+(this.ip-this.jj>>5);this.t=this.ll-(this.jj-this.ip_start-this.ti)},this.compress=function(e){for(this.state=e,this.ip=0,this.buf=this.state.inputBuffer,this.maxSize=this.buf.length+Math.ceil(this.buf.length/16)+64+3,this.maxSize>this.out.length&&(this.out=new Uint8Array(this.maxSize)),this.op=0,this.l=this.buf.length,this.t=0;20<this.l&&(this.ll=this.l<=49152?this.l:49152,!(this.t+this.ll>>5<=0));)this.dict.set(this.emptyDict),this.prev_ip=this.ip,this._compressCore(),this.ip=this.prev_ip+this.ll,this.l-=this.ll;if(this.t+=this.l,0<this.t){if(this.ii=this.buf.length-this.t,0===this.op&&this.t<=238)this.out[this.op++]=17+this.t;else if(this.t<=3)this.out[this.op-2]|=this.t;else if(this.t<=18)this.out[this.op++]=this.t-3;else{for(this.tt=this.t-18,this.out[this.op++]=0;255<this.tt;)this.tt-=255,this.out[this.op++]=0;this.out[this.op++]=this.tt}for(;this.out[this.op++]=this.buf[this.ii++],0<--this.t;);}return this.out[this.op++]=17,this.out[this.op++]=0,this.out[this.op++]=0,this.state.outputBuffer=!0===this.returnNewBuffers?new Uint8Array(this.out.subarray(0,this.op)):this.out.subarray(0,this.op),this.OK}};return{setBlockSize:function(e){return i.setBlockSize(e)},setOutputEstimate:function(e){return i.setOutputSize(e)},setReturnNewBuffers:function(e){i.setReturnNewBuffers(e)},compress:function(e,t){return void 0!==t&&i.applyConfig(t),i.compress(e)},decompress:function(e,t){return void 0!==t&&i.applyConfig(t),i.decompress(e)}}}()},163:function(h,l,c){var u;!function(){"use strict";function e(e,t){return function(){return t.apply(e,arguments)}}function i(){for(var e,t=arguments,i=t[0],s=1;s<t.length;s++)for(e in t[s])e in i||!t[s].hasOwnProperty(e)||(i[e]=t[s][e]);return i}var s,o={VERSION:"1.4.1"},r={},t=function(e,t){return{value:e,name:t}};o.DEBUG=t(1,"DEBUG"),o.INFO=t(2,"INFO"),o.TIME=t(3,"TIME"),o.WARN=t(4,"WARN"),o.ERROR=t(8,"ERROR"),o.OFF=t(99,"OFF");function a(e){this.context=e,this.setLevel(e.filterLevel),this.log=this.info}a.prototype={setLevel:function(e){e&&"value"in e&&(this.context.filterLevel=e)},getLevel:function(){return this.context.filterLevel},enabledFor:function(e){var t=this.context.filterLevel;return e.value>=t.value},debug:function(){this.invoke(o.DEBUG,arguments)},info:function(){this.invoke(o.INFO,arguments)},warn:function(){this.invoke(o.WARN,arguments)},error:function(){this.invoke(o.ERROR,arguments)},time:function(e){"string"==typeof e&&0<e.length&&this.invoke(o.TIME,[e,"start"])},timeEnd:function(e){"string"==typeof e&&0<e.length&&this.invoke(o.TIME,[e,"end"])},invoke:function(e,t){s&&this.enabledFor(e)&&s(t,i({level:e},this.context))}};var n=new a({filterLevel:o.OFF});(t=o).enabledFor=e(n,n.enabledFor),t.debug=e(n,n.debug),t.time=e(n,n.time),t.timeEnd=e(n,n.timeEnd),t.info=e(n,n.info),t.warn=e(n,n.warn),t.error=e(n,n.error),t.log=t.info,o.setHandler=function(e){s=e},o.setLevel=function(e){for(var t in n.setLevel(e),r)r.hasOwnProperty(t)&&r[t].setLevel(e)},o.getLevel=function(){return n.getLevel()},o.get=function(e){return r[e]||(r[e]=new a(i({name:e},n.context)))},o.createDefaultHandler=function(r){(r=r||{}).formatter=r.formatter||function(e,t){t.name&&e.unshift("["+t.name+"]")};function a(e,t){Function.prototype.apply.call(e,console,t)}var n={};return"undefined"==typeof console?function(){}:function(e,t){e=Array.prototype.slice.call(e);var i,s=console.log;t.level===o.TIME?(i=(t.name?"["+t.name+"] ":"")+e[0],"start"===e[1]?console.time?console.time(i):n[i]=(new Date).getTime():console.timeEnd?console.timeEnd(i):a(s,[i+": "+((new Date).getTime()-n[i])+"ms"])):(t.level===o.WARN&&console.warn?s=console.warn:t.level===o.ERROR&&console.error?s=console.error:t.level===o.INFO&&console.info?s=console.info:t.level===o.DEBUG&&console.debug&&(s=console.debug),r.formatter(e,t),a(s,e))}},o.useDefaults=function(e){o.setLevel(e&&e.defaultLevel||o.DEBUG),o.setHandler(o.createDefaultHandler(e))},void 0===(u="function"==typeof(u=o)?u.call(l,c,l,h):u)||(h.exports=u)}()},948:e=>{function t(e){null==e&&(e=(new Date).getTime()),this.N=624,this.M=397,this.MATRIX_A=2567483615,this.UPPER_MASK=2147483648,this.LOWER_MASK=2147483647,this.mt=new Array(this.N),this.mti=this.N+1,e.constructor==Array?this.init_by_array(e,e.length):this.init_seed(e)}t.prototype.init_seed=function(e){for(this.mt[0]=e>>>0,this.mti=1;this.mti<this.N;this.mti++){e=this.mt[this.mti-1]^this.mt[this.mti-1]>>>30;this.mt[this.mti]=(1812433253*((4294901760&e)>>>16)<<16)+1812433253*(65535&e)+this.mti,this.mt[this.mti]>>>=0}},t.prototype.init_by_array=function(e,t){var i,s,r;for(this.init_seed(19650218),i=1,s=0,r=this.N>t?this.N:t;r;r--){var a=this.mt[i-1]^this.mt[i-1]>>>30;this.mt[i]=(this.mt[i]^(1664525*((4294901760&a)>>>16)<<16)+1664525*(65535&a))+e[s]+s,this.mt[i]>>>=0,s++,++i>=this.N&&(this.mt[0]=this.mt[this.N-1],i=1),t<=s&&(s=0)}for(r=this.N-1;r;r--){a=this.mt[i-1]^this.mt[i-1]>>>30;this.mt[i]=(this.mt[i]^(1566083941*((4294901760&a)>>>16)<<16)+1566083941*(65535&a))-i,this.mt[i]>>>=0,++i>=this.N&&(this.mt[0]=this.mt[this.N-1],i=1)}this.mt[0]=2147483648},t.prototype.random_int=function(){var e,t,i=new Array(0,this.MATRIX_A);if(this.mti>=this.N){for(this.mti==this.N+1&&this.init_seed(5489),t=0;t<this.N-this.M;t++)e=this.mt[t]&this.UPPER_MASK|this.mt[t+1]&this.LOWER_MASK,this.mt[t]=this.mt[t+this.M]^e>>>1^i[1&e];for(;t<this.N-1;t++)e=this.mt[t]&this.UPPER_MASK|this.mt[t+1]&this.LOWER_MASK,this.mt[t]=this.mt[t+(this.M-this.N)]^e>>>1^i[1&e];e=this.mt[this.N-1]&this.UPPER_MASK|this.mt[0]&this.LOWER_MASK,this.mt[this.N-1]=this.mt[this.M-1]^e>>>1^i[1&e],this.mti=0}return e=this.mt[this.mti++],e^=e>>>11,e^=e<<7&2636928640,e^=e<<15&4022730752,(e^=e>>>18)>>>0},t.prototype.random_int31=function(){return this.random_int()>>>1},t.prototype.random_incl=function(){return this.random_int()*(1/4294967295)},t.prototype.random=function(){return this.random_int()*(1/4294967296)},t.prototype.random_excl=function(){return(this.random_int()+.5)*(1/4294967296)},t.prototype.random_long=function(){return 1/9007199254740992*(67108864*(this.random_int()>>>5)+(this.random_int()>>>6))},e.exports=t},91:e=>{e.exports=__WEBPACK_EXTERNAL_MODULE_fetch_blob_71f8024a__},949:e=>{e.exports=__WEBPACK_EXTERNAL_MODULE_three__}},__webpack_module_cache__={};function __webpack_require__(e){var t=__webpack_module_cache__[e];if(void 0!==t)return t.exports;t=__webpack_module_cache__[e]={exports:{}};return __webpack_modules__[e].call(t.exports,t,t.exports,__webpack_require__),t.exports}__webpack_require__.n=e=>{var t=e&&e.__esModule?()=>e.default:()=>e;return __webpack_require__.d(t,{a:t}),t},__webpack_require__.d=(e,t)=>{for(var i in t)__webpack_require__.o(t,i)&&!__webpack_require__.o(e,i)&&Object.defineProperty(e,i,{enumerable:!0,get:t[i]})},__webpack_require__.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t),__webpack_require__.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var __webpack_exports__={};(()=>{__webpack_require__.r(__webpack_exports__),__webpack_require__.d(__webpack_exports__,{ApiEventType:()=>hp,ArmorType:()=>ni,AttackState:()=>bn,Bot:()=>tp,Box2:()=>Yn,BuildCat:()=>es,BuildStatus:()=>xn,Cylindrical:()=>n0,Euler:()=>s0,FactoryStatus:()=>_n,FactoryType:()=>ts,GameInstanceApi:()=>Lm,GameMath:()=>Ki,InfDeathType:()=>ii,LandTargeting:()=>oi,LandType:()=>ei,LocomotorType:()=>ri,Matrix4:()=>Qs,MovementZone:()=>ai,NavalTargeting:()=>hi,ObjectType:()=>Et,OrderType:()=>Pn,PipColor:()=>si,PrereqCategory:()=>Kt,PublicApi:()=>Hm,Quaternion:()=>Ji,QueueStatus:()=>Tn,QueueType:()=>wn,RadarEventType:()=>Yt,SideType:()=>Qt,SpeedType:()=>ti,Spherical:()=>a0,StanceType:()=>Fs,SuperWeaponStatus:()=>Ds,SuperWeaponType:()=>ss,TagRepeatType:()=>qt,TerrainType:()=>Jt,TheaterType:()=>I,Vector2:()=>Os,Vector3:()=>as,VeteranAbility:()=>ci,VeteranLevel:()=>ta,VhpScan:()=>ui,WeaponType:()=>li,ZoneType:()=>Ss,cdapi:()=>o0});__WEBPACK_EXTERNAL_MODULE_websocket_polyfill_8396782d__;const S=__WEBPACK_EXTERNAL_createRequire(import.meta.url)("node:crypto"),a=__WEBPACK_EXTERNAL_createRequire(import.meta.url)("path");const e=__WEBPACK_EXTERNAL_MODULE_es_dirname_044d89a0__;const n=__WEBPACK_EXTERNAL_MODULE_file_system_access_58c08c7f__;const o=__WEBPACK_EXTERNAL_MODULE_file_system_access_lib_adapters_node_js_b1c03fd5__;class h{constructor(e){this.entries=new Map,this.sections=new Map,this.name=e}fromJson(e){for(var t in e){var i;e.hasOwnProperty(t)&&(i=e[t],Array.isArray(i)||"object"!=typeof i?this.set(t,i):this.sections.set(t,new h(t).fromJson(i)))}return this}clone(){let i=new h(this.name);return this.entries.forEach((e,t)=>{i.set(t,e)}),this.sections.forEach((e,t)=>{i.sections.set(t,e.clone())}),i}set(e,t){this.entries.set(e,t)}get(e){return this.entries.get(e)}has(e){return this.entries.has(e)}getString(e,t=""){e=this.get(e);return e&&"string"==typeof e?e:t}getNumber(e,t=0){var i=this.get(e);if(!i||"string"!=typeof i)return t;var s=this.parseNumber(i);return void 0===s?(console.warn(`Invalid value for key ${e}. "${i}" is not a valid number or percentage string.`),t):s}parseNumber(e){let t;if(t=e.match(/%$/)?Number(e.replace("%",""))/100:Number(e),!isNaN(t))return t}getFixed(e,t=0){return this.toFixedPointPrecision(this.getNumber(e,t))}toFixedPointPrecision(e){return(65536*e|0)/65536}getBool(e,t=!1){let i=this.getString(e).trim();return i=i&&i.toLowerCase(),!(!i||-1===["yes","1","true","on"].indexOf(i))||(!i||-1===["no","0","false","off"].indexOf(i))&&t}getKeyArray(e,t=[]){e=this.get(e);return e&&Array.isArray(e)?e:t}getArray(e,t=/,\s*/,i=[]){let s=this.getString(e).trim();return s=s.replace(/,$/,"").replace(/,+/g,","),s?s.split(t):i}getNumberArray(e,t=/,\s*/,i=[]){let s=this.getString(e).trim();if(!s)return i;let r=[];for(var a of s.split(t)){if(!a)return i;var n=this.parseNumber(a);if(void 0===n)return console.warn(`Invalid value for key ${e}. "${a}" is not a valid number or percentage string.`),i;r.push(n)}return r}getFixedArray(e,t=/,\s*/,i=[]){return this.getNumberArray(e,t,i).map(e=>this.toFixedPointPrecision(e))}getEnum(e,t,i,s=!1){let r=this.getString(e).trim();if(!r)return i;let a;if(s){let e=Object.getOwnPropertyNames(t);s=e.find(e=>e.toLowerCase()===r.toLowerCase());s&&(a=t[s])}else t.hasOwnProperty(r)&&(a=t[r]);return void 0===a?(console.warn(`Invalid value for key "${e}". "${r}" is not an accepted enum value.`),i):a}getEnumNumeric(e,t,i){var s=this.getString(e).trim();if(!s)return i;let r;return Number.isInteger(parseInt(s,10))&&t.hasOwnProperty(s)&&(r=parseInt(s,10)),void 0===r?(console.warn(`Invalid value for key "${e}". "${s}" is not an accepted enum value.`),i):r}getEnumArray(e,s,t=/,\s*/,r=[],a=!1){let n=this.getString(e).trim();if(!n)return r;let o=[];for(let i of n.split(t)){if(!i)return r;let t=!1;if(a){let e=Object.getOwnPropertyNames(s);var h=e.find(e=>e.toLowerCase()===i.toLowerCase());h&&(o.push(s[h]),t=!0)}else s.hasOwnProperty(i)&&(o.push(s[i]),t=!0);if(!t)return console.warn(`Invalid value "${i}" for key "${e}".`),r}return o}getHighestNumericIndex(){let i=0,s;return this.entries.forEach((e,t)=>{s=parseInt(t,10),s>i&&(i=s)}),i}isNumericIndexArray(){return 0<this.getHighestNumericIndex()||this.has("0")}getConcatenatedValues(){let e="";for(var t of this.entries.values())"string"==typeof t&&(e+=t);return e}toString(e){let t=[],i=`${e?e+".":""}${this.name}`;t.push(`[${i}]`);for(var[s,r]of this.entries)if(Array.isArray(r))for(var a of r)t.push(`${s}[]=${a}`);else t.push(`${s}=${r}`);return t.push(""),t.join("\r\n")+[...this.sections.values()].map(e=>e.toString(i)).join("\r\n")}mergeWith(e){if(this.isNumericIndexArray()){let i=this.getHighestNumericIndex()+1;e.entries.forEach((e,t)=>{Number.isNaN(Number(t))||Array.isArray(e)||this.set((i++).toString(),e)})}else e.entries.forEach((e,t)=>{this.set(t,Array.isArray(e)?[...e]:e)});e.sections.forEach((e,t)=>{let i=this.getOrCreateSection(t);i.mergeWith(e)})}getOrCreateSection(e){let t=this.sections.get(e);return t||(t=new h(e),this.sections.set(e,t)),t}getSection(e){return this.sections.get(e)}getOrderedSections(){return[...this.sections.values()]}}class t{parse(e){let a={},i=a,s,r=/^\[([^\]]*)\]\s*$|^([^=]+)(=(.*))?$/i,t=e.split(/[\r\n]+/g);return t.forEach(t=>{if(t&&!t.match(/^\s*[;#]/)){t=(t=t.replace(/]\s*(\/\/|;|#).*$/,"]")).match(r);if(t){if(void 0!==t[1])return s=this.unsafe(t[1]),void(i=a[s]=a[s]||{});let e=this.unsafe(t[2]);t=t[3]?this.unsafe(t[4]||""):"";2<e.length&&"[]"===e.slice(-2)&&(e=e.substring(0,e.length-2),i[e]?Array.isArray(i[e])||(i[e]=[i[e]]):i[e]=[]),Array.isArray(i[e])?i[e].push(t):i[e]=t}}}),Object.keys(a).filter(e=>{if(!a[e]||"object"!=typeof a[e]||Array.isArray(a[e]))return!1;let t=this.dotSplit(e),i=a,s=t.pop();var r=s.replace(/\\\./g,".");return t.forEach(function(e){i[e]&&"object"==typeof i[e]||(i[e]={}),i=i[e]}),(i!==a||r!==s)&&(i[r]=a[e],!0)}).forEach(function(e){delete a[e]}),a}dotSplit(e){return e.replace(/\x01/g,"LITERAL\\1LITERAL").replace(/\\\./g,"").split(/\./).map(e=>e.replace(/\x01/g,"\\.").replace(/\x02LITERAL\\1LITERAL\x02/g,""))}isQuoted(e){return'"'===e.charAt(0)&&'"'===e.slice(-1)||"'"===e.charAt(0)&&"'"===e.slice(-1)}unsafe(r){if(r=(r||"").trim(),this.isQuoted(r))return r=r.substr(1,r.length-2);{let i=!1,s="";for(let e=0,t=r.length;e<t;e++){var a=r.charAt(e);if(i)-1!=="\\;#".indexOf(a)?s+=a:s+="\\"+a,i=!1;else{if(-1!==";#".indexOf(a))break;"\\"===a?i=!0:s+=a}}return i&&(s+="\\"),s=s.trim(),s}}}class k{constructor(e,t,i=k.LITTLE_ENDIAN){this.endianness=i,this.position=0,this._dynamicSize=!0,this._byteLength=0,this._byteOffset=t||0,e instanceof ArrayBuffer?this.buffer=e:"object"==typeof e?(this.dataView=e,t&&(this._byteOffset+=t)):this.buffer=new ArrayBuffer(e||0)}get dynamicSize(){return this._dynamicSize}set dynamicSize(e){e||this._trimAlloc(),this._dynamicSize=e}get byteLength(){return this._byteLength-this._byteOffset}get buffer(){return this._trimAlloc(),this._buffer}set buffer(e){this._buffer=e,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._buffer.byteLength}get byteOffset(){return this._byteOffset}set byteOffset(e){this._byteOffset=e,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._buffer.byteLength}get dataView(){return this._dataView}set dataView(e){this._byteOffset=e.byteOffset,this._buffer=e.buffer,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._byteOffset+e.byteLength}bigEndian(){return this.endianness=k.BIG_ENDIAN,this}_realloc(t){if(this._dynamicSize){var i=this._byteOffset+this.position+t;let e=this._buffer.byteLength;if(i<=e)i>this._byteLength&&(this._byteLength=i);else{for(e<1&&(e=1);i>e;)e*=2;var s=new ArrayBuffer(e),t=new Uint8Array(this._buffer);const r=new Uint8Array(s,0,t.length);r.set(t),this.buffer=s,this._byteLength=i}}}_trimAlloc(){if(this._byteLength!==this._buffer.byteLength){var e=new ArrayBuffer(this._byteLength);const i=new Uint8Array(e);var t=new Uint8Array(this._buffer,0,i.length);i.set(t),this.buffer=e}}seek(e){e=Math.max(0,Math.min(this.byteLength,e));this.position=isNaN(e)||!isFinite(e)?0:e}isEof(){return this.position>=this.byteLength}mapInt32Array(e,t){this._realloc(4*e);var i=new Int32Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}mapInt16Array(e,t){this._realloc(2*e);var i=new Int16Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=2*e,i}mapInt8Array(e){this._realloc(e);var t=new Int8Array(this._buffer,this.byteOffset+this.position,e);return this.position+=e,t}mapUint32Array(e,t){this._realloc(4*e);var i=new Uint32Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}mapUint16Array(e,t){this._realloc(2*e);var i=new Uint16Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=2*e,i}mapUint8Array(e){this._realloc(e);var t=new Uint8Array(this._buffer,this.byteOffset+this.position,e);return this.position+=e,t}mapFloat64Array(e,t){this._realloc(8*e);var i=new Float64Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=8*e,i}mapFloat32Array(e,t){this._realloc(4*e);var i=new Float32Array(this._buffer,this.byteOffset+this.position,e);return k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}readInt32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Int32Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readInt16Array(e,t){e=void 0===e?this.byteLength-this.position/2:e;var i=new Int16Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readInt8Array(e){e=void 0===e?this.byteLength-this.position:e;var t=new Int8Array(e);return k.memcpy(t.buffer,0,this.buffer,this.byteOffset+this.position,e*t.BYTES_PER_ELEMENT),this.position+=t.byteLength,t}readUint32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Uint32Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readUint16Array(e,t){e=void 0===e?this.byteLength-this.position/2:e;var i=new Uint16Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readUint8Array(e){e=void 0===e?this.byteLength-this.position:e;var t=new Uint8Array(e);return k.memcpy(t.buffer,0,this.buffer,this.byteOffset+this.position,e*t.BYTES_PER_ELEMENT),this.position+=t.byteLength,t}readFloat64Array(e,t){e=void 0===e?this.byteLength-this.position/8:e;var i=new Float64Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readFloat32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Float32Array(e);return k.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),k.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}writeInt32Array(t,i){if(this._realloc(4*t.length),t instanceof Int32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeInt32(t[e],i);return this}writeInt16Array(t,i){if(this._realloc(2*t.length),t instanceof Int16Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt16Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeInt16(t[e],i);return this}writeInt8Array(t){if(this._realloc(t.length),t instanceof Int8Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt8Array(t.length);else for(let e=0;e<t.length;e++)this.writeInt8(t[e]);return this}writeUint32Array(t,i){if(this._realloc(4*t.length),t instanceof Uint32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeUint32(t[e],i);return this}writeUint16Array(t,i){if(this._realloc(2*t.length),t instanceof Uint16Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint16Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeUint16(t[e],i);return this}writeUint8Array(t){if(this._realloc(t.length),t instanceof Uint8Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint8Array(t.length);else for(let e=0;e<t.length;e++)this.writeUint8(t[e]);return this}writeFloat64Array(t,i){if(this._realloc(8*t.length),t instanceof Float64Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapFloat64Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeFloat64(t[e],i);return this}writeFloat32Array(t,i){if(this._realloc(4*t.length),t instanceof Float32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)k.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapFloat32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeFloat32(t[e],i);return this}readInt32(e){e=this._dataView.getInt32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readInt16(e){e=this._dataView.getInt16(this.position,void 0===e?this.endianness:e);return this.position+=2,e}readInt8(){var e=this._dataView.getInt8(this.position);return this.position+=1,e}readUint32(e){e=this._dataView.getUint32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readUint16(e){e=this._dataView.getUint16(this.position,void 0===e?this.endianness:e);return this.position+=2,e}readUint8(){var e=this._dataView.getUint8(this.position);return this.position+=1,e}readFloat32(e){e=this._dataView.getFloat32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readFloat64(e){e=this._dataView.getFloat64(this.position,void 0===e?this.endianness:e);return this.position+=8,e}writeInt32(e,t){return this._realloc(4),this._dataView.setInt32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeInt16(e,t){return this._realloc(2),this._dataView.setInt16(this.position,e,void 0===t?this.endianness:t),this.position+=2,this}writeInt8(e){return this._realloc(1),this._dataView.setInt8(this.position,e),this.position+=1,this}writeUint32(e,t){return this._realloc(4),this._dataView.setUint32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeUint16(e,t){return this._realloc(2),this._dataView.setUint16(this.position,e,void 0===t?this.endianness:t),this.position+=2,this}writeUint8(e){return this._realloc(1),this._dataView.setUint8(this.position,e),this.position+=1,this}writeFloat32(e,t){return this._realloc(4),this._dataView.setFloat32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeFloat64(e,t){return this._realloc(8),this._dataView.setFloat64(this.position,e,void 0===t?this.endianness:t),this.position+=8,this}static memcpy(e,t,i,s,r){const a=new Uint8Array(e,t,r);r=new Uint8Array(i,s,r);a.set(r)}static arrayToNative(e,t){return t===this.endianness?e:this.flipArrayEndianness(e)}static nativeToEndian(e,t){return this.endianness===t?e:this.flipArrayEndianness(e)}static flipArrayEndianness(s){const r=new Uint8Array(s.buffer,s.byteOffset,s.byteLength);for(let i=0;i<s.byteLength;i+=s.BYTES_PER_ELEMENT)for(let e=i+s.BYTES_PER_ELEMENT-1,t=i;e>t;e--,t++){var a=r[t];r[t]=r[e],r[e]=a}return s}static createStringFromArray(t){const i=[];for(let e=0;e<t.length;e+=32768)i.push(String.fromCharCode.apply(void 0,t.subarray(e,e+32768)));return i.join("")}readUCS2String(e,t){return k.createStringFromArray(this.readUint16Array(e,t))}writeUCS2String(e,t,i){void 0===i&&(i=e.length);let s=0;for(;s<e.length&&s<i;s++)this.writeUint16(e.charCodeAt(s),t);for(;s<i;s++)this.writeUint16(0);return this}readString(e,t){return void 0===t||"ASCII"===t?k.createStringFromArray(this.mapUint8Array(void 0===e?this.byteLength-this.position:e)):new TextDecoder(t).decode(this.mapUint8Array(e))}writeString(t,e,i){if(void 0===e||"ASCII"===e)if(void 0!==i){let e;var s=Math.min(t.length,i);for(e=0;e<s;e++)this.writeUint8(t.charCodeAt(e));for(;e<i;e++)this.writeUint8(0)}else for(let e=0;e<t.length;e++)this.writeUint8(t.charCodeAt(e));else this.writeUint8Array((new TextEncoder).encode(t.substring(0,i)));return this}writeUtf8WithLen(e){e=(new TextEncoder).encode(e);return this.writeUint16(e.length).writeUint8Array(e)}readUtf8WithLen(){var e=this.readUint16();return(new TextDecoder).decode(this.mapUint8Array(e))}readCString(e){var t=this.byteLength-this.position,i=new Uint8Array(this._buffer,this._byteOffset+this.position);let s=t;void 0!==e&&(s=Math.min(e,t));let r=0;for(;r<s&&0!==i[r];r++);var a=k.createStringFromArray(this.mapUint8Array(r));return void 0!==e?this.position+=s-r:r!==t&&(this.position+=1),a}writeCString(t,i){if(void 0!==i){let e;var s=Math.min(t.length,i);for(e=0;e<s;e++)this.writeUint8(t.charCodeAt(e));for(;e<i;e++)this.writeUint8(0)}else{for(let e=0;e<t.length;e++)this.writeUint8(t.charCodeAt(e));this.writeUint8(0)}return this}toUint8Array(){return new Uint8Array(this.buffer,this.byteOffset,this.byteLength)}}k.BIG_ENDIAN=!1,k.LITTLE_ENDIAN=!0,k.endianness=0<new Int8Array(new Int16Array([1]).buffer)[0];class l extends Error{constructor(){super(...arguments),this.name="IOError"}}class i{static async fromRealFile(t){try{const e=new k(await t.arrayBuffer());return e._trimAlloc=()=>{},new this(e,t.name)}catch(e){if(e instanceof DOMException)throw new l(`File "${t.name}" could not be read (${e.name})`,{cause:e});throw e}}static fromBytes(e,t){let i=new k(e);return i._trimAlloc=()=>{},new this(i,t)}static factory(e,t,i=0,s=e.byteLength){s=new DataView(e.buffer,e.byteOffset+i,s);const r=new k(s);return r._trimAlloc=()=>{},new this(r,t)}constructor(e,t){this.stream=e,this.filename=t}readAsString(e){return this.stream.seek(0),this.stream.readString(this.stream.byteLength,e)}getBytes(){return new Uint8Array(this.stream.buffer,this.stream.byteOffset,this.stream.byteLength)}getSize(){return this.stream.byteLength}asFile(e){return new File([this.getBytes()],this.filename,{type:e})}}class D{constructor(e){this.sections=new Map,e instanceof i?this.fromVirtualFile(e):"object"==typeof e?this.fromJson(e):"string"==typeof e&&this.fromString(e)}fromVirtualFile(e){return this.fromString(e.readAsString())}fromString(e){return this.fromJson((new t).parse(e))}fromJson(e){for(var t in e){var i;e.hasOwnProperty(t)&&(i=new h(t).fromJson(e[t]),this.sections.set(t,i))}return this}toString(){let e=[];for(var t of this.sections.values())e.push(t.toString());return e.join("\r\n")}clone(){let i=new D;return this.sections.forEach((e,t)=>{i.sections.set(t,e.clone())}),i}getOrCreateSection(e){let t=this.sections.get(e);return t||(t=new h(e),this.sections.set(e,t)),t}getSection(e){return this.sections.get(e)}getOrderedSections(){return[...this.sections.values()]}mergeWith(e){return e.sections.forEach((e,t)=>{let i=this.getOrCreateSection(t);i.mergeWith(e)}),this}}class d{constructor(e){this.height=1,this.width=1,this.x=0,this.y=0,this.imageData=e??new Uint8Array(0)}clip(i,e){let t=new d;t.width=Math.min(this.width,i),t.height=Math.min(this.height,e);let s=new Uint8Array(i*e),r=0;for(let t=0;t<this.height&&!(t>=e);t++)for(let e=0;e<this.width;e++)e>=i||(s[r++]=this.imageData[t*this.width+e]);return t.imageData=s,t.x=this.x,t.y=this.y,t}}class s{constructor(e){this.height=0,this.width=0,this.numImages=0,this.images=[],e instanceof i&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let r=e.stream;if(0===r.readInt16()){this.width=r.readInt16(),this.height=r.readInt16(),this.numImages=r.readInt16();let s=[];for(let e=0;e<this.numImages;++e)s.push(this.readFrameHeader(r));this.images=[];for(let i=0;i<this.numImages;++i){var{compressionType:a,imageDataStartOffset:n,x:o,y:h,width:l,height:c}=s[i];let e=i<this.numImages-1?s[i+1].imageDataStartOffset:r.byteLength;e<n&&(e=r.byteLength);var u=e-n;r.seek(n);u=this.readImageData(r,l,c,a,u);let t=new d(u);t.x=o,t.y=h,t.width=l,t.height=c,this.images.push(t)}}}readFrameHeader(e){var t=e.readInt16(),i=e.readInt16(),s=e.readInt16(),r=e.readInt16(),a=e.readUint8();return e.readUint8(),e.readUint8(),e.readUint8(),e.readInt32(),e.readInt32(),{x:t,y:i,width:s,height:r,compressionType:a,imageDataStartOffset:e.readInt32()}}readImageData(s,e,r,t,i){var a=e*r;if(t<=1){var n=new Uint8Array(s.buffer,s.byteOffset+s.position,a);return s.position+=a,n}if(2===t){let t=0,i=new Uint8Array(a);for(let e=0;e<r;++e){var o=s.readUint16()-2;i.set(new Uint8Array(s.buffer,s.byteOffset+s.position,o),t),s.position+=o,t+=o}return i}if(3!==t)return new Uint8Array;t=new Uint8Array(s.buffer,s.byteOffset+s.position,i);return s.position+=i,class{static decode(s,r,t){let a=new Uint8Array(r*t),n=0,o=0;for(let e=0;e<t;e++){let t=(s[n+1]<<8|s[n])-2;n+=2;let i=0;for(;0<t--;){let e=s[n++];if(0!==e)i++,a[o++]=e;else for(t--,e=s[n++],i+e>r&&(e=r-i&255),i+=e;0!=e--;)a[o++]=0}}return a}}.decode(t,e,r)}getImage(e){if(e<0||this.images.length<=e)throw new RangeError(`Image index out of bounds (file=${this.filename}, index=${e}, length=${this.images.length})`);return this.images[e]}addImage(e){this.images.push(e),this.numImages++}clip(e,t){let i=new s;return i.filename=this.filename,i.width=Math.min(this.width,e),i.height=Math.min(this.height,t),i.images=this.images.map(e=>e.clip(i.width,i.height)),i.numImages=this.numImages,i}}var r=__webpack_require__(949).Vector3;const c=[new r(.54946297,-183e-6,-.835518),new r(.00014400001,.54940403,-.83555698),new r(-.54940403,-68000001e-12,-.83555698),new r(106e-6,-.54946297,-.835518),new r(.94900799,.00031599999,-.31525001),new r(-186e-6,.94899702,-.31528401),new r(-.94899702,.00031800001,-.31528401),new r(-447e-6,-.94900799,-.31525001),new r(.95084399,-279e-6,.30967101),new r(202e-6,.95084798,.30965701),new r(-.95084798,-70000002e-12,.30965701),new r(147e-6,-.95084399,.30967101),new r(.55237001,-11e-6,.83359897),new r(19999999e-12,.55238003,.833592),new r(-.55238003,57000001e-12,.83359301),new r(-66000001e-12,-.55237001,.83359897)],u=[new r(.67121398,.19849201,-.714194),new r(.26964301,.58439398,-.76536),new r(-.040546,.096988,-.99445897),new r(-.57242799,-.091913998,-.81478697),new r(-.17140099,-.57270998,-.80163902),new r(.36255699,-.30299899,-.88133103),new r(.81034702,-.34897199,-.470698),new r(.103962,.93867201,-.328767),new r(-.324047,.58766901,-.74137598),new r(-.80086499,.34046099,-.49264699),new r(-.66549802,-.59014702,-.45698899),new r(.314767,-.803002,-.506073),new r(.97262901,.151076,-.17655),new r(.680291,.68423599,-.26272699),new r(-.52007902,.82777703,-.210483),new r(-.96164399,-.179001,-.207847),new r(-.262714,-.937451,-.22840101),new r(.219707,-.97130102,.091124997),new r(.92380798,-.229975,.30608699),new r(-.082488999,.97065997,.225866),new r(-.59179801,.69678998,.40528899),new r(-.92529601,.36660099,.097111002),new r(-.705051,-.68777502,.172828),new r(.7324,-.68036699,-.026304999),new r(.85516202,.37458199,.358311),new r(.47300601,.83648002,.276705),new r(-.097617,.65411198,.750072),new r(-.90412402,-.153725,.39865801),new r(-.211916,-.85808998,.46773201),new r(.50022697,-.67440802,.543091),new r(.584539,-.110249,.80384099),new r(.43737301,.45464399,.77588898),new r(-.042440999,.083318003,.995619),new r(-.59625101,.22013199,.77202803),new r(-.506455,-.39697701,.76544899),new r(.070569001,-.47847399,.87526202)],g=[new r(.45651099,-.073968001,-.88663799),new r(.50769401,.38511699,-.77067),new r(.095431998,.22666401,-.96928602),new r(-.35876599,.54318798,-.75910097),new r(-.361276,.13299499,-.92292601),new r(-.48311701,-.32406601,-.813375),new r(-.018073,-.197559,-.980124),new r(.3211,-.501477,-.80337799),new r(.79949099,.069615997,-.59662998),new r(.390971,.77130598,-.50222403),new r(.080782004,.61448997,-.784778),new r(-.73275,.41143101,-.54203498),new r(-.73525399,.0091019999,-.67773098),new r(-.80249399,-.39490801,-.44727099),new r(-.13413,-.58915502,-.79680902),new r(.71955299,-.37622699,-.58369303),new r(.96687502,.173593,-.187132),new r(.760831,.51910597,-.38944301),new r(-.114642,.87551898,-.46938601),new r(-.53236699,.76885903,-.354177),new r(-.96226698,.024977,-.27095801),new r(-.46738699,-.721986,-.51018202),new r(.058449998,-.85235399,-.51968902),new r(.49823299,-.74374002,-.44566301),new r(.93915099,-.27024499,-.212044),new r(.58393198,.80944198,-.061857),new r(.183797,.97322798,-.138007),new r(-.88435501,.45221901,-.115822),new r(-.943178,-.33206701,.012138),new r(-.69844002,-.70656699,-.113772),new r(-.228411,-.95470601,-.190694),new r(.73156399,-.675861,-.089588001),new r(.96925098,.046804,.24158201),new r(.85564703,.50347698,.119916),new r(-.25115299,.96794701,-80999998e-12),new r(-.64779502,.75674897,.087711997),new r(-.96916401,.14519399,.1991),new r(-.41479301,-.88896698,.194126),new r(.25077501,-.961178,-.115109),new r(.47862899,-.84259301,.246883),new r(.89004397,-.39614201,.225595),new r(.52405101,.76235998,.37970701),new r(.11962,.94548202,.30291),new r(-.76085001,.49007499,.42536199),new r(-.86978501,-.20215,.450122),new r(-.70946699,-.60242403,.36570701),new r(.019308999,-.95887101,.28318599),new r(.626113,-.564677,.53770101),new r(.769943,-.126663,.62541503),new r(.76419097,.35070199,.54131401),new r(-.001878,.74136698,.67109799),new r(-.37088001,.81836802,.43900099),new r(-.71390897,.12865201,.68831801),new r(-.295165,-.73866397,.60601401),new r(.186195,-.73836899,.648184),new r(.387523,-.35878301,.84917599),new r(.481022,.124846,.86777401),new r(.391808,.54505599,.741216),new r(-.0035359999,.36559799,.93076599),new r(-.42049801,.484961,.76680797),new r(-.35490301,.019470001,.93470001),new r(-.54783702,-.35920799,.75554299),new r(-.106662,-.445115,.88909799),new r(.086796001,-.059307002,.99445897)],p=[new r(.52657801,-.35962099,-.77031702),new r(.150482,.43598399,.88728398),new r(.414195,.73825502,-.53237402),new r(.075152002,.91624898,-.393498),new r(-.316149,.93073601,-.18379299),new r(-.77381903,.62333399,-.11251),new r(-.90084201,.42853701,-.069568001),new r(-.99894202,-.010971,.044665001),new r(-.979761,-.15767001,-.123324),new r(-.91127402,-.362371,-.19562),new r(-.62406898,-.72094101,-.301301),new r(-.310173,-.80934501,-.498752),new r(.146613,-.81581903,-.55941403),new r(-.71651602,-.69435602,-.066887997),new r(.50397199,-.114202,-.85613698),new r(.45549101,.87262702,-.176211),new r(-.00501,-.114373,-.99342501),new r(-.104675,-.327701,-.93896502),new r(.56041199,.75258899,-.34575599),new r(-.060575999,.82162797,-.566796),new r(-.30234101,.79700702,-.522847),new r(-.671543,.67074001,-.314863),new r(-.77840102,-.12835699,.61450499),new r(-.92404997,.278382,-.261985),new r(-.69977301,-.55049098,-.45527801),new r(-.56824797,-.51718903,-.64000797),new r(.054097999,-.93286401,-.356143),new r(.75838202,.57289302,-.31088799),new r(.0036200001,.30502599,-.95233703),new r(-.060849998,-.98688602,-.14951099),new r(.63523,.045478001,-.77098298),new r(.52170497,.241309,-.81828701),new r(.26940399,.63542497,-.72364098),new r(.045676,.67275399,-.738455),new r(-.180511,.67465699,-.71571898),new r(-.397131,.63664001,-.66104198),new r(-.55200398,.47251499,-.687038),new r(-.77217001,.08309,-.62996),new r(-.669819,-.119533,-.73284),new r(-.54045498,-.31844401,-.77878201),new r(-.38613501,-.522789,-.75999397),new r(-.261466,-.68856698,-.676395),new r(-.019412,-.69610298,-.71767998),new r(.30356899,-.48184401,-.82199299),new r(.68193901,-.19512901,-.70490003),new r(-.24488901,-.116562,-.96251899),new r(.80075902,-.022979001,-.59854603),new r(-.37027499,.095583998,-.92399102),new r(-.33067101,-.32657799,-.88543999),new r(-.16322,-.52757901,-.83367902),new r(.12639,-.313146,-.941257),new r(.34954801,-.27222601,-.89649802),new r(.23991799,-.085825004,-.96699202),new r(.390845,.081537001,-.91683799),new r(.25526699,.26869699,-.92878503),new r(.146245,.48043799,-.86474901),new r(-.32601601,.47845599,-.81534898),new r(-.46968201,-.112519,-.87563598),new r(.81844002,-.25852001,-.51315099),new r(-.474318,.292238,-.83043301),new r(.778943,.39584199,-.48637101),new r(.62409401,.39377299,-.67487001),new r(.74088597,.203834,-.63995302),new r(.48021701,.565768,-.67029703),new r(.38093001,.42453501,-.82137799),new r(-.093422003,.50112402,-.86031801),new r(-.236485,.29619801,-.92538702),new r(-.131531,.093959004,-.98684901),new r(-.82356203,.29577699,-.48400599),new r(.61106598,-.624304,-.486664),new r(.069495998,-.52033001,-.85113299),new r(.226522,-.66487902,-.711775),new r(.47130799,-.56890398,-.67395699),new r(.38842499,-.74262398,-.54556),new r(.78367501,-.48072901,-.39338499),new r(.962394,.135676,-.235349),new r(.876607,.172034,-.449406),new r(.63340503,.58979303,-.50094098),new r(.182276,.80065799,-.57072097),new r(.177003,.76413399,.62029701),new r(-.544016,.675515,-.49772099),new r(-.67929697,.28646699,-.67564201),new r(-.59039098,.091369003,-.801929),new r(-.82436001,-.13312399,-.55018902),new r(-.71579403,-.33454201,-.61296099),new r(.17428599,-.89248401,.416049),new r(-.082528003,-.83712298,-.54075301),new r(.28333101,-.88087398,-.37918901),new r(.675134,-.42662701,-.60181701),new r(.84372002,-.512335,-.160156),new r(.97730398,-.098555997,-.18752),new r(.846295,.522672,-.102947),new r(.67714101,.72132498,-.145501),new r(.32096499,.87089199,-.37219399),new r(-.178978,.911533,-.37023601),new r(-.44716901,.82670099,-.341474),new r(-.70320302,.496328,-.50908101),new r(-.97718102,.063562997,-.202674),new r(-.87817001,-.412938,.241455),new r(-.83583099,-.35855001,-.415728),new r(-.499174,-.69343299,-.51959199),new r(-.188789,-.92375302,-.33322501),new r(.19225401,-.96936101,-.152896),new r(.51594001,-.783907,-.34539199),new r(.90592498,-.30095199,-.29787099),new r(.99111199,-.127746,.037106998),new r(.99513501,.098424003,-.0043830001),new r(.76012301,.64627701,.067367002),new r(.205221,.95958,-.192591),new r(-.042750001,.97951299,-.19679099),new r(-.43801701,.89892697,.0084920004),new r(-.82199401,.48078501,-.30523899),new r(-.89991701,.081710003,-.42833701),new r(-.92661202,-.144618,-.347096),new r(-.79365999,-.55779201,-.24283899),new r(-.43134999,-.84777898,-.30855799),new r(-.0054919999,-.96499997,.26219299),new r(.58790499,-.80402601,-.088940002),new r(.69949299,-.66768599,-.254765),new r(.88930303,.359795,-.282291),new r(.780972,.197037,.59267199),new r(.52012098,.50669599,.68755698),new r(.40389499,.69396102,.59605998),new r(-.154983,.89923602,.40909001),new r(-.65733802,.53716803,.528543),new r(-.74619502,.33409101,.575827),new r(-.62495202,-.049144,.77911502),new r(.31814101,-.254715,.913185),new r(-.555897,.405294,.725752),new r(-.79443401,.099405997,.59916002),new r(-.64036101,-.68946302,.33849499),new r(-.12671299,-.73409498,.66711998),new r(.105457,-.78081697,.61579502),new r(.40799299,-.48091599,.77605498),new r(.69513601,-.54512,.468647),new r(.97319102,-.0064889998,.229908),new r(.94689399,.317509,-.050799001),new r(.56358302,.82561201,.027183),new r(.325773,.94542301,.0069490001),new r(-.171821,.98509699,-.0078149997),new r(-.67044097,.73993897,.054768998),new r(-.822981,.55496198,.121322),new r(-.96619302,.117857,.229307),new r(-.95376903,-.29470399,.058945),new r(-.86438698,-.50272799,-.010015),new r(-.53060901,-.84200603,-.097365998),new r(-.162618,-.98407501,.071772002),new r(.081446998,-.99601102,.036439002),new r(.74598402,-.66596299,.00076199998),new r(.94205701,-.32926899,-.064106002),new r(.93970197,-.28108999,.194803),new r(.77121401,.55067003,.319363),new r(.641348,.73069,.23402099),new r(.080682002,.99669099,.0098789996),new r(-.046725001,.97664303,.20972501),new r(-.53107601,.82100099,.209562),new r(-.69581503,.65599,.29243499),new r(-.97612202,.216709,-.014913),new r(-.96166098,-.14412899,.23331399),new r(-.772084,-.61364698,.165299),new r(-.44960001,-.83605999,.314426),new r(-.39269999,-.91461599,.096247002),new r(.390589,-.91947001,.044890001),new r(.58252901,-.79919797,.148127),new r(.866431,-.48981199,.096864),new r(.90458697,.111498,.41145),new r(.95353699,.23232999,.191806),new r(.497311,.77080297,.398177),new r(.194066,.95631999,.218611),new r(.422876,.882276,.206797),new r(-.373797,.84956598,.37217399),new r(-.53449702,.71402299,.4522),new r(-.881827,.23716,.40759799),new r(-.904948,-.014069,.42528901),new r(-.751827,-.51281703,.41445801),new r(-.50101501,-.69791698,.51175803),new r(-.23519,-.92592299,.295555),new r(.228983,-.95393997,.193819),new r(.734025,-.63489801,.241062),new r(.91375297,-.063253,-.40131599),new r(.90573502,-.161487,.391875),new r(.85892999,.342446,.38074899),new r(.62448603,.60758102,.49077699),new r(.28926399,.85747898,.42550799),new r(.069968,.90216899,.42567101),new r(-.28617999,.94069999,.182165),new r(-.57401299,.80511898,-.14930899),new r(.111258,.099717997,-.98877603),new r(-.30539301,-.94422799,-.12316),new r(-.60116601,-.78957599,.123163),new r(-.290645,-.81213999,.50591898),new r(-.064920001,-.87716299,.47578499),new r(.408301,-.862216,.29978901),new r(.56609702,-.72556603,.39126399),new r(.83936399,-.427387,.33586901),new r(.81889999,-.041305002,.57244802),new r(.71978402,.41499701,.55649698),new r(.88174403,.45027,.140659),new r(.40182301,-.89822,-.17815199),new r(-.054019999,.79134399,.60898),new r(-.29377401,.76399398,.57446498),new r(-.450798,.61034697,.65135098),new r(-.63822103,.186694,.74687302),new r(-.87287003,-.25712699,.41470799),new r(-.58725703,-.52170998,.618828),new r(-.35365799,-.64197397,.680291),new r(.041648999,-.61127299,.79032302),new r(.348342,-.77918297,.52108699),new r(.499167,-.62244099,.602826),new r(.79001898,-.30383101,.53250003),new r(.66011798,.060733002,.74870199),new r(.60492098,.29416099,.73996001),new r(.38569701,.37934601,.84103203),new r(.239693,.207876,.94833201),new r(.012623,.25853199,.96591997),new r(-.100557,.457147,.88368797),new r(.046967,.62858802,.77631903),new r(-.43039101,-.44540501,.785097),new r(-.43429101,-.196228,.87913901),new r(-.25663701,-.336867,.90590203),new r(-.131372,-.15891001,.97851402),new r(.102379,-.208767,.972592),new r(.195687,-.450129,.87125802),new r(.62731898,-.42314801,.65377098),new r(.68743902,-.171583,.70568198),new r(.27592,-.021255,.96094602),new r(.45936701,.15746599,.87417799),new r(.285395,.583184,.76055598),new r(-.81217402,.46030301,.35846099),new r(-.189068,.64122301,.743698),new r(-.338875,.47648001,.811252),new r(-.92099398,.347186,.176727),new r(.040638998,.024465,.99887401),new r(-.73913199,-.35374701,.57318997),new r(-.60351199,-.28661501,.74405998),new r(-.188676,-.547059,.81555402),new r(-.026045,-.39782,.91709399),new r(.26789701,-.649041,.71202302),new r(.518246,-.28489101,.80638599),new r(.493451,-.066532999,.86722499),new r(-.328188,.140251,.93414301),new r(.328188,.140251,.93414301),new r(-.328188,.140251,.93414301),new r(-.328188,.140251,.93414301),new r(-.328188,.140251,.93414301)];class m{constructor(e,t,i){this.sizeX=e,this.sizeY=t,this.sizeZ=i,this.arr=new Array(e*t*i)}add(e){this.arr[e.x+e.y*this.sizeX+e.z*this.sizeX*this.sizeY]=e}get(e,t,i){if(!(e>=this.sizeX||t>=this.sizeY||i>=this.sizeZ))return this.arr[e+t*this.sizeX+i*this.sizeX*this.sizeY]}}var f=__webpack_require__(949);class y{get spanX(){return this.maxBounds.x-this.minBounds.x}get spanY(){return this.maxBounds.y-this.minBounds.y}get spanZ(){return this.maxBounds.z-this.minBounds.z}get scaleX(){return this.spanX/this.sizeX}get scaleY(){return this.spanY/this.sizeY}get scaleZ(){return this.spanZ/this.sizeZ}get scale(){return new f.Vector3(this.scaleX,this.scaleY,this.scaleZ)}getAllVoxels(){let i=[],s=new m(this.sizeX+1,this.sizeY+1,this.sizeZ+1);for(let e=0,t=this.spans.length;e<t;e++){var r=this.spans[e].voxels;for(let e=0,t=r.length;e<t;e++){var a=r[e];i.push(a),s.add(a)}}return{voxels:i,voxelField:s}}getNormals(){switch(this.normalsMode){case 1:return c;case 2:return u;case 3:return g;case 4:return p;default:throw new Error(`Invalid normalsmode ${this.normalsMode}`)}}scaleHvaMatrix(e){return(e=e.clone()).elements[12]*=this.hvaMultiplier,e.elements[13]*=this.hvaMultiplier,e.elements[14]*=this.hvaMultiplier,e}toPlain(){return{name:this.name,normalsMode:this.normalsMode,minBounds:this.minBounds.toArray(),maxBounds:this.maxBounds.toArray(),sizeX:this.sizeX,sizeY:this.sizeY,sizeZ:this.sizeZ,hvaMultiplier:this.hvaMultiplier,transfMatrix:this.transfMatrix.toArray(),spans:this.spans}}fromPlain(e){return this.name=e.name,this.normalsMode=e.normalsMode,this.minBounds=(new f.Vector3).fromArray(e.minBounds),this.maxBounds=(new f.Vector3).fromArray(e.maxBounds),this.sizeX=e.sizeX,this.sizeY=e.sizeY,this.sizeZ=e.sizeZ,this.hvaMultiplier=e.hvaMultiplier,this.transfMatrix=(new f.Matrix4).fromArray(e.transfMatrix),this.spans=e.spans,this}}class w{read(e){this.fileName=e.readCString(16),this.paletteCount=e.readUint32(),this.headerCount=e.readUint32(),this.tailerCount=e.readUint32(),this.bodySize=e.readUint32(),this.paletteRemapStart=e.readUint8(),this.paletteRemapEnd=e.readUint8(),e.seek(e.position+768)}}w.size=32;var T=__webpack_require__(949);class b{constructor(e){this.voxelCount=0,e instanceof i&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let r=e.stream;if(this.sections=[],!(r.byteLength<w.size)){let s=new w;if(s.read(r),s.headerCount&&s.tailerCount&&s.tailerCount===s.headerCount){for(let e=0;e<s.headerCount;++e){const n=new y;this.readSectionHeader(n,r),this.sections.find(e=>e.name===n.name)&&console.warn(`Duplicate section name "${n.name}" found in VXL "${this.filename}".`),this.sections.push(n)}var a=r.position;r.seek(r.position+s.bodySize);let t=[];for(let e=0;e<s.tailerCount;++e)t[e]=this.readSectionTailer(this.sections[e],r);let i=0;for(let e=0;e<s.headerCount;++e)r.seek(a),i+=this.readSectionBodySpans(this.sections[e],t[e],r);this.voxelCount=i}}}readSectionHeader(e,t){e.name=t.readCString(16),t.readUint32(),t.readUint32(),t.readUint32()}readSectionTailer(e,t){var i=t.readUint32(),s=t.readUint32(),r=t.readUint32();return e.hvaMultiplier=t.readFloat32(),e.transfMatrix=this.readTransfMatrix(t),e.minBounds=new T.Vector3(t.readFloat32(),t.readFloat32(),t.readFloat32()),e.maxBounds=new T.Vector3(t.readFloat32(),t.readFloat32(),t.readFloat32()),e.sizeX=t.readUint8(),e.sizeY=t.readUint8(),e.sizeZ=t.readUint8(),e.normalsMode=t.readUint8(),{startingSpanOffset:i,endingSpanOffset:s,dataSpanOffset:r}}readTransfMatrix(t){let i=[];for(let e=0;e<3;++e)i.push(t.readFloat32(),t.readFloat32(),t.readFloat32(),t.readFloat32());return i.push(0,0,0,1),(new T.Matrix4).fromArray(i).transpose()}readSectionBodySpans(e,t,i){i.seek(i.position+t.startingSpanOffset);var{sizeX:s,sizeY:r,sizeZ:a}=e;let n=new Array(r);for(let t=0;t<r;++t){n[t]=new Array(s);for(let e=0;e<s;++e)n[t][e]=i.readInt32()}let o=new Array(r);for(let t=0;t<r;++t){o[t]=new Array(s);for(let e=0;e<s;++e)o[t][e]=i.readInt32()}let h=e.spans=[],l=0;for(let t=0;t<r;++t)for(let e=0;e<s;++e){var c={x:e,y:t,voxels:this.readSpanVoxels(n[t][e],o[t][e],e,t,a,i)};h.push(c),l+=c.voxels.length}return l}readSpanVoxels(e,t,i,s,r,a){if(-1===e||-1===t)return[];let n=[];for(let t=0;t<r;){t+=a.readUint8();var o=a.readUint8();for(let e=0;e<o;++e){var h={x:i,y:s,z:t++,colorIndex:a.readUint8(),normalIndex:a.readUint8()};n.push(h)}a.readUint8()}return n}fromPlain(e){return this.sections=e.sections.map(e=>(new y).fromPlain(e)),this.voxelCount=e.voxelCount,this}toPlain(){return{sections:this.sections.map(e=>e.toPlain()),voxelCount:this.voxelCount}}getSection(e){return this.sections[e]}}var v,O,_,I,C,A=__webpack_require__(949);(r=v=v||{})[r.ExtraData=1]="ExtraData",r[r.ZData=2]="ZData",r[r.DamagedData=4]="DamagedData";const B=e=>e<0?e+256:e;class x{constructor(e,t,i){this.fromStream(e,t,i)}fromStream(e,t,i){this.x=e.readInt32(),this.y=e.readInt32(),e.readInt32(),e.readInt32();var s=e.readInt32();this.extraX=e.readInt32(),this.extraY=e.readInt32(),this.extraWidth=e.readInt32(),this.extraHeight=e.readInt32();var r=e.readUint32();this.height=e.readUint8(),this.terrainType=e.readUint8(),this.rampType=e.readUint8(),this.radarLeft=this.readRadarRgb(e.readInt8(),e.readInt8(),e.readInt8()),this.radarRight=this.readRadarRgb(e.readInt8(),e.readInt8(),e.readInt8()),e.seek(e.position+3),this.tileData=new Uint8Array(e.buffer,e.byteOffset+e.position,t*i/2),e.position+=t*i/2,this.hasZData=(r&v.ZData)===v.ZData,this.hasZData&&(e.position+=t*i/2),this.hasExtraData=(r&v.ExtraData)===v.ExtraData,this.hasExtraData&&(r=Math.abs(this.extraWidth*this.extraHeight),this.extraData=new Uint8Array(e.buffer,e.byteOffset+e.position,r),e.position+=r),this.hasZData&&this.hasExtraData&&0<s&&s<e.byteLength&&(e.position+=Math.abs(this.extraWidth*this.extraHeight))}readRadarRgb(e,t,i){return new A.Color(B(e)/255,B(t)/255,B(i)/255)}}class E{constructor(e){this.images=[],e instanceof i&&this.fromVirtualFile(e)}fromVirtualFile(e){let t=e.stream;this.width=t.readInt32(),this.height=t.readInt32(),this.blockWidth=t.readInt32(),this.blockHeight=t.readInt32();var i=this.width*this.height,s=new Uint8Array(t.buffer,t.byteOffset+t.position,4*i);this.images=[];for(let e=0;e<i;e++){var r=s[4*e+3]<<24|s[4*e+2]<<16|s[4*e+1]<<8|s[4*e];t.seek(r);r=new x(t,this.blockWidth,this.blockHeight);this.images.push(r)}}}class P{static encode(e){return void 0!==globalThis.btoa?globalThis.btoa(e):Buffer.from(e,"binary").toString("base64")}static decode(e){return void 0!==globalThis.atob?globalThis.atob(e):Buffer.from(e,"base64").toString("binary")}static isBase64(e){return!!e.match(/^([A-Za-z0-9+/]{4})*([A-Za-z0-9+/]{3}=|[A-Za-z0-9+/]{2}==)?$/)}}function N(e,t="0000"){e=""+e;return t.substring(0,t.length-e.length)+e}function M(e,t){return e.toLowerCase()===t.toLowerCase()}function R(t){var i=t.length;let s=new Uint8Array(i);for(let e=0;e<i;e++)s[e]=t.charCodeAt(e);return s}function L(e){return R(P.decode(e))}function F(e){return e.reduce((e,t)=>e+String.fromCharCode(t),"")}function j(t){var i=t.length;let s="";for(let e=0;e<i;e++){var r=t.charCodeAt(e);s+=String.fromCharCode(r>>8),s+=String.fromCharCode(255&r)}return s}function U(t){var i=t.length;let s="";for(let e=0;e<i;e+=2){var r=(t.charCodeAt(e)<<8)+t.charCodeAt(e+1);s+=String.fromCharCode(r)}return s}class W{static fromRgb(e,t,i){return new W(e,t,i)}static fromHsv(e,t,i){let s=0,r=0,a=0;if(e=e/255*360%360,i/=255,0===(t/=255))s=i,r=i,a=i;else{var n=e/60,e=Math.floor(n),n=n-e,o=i*(1-t),h=i*(1-t*n),l=i*(1-t*(1-n));switch(e){case 0:s=i,r=l,a=o;break;case 1:s=h,r=i,a=o;break;case 2:s=o,r=i,a=l;break;case 3:s=o,r=h,a=i;break;case 4:s=l,r=o,a=i;break;case 5:s=i,r=o,a=h}}return W.fromRgb(Math.floor(255*s),Math.floor(255*r),Math.floor(255*a))}constructor(e,t,i){this.r=e,this.g=t,this.b=i}asHex(){return(this.r<<16)+(this.g<<8)+this.b}asHexString(){return"#"+N(this.asHex().toString(16),"000000")}clone(){return new W(this.r,this.g,this.b)}}function z(e,t,i){return Math.min(i,Math.max(e,t))}function V(e,t,i){return t<=e&&e<=i}function H(e,t,i){return(1-i)*e+i*t}function G(i){let s=2166136261;for(let e=0,t=i.length;e<t;++e)s^=i[e],s+=(s<<1)+(s<<4)+(s<<7)+(s<<8)+(s<<24);return s>>>0}class ${constructor(e){e instanceof i?this.fromVirtualFile(e):"object"==typeof e&&this.fromJson(e)}fromVirtualFile(e){e=e.stream.readUint8Array(768);this.fromJson(e)}fromJson(t){this.colors=[];for(let e=0;e<t.length/3;++e)this.colors.push(W.fromRgb(4*t[3*e],4*t[3*e+1],4*t[3*e+2]));this._hash=this.computeHash(this.colors)}getColor(e){return this.colors[e]}getColorAsHex(e){return this.getColor(e).asHex()}setColors(e){this.colors=e,this._hash=this.computeHash(this.colors)}get size(){return this.colors.length}get hash(){return this._hash}computeHash(e){let t=new Uint8Array(3*this.size),i=0;for(var s of e)t[i]=s.r,t[i+1]=s.g,t[i+2]=s.b,i+=3;return G(t)}clone(){let e=new $;return e.colors=this.colors.map(e=>e.clone()),e._hash=this._hash,e}remap(t){var i=[63,59,55,52,48,44,41,37,33,30,26,22,19,15,11,8];for(let e=$.REMAP_START_IDX;e<$.REMAP_START_IDX+i.length;e++)this.colors[e].r=Math.floor(t.r/255*i[e-$.REMAP_START_IDX]*4),this.colors[e].g=Math.floor(t.g/255*i[e-$.REMAP_START_IDX]*4),this.colors[e].b=Math.floor(t.b/255*i[e-$.REMAP_START_IDX]*4);return this._hash=this.computeHash(this.colors),this}}$.REMAP_START_IDX=16;class q{constructor(e,t){this.owner=e,this.index=t,this.files=[]}addFile(e){this.files.push(e)}setAnimation(e){this.animation=e}getAnimation(){return this.animation}getTmpFile(e,t,i=!1){if(this.files.length){t=this.files[t(0,this.files.length-1)];return t.images[Math.min(e,t.images.length-1)].hasDamagedData?this.files[Math.min(i?1:0,this.files.length-1)]:t}}}class X{constructor(e,t,i){this.fileName=e,this.setName=t,this.tilesInSet=i,this.entries=[]}}class Z{constructor(e,t,i,s){this.name=e,this.subTile=t,this.offsetX=i,this.offsetY=s}}(r=O=O||{})[r.TopLeft=0]="TopLeft",r[r.BottomRight=1]="BottomRight",r[r.TopRight=2]="TopRight",r[r.BottomLeft=3]="BottomLeft",r[r.MiddleTlBr=4]="MiddleTlBr",r[r.MiddleTrBl=5]="MiddleTrBl";const Q=new Map([[O.TopLeft,["BridgeTopLeft1","BridgeTopLeft2"]],[O.BottomRight,["BridgeBottomRight1","BridgeBottomRight2"]],[O.TopRight,["BridgeTopRight1","BridgeTopRight2"]],[O.BottomLeft,["BridgeBottomLeft1","BridgeBottomLeft2"]],[O.MiddleTlBr,["BridgeMiddle1"]],[O.MiddleTrBl,["BridgeMiddle2"]]]);class Y{constructor(e){this.theaterIni=e,this.tileSets=[],this.orderedEntries=[],this.highBridgeSetNums=[this.getGeneralValue("BridgeSet"),this.getGeneralValue("WoodBridgeSet")],this.cliffSetNums=[this.getGeneralValue("CliffSet"),this.getGeneralValue("WaterCliffs"),this.getGeneralValue("DestroyableCliffs")]}getTile(e){return this.orderedEntries[e]}getTileImage(e,t,i){let s=this.getTile(e);if(!s)throw new Error(`TileNum ${e} not found`);i=s.getTmpFile(t,i);if(!i||t>=i.images.length)throw new Error(`SubTile ${t} not found`);return i.images[t]}getSetNum(e){var t=this.orderedEntries[e];if(!t)throw new Error("Invalid tileNum "+e);return this.tileSets.indexOf(t.owner)}getTileNumFromSet(i,s=0){let r=0;return this.tileSets.some((e,t)=>t===i?(r+=s,!0):(r+=e.entries.length,!1)),r}getGeneralValue(e){let t=this.theaterIni.getSection("General");if(!t)throw new Error("Missing [General] section in theather ini");return t.getNumber(e)}loadTileData(e,t){this.tileSets.length=0,this.orderedEntries.length=0,this.initTileSets(e,t),this.initAnimations()}readMaxTileNum(){let t=0,i=0;for(;;){var s="TileSet"+N(t,"0000");let e=this.theaterIni.getSection(s);if(!e)break;t++,i+=e.getNumber("TilesInSet")}return i}initTileSets(a,n){let e=0,t;for(var i;;){if(i="TileSet"+N(e,"0000"),t=this.theaterIni.getSection(i),!t)break;e++;let r=new X(t.getString("FileName"),t.getString("SetName"),t.getNumber("TilesInSet"));this.tileSets.push(r);for(let s=1;s<=r.tilesInSet;s++){let i=new q(r,s-1);var o="a".charCodeAt(0);for(let t=o-1;t<="z".charCodeAt(0);t++)if(!(t>=o&&"Bridges"===r.setName)){let e=r.fileName+N(s,"00");t>=o&&(e+=String.fromCharCode(t)),e+=n;var h=a.get(e);if(!h)break;i.addFile(h)}r.entries.push(i),this.orderedEntries.push(i)}}}initAnimations(){var s=this.theaterIni.getOrderedSections();for(let e=this.tileSets.length;e<s.length;++e){let t=s[e],i=this.tileSets.find(e=>e.setName===t.name);if(i)for(let e=1;e<=i.tilesInSet;++e){var r=`Tile${N(e,"00")}`,a=`${r}Anim`,n=t.getString(a);n?(r=new Z(n,t.getNumber(`${r}AttachesTo`),t.getNumber(`${r}XOffset`),t.getNumber(`${r}YOffset`)),i.entries[e-1].setAnimation(r)):console.warn(`Missing anim "${a}" for tileset ${i.setName}`)}}}isLAT(e){return e===this.getGeneralValue("RoughTile")||e===this.getGeneralValue("SandTile")||e===this.getGeneralValue("GreenTile")||e===this.getGeneralValue("PaveTile")}isCLAT(e){return e===this.getGeneralValue("ClearToRoughLat")||e===this.getGeneralValue("ClearToSandLat")||e===this.getGeneralValue("ClearToGreenLat")||e===this.getGeneralValue("ClearToPaveLat")}getLAT(e){return e===this.getGeneralValue("ClearToRoughLat")?this.getGeneralValue("RoughTile"):e===this.getGeneralValue("ClearToSandLat")?this.getGeneralValue("SandTile"):e===this.getGeneralValue("ClearToGreenLat")?this.getGeneralValue("GreenTile"):e===this.getGeneralValue("ClearToPaveLat")?this.getGeneralValue("PaveTile"):-1}getCLATSet(e){return e===this.getGeneralValue("RoughTile")?this.getGeneralValue("ClearToRoughLat"):e===this.getGeneralValue("SandTile")?this.getGeneralValue("ClearToSandLat"):e===this.getGeneralValue("GreenTile")?this.getGeneralValue("ClearToGreenLat"):e===this.getGeneralValue("PaveTile")?this.getGeneralValue("ClearToPaveLat"):-1}canConnectTiles(e,t){if(e===t)return!1;var i=this.getGeneralValue("GreenTile"),s=this.getGeneralValue("PaveTile"),r=this.getGeneralValue("MiscPaveTile"),a=this.getGeneralValue("ShorePieces"),n=this.getGeneralValue("WaterBridge"),o=this.getGeneralValue("PavedRoads"),h=this.getGeneralValue("Medians");return!(e===i&&t===a||t===i&&e===a)&&(!(e===i&&t===n||t===i&&e===n)&&(!(e===s&&t===o||t===s&&e===o)&&(!(e===s&&t===r||t===s&&e===r)&&!(e===s&&t===h||t===s&&e===h))))}getHighBridgeHeadType(e){for(var[t,i]of Q)for(var s of i)if(this.getGeneralValue(s)===e+1)return t}getOppositeHighBridgeHeadType(e){switch(e){case O.TopLeft:return O.BottomRight;case O.TopRight:return O.BottomLeft;case O.BottomLeft:return O.TopRight;case O.BottomRight:return O.TopLeft;case O.MiddleTlBr:case O.MiddleTrBl:throw new Error("Middle bridge heads can't have opposites");default:throw new Error(`Unhandled headType ${e}`)}}isCliffTile(e){return this.cliffSetNums.includes(this.getSetNum(e))}isHighBridgeBoundaryTile(e){if(this.highBridgeSetNums.includes(this.getSetNum(e))){e=this.getTile(e),e=this.getHighBridgeHeadType(e.index);return void 0!==e&&![O.MiddleTlBr,O.MiddleTrBl].includes(e)}return!1}isHighBridgeMiddleTile(e){if(this.highBridgeSetNums.includes(this.getSetNum(e))){e=this.getTile(e),e=this.getHighBridgeHeadType(e.index);return void 0!==e&&[O.MiddleTlBr,O.MiddleTrBl].includes(e)}return!1}}(r=_=_||{})[r.None=0]="None",r[r.Iso=1]="Iso",r[r.Unit=2]="Unit",r[r.Overlay=3]="Overlay",r[r.Anim=4]="Anim",r[r.Custom=5]="Custom",r[r.Default=6]="Default";(r=I=I||{})[r.None=0]="None",r[r.Temperate=1]="Temperate",r[r.Urban=2]="Urban",r[r.Snow=4]="Snow",r[r.Lunar=8]="Lunar",r[r.Desert=16]="Desert",r[r.NewUrban=32]="NewUrban",r[r.All=63]="All";class K{constructor(){this.fileData=new Map}fromVirtualFile(e,t){var i,s;for([i,s]of t.entries){var r=this.buildWavData(e.stream,s);this.fileData.set(i,r)}return this}getFileList(){return[...this.fileData.keys()]}containsFile(e){return this.fileData.has(e)}openFile(e){if(!this.containsFile(e))throw new Error(`File "${e}" not found`);return new i(this.fileData.get(e),e)}buildWavData(e,t){let i=new k;var s,r,a,n,o=0<(1&t.flags)?2:1;let h=0;0<(2&t.flags)?(i.writeString("RIFF"),i.writeUint32(t.length+36),i.writeString("WAVE"),i.writeString("fmt "),i.writeInt32(16),i.writeInt16(1),i.writeInt16(o),i.writeUint32(t.sampleRate),i.writeUint32(2*o*t.sampleRate),i.writeInt16(2*o),i.writeInt16(16),i.writeString("data"),i.writeUint32(t.length)):0<(8&t.flags)&&(s=11100*o*(t.sampleRate/22050|0),r=t.chunkSize,a=1017*(n=Math.max(2,Math.ceil(t.length/r))),n=n*r,h=n-t.length,i.writeString("RIFF"),i.writeUint32(52+n),i.writeString("WAVE"),i.writeString("fmt "),i.writeUint32(20),i.writeInt16(17),i.writeInt16(o),i.writeUint32(t.sampleRate),i.writeInt32(s),i.writeInt16(r),i.writeInt16(4),i.writeInt16(2),i.writeInt16(1017),i.writeString("fact"),i.writeUint32(4),i.writeInt32(a),i.writeString("data"),i.writeUint32(n)),e.seek(t.offset),i.writeUint8Array(e.readUint8Array(t.length));for(let e=0;e<h;e++)i.writeUint8(0);return i.seek(0),i._trimAlloc=()=>{},i}}class J{}class ee{constructor(e){this.entries=new Map,this.parse(e)}parse(t){var e=t.readCString(4);if("GABA"!==e)throw new Error(`Unable to load Idx file, did not find magic id, found ${e} instead`);e=t.readInt32();if(2!==e)throw new Error(`Unable to load Idx file, did not find magic number 2, found ${e} instead`);var i=t.readInt32();for(let e=0;e<i;e++){const r=new J;let e=t.readString(16);var s=e.indexOf("\0");0!==s&&(e=e.substr(0,s)),r.filename=e+".wav",r.offset=t.readUint32(),r.length=t.readUint32(),r.sampleRate=t.readUint32(),r.flags=t.readUint32(),r.chunkSize=t.readUint32(),this.entries.set(r.filename,r)}}}function te(e){return e=((e=(e<<16>>>0|e>>>16)>>>0)<<8>>>0&4278255360|e>>>8&16711935)>>>0}class ie{constructor(i){this.m_p=new Uint32Array([608135816,2242054355,320440878,57701188,2752067618,698298832,137296536,3964562569,1160258022,953160567,3193202383,887688300,3232508343,3380367581,1065670069,3041331479,2450970073,2306472731]),this.m_s=[new Uint32Array([3509652390,2564797868,805139163,3491422135,3101798381,1780907670,3128725573,4046225305,614570311,3012652279,134345442,2240740374,1667834072,1901547113,2757295779,4103290238,227898511,1921955416,1904987480,2182433518,2069144605,3260701109,2620446009,720527379,3318853667,677414384,3393288472,3101374703,2390351024,1614419982,1822297739,2954791486,3608508353,3174124327,2024746970,1432378464,3864339955,2857741204,1464375394,1676153920,1439316330,715854006,3033291828,289532110,2706671279,2087905683,3018724369,1668267050,732546397,1947742710,3462151702,2609353502,2950085171,1814351708,2050118529,680887927,999245976,1800124847,3300911131,1713906067,1641548236,4213287313,1216130144,1575780402,4018429277,3917837745,3693486850,3949271944,596196993,3549867205,258830323,2213823033,772490370,2760122372,1774776394,2652871518,566650946,4142492826,1728879713,2882767088,1783734482,3629395816,2517608232,2874225571,1861159788,326777828,3124490320,2130389656,2716951837,967770486,1724537150,2185432712,2364442137,1164943284,2105845187,998989502,3765401048,2244026483,1075463327,1455516326,1322494562,910128902,469688178,1117454909,936433444,3490320968,3675253459,1240580251,122909385,2157517691,634681816,4142456567,3825094682,3061402683,2540495037,79693498,3249098678,1084186820,1583128258,426386531,1761308591,1047286709,322548459,995290223,1845252383,2603652396,3431023940,2942221577,3202600964,3727903485,1712269319,422464435,3234572375,1170764815,3523960633,3117677531,1434042557,442511882,3600875718,1076654713,1738483198,4213154764,2393238008,3677496056,1014306527,4251020053,793779912,2902807211,842905082,4246964064,1395751752,1040244610,2656851899,3396308128,445077038,3742853595,3577915638,679411651,2892444358,2354009459,1767581616,3150600392,3791627101,3102740896,284835224,4246832056,1258075500,768725851,2589189241,3069724005,3532540348,1274779536,3789419226,2764799539,1660621633,3471099624,4011903706,913787905,3497959166,737222580,2514213453,2928710040,3937242737,1804850592,3499020752,2949064160,2386320175,2390070455,2415321851,4061277028,2290661394,2416832540,1336762016,1754252060,3520065937,3014181293,791618072,3188594551,3933548030,2332172193,3852520463,3043980520,413987798,3465142937,3030929376,4245938359,2093235073,3534596313,375366246,2157278981,2479649556,555357303,3870105701,2008414854,3344188149,4221384143,3956125452,2067696032,3594591187,2921233993,2428461,544322398,577241275,1471733935,610547355,4027169054,1432588573,1507829418,2025931657,3646575487,545086370,48609733,2200306550,1653985193,298326376,1316178497,3007786442,2064951626,458293330,2589141269,3591329599,3164325604,727753846,2179363840,146436021,1461446943,4069977195,705550613,3059967265,3887724982,4281599278,3313849956,1404054877,2845806497,146425753,1854211946]),new Uint32Array([1266315497,3048417604,3681880366,3289982499,290971e4,1235738493,2632868024,2414719590,3970600049,1771706367,1449415276,3266420449,422970021,1963543593,2690192192,3826793022,1062508698,1531092325,1804592342,2583117782,2714934279,4024971509,1294809318,4028980673,1289560198,2221992742,1669523910,35572830,157838143,1052438473,1016535060,1802137761,1753167236,1386275462,3080475397,2857371447,1040679964,2145300060,2390574316,1461121720,2956646967,4031777805,4028374788,33600511,2920084762,1018524850,629373528,3691585981,3515945977,2091462646,2486323059,586499841,988145025,935516892,3367335476,2599673255,2839830854,265290510,3972581182,2759138881,3795373465,1005194799,847297441,406762289,1314163512,1332590856,1866599683,4127851711,750260880,613907577,1450815602,3165620655,3734664991,3650291728,3012275730,3704569646,1427272223,778793252,1343938022,2676280711,2052605720,1946737175,3164576444,3914038668,3967478842,3682934266,1661551462,3294938066,4011595847,840292616,3712170807,616741398,312560963,711312465,1351876610,322626781,1910503582,271666773,2175563734,1594956187,70604529,3617834859,1007753275,1495573769,4069517037,2549218298,2663038764,504708206,2263041392,3941167025,2249088522,1514023603,1998579484,1312622330,694541497,2582060303,2151582166,1382467621,776784248,2618340202,3323268794,2497899128,2784771155,503983604,4076293799,907881277,423175695,432175456,1378068232,4145222326,3954048622,3938656102,3820766613,2793130115,2977904593,26017576,3274890735,3194772133,1700274565,1756076034,4006520079,3677328699,720338349,1533947780,354530856,688349552,3973924725,1637815568,332179504,3949051286,53804574,2852348879,3044236432,1282449977,3583942155,3416972820,4006381244,1617046695,2628476075,3002303598,1686838959,431878346,2686675385,1700445008,1080580658,1009431731,832498133,3223435511,2605976345,2271191193,2516031870,1648197032,4164389018,2548247927,300782431,375919233,238389289,3353747414,2531188641,2019080857,1475708069,455242339,2609103871,448939670,3451063019,1395535956,2413381860,1841049896,1491858159,885456874,4264095073,4001119347,1565136089,3898914787,1108368660,540939232,1173283510,2745871338,3681308437,4207628240,3343053890,4016749493,1699691293,1103962373,3625875870,2256883143,3830138730,1031889488,3479347698,1535977030,4236805024,3251091107,2132092099,1774941330,1199868427,1452454533,157007616,2904115357,342012276,595725824,1480756522,206960106,497939518,591360097,863170706,2375253569,3596610801,1814182875,2094937945,3421402208,1082520231,3463918190,2785509508,435703966,3908032597,1641649973,2842273706,3305899714,1510255612,2148256476,2655287854,3276092548,4258621189,236887753,3681803219,274041037,1734335097,3815195456,3317970021,1899903192,1026095262,4050517792,356393447,2410691914,3873677099,3682840055]),new Uint32Array([3913112168,2491498743,4132185628,2489919796,1091903735,1979897079,3170134830,3567386728,3557303409,857797738,1136121015,1342202287,507115054,2535736646,337727348,3213592640,1301675037,2528481711,1895095763,1721773893,3216771564,62756741,2142006736,835421444,2531993523,1442658625,3659876326,2882144922,676362277,1392781812,170690266,3921047035,1759253602,3611846912,1745797284,664899054,1329594018,3901205900,3045908486,2062866102,2865634940,3543621612,3464012697,1080764994,553557557,3656615353,3996768171,991055499,499776247,1265440854,648242737,3940784050,980351604,3713745714,1749149687,3396870395,4211799374,3640570775,1161844396,3125318951,1431517754,545492359,4268468663,3499529547,1437099964,2702547544,3433638243,2581715763,2787789398,1060185593,1593081372,2418618748,4260947970,69676912,2159744348,86519011,2512459080,3838209314,1220612927,3339683548,133810670,1090789135,1078426020,1569222167,845107691,3583754449,4072456591,1091646820,628848692,1613405280,3757631651,526609435,236106946,48312990,2942717905,3402727701,1797494240,859738849,992217954,4005476642,2243076622,3870952857,3732016268,765654824,3490871365,2511836413,1685915746,3888969200,1414112111,2273134842,3281911079,4080962846,172450625,2569994100,980381355,4109958455,2819808352,2716589560,2568741196,3681446669,3329971472,1835478071,660984891,3704678404,4045999559,3422617507,3040415634,1762651403,1719377915,3470491036,2693910283,3642056355,3138596744,1364962596,2073328063,1983633131,926494387,3423689081,2150032023,4096667949,1749200295,3328846651,309677260,2016342300,1779581495,3079819751,111262694,1274766160,443224088,298511866,1025883608,3806446537,1145181785,168956806,3641502830,3584813610,1689216846,3666258015,3200248200,1692713982,2646376535,4042768518,1618508792,1610833997,3523052358,4130873264,2001055236,3610705100,2202168115,4028541809,2961195399,1006657119,2006996926,3186142756,1430667929,3210227297,1314452623,4074634658,4101304120,2273951170,1399257539,3367210612,3027628629,1190975929,2062231137,2333990788,2221543033,2438960610,1181637006,548689776,2362791313,3372408396,3104550113,3145860560,296247880,1970579870,3078560182,3769228297,1714227617,3291629107,3898220290,166772364,1251581989,493813264,448347421,195405023,2709975567,677966185,3703036547,1463355134,2715995803,1338867538,1343315457,2802222074,2684532164,233230375,2599980071,2000651841,3277868038,1638401717,4028070440,3237316320,6314154,819756386,300326615,590932579,1405279636,3267499572,3150704214,2428286686,3959192993,3461946742,1862657033,1266418056,963775037,2089974820,2263052895,1917689273,448879540,3550394620,3981727096,150775221,3627908307,1303187396,508620638,2975983352,2726630617,1817252668,1876281319,1457606340,908771278,3720792119,3617206836,2455994898,1729034894,1080033504]),new Uint32Array([976866871,3556439503,2881648439,1522871579,1555064734,1336096578,3548522304,2579274686,3574697629,3205460757,3593280638,3338716283,3079412587,564236357,2993598910,1781952180,1464380207,3163844217,3332601554,1699332808,1393555694,1183702653,3581086237,1288719814,691649499,2847557200,2895455976,3193889540,2717570544,1781354906,1676643554,2592534050,3230253752,1126444790,2770207658,2633158820,2210423226,2615765581,2414155088,3127139286,673620729,2805611233,1269405062,4015350505,3341807571,4149409754,1057255273,2012875353,2162469141,2276492801,2601117357,993977747,3918593370,2654263191,753973209,36408145,2530585658,25011837,3520020182,2088578344,530523599,2918365339,1524020338,1518925132,3760827505,3759777254,1202760957,3985898139,3906192525,674977740,4174734889,2031300136,2019492241,3983892565,4153806404,3822280332,352677332,2297720250,60907813,90501309,3286998549,1016092578,2535922412,2839152426,457141659,509813237,4120667899,652014361,1966332200,2975202805,55981186,2327461051,676427537,3255491064,2882294119,3433927263,1307055953,942726286,933058658,2468411793,3933900994,4215176142,1361170020,2001714738,2830558078,3274259782,1222529897,1679025792,2729314320,3714953764,1770335741,151462246,3013232138,1682292957,1483529935,471910574,1539241949,458788160,3436315007,1807016891,3718408830,978976581,1043663428,3165965781,1927990952,4200891579,2372276910,3208408903,3533431907,1412390302,2931980059,4132332400,1947078029,3881505623,4168226417,2941484381,1077988104,1320477388,886195818,18198404,3786409e3,2509781533,112762804,3463356488,1866414978,891333506,18488651,661792760,1628790961,3885187036,3141171499,876946877,2693282273,1372485963,791857591,2686433993,3759982718,3167212022,3472953795,2716379847,445679433,3561995674,3504004811,3574258232,54117162,3331405415,2381918588,3769707343,4154350007,1140177722,4074052095,668550556,3214352940,367459370,261225585,2610173221,4209349473,3468074219,3265815641,314222801,3066103646,3808782860,282218597,3406013506,3773591054,379116347,1285071038,846784868,2669647154,3771962079,3550491691,2305946142,453669953,1268987020,3317592352,3279303384,3744833421,2610507566,3859509063,266596637,3847019092,517658769,3462560207,3443424879,370717030,4247526661,2224018117,4143653529,4112773975,2788324899,2477274417,1456262402,2901442914,1517677493,1846949527,2295493580,3734397586,2176403920,1280348187,1908823572,3871786941,846861322,1172426758,3287448474,3383383037,1655181056,3139813346,901632758,1897031941,2986607138,3066810236,3447102507,1393639104,373351379,950779232,625454576,3124240540,4148612726,2007998917,544563296,2244738638,2330496472,2058025392,1291430526,424198748,50039436,29584100,3605783033,2429876329,2791104160,1057563949,3255363231,3075367218,3463963227,1469046755,985887462])];for(let e=0,t=0;e<18;++e){var s=i[t++%i.length],r=i[t++%i.length],a=i[t++%i.length],n=i[t++%i.length];this.m_p[e]^=s<<24|r<<16|a<<8|n}let o=0,h=0;for(let e=0;e<18;)[o,h]=this._encrypt(o,h),this.m_p[e++]=o,this.m_p[e++]=h;for(let t=0;t<4;++t)for(let e=0;e<256;)[o,h]=this._encrypt(o,h),this.m_s[t][e++]=o,this.m_s[t][e++]=h}encrypt(e){return this.runCipher(e,this._encrypt.bind(this))}decrypt(e){return this.runCipher(e,this._decrypt.bind(this))}runCipher(e,t){let i=new Uint32Array(e.length),s=e.length/2|0,r=0;for(;0<s--;){var a=te(e[r]),n=te(e[r+1]);[a,n]=t(a,n),i[r++]=te(a),i[r++]=te(n)}return i}_encrypt(e,t){let i=e,s=t;i^=this.m_p[0];let r=!1;for(let e=1;e<=16;e++,r=!r)r?i=this.round(i,s,e):s=this.round(s,i,e);return s^=this.m_p[17],[s,i]}_decrypt(e,t){let i=e,s=t;i^=this.m_p[17];let r=!1;for(let e=16;1<=e;e--,r=!r)r?i=this.round(i,s,e):s=this.round(s,i,e);return s^=this.m_p[0],[s,i]}s(e,t){return this.m_s[t][e>>(3-t<<3)&255]}bf_f(e){return(this.s(e,0)+this.s(e,1)>>>0^this.s(e,2))+this.s(e,3)>>>0}round(e,t,i){return e^(this.bf_f(t)^this.m_p[i])}}const se="AihRvNoIbTn85FZRYNZRcT+i6KpU+maCsEqr3Q5q+LDB5tH7Tz2qQ38V",re=new Int8Array([-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,62,-1,-1,-1,63,52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-1,-1,-1,-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1,-1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1]);class ae{constructor(){this.key1=new Uint32Array(64),this.key2=new Uint32Array(64)}}class ne{constructor(){this.pubkey=new ae,this.glob1=new Uint32Array(64),this.glob2=new Uint32Array(130),this.glob1_hi=new Uint32Array(4),this.glob1_hi_inv=new Uint32Array(4)}init_bignum(t,e,i){for(let e=0;e<i;e++)t[e]=0;t[0]=e}move_key_to_big(e,t,i,s){let r;r=0!=(128&t[0])?255:0;const a=new Uint8Array(e.buffer,e.byteOffset);let n=4*s;for(;n>i;n--)a[n-1]=r;for(;0<n;n--)a[n-1]=t[i-n]}key_to_bignum(e,t,i){let s,r,a=0;if(2===t[a]){if(a++,0!=(128&t[a])){for(s=0,r=0;r<(127&t[a]);r++)s=(s<<8>>>0|t[a+r+1])>>>0;a+=1+(127&t[a])}else s=t[a],a++;s<=4*i&&this.move_key_to_big(e,t.subarray(a),s,i)}}len_bignum(e,t){let i=t-1;for(;0<=i&&0===e[i];)i--;return i+1}bitlen_bignum(e,t){var i;let s,r;if(0===(i=this.len_bignum(e,t)))return 0;for(s=32*i,r=2147483648;0==(r&e[i-1]);)r>>>=1,s--;return s}init_pubkey(){let e=0,t;var i;const s=new Uint8Array(256);for(this.init_bignum(this.pubkey.key2,65537,64),t=0;e<se.length;)i=(((re[se.charCodeAt(e++)]>>>0<<6>>>0|255&re[se.charCodeAt(e++)])>>>0<<6>>>0|255&re[se.charCodeAt(e++)])>>>0<<6>>>0|255&re[se.charCodeAt(e++)])>>>0,s[t++]=i>>16&255,s[t++]=i>>8&255,s[t++]=255&i;this.key_to_bignum(this.pubkey.key1,s,64),this.pubkey.len=this.bitlen_bignum(this.pubkey.key1,64)-1}len_predata(){var e=(this.pubkey.len-1)/8|0;return(1+(55/e|0))*(1+e)>>>0}cmp_bignum(e,t,i){for(;0<i;){if(e[--i]<t[i])return-1;if(e[i]>t[i])return 1}return 0}mov_bignum(t,i,s){for(let e=0;e<s;e++)t[e]=i[e]}shr_bignum(e,t,i){let s;var r=t/32|0;if(0<r){for(s=0;s<i-r;s++)e[s]=e[s+r];for(;s<i;s++)e[s]=0;t%=32}if(0!==t){for(s=0;s<i-1;s++)e[s]=(e[s]>>>t|e[s+1]<<32-t>>>0)>>>0;e[s]=e[s]>>>t}}shl_bignum(e,t,i){let s;var r=t/32|0;if(0<r){for(s=i-1;s>r;s--)e[s]=e[s-r];for(;0<s;s--)e[s]=0;t%=32}if(0!==t){for(s=i-1;0<s;s--)e[s]=(e[s]<<t>>>0|e[s-1]>>>32-t)>>>0;e[0]=e[0]<<t>>>0}}sub_bignum(e,t,i,s,r){var a,n;r+=r;var o=new Uint16Array(t.buffer,t.byteOffset),h=new Uint16Array(i.buffer,i.byteOffset);const l=new Uint16Array(e.buffer,e.byteOffset);let c=0;for(;-1!=--r;)a=o[c],n=h[c],l[c]=a-n-s&65535,s=0!=(a-n-s&65536)?1:0,c++;return s}sub_bignum_word(e,t,i,s,r){var a,n;let o=0;for(;-1!=--r;)a=t[o],n=i[o],e[o]=a-n-s&65535,s=0!=(a-n-s&65536)?1:0,o++;return s}inv_bignum(e,t,i){const s=new Uint32Array(64);var r;let a,n,o=0;for(this.init_bignum(s,0,i),this.init_bignum(e,0,i),n=this.bitlen_bignum(t,i),a=1<<n%32>>>0,o=((n+32)/32|0)-1,r=4*((n-1)/32|0)>>>0,s[r/4|0]=s[r/4|0]|1<<(n-1&31)>>>0;0<n;)n--,this.shl_bignum(s,1,i),-1!==this.cmp_bignum(s,t,i)&&(this.sub_bignum(s,s,t,0,i),e[o]=e[o]|a>>>0),a>>>=1,0===a&&(o--,a=2147483648);this.init_bignum(s,0,i)}inc_bignum(e,t){let i=0;for(;0==++e[i]&&0<--t;)i++}init_two_dw(e,t){this.mov_bignum(this.glob1,e,t),this.glob1_bitlen=this.bitlen_bignum(this.glob1,t),this.glob1_len_x2=(this.glob1_bitlen+15)/16|0,this.mov_bignum(this.glob1_hi,this.glob1.subarray(this.len_bignum(this.glob1,t)-2),2),this.glob1_hi_bitlen=this.bitlen_bignum(this.glob1_hi,2)-32>>>0,this.shr_bignum(this.glob1_hi,this.glob1_hi_bitlen,2),this.inv_bignum(this.glob1_hi_inv,this.glob1_hi,2),this.shr_bignum(this.glob1_hi_inv,1,2),this.glob1_hi_bitlen=(this.glob1_hi_bitlen+15)%16+1>>>0,this.inc_bignum(this.glob1_hi_inv,2),32<this.bitlen_bignum(this.glob1_hi_inv,2)&&(this.shr_bignum(this.glob1_hi_inv,1,2),this.glob1_hi_bitlen--),this.glob1_hi_inv_lo=65535&this.glob1_hi_inv[0],this.glob1_hi_inv_hi=this.glob1_hi_inv[0]>>>16&65535}mul_bignum_word(e,t,i,s){let r,a;var n=new Uint16Array(t.buffer,t.byteOffset);let o=a=0;for(r=0;r<s;r++)a=i*n[o]+e[o]+a,e[o]=65535&a,o++,a>>>=16;e[o]+=65535&a}mul_bignum(e,t,i,s){let r;var a=new Uint16Array(i.buffer,i.byteOffset);let n=new Uint16Array(e.buffer,e.byteOffset);this.init_bignum(e,0,2*s);let o=0;for(r=0;r<2*s;r++)this.mul_bignum_word(n.subarray(o),t,a[o],2*s),o++}not_bignum(e,t){let i;for(i=0;i<t;i++)e[i]=~e[i]>>>0}neg_bignum(e,t){this.not_bignum(e,t),this.inc_bignum(e,t)}get_mulword(e,t){let i=((((65535&(65535^e[t-1]))*this.glob1_hi_inv_lo+65536>>>1)+((65535^e[t-2])*this.glob1_hi_inv_hi+this.glob1_hi_inv_hi>>>1)+1>>>16)+((65535&(65535^e[t-1]))*this.glob1_hi_inv_hi>>>1)+((65535^e[t])*this.glob1_hi_inv_lo>>>1)+1>>>14)+this.glob1_hi_inv_hi*(65535^e[t])*2>>>this.glob1_hi_bitlen>>>0;return 65535<i&&(i=65535),65535&i}dec_bignum(e,t){let i=0;for(;--e[i]>>>0==4294967295&&0<--t;)i++}calc_a_bignum(e,t,s,r){let a;var n=this.glob1,o=this.glob2;if(this.mul_bignum(this.glob2,t,s,r),this.glob2[2*r]=0,(s=2*this.len_bignum(this.glob2,2*r+1))>=this.glob1_len_x2){this.inc_bignum(this.glob2,2*r+1),this.neg_bignum(this.glob2,2*r+1),a=1+s-this.glob1_len_x2;let e=new Uint16Array(o.buffer),t=a,i=1+s;for(;0!==a;a--){i--;var h=this.get_mulword(e,i);t--;var l=e.subarray(t);0<h&&(this.mul_bignum_word(l,this.glob1,h,2*r),0==(32768&e[i])&&0!==this.sub_bignum_word(l,l,new Uint16Array(n.buffer),0,2*r)&&e[i]--)}this.neg_bignum(this.glob2,r),this.dec_bignum(this.glob2,r)}this.mov_bignum(e,this.glob2,r)}clear_tmp_vars(e){this.init_bignum(this.glob1,0,e),this.init_bignum(this.glob2,0,e),this.init_bignum(this.glob1_hi_inv,0,4),this.init_bignum(this.glob1_hi,0,4),this.glob1_bitlen=0,this.glob1_hi_bitlen=0,this.glob1_len_x2=0,this.glob1_hi_inv_lo=0,this.glob1_hi_inv_hi=0}calc_a_key(e,t,i,s,r){var a,n=new Uint32Array(64);let o,h,l=0;for(this.init_bignum(e,1,r),a=this.len_bignum(s,r),this.init_two_dw(s,a),o=this.bitlen_bignum(i,a)<<24>>24,s=((o+31)/32|0)>>>0,h=1<<(o-1)%32>>>1,l+=s-1,o--,this.mov_bignum(e,t,a);-1!=--o;)0===h&&(h=2147483648,l--),this.calc_a_bignum(n,e,e,a),0!=(i[l]&h)?this.calc_a_bignum(e,n,t,a):this.mov_bignum(e,n,a),h>>>=1;this.init_bignum(n,0,a),this.clear_tmp_vars(r)}memcpy(e,t,i){let s=0;for(;0!=i--;)e[s]=t[s],s++}process_predata(e,t,i){var s=new Uint32Array(64),r=new Uint32Array(64);let a=0,n=0;for(var o=(this.pubkey.len-1)/8|0;1+o<=t;)this.init_bignum(s,0,64),this.memcpy(new Uint8Array(s.buffer),e.subarray(a),1+o),this.calc_a_key(r,s,this.pubkey.key2,this.pubkey.key1,64),this.memcpy(i.subarray(n),new Uint8Array(r.buffer),o),t-=1+o,a+=1+o,n+=o}decryptKey(e){this.init_pubkey();let t=new Uint8Array(256);return this.process_predata(e,this.len_predata(),t),t.subarray(0,56)}}class oe{static calculateCrc(i,e=4294967295){let s=e;for(let e=0,t=i.length;e<t;e++)s=(s>>>8^this.lookUp[255&s^i[e]])>>>0;return s=(s^e)>>>0,s}constructor(e=4294967295){this.polynomal=e,this.crc=e}append(i){for(let e=0,t=i.length;e<t;e++)this.crc=(this.crc>>>8^oe.lookUp[255&this.crc^i[e]])>>>0}get(){return(this.crc^this.polynomal)>>>0}}oe.lookUp=new Uint32Array([0,1996959894,3993919788,2567524794,124634137,1886057615,3915621685,2657392035,249268274,2044508324,3772115230,2547177864,162941995,2125561021,3887607047,2428444049,498536548,1789927666,4089016648,2227061214,450548861,1843258603,4107580753,2211677639,325883990,1684777152,4251122042,2321926636,335633487,1661365465,4195302755,2366115317,997073096,1281953886,3579855332,2724688242,1006888145,1258607687,3524101629,2768942443,901097722,1119000684,3686517206,2898065728,853044451,1172266101,3705015759,2882616665,651767980,1373503546,3369554304,3218104598,565507253,1454621731,3485111705,3099436303,671266974,1594198024,3322730930,2970347812,795835527,1483230225,3244367275,3060149565,1994146192,31158534,2563907772,4023717930,1907459465,112637215,2680153253,3904427059,2013776290,251722036,2517215374,3775830040,2137656763,141376813,2439277719,3865271297,1802195444,476864866,2238001368,4066508878,1812370925,453092731,2181625025,4111451223,1706088902,314042704,2344532202,4240017532,1658658271,366619977,2362670323,4224994405,1303535960,984961486,2747007092,3569037538,1256170817,1037604311,2765210733,3554079995,1131014506,879679996,2909243462,3663771856,1141124467,855842277,2852801631,3708648649,1342533948,654459306,3188396048,3373015174,1466479909,544179635,3110523913,3462522015,1591671054,702138776,2966460450,3352799412,1504918807,783551873,3082640443,3233442989,3988292384,2596254646,62317068,1957810842,3939845945,2647816111,81470997,1943803523,3814918930,2489596804,225274430,2053790376,3826175755,2466906013,167816743,2097651377,4027552580,2265490386,503444072,1762050814,4150417245,2154129355,426522225,1852507879,4275313526,2312317920,282753626,1742555852,4189708143,2394877945,397917763,1622183637,3604390888,2714866558,953729732,1340076626,3518719985,2797360999,1068828381,1219638859,3624741850,2936675148,906185462,1090812512,3747672003,2825379669,829329135,1181335161,3412177804,3160834842,628085408,1382605366,3423369109,3138078467,570562233,1426400815,3317316542,2998733608,733239954,1555261956,3268935591,3050360625,752459403,1541320221,2607071920,3965973030,1969922972,40735498,2617837225,3943577151,1913087877,83908371,2512341634,3803740692,2075208622,213261112,2463272603,3855990285,2094854071,198958881,2262029012,4057260610,1759359992,534414190,2176718541,4139329115,1873836001,414664567,2282248934,4279200368,1711684554,285281116,2405801727,4167216745,1634467795,376229701,2685067896,3608007406,1308918612,956543938,2808555105,3495958263,1231636301,1047427035,2932959818,3654703836,1088359270,936918e3,2847714899,3736837829,1202900863,817233897,3183342108,3401237130,1404277552,615818150,3134207493,3453421203,1423857449,601450431,3009837614,3294710456,1567103746,711928724,3020668471,3272380065,1510334235,755167117]);class he{static hashFilename(t){var i=(t=t.toUpperCase()).length,s=i>>2;if(0!=(3&i)){t+=String.fromCharCode(i-(s<<2));let e=3-(3&i);for(;0!=e--;)t+=t[s<<2]}return oe.calculateCrc(R(t))}constructor(e,t,i){this.hash=e,this.offset=t,this.length=i}}he.size=12,(r=C=C||{})[r.Checksum=65536]="Checksum",r[r.Encrypted=131072]="Encrypted";class le{constructor(e){this.stream=e,this.headerStart=84,this.index=new Map,this.parseHeader()}parseHeader(){var e=this.stream.readUint32(),t=0==(e&~(C.Checksum|C.Encrypted));if(t){if(0!=(e&C.Encrypted))return void(this.dataStart=this.parseRaHeader())}else this.stream.seek(0);this.dataStart=this.parseTdHeader(this.stream)}parseRaHeader(){const e=this.stream;var t=e.readUint8Array(80),i=(new ne).decryptKey(t),s=e.readUint32Array(2);const r=new ie(i);let a=new k(r.decrypt(s));t=a.readUint16();a.readUint32(),e.position=this.headerStart;i=6+t*he.size,t=(3+i)/4|0,s=e.readUint32Array(t+t%2);a=new k(r.decrypt(s));i=this.headerStart+i+(1+(~i>>>0)&7);return this.parseTdHeader(a),i}parseTdHeader(t){var i=t.readUint16();t.readUint32();for(let e=0;e<i;e++){var s=new he(t.readUint32(),t.readUint32(),t.readUint32());this.index.set(s.hash,s)}return t.position}containsFile(e){return this.index.has(he.hashFilename(e))}openFile(e){var t=this.index.get(he.hashFilename(e));if(!t)throw new Error(`File "${e}" not found`);return i.factory(this.stream,e,this.dataStart+t.offset,t.length)}}class ce extends Error{constructor(){super(...arguments),this.name="FileNotFoundError"}}class ue{constructor(){this.entries=new Map}addFile(e){this.entries.set(e.filename,e)}containsFile(e){return this.entries.has(e)}openFile(e){if(!this.containsFile(e))throw new Error(`File "${e}" not found`);return this.entries.get(e)}}class de{constructor(e,t){this.rfs=e,this.logger=t,this.allArchives=new Map,this.archivesByPriority=[]}fileExists(e){for(const t of this.archivesByPriority)if(t.containsFile(e))return!0;return!1}openFile(e){for(const t of this.archivesByPriority)if(t.containsFile(e))return t.openFile(e);throw new ce(`File "${e}" not found in VFS`)}addArchive(e,t){this.allArchives.has(t)||(this.allArchives.set(t,e),this.archivesByPriority.push(e)),this.logger.info(`Added archive "${t}" to VFS`)}hasArchive(e){return this.allArchives.has(e)}removeArchive(e){var t=this.allArchives.get(e);t&&(this.allArchives.delete(e),this.archivesByPriority.splice(this.archivesByPriority.indexOf(t),1),this.logger.info(`Removed archive "${e}" from VFS`))}listArchives(){return[...this.allArchives.keys()]}async addMixFile(e){await this.addArchiveByFilename(e,e=>new le(e.stream))}async addBagFile(e){const i=await this.openFileWithRfs(e.replace(".bag",".idx"));await this.addArchiveByFilename(e,e=>{var t=new ee(i.stream);return(new K).fromVirtualFile(e,t)})}async addArchiveByFilename(e,t){var i;this.allArchives.has(e)||(i=await this.openFileWithRfs(e))&&this.addArchive(t(i),e)}async openFileWithRfs(e){let t;try{t=await this.rfs.openFile(e)}catch(e){if(!(e instanceof ce))throw e}if(!t){if(!this.fileExists(e))throw new ce(`File "${e}" not found`);t=this.openFile(e)}return t}async loadImplicitMixFiles(e){this.logger.info("Initializing implicit mix files..."),e===xt.YurisRevenge&&await this.addMixFile("langmd.mix"),await this.addMixFile("language.mix"),e===xt.YurisRevenge&&await this.addMixFile("ra2md.mix"),await this.addMixFile("ra2.mix"),e===xt.YurisRevenge&&await this.addMixFile("cachemd.mix"),await this.addMixFile("cache.mix"),e===xt.YurisRevenge&&await this.addMixFile("loadmd.mix"),await this.addMixFile("load.mix"),e===xt.YurisRevenge&&await this.addMixFile("localmd.mix"),await this.addMixFile("local.mix"),e===xt.YurisRevenge&&await this.addMixFile("ntrlmd.mix"),await this.addMixFile("neutral.mix"),e===xt.YurisRevenge&&await this.addMixFile("audiomd.mix"),await this.addMixFile("audio.mix"),await this.addBagFile("audio.bag"),await this.addMixFile("conquer.mix"),e===xt.YurisRevenge&&(await this.addMixFile("conqmd.mix"),await this.addMixFile("genermd.mix")),await this.addMixFile("generic.mix"),e===xt.YurisRevenge&&await this.addMixFile("isogenmd.mix"),await this.addMixFile("isogen.mix"),e===xt.YurisRevenge&&await this.addMixFile("cameomd.mix"),await this.addMixFile("cameo.mix"),await this.addMixFile("cameocd.mix"),e===xt.YurisRevenge&&await this.addMixFile("multimd.mix"),await this.addMixFile("multi.mix")}async loadExtraMixFiles(i){let s=new Set;for await(var e of this.rfs.getEntries())s.add(e.toLowerCase());for(var r of["ecache","expand","elocal"])for(let t=99;0<=t;t--){let e=[`${r}${N(t,"00")}.mix`];i===xt.YurisRevenge&&e.push(`${r}md${N(t,"00")}.mix`);for(var a of e)s.has(a)&&await this.addMixFile(a)}let t=[".mmx"];i===xt.YurisRevenge&&t.push(".yro");for(const n of t)for(const o of s)o.endsWith(n)&&this.addArchive(new le((await this.rfs.openFile(o)).stream),o)}async loadStandaloneFiles(e){let i=["ini","csf"],s=new Set(e?.exclude),r=[];for await(var a of this.rfs.getEntries()){let t=a.toLowerCase();i.some(e=>t.endsWith("."+e))&&!s.has(t)&&r.push(await this.rfs.openFile(a,!0))}if(r.length){let e=new ue;for(var t of r)e.addFile(t);this.addArchive(e,"mem.archive")}}}class ge extends Error{constructor(e){super("Storage quota exceeded",e),this.name="StorageQuotaError"}}class pe extends l{constructor(){super(...arguments),this.name="NameNotAllowedError"}}class me{constructor(e,t=!1){this.handle=e,this.caseSensitive=t}get name(){return this.handle.name}async*getEntries(){try{for await(var e of this.handle.keys())yield e}catch(e){if("NotFoundError"===e.name)throw new ce(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof DOMException)throw new l(`Directory "${this.handle.name}" could not be read (${e.name})`,{cause:e});throw e}}async listEntries(){let e=[];for await(var t of this.getEntries())e.push(t);return e}async*getFileHandles(){try{for await(const e of this.handle.values())"file"===e.kind&&(yield e)}catch(e){if("NotFoundError"===e.name)throw new ce(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof DOMException)throw new l(`Directory "${this.handle.name}" could not be read (${e.name})`,{cause:e});throw e}}async*getRawFiles(){for await(const e of this.getFileHandles())yield await e.getFile()}async containsEntry(e){return void 0!==await this.resolveEntryName(e)}async resolveEntryName(e){if(this.caseSensitive)return(await this.handle.getFileHandle(e).catch(()=>this.handle.getDirectoryHandle(e)).catch(()=>{}))?.name;for await(const t of this.getEntries())if(M(t,e))return t}async fixEntryCase(e){if(!this.caseSensitive)for await(var t of this.getEntries())if(M(t,e)){e=t;break}return e}async getRawFile(t,e=!1,i){let s;try{var r=e?t:await this.fixEntryCase(t);s=await this.handle.getFileHandle(r)}catch(e){if("NotFoundError"===e.name)throw new ce(`File "${t}" not found in directory "${this.handle.name}"`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`File name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`File "${t}" could not be read (${e.name})`,{cause:e});throw e}t=await s.getFile();return i?new File([t],t.name,{type:i}):t}async openFile(e,t=!1){t=await this.getRawFile(e,t);return i.fromRealFile(t)}async writeFile(i,s){s=s??(i instanceof File?i.name:i.filename);try{var r=await this.fixEntryCase(s);await this.deleteFile(r,!0);let e=await this.handle.getFileHandle(r,{create:!0}),t=await e.createWritable();try{await t.write(i instanceof File?i:new Uint8Array(i.stream.buffer,i.stream.byteOffset,i.stream.byteLength)),await t.close()}catch(e){throw await t.abort(),e}}catch(e){if("QuotaExceededError"===e.name)throw new ge({cause:e});if("NotFoundError"===e.name)throw new ce(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`File name "${s}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`File "${s}" could not be written (${e.name})`,{cause:e});throw e}}async deleteFile(t,i=!1){t=i?t:await this.resolveEntryName(t);if(t)try{await this.handle.removeEntry(t)}catch(e){if(i&&"NotFoundError"===e.name)return;if("QuotaExceededError"===e.name)throw new ge({cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`File name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`File "${t}" could not be deleted (${e.name})`,{cause:e});throw e}}async getDirectory(t,e=this.caseSensitive){var i=e?t:await this.fixEntryCase(t);let s;try{s=await this.handle.getDirectoryHandle(i)}catch(e){if("NotFoundError"===e.name)throw new ce(`Directory "${t}" not found or parent directory "${this.handle.name}" is gone`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`Directory "${t}" could not be read (${e.name})`,{cause:e});throw e}return new me(s,e)}async getOrCreateDirectory(t,e=this.caseSensitive){var i=e?t:await this.fixEntryCase(t);try{return new me(await this.handle.getDirectoryHandle(i,{create:!0}),e)}catch(e){if("QuotaExceededError"===e.name)throw new ge({cause:e});if("NotFoundError"===e.name)throw new ce(`Directory "${this.handle.name}" not found"`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`Directory "${t}" could not be created (${e.name})`,{cause:e});throw e}}async deleteDirectory(t,e=!1){t=await this.resolveEntryName(t);if(t)try{await this.handle.removeEntry(t,{recursive:e})}catch(e){if("QuotaExceededError"===e.name)throw new ge({cause:e});if("InvalidModificationError"===e.name)throw new l("Can't delete non-empty directory when recursive = false");if(e instanceof TypeError&&e.message.includes("not allowed"))throw new pe(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new l(`Directory "${t}" could not be deleted (${e.name})`,{cause:e});throw e}}}class fe{constructor(){this.directories=[]}addRootDirectoryHandle(e){this.rootDirectory=this.addDirectoryHandle(e),this.rootDirectoryHandle=e}getRootDirectoryHandle(){return this.rootDirectoryHandle}addDirectoryHandle(e){e=new me(e);return this.directories.push(e),e}addDirectory(e){this.directories.push(e)}async getDirectory(e){var t=await this.findDirectory(e);if(!t)throw new Error(`Directory "${e}" not found in real file system`);return t}async findDirectory(e){for(const t of this.directories)if(await t.containsEntry(e))return await t.getDirectory(e)}getRootDirectory(){return this.rootDirectory}async containsEntry(e){for(const t of this.directories)if(await t.containsEntry(e))return!0;return!1}async openFile(e,t=!1){for(const i of this.directories)try{return await i.openFile(e,t)}catch(e){if(!(e instanceof ce))throw e}throw new ce(`File "${e}" not found in real file system`)}async getRawFile(e){for(const t of this.directories)if(await t.containsEntry(e))return await t.getRawFile(e);throw new Error(`File "${e}" not found in real file system`)}async*getEntries(){for(var e of this.directories)for await(var t of e.getEntries())yield t}}class ye{constructor(e){this.resourceFactory=e,this.resources=new Map}setVfs(e){this.vfs=e}set(e,t){this.resources.set(e,t)}has(e){return!!this.resources.has(e)||(this.vfs?.fileExists(e)??!1)}get(e){let t;return t=this.resources.get(e),!t&&this.vfs?.fileExists(e)&&(t=this.resourceFactory(this.vfs.openFile(e)),this.resources.set(e,t)),t}clear(e){e?this.resources.delete(e):this.resources.clear()}}const we="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";function Te(s,e,r,t){if(-1<["32f","64"].indexOf(e)&&-1<["32f","64"].indexOf(t))r.set(s);else{ke(e),ke(t);let i=function(e,t){let i=function(e){return e};e!=t&&(i=["32f","64"].includes(e)?ve:["32f","64"].includes(t)?Se:be);return i}(e,t);var a={oldMin:Math.pow(2,parseInt(e,10))/2,newMin:Math.pow(2,parseInt(t,10))/2,oldMax:Math.pow(2,parseInt(e,10))/2-1,newMax:Math.pow(2,parseInt(t,10))/2-1};Oe(e,s,!0);for(let e=0,t=s.length;e<t;e++)r[e]=i(s[e],a);Oe(t,r,!1)}}function be(e,t){return e=0<e?parseInt(e/t.oldMax*t.newMax,10):parseInt(e/t.oldMin*t.newMin,10)}function ve(e,t){return parseInt(0<e?e*t.newMax:e*t.newMin,10)}function Se(e,t){return 0<e?e/t.oldMax:e/t.oldMin}function ke(e){if("32f"!=e&&"64"!=e&&(parseInt(e,10)<"8"||"53"<parseInt(e,10)))throw new Error("Invalid bit depth.")}function Oe(e,i,t){if("8"==e){var s=t?-128:128;for(let e=0,t=i.length;e<t;e++)i[e]=i[e]+=s}}const _e=[-1,-1,-1,-1,2,4,6,8,-1,-1,-1,-1,2,4,6,8],Ie=[7,8,9,10,11,12,13,14,16,17,19,21,23,25,28,31,34,37,41,45,50,55,60,66,73,80,88,97,107,118,130,143,157,173,190,209,230,253,279,307,337,371,408,449,494,544,598,658,724,796,876,963,1060,1166,1282,1411,1552,1707,1878,2066,2272,2499,2749,3024,3327,3660,4026,4428,4871,5358,5894,6484,7132,7845,8630,9493,10442,11487,12635,13899,15289,16818,18500,20350,22385,24623,27086,29794,32767];function Ce(i){var s={index:0,predicted:0,step:7};let r=new Uint8Array(i.length),a=[],n=0,o=0;for(let e=0,t=i.length;e<t;e++)e%505==0&&0!=e&&(r.set(function(i,s){let r=function(e,t){Be(e,t);let i=[];return i.push(255&e),i.push(e>>8&255),i.push(t.index),i.push(0),i}(i[0],s);for(let e=3,t=i.length;e<t;e+=2){var a=Be(i[e],s),n=Be(i[e+1],s);r.push(n<<4|a)}return r}(a,s),n),n+=256,a=[],o++),a.push(i[e]);let e=i.length/2;return e%2&&e++,r.slice(0,e+512+4*o)}function Ae(t,e=256){var i={index:0,predicted:0,step:7};let s=new Int16Array(2*t.length),r=[],a=0,n=t.length,o=0;for(;0<n;){var h=Math.min(n,e);for(let e=0;e<h;e++)r.push(t[o]),o++;var l=function(i,s){s.predicted=function(e){return 32767<e?e-65536:e}(i[1]<<8|i[0]),s.index=i[2],s.step=Ie[s.index];let r=[s.predicted];for(let e=4,t=i.length;e<t;e++){var a=i[e],n=a>>4,a=n<<4^a;r.push(xe(a,s)),r.push(xe(n,s))}return r}(r,i);s.set(l,a),a+=l.length,r=[],n-=e}return s.slice(0,a)}function Be(e,t){let i=e-t.predicted,s=0;0<=i?s=0:(s=8,i=-i);let r=Ie[t.index],a=r>>3;return i>r&&(s|=4,i-=r,a+=r),r>>=1,i>r&&(s|=2,i-=r,a+=r),r>>=1,i>r&&(s|=1,a+=r),function(e,t,i){8&e?i.predicted-=t:i.predicted+=t;i.predicted<-32768?i.predicted=-32768:32767<i.predicted&&(i.predicted=32767);i.index+=_e[7&e],i.index<0?i.index=0:88<i.index&&(i.index=88)}(s,a,t),s}function xe(e,t){let i=0;return 4&e&&(i+=t.step),2&e&&(i+=t.step>>1),1&e&&(i+=t.step>>2),i+=t.step>>3,8&e&&(i=-i),t.predicted+=i,32767<t.predicted?t.predicted=32767:t.predicted<-32768&&(t.predicted=-32768),function(e,t){t.index+=_e[e],t.index<0?t.index=0:88<t.index&&(t.index=88);t.step=Ie[t.index]}(e,t),t.predicted}const Ee=[1,1,2,2,3,3,3,3,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7];function Pe(i){let s=new Uint8Array(i.length);for(let e=0,t=i.length;e<t;e++)s[e]=function(e){let t;var i,s=~(e=-32768==e?-32767:e)>>8&128;return s||(e*=-1),32635<e&&(e=32635),t=256<=e?(i=Ee[e>>8&127])<<4|e>>i+3&15:e>>4,85^t^s}(i[e]);return s}function Ne(i){let s=new Int16Array(i.length);for(let e=0,t=i.length;e<t;e++)s[e]=function(e){let t=0;0!=(128&(e^=85))&&(e&=-129,t=-1);var i=4+((240&e)>>4);let s=0;return s=4!=i?1<<i|(15&e)<<i-4|1<<i-5:e<<1|1,s=0===t?s:-s,8*s*-1}(i[e]);return s}const De=132,Me=32635,Re=[0,0,1,1,2,2,2,2,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7],Le=[0,132,396,924,1980,4092,8316,16764];function Fe(i){let s=new Uint8Array(i.length);for(let e=0,t=i.length;e<t;e++)s[e]=(r=i[e],a=void 0,0!=(a=r>>8&128)&&(r=-r),(r+=De)>Me&&(r=Me),~(a|(a=Re[r>>7&255])<<4|r>>a+3&15));var r,a;return s}function je(i){let s=new Int16Array(i.length);for(let e=0,t=i.length;e<t;e++)s[e]=function(e){var t,i;let s;return t=128&(e=~e),i=e>>4&7,e=15&e,s=Le[i]+(e<<3+i),0!=t&&(s=-s),s}(i[e]);return s}function Ue(t,i,s=0,r=t.length){for(let e=s;e<r;e+=i)!function(t,i,s){i--;for(let e=0;e<i;e++){var r=t[s+e];t[s+e]=t[s+i],t[s+i]=r,i--}}(t,i,e)}function We(e,i,s=0){let r=0;for(var t=e.length;r<t;){var a=e.codePointAt(r);if(a<128)i[s]=a,s++;else{let e=0,t=0;for(a<=2047?(e=1,t=192):a<=65535?(e=2,t=224):a<=1114111&&(e=3,t=240,r++),i[s]=(a>>6*e)+t,s++;0<e;)i[s]=128|a>>6*(e-1)&63,s++,e--}r++}return s}const ze=new Array(8).fill(0).map((e,t)=>Math.pow(2,8*t));class Ve{constructor(e,t=!1){this.bits=e,this.offset=Math.ceil(e/8),this.max=Math.pow(2,e)-1,this.min=0,this.unpack=this.unpack_,t&&(this.max=Math.pow(2,e)/2-1,this.min=-this.max-1,this.unpack=this.unpackSigned_)}pack(i,s,r=0){s=this.clamp_(Math.round(s));for(let e=0,t=this.offset;e<t;e++)i[r]=255&Math.floor(s/ze[e]),r++;return r}unpack_(t,i=0){let s=0;for(let e=0;e<this.offset;e++)s+=t[i+e]*ze[e];return s}unpackSigned_(e,t=0){return this.sign_(this.unpack_(e,t))}clamp_(e){return e>this.max?this.max:e<this.min?this.min:e}sign_(e){return e>this.max&&(e-=2*this.max+2),e}}class He{constructor(e,t){this.offset=Math.ceil((e+t)/8),this.ebits=e,this.fbits=t,this.bias=(1<<e-1)-1,this.biasP2=Math.pow(2,this.bias+1),this.ebitsFbits=e+t,this.fbias=Math.pow(2,-(8*this.offset-1-e))}pack(e,t,i){var s=((t=+(t=Math.abs(t)>this.biasP2-2*this.ebitsFbits?t<0?-1/0:1/0:t))||1/t)<0||t<0?1:0;t=Math.abs(t);let r=Math.min(Math.floor(Math.log(t)/Math.LN2),1023),a=Ge(t/Math.pow(2,r)*Math.pow(2,this.fbits));return t!=t?(a=Math.pow(2,this.fbits-1),r=(1<<this.ebits)-1):0!==t&&(t>=Math.pow(2,1-this.bias)?(2<=a/Math.pow(2,this.fbits)&&(r+=1,a=1),a=r>this.bias?(r=(1<<this.ebits)-1,0):(r+=this.bias,Ge(a)-Math.pow(2,this.fbits))):(a=Ge(t/Math.pow(2,1-this.bias-this.fbits)),r=0)),this.packFloatBits_(e,i,s,r,a)}unpack(t,i){var e=(1<<this.ebits)-1;let s,r="";for(let e=this.offset-1;0<=e;e--){var a=t[e+i].toString(2);r+="00000000".substring(a.length)+a}var n="1"==r.charAt(0)?-1:1;r=r.substring(1);let o=parseInt(r.substring(0,this.ebits),2);return r=r.substring(this.ebits),o==e?0!==parseInt(r,2)?NaN:1/0*n:(s=0===o?(o+=1,parseInt(r,2)):parseInt("1"+r,2),n*s*this.fbias*Math.pow(2,o-this.bias))}packFloatBits_(e,t,i,s,r){let a=[];a.push(i);for(let e=this.ebits;0<e;--e)a[e]=s%2?1:0,s=Math.floor(s/2);var n=a.length;for(let e=this.fbits;0<e;--e)a[n+e]=r%2?1:0,r=Math.floor(r/2);let o=a.join(""),h=this.offset+t-1,l=t;for(;h>=t;)e[h]=parseInt(o.substring(0,8),2),o=o.substring(8),h--,l++;return l}}function Ge(e){var t=Math.floor(e),e=e-t;return!(e<.5)&&(.5<e||t%2)?t+1:t}function $e(e,t=0,i=e.length){return function(o,e=0,t=o.length){let h="";for(let n=e;n<t;){let i=128,s=191,r=!1,a=o[n++];if(0<=a&&a<=127)h+=String.fromCharCode(a);else{let t=0;194<=a&&a<=223?t=1:224<=a&&a<=239?(t=2,224===o[n]&&(i=160),237===o[n]&&(s=159)):240<=a&&a<=244?(t=3,240===o[n]&&(i=144),244===o[n]&&(s=143)):r=!0,a&=(1<<8-t-1)-1;for(let e=0;e<t;e++)(o[n]<i||o[n]>s)&&(r=!0),a=a<<6|63&o[n],n++;r?h+=String.fromCharCode(65533):a<=65535?h+=String.fromCharCode(a):(a-=65536,h+=String.fromCharCode(55296+(a>>10&1023),56320+(1023&a)))}}return h}(e,t,i)}function qe(e){var t=[];return We(e,t),t}function Xe(e,t,i=0){return We(e,t,i)}function Ze(e,t,i,s=0){let r=tt((t=t||{}).bits,t.fp,t.signed);var a=Math.ceil(t.bits/8);let n=0;for(var o=s,h=e.length;n<h;n++)s=r.pack(i,e[n],s);return t.be&&Ue(i,a,o,s),s}function Qe(e,t,i,s=0,r=e.length){var a,n=tt((t=t||{}).bits,t.fp,t.signed);r=function(e,t,i){i=(t-e)%i;return t-i}(s,r,n.offset),t.be?(a=new Uint8Array(e),t.be&&Ue(a,n.offset,s,r),et(a,i,s,r,n)):et(e,i,s,r,n)}function Ye(e,t,i,s=0){return Ze([e],t,i,s)}function Ke(e,t){var i=[];return Ye(e,t,i,0),i}function Je(e,t,i=0){var s=[];return Qe(e,t,s,i,i+Math.ceil(t.bits/8)),s[0]}function et(i,s,r,a,n){var o=n.offset;for(let e=0,t=r;t<a;t+=o,e++)s[e]=n.unpack(i,t)}function tt(e,t,i){return t&&32==e?new He(8,23):t&&64==e?new He(11,52):new Ve(e,i)}function it(e,t){let i=qe(e);for(let e=i.length;e<t;e++)i.push(0);return i}(class h0 extends class{constructor(){this.container="",this.chunkSize=0,this.format="",this.signature=null,this.head=0,this.uInt32={bits:32,be:!1},this.supported_containers=["RIFF","RIFX"]}setSignature(e){if(this.head=0,this.container=this.readString(e,4),-1===this.supported_containers.indexOf(this.container))throw Error("Not a supported format.");this.uInt32.be="RIFX"===this.container,this.chunkSize=this.readUInt32(e),this.format=this.readString(e,4),this.signature={chunkId:this.container,chunkSize:this.chunkSize,format:this.format,subChunks:this.getSubChunksIndex_(e)}}findChunk(t,i=!1){var s=this.signature.subChunks;let r=[];for(let e=0;e<s.length;e++)if(s[e].chunkId==t){if(!i)return s[e];r.push(s[e])}return"LIST"==t&&r.length?r:null}readString(e,t){e=$e(e,this.head,this.head+t);return this.head+=t,e}readUInt32(e){return e=Je(e,this.uInt32,this.head),this.head+=4,e}getSubChunksIndex_(e){let t=[],i=this.head;for(;i<=e.length-8;)t.push(this.getSubChunkIndex_(e,i)),i+=8+t[t.length-1].chunkSize,i=i%2?i+1:i;return t}getSubChunkIndex_(e,t){let i={chunkId:this.getChunkId_(e,t),chunkSize:this.getChunkSize_(e,t)};return"LIST"==i.chunkId?(i.format=$e(e,t+8,t+12),this.head+=4,i.subChunks=this.getSubChunksIndex_(e)):(e=i.chunkSize%2?i.chunkSize+1:i.chunkSize,this.head=t+8+e,i.chunkData={start:t+8,end:this.head}),i}getChunkId_(e,t){return this.head+=4,$e(e,t,t+4)}getChunkSize_(e,t){return this.head+=4,Je(e,this.uInt32,t+4)}}{constructor(){super(),this.supported_containers.push("RF64"),this.fmt={chunkId:"",chunkSize:0,audioFormat:0,numChannels:0,sampleRate:0,byteRate:0,blockAlign:0,bitsPerSample:0,cbSize:0,validBitsPerSample:0,dwChannelMask:0,subformat:[]},this.fact={chunkId:"",chunkSize:0,dwSampleLength:0},this.cue={chunkId:"",chunkSize:0,dwCuePoints:0,points:[]},this.smpl={chunkId:"",chunkSize:0,dwManufacturer:0,dwProduct:0,dwSamplePeriod:0,dwMIDIUnityNote:0,dwMIDIPitchFraction:0,dwSMPTEFormat:0,dwSMPTEOffset:0,dwNumSampleLoops:0,dwSamplerData:0,loops:[]},this.bext={chunkId:"",chunkSize:0,description:"",originator:"",originatorReference:"",originationDate:"",originationTime:"",timeReference:[0,0],version:0,UMID:"",loudnessValue:0,loudnessRange:0,maxTruePeakLevel:0,maxMomentaryLoudness:0,maxShortTermLoudness:0,reserved:"",codingHistory:""},this.iXML={chunkId:"",chunkSize:0,value:""},this.ds64={chunkId:"",chunkSize:0,riffSizeHigh:0,riffSizeLow:0,dataSizeHigh:0,dataSizeLow:0,originationTime:0,sampleCountHigh:0,sampleCountLow:0},this.data={chunkId:"",chunkSize:0,samples:new Uint8Array(0)},this.LIST=[],this.junk={chunkId:"",chunkSize:0,chunkData:[]},this._PMX={chunkId:"",chunkSize:0,value:""},this.uInt16={bits:16,be:!1,signed:!1,fp:!1}}fromBuffer(e,t=!0){if(this.clearHeaders(),this.setSignature(e),this.uInt16.be=this.uInt32.be,"WAVE"!=this.format)throw Error('Could not find the "WAVE" format identifier');this.readDs64Chunk_(e),this.readFmtChunk_(e),this.readFactChunk_(e),this.readBextChunk_(e),this.readiXMLChunk_(e),this.readCueChunk_(e),this.readSmplChunk_(e),this.readDataChunk_(e,t),this.readJunkChunk_(e),this.readLISTChunk_(e),this.read_PMXChunk_(e)}clearHeaders(){var e=new h0;Object.assign(this.fmt,e.fmt),Object.assign(this.fact,e.fact),Object.assign(this.cue,e.cue),Object.assign(this.smpl,e.smpl),Object.assign(this.bext,e.bext),Object.assign(this.iXML,e.iXML),Object.assign(this.ds64,e.ds64),Object.assign(this.data,e.data),this.LIST=[],Object.assign(this.junk,e.junk),Object.assign(this._PMX,e._PMX)}readFmtChunk_(e){var t=this.findChunk("fmt ");if(!t)throw Error('Could not find the "fmt " chunk');this.head=t.chunkData.start,this.fmt.chunkId=t.chunkId,this.fmt.chunkSize=t.chunkSize,this.fmt.audioFormat=this.readUInt16_(e),this.fmt.numChannels=this.readUInt16_(e),this.fmt.sampleRate=this.readUInt32(e),this.fmt.byteRate=this.readUInt32(e),this.fmt.blockAlign=this.readUInt16_(e),this.fmt.bitsPerSample=this.readUInt16_(e),this.readFmtExtension_(e)}readFmtExtension_(e){16<this.fmt.chunkSize&&(this.fmt.cbSize=this.readUInt16_(e),18<this.fmt.chunkSize&&(this.fmt.validBitsPerSample=this.readUInt16_(e),20<this.fmt.chunkSize&&(this.fmt.dwChannelMask=this.readUInt32(e),this.fmt.subformat=[this.readUInt32(e),this.readUInt32(e),this.readUInt32(e),this.readUInt32(e)])))}readFactChunk_(e){var t=this.findChunk("fact");t&&(this.head=t.chunkData.start,this.fact.chunkId=t.chunkId,this.fact.chunkSize=t.chunkSize,this.fact.dwSampleLength=this.readUInt32(e))}readCueChunk_(t){var e=this.findChunk("cue ");if(e){this.head=e.chunkData.start,this.cue.chunkId=e.chunkId,this.cue.chunkSize=e.chunkSize,this.cue.dwCuePoints=this.readUInt32(t);for(let e=0;e<this.cue.dwCuePoints;e++)this.cue.points.push({dwName:this.readUInt32(t),dwPosition:this.readUInt32(t),fccChunk:this.readString(t,4),dwChunkStart:this.readUInt32(t),dwBlockStart:this.readUInt32(t),dwSampleOffset:this.readUInt32(t)})}}readSmplChunk_(t){var e=this.findChunk("smpl");if(e){this.head=e.chunkData.start,this.smpl.chunkId=e.chunkId,this.smpl.chunkSize=e.chunkSize,this.smpl.dwManufacturer=this.readUInt32(t),this.smpl.dwProduct=this.readUInt32(t),this.smpl.dwSamplePeriod=this.readUInt32(t),this.smpl.dwMIDIUnityNote=this.readUInt32(t),this.smpl.dwMIDIPitchFraction=this.readUInt32(t),this.smpl.dwSMPTEFormat=this.readUInt32(t),this.smpl.dwSMPTEOffset=this.readUInt32(t),this.smpl.dwNumSampleLoops=this.readUInt32(t),this.smpl.dwSamplerData=this.readUInt32(t);for(let e=0;e<this.smpl.dwNumSampleLoops;e++)this.smpl.loops.push({dwName:this.readUInt32(t),dwType:this.readUInt32(t),dwStart:this.readUInt32(t),dwEnd:this.readUInt32(t),dwFraction:this.readUInt32(t),dwPlayCount:this.readUInt32(t)})}}readDataChunk_(e,t){var i=this.findChunk("data");if(!i)throw Error('Could not find the "data" chunk');this.data.chunkId="data",this.data.chunkSize=i.chunkSize,t&&(this.data.samples=e.slice(i.chunkData.start,i.chunkData.end))}readBextChunk_(e){var t=this.findChunk("bext");t&&(this.head=t.chunkData.start,this.bext.chunkId=t.chunkId,this.bext.chunkSize=t.chunkSize,this.bext.description=this.readString(e,256),this.bext.originator=this.readString(e,32),this.bext.originatorReference=this.readString(e,32),this.bext.originationDate=this.readString(e,10),this.bext.originationTime=this.readString(e,8),this.bext.timeReference=[this.readUInt32(e),this.readUInt32(e)],this.bext.version=this.readUInt16_(e),this.bext.UMID=this.readString(e,64),this.bext.loudnessValue=this.readUInt16_(e),this.bext.loudnessRange=this.readUInt16_(e),this.bext.maxTruePeakLevel=this.readUInt16_(e),this.bext.maxMomentaryLoudness=this.readUInt16_(e),this.bext.maxShortTermLoudness=this.readUInt16_(e),this.bext.reserved=this.readString(e,180),this.bext.codingHistory=this.readString(e,this.bext.chunkSize-602))}readiXMLChunk_(e){var t=this.findChunk("iXML");t&&(this.head=t.chunkData.start,this.iXML.chunkId=t.chunkId,this.iXML.chunkSize=t.chunkSize,this.iXML.value=$e(e,this.head,this.head+this.iXML.chunkSize))}readDs64Chunk_(e){var t=this.findChunk("ds64");if(t)this.head=t.chunkData.start,this.ds64.chunkId=t.chunkId,this.ds64.chunkSize=t.chunkSize,this.ds64.riffSizeHigh=this.readUInt32(e),this.ds64.riffSizeLow=this.readUInt32(e),this.ds64.dataSizeHigh=this.readUInt32(e),this.ds64.dataSizeLow=this.readUInt32(e),this.ds64.originationTime=this.readUInt32(e),this.ds64.sampleCountHigh=this.readUInt32(e),this.ds64.sampleCountLow=this.readUInt32(e);else if("RF64"==this.container)throw Error('Could not find the "ds64" chunk')}readLISTChunk_(t){var i=this.findChunk("LIST",!0);if(null!==i)for(let e=0;e<i.length;e++){var s=i[e];this.LIST.push({chunkId:s.chunkId,chunkSize:s.chunkSize,format:s.format,subChunks:[]});for(let e=0;e<s.subChunks.length;e++)this.readLISTSubChunks_(s.subChunks[e],s.format,t)}}readLISTSubChunks_(e,t,i){"adtl"==t?-1<["labl","note","ltxt"].indexOf(e.chunkId)&&this.readLISTadtlSubChunks_(i,e):"INFO"==t&&this.readLISTINFOSubChunks_(i,e)}readLISTadtlSubChunks_(e,t){this.head=t.chunkData.start;let i={chunkId:t.chunkId,chunkSize:t.chunkSize,dwName:this.readUInt32(e)};"ltxt"==t.chunkId?(i.dwSampleLength=this.readUInt32(e),i.dwPurposeID=this.readUInt32(e),i.dwCountry=this.readUInt16_(e),i.dwLanguage=this.readUInt16_(e),i.dwDialect=this.readUInt16_(e),i.dwCodePage=this.readUInt16_(e),i.value=""):i.value=this.readZSTR_(e,this.head),this.LIST[this.LIST.length-1].subChunks.push(i)}readLISTINFOSubChunks_(e,t){this.head=t.chunkData.start,this.LIST[this.LIST.length-1].subChunks.push({chunkId:t.chunkId,chunkSize:t.chunkSize,value:this.readZSTR_(e,this.head)})}readJunkChunk_(e){var t=this.findChunk("junk");t&&(this.junk={chunkId:t.chunkId,chunkSize:t.chunkSize,chunkData:[].slice.call(e.slice(t.chunkData.start,t.chunkData.end))})}read_PMXChunk_(e){var t=this.findChunk("_PMX");t&&(this.head=t.chunkData.start,this._PMX.chunkId=t.chunkId,this._PMX.chunkSize=t.chunkSize,this._PMX.value=$e(e,this.head,this.head+this._PMX.chunkSize))}readZSTR_(t,i=0){for(let e=i;e<t.length&&(this.head++,0!==t[e]);e++);return $e(t,i,this.head-1)}readUInt16_(e){return e=Je(e,this.uInt16,this.head),this.head+=2,e}});function st(e,t,i){return!(i<1||4294967295<e*(t/8)*i)}class rt extends class extends class h0 extends class{constructor(){this.container="",this.chunkSize=0,this.format="",this.signature=null,this.head=0,this.uInt32={bits:32,be:!1},this.supported_containers=["RIFF","RIFX"]}setSignature(e){if(this.head=0,this.container=this.readString(e,4),-1===this.supported_containers.indexOf(this.container))throw Error("Not a supported format.");this.uInt32.be="RIFX"===this.container,this.chunkSize=this.readUInt32(e),this.format=this.readString(e,4),this.signature={chunkId:this.container,chunkSize:this.chunkSize,format:this.format,subChunks:this.getSubChunksIndex_(e)}}findChunk(t,i=!1){var s=this.signature.subChunks;let r=[];for(let e=0;e<s.length;e++)if(s[e].chunkId==t){if(!i)return s[e];r.push(s[e])}return"LIST"==t&&r.length?r:null}readString(e,t){e=$e(e,this.head,this.head+t);return this.head+=t,e}readUInt32(e){return e=Je(e,this.uInt32,this.head),this.head+=4,e}getSubChunksIndex_(e){let t=[],i=this.head;for(;i<=e.length-8;)t.push(this.getSubChunkIndex_(e,i)),i+=8+t[t.length-1].chunkSize,i=i%2?i+1:i;return t}getSubChunkIndex_(e,t){let i={chunkId:this.getChunkId_(e,t),chunkSize:this.getChunkSize_(e,t)};return"LIST"==i.chunkId?(i.format=$e(e,t+8,t+12),this.head+=4,i.subChunks=this.getSubChunksIndex_(e)):(e=i.chunkSize%2?i.chunkSize+1:i.chunkSize,this.head=t+8+e,i.chunkData={start:t+8,end:this.head}),i}getChunkId_(e,t){return this.head+=4,$e(e,t,t+4)}getChunkSize_(e,t){return this.head+=4,Je(e,this.uInt32,t+4)}}{constructor(){super(),this.supported_containers.push("RF64"),this.fmt={chunkId:"",chunkSize:0,audioFormat:0,numChannels:0,sampleRate:0,byteRate:0,blockAlign:0,bitsPerSample:0,cbSize:0,validBitsPerSample:0,dwChannelMask:0,subformat:[]},this.fact={chunkId:"",chunkSize:0,dwSampleLength:0},this.cue={chunkId:"",chunkSize:0,dwCuePoints:0,points:[]},this.smpl={chunkId:"",chunkSize:0,dwManufacturer:0,dwProduct:0,dwSamplePeriod:0,dwMIDIUnityNote:0,dwMIDIPitchFraction:0,dwSMPTEFormat:0,dwSMPTEOffset:0,dwNumSampleLoops:0,dwSamplerData:0,loops:[]},this.bext={chunkId:"",chunkSize:0,description:"",originator:"",originatorReference:"",originationDate:"",originationTime:"",timeReference:[0,0],version:0,UMID:"",loudnessValue:0,loudnessRange:0,maxTruePeakLevel:0,maxMomentaryLoudness:0,maxShortTermLoudness:0,reserved:"",codingHistory:""},this.iXML={chunkId:"",chunkSize:0,value:""},this.ds64={chunkId:"",chunkSize:0,riffSizeHigh:0,riffSizeLow:0,dataSizeHigh:0,dataSizeLow:0,originationTime:0,sampleCountHigh:0,sampleCountLow:0},this.data={chunkId:"",chunkSize:0,samples:new Uint8Array(0)},this.LIST=[],this.junk={chunkId:"",chunkSize:0,chunkData:[]},this._PMX={chunkId:"",chunkSize:0,value:""},this.uInt16={bits:16,be:!1,signed:!1,fp:!1}}fromBuffer(e,t=!0){if(this.clearHeaders(),this.setSignature(e),this.uInt16.be=this.uInt32.be,"WAVE"!=this.format)throw Error('Could not find the "WAVE" format identifier');this.readDs64Chunk_(e),this.readFmtChunk_(e),this.readFactChunk_(e),this.readBextChunk_(e),this.readiXMLChunk_(e),this.readCueChunk_(e),this.readSmplChunk_(e),this.readDataChunk_(e,t),this.readJunkChunk_(e),this.readLISTChunk_(e),this.read_PMXChunk_(e)}clearHeaders(){var e=new h0;Object.assign(this.fmt,e.fmt),Object.assign(this.fact,e.fact),Object.assign(this.cue,e.cue),Object.assign(this.smpl,e.smpl),Object.assign(this.bext,e.bext),Object.assign(this.iXML,e.iXML),Object.assign(this.ds64,e.ds64),Object.assign(this.data,e.data),this.LIST=[],Object.assign(this.junk,e.junk),Object.assign(this._PMX,e._PMX)}readFmtChunk_(e){var t=this.findChunk("fmt ");if(!t)throw Error('Could not find the "fmt " chunk');this.head=t.chunkData.start,this.fmt.chunkId=t.chunkId,this.fmt.chunkSize=t.chunkSize,this.fmt.audioFormat=this.readUInt16_(e),this.fmt.numChannels=this.readUInt16_(e),this.fmt.sampleRate=this.readUInt32(e),this.fmt.byteRate=this.readUInt32(e),this.fmt.blockAlign=this.readUInt16_(e),this.fmt.bitsPerSample=this.readUInt16_(e),this.readFmtExtension_(e)}readFmtExtension_(e){16<this.fmt.chunkSize&&(this.fmt.cbSize=this.readUInt16_(e),18<this.fmt.chunkSize&&(this.fmt.validBitsPerSample=this.readUInt16_(e),20<this.fmt.chunkSize&&(this.fmt.dwChannelMask=this.readUInt32(e),this.fmt.subformat=[this.readUInt32(e),this.readUInt32(e),this.readUInt32(e),this.readUInt32(e)])))}readFactChunk_(e){var t=this.findChunk("fact");t&&(this.head=t.chunkData.start,this.fact.chunkId=t.chunkId,this.fact.chunkSize=t.chunkSize,this.fact.dwSampleLength=this.readUInt32(e))}readCueChunk_(t){var e=this.findChunk("cue ");if(e){this.head=e.chunkData.start,this.cue.chunkId=e.chunkId,this.cue.chunkSize=e.chunkSize,this.cue.dwCuePoints=this.readUInt32(t);for(let e=0;e<this.cue.dwCuePoints;e++)this.cue.points.push({dwName:this.readUInt32(t),dwPosition:this.readUInt32(t),fccChunk:this.readString(t,4),dwChunkStart:this.readUInt32(t),dwBlockStart:this.readUInt32(t),dwSampleOffset:this.readUInt32(t)})}}readSmplChunk_(t){var e=this.findChunk("smpl");if(e){this.head=e.chunkData.start,this.smpl.chunkId=e.chunkId,this.smpl.chunkSize=e.chunkSize,this.smpl.dwManufacturer=this.readUInt32(t),this.smpl.dwProduct=this.readUInt32(t),this.smpl.dwSamplePeriod=this.readUInt32(t),this.smpl.dwMIDIUnityNote=this.readUInt32(t),this.smpl.dwMIDIPitchFraction=this.readUInt32(t),this.smpl.dwSMPTEFormat=this.readUInt32(t),this.smpl.dwSMPTEOffset=this.readUInt32(t),this.smpl.dwNumSampleLoops=this.readUInt32(t),this.smpl.dwSamplerData=this.readUInt32(t);for(let e=0;e<this.smpl.dwNumSampleLoops;e++)this.smpl.loops.push({dwName:this.readUInt32(t),dwType:this.readUInt32(t),dwStart:this.readUInt32(t),dwEnd:this.readUInt32(t),dwFraction:this.readUInt32(t),dwPlayCount:this.readUInt32(t)})}}readDataChunk_(e,t){var i=this.findChunk("data");if(!i)throw Error('Could not find the "data" chunk');this.data.chunkId="data",this.data.chunkSize=i.chunkSize,t&&(this.data.samples=e.slice(i.chunkData.start,i.chunkData.end))}readBextChunk_(e){var t=this.findChunk("bext");t&&(this.head=t.chunkData.start,this.bext.chunkId=t.chunkId,this.bext.chunkSize=t.chunkSize,this.bext.description=this.readString(e,256),this.bext.originator=this.readString(e,32),this.bext.originatorReference=this.readString(e,32),this.bext.originationDate=this.readString(e,10),this.bext.originationTime=this.readString(e,8),this.bext.timeReference=[this.readUInt32(e),this.readUInt32(e)],this.bext.version=this.readUInt16_(e),this.bext.UMID=this.readString(e,64),this.bext.loudnessValue=this.readUInt16_(e),this.bext.loudnessRange=this.readUInt16_(e),this.bext.maxTruePeakLevel=this.readUInt16_(e),this.bext.maxMomentaryLoudness=this.readUInt16_(e),this.bext.maxShortTermLoudness=this.readUInt16_(e),this.bext.reserved=this.readString(e,180),this.bext.codingHistory=this.readString(e,this.bext.chunkSize-602))}readiXMLChunk_(e){var t=this.findChunk("iXML");t&&(this.head=t.chunkData.start,this.iXML.chunkId=t.chunkId,this.iXML.chunkSize=t.chunkSize,this.iXML.value=$e(e,this.head,this.head+this.iXML.chunkSize))}readDs64Chunk_(e){var t=this.findChunk("ds64");if(t)this.head=t.chunkData.start,this.ds64.chunkId=t.chunkId,this.ds64.chunkSize=t.chunkSize,this.ds64.riffSizeHigh=this.readUInt32(e),this.ds64.riffSizeLow=this.readUInt32(e),this.ds64.dataSizeHigh=this.readUInt32(e),this.ds64.dataSizeLow=this.readUInt32(e),this.ds64.originationTime=this.readUInt32(e),this.ds64.sampleCountHigh=this.readUInt32(e),this.ds64.sampleCountLow=this.readUInt32(e);else if("RF64"==this.container)throw Error('Could not find the "ds64" chunk')}readLISTChunk_(t){var i=this.findChunk("LIST",!0);if(null!==i)for(let e=0;e<i.length;e++){var s=i[e];this.LIST.push({chunkId:s.chunkId,chunkSize:s.chunkSize,format:s.format,subChunks:[]});for(let e=0;e<s.subChunks.length;e++)this.readLISTSubChunks_(s.subChunks[e],s.format,t)}}readLISTSubChunks_(e,t,i){"adtl"==t?-1<["labl","note","ltxt"].indexOf(e.chunkId)&&this.readLISTadtlSubChunks_(i,e):"INFO"==t&&this.readLISTINFOSubChunks_(i,e)}readLISTadtlSubChunks_(e,t){this.head=t.chunkData.start;let i={chunkId:t.chunkId,chunkSize:t.chunkSize,dwName:this.readUInt32(e)};"ltxt"==t.chunkId?(i.dwSampleLength=this.readUInt32(e),i.dwPurposeID=this.readUInt32(e),i.dwCountry=this.readUInt16_(e),i.dwLanguage=this.readUInt16_(e),i.dwDialect=this.readUInt16_(e),i.dwCodePage=this.readUInt16_(e),i.value=""):i.value=this.readZSTR_(e,this.head),this.LIST[this.LIST.length-1].subChunks.push(i)}readLISTINFOSubChunks_(e,t){this.head=t.chunkData.start,this.LIST[this.LIST.length-1].subChunks.push({chunkId:t.chunkId,chunkSize:t.chunkSize,value:this.readZSTR_(e,this.head)})}readJunkChunk_(e){var t=this.findChunk("junk");t&&(this.junk={chunkId:t.chunkId,chunkSize:t.chunkSize,chunkData:[].slice.call(e.slice(t.chunkData.start,t.chunkData.end))})}read_PMXChunk_(e){var t=this.findChunk("_PMX");t&&(this.head=t.chunkData.start,this._PMX.chunkId=t.chunkId,this._PMX.chunkSize=t.chunkSize,this._PMX.value=$e(e,this.head,this.head+this._PMX.chunkSize))}readZSTR_(t,i=0){for(let e=i;e<t.length&&(this.head++,0!==t[e]);e++);return $e(t,i,this.head-1)}readUInt16_(e){return e=Je(e,this.uInt16,this.head),this.head+=2,e}}{toBuffer(){this.uInt16.be="RIFX"===this.container,this.uInt32.be=this.uInt16.be;var t=[this.getJunkBytes_(),this.getDs64Bytes_(),this.getBextBytes_(),this.getiXMLBytes_(),this.getFmtBytes_(),this.getFactBytes_(),qe(this.data.chunkId),Ke(this.data.samples.length,this.uInt32),this.data.samples,this.getCueBytes_(),this.getSmplBytes_(),this.getLISTBytes_(),this.get_PMXBytes_()];let i=0;for(let e=0;e<t.length;e++)i+=t[e].length;let s=new Uint8Array(i+12),r=0;r=Xe(this.container,s,r),r=Ye(i+4,this.uInt32,s,r),r=Xe(this.format,s,r);for(let e=0;e<t.length;e++)s.set(t[e],r),r+=t[e].length;return s}getBextBytes_(){let e=[];return this.enforceBext_(),this.bext.chunkId&&(this.bext.chunkSize=602+this.bext.codingHistory.length,e=e.concat(qe(this.bext.chunkId),Ke(602+this.bext.codingHistory.length,this.uInt32),it(this.bext.description,256),it(this.bext.originator,32),it(this.bext.originatorReference,32),it(this.bext.originationDate,10),it(this.bext.originationTime,8),Ke(this.bext.timeReference[0],this.uInt32),Ke(this.bext.timeReference[1],this.uInt32),Ke(this.bext.version,this.uInt16),it(this.bext.UMID,64),Ke(this.bext.loudnessValue,this.uInt16),Ke(this.bext.loudnessRange,this.uInt16),Ke(this.bext.maxTruePeakLevel,this.uInt16),Ke(this.bext.maxMomentaryLoudness,this.uInt16),Ke(this.bext.maxShortTermLoudness,this.uInt16),it(this.bext.reserved,180),it(this.bext.codingHistory,this.bext.codingHistory.length))),this.enforceByteLen_(e),e}enforceBext_(){for(var e in this.bext)if(this.bext.hasOwnProperty(e)&&this.bext[e]&&"timeReference"!=e){this.bext.chunkId="bext";break}(this.bext.timeReference[0]||this.bext.timeReference[1])&&(this.bext.chunkId="bext")}getiXMLBytes_(){let e=[];var t;return this.iXML.chunkId&&(t=qe(this.iXML.value),this.iXML.chunkSize=t.length,e=e.concat(qe(this.iXML.chunkId),Ke(this.iXML.chunkSize,this.uInt32),t)),this.enforceByteLen_(e),e}getDs64Bytes_(){let e=[];return this.ds64.chunkId&&(e=e.concat(qe(this.ds64.chunkId),Ke(this.ds64.chunkSize,this.uInt32),Ke(this.ds64.riffSizeHigh,this.uInt32),Ke(this.ds64.riffSizeLow,this.uInt32),Ke(this.ds64.dataSizeHigh,this.uInt32),Ke(this.ds64.dataSizeLow,this.uInt32),Ke(this.ds64.originationTime,this.uInt32),Ke(this.ds64.sampleCountHigh,this.uInt32),Ke(this.ds64.sampleCountLow,this.uInt32))),this.enforceByteLen_(e),e}getCueBytes_(){let e=[];var t;return this.cue.chunkId&&(t=this.getCuePointsBytes_(),e=e.concat(qe(this.cue.chunkId),Ke(t.length+4,this.uInt32),Ke(this.cue.dwCuePoints,this.uInt32),t)),this.enforceByteLen_(e),e}getCuePointsBytes_(){let t=[];for(let e=0;e<this.cue.dwCuePoints;e++)t=t.concat(Ke(this.cue.points[e].dwName,this.uInt32),Ke(this.cue.points[e].dwPosition,this.uInt32),qe(this.cue.points[e].fccChunk),Ke(this.cue.points[e].dwChunkStart,this.uInt32),Ke(this.cue.points[e].dwBlockStart,this.uInt32),Ke(this.cue.points[e].dwSampleOffset,this.uInt32));return t}getSmplBytes_(){let e=[];var t;return this.smpl.chunkId&&(t=this.getSmplLoopsBytes_(),e=e.concat(qe(this.smpl.chunkId),Ke(t.length+36,this.uInt32),Ke(this.smpl.dwManufacturer,this.uInt32),Ke(this.smpl.dwProduct,this.uInt32),Ke(this.smpl.dwSamplePeriod,this.uInt32),Ke(this.smpl.dwMIDIUnityNote,this.uInt32),Ke(this.smpl.dwMIDIPitchFraction,this.uInt32),Ke(this.smpl.dwSMPTEFormat,this.uInt32),Ke(this.smpl.dwSMPTEOffset,this.uInt32),Ke(this.smpl.dwNumSampleLoops,this.uInt32),Ke(this.smpl.dwSamplerData,this.uInt32),t)),this.enforceByteLen_(e),e}getSmplLoopsBytes_(){let t=[];for(let e=0;e<this.smpl.dwNumSampleLoops;e++)t=t.concat(Ke(this.smpl.loops[e].dwName,this.uInt32),Ke(this.smpl.loops[e].dwType,this.uInt32),Ke(this.smpl.loops[e].dwStart,this.uInt32),Ke(this.smpl.loops[e].dwEnd,this.uInt32),Ke(this.smpl.loops[e].dwFraction,this.uInt32),Ke(this.smpl.loops[e].dwPlayCount,this.uInt32));return t}getFactBytes_(){let e=[];return this.fact.chunkId&&(e=e.concat(qe(this.fact.chunkId),Ke(this.fact.chunkSize,this.uInt32),Ke(this.fact.dwSampleLength,this.uInt32))),this.enforceByteLen_(e),e}getFmtBytes_(){if(this.fmt.chunkId){var e=[].concat(qe(this.fmt.chunkId),Ke(this.fmt.chunkSize,this.uInt32),Ke(this.fmt.audioFormat,this.uInt16),Ke(this.fmt.numChannels,this.uInt16),Ke(this.fmt.sampleRate,this.uInt32),Ke(this.fmt.byteRate,this.uInt32),Ke(this.fmt.blockAlign,this.uInt16),Ke(this.fmt.bitsPerSample,this.uInt16),this.getFmtExtensionBytes_());return this.enforceByteLen_(e),e}throw Error('Could not find the "fmt " chunk')}getFmtExtensionBytes_(){let e=[];return 16<this.fmt.chunkSize&&(e=e.concat(Ke(this.fmt.cbSize,this.uInt16))),18<this.fmt.chunkSize&&(e=e.concat(Ke(this.fmt.validBitsPerSample,this.uInt16))),20<this.fmt.chunkSize&&(e=e.concat(Ke(this.fmt.dwChannelMask,this.uInt32))),24<this.fmt.chunkSize&&(e=e.concat(Ke(this.fmt.subformat[0],this.uInt32),Ke(this.fmt.subformat[1],this.uInt32),Ke(this.fmt.subformat[2],this.uInt32),Ke(this.fmt.subformat[3],this.uInt32))),e}getLISTBytes_(){let t=[];for(let e=0;e<this.LIST.length;e++){var i=this.getLISTSubChunksBytes_(this.LIST[e].subChunks,this.LIST[e].format);t=t.concat(qe(this.LIST[e].chunkId),Ke(i.length+4,this.uInt32),qe(this.LIST[e].format),i)}return this.enforceByteLen_(t),t}getLISTSubChunksBytes_(i,s){let r=[];for(let e=0,t=i.length;e<t;e++)"INFO"==s?r=r.concat(this.getLISTINFOSubChunksBytes_(i[e])):"adtl"==s&&(r=r.concat(this.getLISTadtlSubChunksBytes_(i[e]))),this.enforceByteLen_(r);return r}getLISTINFOSubChunksBytes_(e){let t=[];var i=it(e.value,e.value.length);return t=t.concat(qe(e.chunkId),Ke(i.length+1,this.uInt32),i),t.push(0),t}getLISTadtlSubChunksBytes_(e){let t=[];var i;return-1<["labl","note"].indexOf(e.chunkId)?(i=it(e.value,e.value.length),t=t.concat(qe(e.chunkId),Ke(i.length+4+1,this.uInt32),Ke(e.dwName,this.uInt32),i),t.push(0)):"ltxt"==e.chunkId&&(t=t.concat(this.getLtxtChunkBytes_(e))),t}getLtxtChunkBytes_(e){return[].concat(qe(e.chunkId),Ke(e.value.length+20,this.uInt32),Ke(e.dwName,this.uInt32),Ke(e.dwSampleLength,this.uInt32),Ke(e.dwPurposeID,this.uInt32),Ke(e.dwCountry,this.uInt16),Ke(e.dwLanguage,this.uInt16),Ke(e.dwDialect,this.uInt16),Ke(e.dwCodePage,this.uInt16),it(e.value,e.value.length))}get_PMXBytes_(){let e=[];var t;return this._PMX.chunkId&&(t=qe(this._PMX.value),this._PMX.chunkSize=t.length,e=e.concat(qe(this._PMX.chunkId),Ke(this._PMX.chunkSize,this.uInt32),t)),this.enforceByteLen_(e),e}getJunkBytes_(){let e=[];return this.junk.chunkId?e.concat(qe(this.junk.chunkId),Ke(this.junk.chunkData.length,this.uInt32),this.junk.chunkData):(this.enforceByteLen_(e),e)}enforceByteLen_(e){e.length%2&&e.push(0)}}{constructor(){super(),this.bitDepth="0",this.dataType={bits:0,be:!1},this.WAV_AUDIO_FORMATS={4:17,8:1,"8a":6,"8m":7,16:1,24:1,32:1,"32f":3,64:3}}fromScratch(e,t,i,s,r){r=r||{},this.clearHeaders(),this.newWavFile_(e,t,i,s,r)}fromBuffer(e,t=!0){super.fromBuffer(e,t),this.bitDepthFromFmt_(),this.updateDataType_()}toBuffer(){return this.validateWavHeader_(),super.toBuffer()}getSamples(e=!1,t=Float64Array){var i=new t(this.data.samples.length/(this.dataType.bits/8));return Qe(this.data.samples,this.dataType,i,0,this.data.samples.length),!e&&1<this.fmt.numChannels?function(s,r,t=Float64Array){let a=[];for(let e=0;e<r;e++)a[e]=new t(s.length/r);for(let i=0;i<r;i++)for(let e=i,t=0;e<s.length;e+=r,t++)a[i][t]=s[e];return a}(i,this.fmt.numChannels,t):i}getSample(e){if((e*=this.dataType.bits/8)+this.dataType.bits/8>this.data.samples.length)throw new Error("Range error");return Je(this.data.samples.slice(e,e+this.dataType.bits/8),this.dataType)}setSample(e,t){if((e*=this.dataType.bits/8)+this.dataType.bits/8>this.data.samples.length)throw new Error("Range error");Ye(t,this.dataType,this.data.samples,e)}getiXML(){return this.iXML.value}setiXML(e){if("string"!=typeof e)throw new TypeError("iXML value must be a string.");this.iXML.value=e,this.iXML.chunkId="iXML"}get_PMX(){return this._PMX.value}set_PMX(e){if("string"!=typeof e)throw new TypeError("_PMX value must be a string.");this._PMX.value=e,this._PMX.chunkId="_PMX"}newWavFile_(e,t,i,s,r){r.container||(r.container="RIFF"),this.container=r.container,this.bitDepth=i,s=function(r){let a=[];if(0<r.length)if(r[0].constructor!==Number){a=new Float64Array(r[0].length*r.length);for(let i=0,e=r[0].length,s=0;i<e;i++)for(let e=0,t=r.length;e<t;e++,s++)a[s]=r[e][i]}else a=r;return a}(s),this.updateDataType_();var a=this.dataType.bits/8;this.data.samples=new Uint8Array(s.length*a),Ze(s,this.dataType,this.data.samples,0),this.makeWavHeader_(i,e,t,a,this.data.samples.length,r),this.data.chunkId="data",this.data.chunkSize=this.data.samples.length,this.validateWavHeader_()}makeWavHeader_(e,t,i,s,r,a){"4"==e?this.createADPCMHeader_(e,t,i,s,r,a):"8a"==e||"8m"==e?this.createALawMulawHeader_(e,t,i,s,r,a):-1==Object.keys(this.WAV_AUDIO_FORMATS).indexOf(e)||2<t?this.createExtensibleHeader_(e,t,i,s,r,a):this.createPCMHeader_(e,t,i,s,r,a)}createPCMHeader_(e,t,i,s,r,a){this.container=a.container,this.chunkSize=36+r,this.format="WAVE",this.bitDepth=e,this.fmt={chunkId:"fmt ",chunkSize:16,audioFormat:this.WAV_AUDIO_FORMATS[e]||65534,numChannels:t,sampleRate:i,byteRate:t*s*i,blockAlign:t*s,bitsPerSample:parseInt(e,10),cbSize:0,validBitsPerSample:0,dwChannelMask:0,subformat:[]}}createADPCMHeader_(e,t,i,s,r,a){this.createPCMHeader_(e,t,i,s,r,a),this.chunkSize=40+r,this.fmt.chunkSize=20,this.fmt.byteRate=4055,this.fmt.blockAlign=256,this.fmt.bitsPerSample=4,this.fmt.cbSize=2,this.fmt.validBitsPerSample=505,this.fact={chunkId:"fact",chunkSize:4,dwSampleLength:2*r}}createExtensibleHeader_(e,t,i,s,r,a){this.createPCMHeader_(e,t,i,s,r,a),this.chunkSize=60+r,this.fmt.chunkSize=40,this.fmt.bitsPerSample=1+(parseInt(e,10)-1|7),this.fmt.cbSize=22,this.fmt.validBitsPerSample=parseInt(e,10),this.fmt.dwChannelMask=function(e){let t=0;1===e?t=4:2===e?t=3:4===e?t=51:6===e?t=63:8===e&&(t=1599);return t}(t),this.fmt.subformat=[1,1048576,2852126848,1905997824]}createALawMulawHeader_(e,t,i,s,r,a){this.createPCMHeader_(e,t,i,s,r,a),this.chunkSize=40+r,this.fmt.chunkSize=20,this.fmt.cbSize=2,this.fmt.validBitsPerSample=8,this.fact={chunkId:"fact",chunkSize:4,dwSampleLength:r}}bitDepthFromFmt_(){3===this.fmt.audioFormat&&32===this.fmt.bitsPerSample?this.bitDepth="32f":6===this.fmt.audioFormat?this.bitDepth="8a":7===this.fmt.audioFormat?this.bitDepth="8m":this.bitDepth=this.fmt.bitsPerSample.toString()}validateBitDepth_(){if(this.WAV_AUDIO_FORMATS[this.bitDepth])return!0;if(8<parseInt(this.bitDepth,10)&&parseInt(this.bitDepth,10)<54)return!0;throw new Error("Invalid bit depth.")}updateDataType_(){this.dataType={bits:1+(parseInt(this.bitDepth,10)-1|7),fp:"32f"==this.bitDepth||"64"==this.bitDepth,signed:"8"!=this.bitDepth,be:"RIFX"==this.container},-1<["4","8a","8m"].indexOf(this.bitDepth)&&(this.dataType.bits=8,this.dataType.signed=!1)}validateWavHeader_(){if(this.validateBitDepth_(),e=this.fmt.numChannels,t=this.fmt.bitsPerSample,e<1||65535<e*t/8)throw new Error("Invalid number of channels.");var e,t;if(!st(this.fmt.numChannels,this.fmt.bitsPerSample,this.fmt.sampleRate))throw new Error("Invalid sample rate.")}}class at extends rt{getTag(e){e=this.getTagIndex_(e);return null!==e.TAG?this.LIST[e.LIST].subChunks[e.TAG].value:null}setTag(e,t){e=function(i){{if(i.constructor!==String)throw new Error("Invalid tag name.");if(i.length<4)for(let e=0,t=4-i.length;e<t;e++)i+=" "}return i}(e);var i=this.getTagIndex_(e);null!==i.TAG?(this.LIST[i.LIST].subChunks[i.TAG].chunkSize=t.length+1,this.LIST[i.LIST].subChunks[i.TAG].value=t):null!==i.LIST?this.LIST[i.LIST].subChunks.push({chunkId:e,chunkSize:t.length+1,value:t}):(this.LIST.push({chunkId:"LIST",chunkSize:8+t.length+1,format:"INFO",subChunks:[]}),this.LIST[this.LIST.length-1].subChunks.push({chunkId:e,chunkSize:t.length+1,value:t}))}deleteTag(e){e=this.getTagIndex_(e);return null!==e.TAG&&(this.LIST[e.LIST].subChunks.splice(e.TAG,1),!0)}listTags(){var i=this.getLISTIndex("INFO");let s={};if(null!==i)for(let e=0,t=this.LIST[i].subChunks.length;e<t;e++)s[this.LIST[i].subChunks[e].chunkId]=this.LIST[i].subChunks[e].value;return s}getLISTIndex(i){for(let e=0,t=this.LIST.length;e<t;e++)if(this.LIST[e].format==i)return e;return null}getTagIndex_(s){let r={LIST:null,TAG:null};for(let i=0,e=this.LIST.length;i<e;i++)if("INFO"==this.LIST[i].format){r.LIST=i;for(let e=0,t=this.LIST[i].subChunks.length;e<t;e++)if(this.LIST[i].subChunks[e].chunkId==s){r.TAG=e;break}break}return r}}class nt extends at{listCuePoints(){let i=this.getCuePoints_();for(let e=0,t=i.length;e<t;e++)i[e].position=i[e].dwSampleOffset/this.fmt.sampleRate*1e3,i[e].dwSampleLength?(i[e].end=i[e].dwSampleLength/this.fmt.sampleRate*1e3,i[e].end+=i[e].position):i[e].end=null,delete i[e].value;return i}setCuePoint(e){this.cue.chunkId="cue ",e.label||(e.label="");var t=this.getCuePoints_();this.clearLISTadtl_(),this.cue.points=[],e.dwSampleOffset=e.position*this.fmt.sampleRate/1e3,e.dwSampleLength=0,e.end&&(e.dwSampleLength=e.end*this.fmt.sampleRate/1e3-e.dwSampleOffset),0===t.length?this.setCuePoint_(e,1):this.setCuePointInOrder_(t,e),this.cue.dwCuePoints=this.cue.points.length}deleteCuePoint(t){this.cue.chunkId="cue ";var i=this.getCuePoints_();this.clearLISTadtl_();var s=this.cue.points.length;this.cue.points=[];for(let e=0;e<s;e++)e+1!==t&&this.setCuePoint_(i[e],e+1);this.cue.dwCuePoints=this.cue.points.length,this.cue.dwCuePoints?this.cue.chunkId="cue ":(this.cue.chunkId="",this.clearLISTadtl_())}updateLabel(i,s){var r=this.getLISTIndex("adtl");if(null!==r)for(let e=0,t=this.LIST[r].subChunks.length;e<t;e++)this.LIST[r].subChunks[e].dwName==i&&(this.LIST[r].subChunks[e].value=s)}getCuePoints_(){let i=[];for(let t=0;t<this.cue.points.length;t++){var s=this.cue.points[t];let e=this.getDataForCuePoint_(s.dwName);e.label=e.value||"",e.dwPosition=s.dwPosition,e.fccChunk=s.fccChunk,e.dwChunkStart=s.dwChunkStart,e.dwBlockStart=s.dwBlockStart,e.dwSampleOffset=s.dwSampleOffset,i.push(e)}return i}getDataForCuePoint_(e){var t=this.getLISTIndex("adtl"),i={};return null!==t&&this.getCueDataFromLIST_(i,t,e),i}getCueDataFromLIST_(i,s,r){for(let e=0,t=this.LIST[s].subChunks.length;e<t;e++){var a;this.LIST[s].subChunks[e].dwName==r&&(a=this.LIST[s].subChunks[e],i.value=a.value||i.value,i.dwName=a.dwName||0,i.dwSampleLength=a.dwSampleLength||0,i.dwPurposeID=a.dwPurposeID||0,i.dwCountry=a.dwCountry||0,i.dwLanguage=a.dwLanguage||0,i.dwDialect=a.dwDialect||0,i.dwCodePage=a.dwCodePage||0)}}setCuePoint_(e,t){this.cue.points.push({dwName:t,dwPosition:e.dwPosition||0,fccChunk:e.fccChunk||"data",dwChunkStart:e.dwChunkStart||0,dwBlockStart:e.dwBlockStart||0,dwSampleOffset:e.dwSampleOffset}),this.setLabl_(e,t)}setCuePointInOrder_(t,i){let s=!1;for(let e=0;e<t.length;e++)t[e].dwSampleOffset>i.dwSampleOffset&&!s?(this.setCuePoint_(i,e+1),this.setCuePoint_(t[e],e+2),s=!0):this.setCuePoint_(t[e],s?e+2:e+1);s||this.setCuePoint_(i,this.cue.points.length+1)}clearLISTadtl_(){for(let e=0,t=this.LIST.length;e<t;e++)"adtl"==this.LIST[e].format&&this.LIST.splice(e)}setLabl_(e,t){let i=this.getLISTIndex("adtl");null===i&&(this.LIST.push({chunkId:"LIST",chunkSize:4,format:"adtl",subChunks:[]}),i=this.LIST.length-1),this.setLabelText_(i,e,t),e.dwSampleLength&&this.setLtxtChunk_(i,e,t)}setLabelText_(e,t,i){this.LIST[e].subChunks.push({chunkId:"labl",chunkSize:4,dwName:i,value:t.label}),this.LIST[e].chunkSize+=12}setLtxtChunk_(e,t,i){this.LIST[e].subChunks.push({chunkId:"ltxt",chunkSize:20,dwName:i,dwSampleLength:t.dwSampleLength,dwPurposeID:t.dwPurposeID||0,dwCountry:t.dwCountry||0,dwLanguage:t.dwLanguage||0,dwDialect:t.dwDialect||0,dwCodePage:t.dwCodePage||0,value:t.label}),this.LIST[e].chunkSize+=28}}class ot{constructor(e,t,i){var s;this.length_=e,this.scaleFactor_=(e-1)/t,this.interpolate=this.sinc,"point"===i.method?this.interpolate=this.point:"linear"===i.method?this.interpolate=this.linear:"cubic"===i.method&&(this.interpolate=this.cubic),this.tangentFactor_=1-Math.max(0,Math.min(1,i.tension||0)),this.sincFilterSize_=i.sincFilterSize||1,this.kernel_=(s=i.sincWindow||ht,function(e){return(0!==(t=e)?Math.sin(Math.PI*t)/(Math.PI*t):1)*s(e);var t})}point(e,t){return this.getClippedInput_(Math.round(this.scaleFactor_*e),t)}linear(e,t){e=this.scaleFactor_*e;var i=Math.floor(e);return(1-(e-=i))*this.getClippedInput_(i,t)+e*this.getClippedInput_(i+1,t)}cubic(e,t){e=this.scaleFactor_*e;var i=Math.floor(e),s=[this.getTangent_(i,t),this.getTangent_(i+1,t)],r=[this.getClippedInput_(i,t),this.getClippedInput_(i+1,t)],t=(e-=i)*e,i=e*t;return(2*i-3*t+1)*r[0]+(i-2*t+e)*s[0]+(-2*i+3*t)*r[1]+(i-t)*s[1]}sinc(t,i){t=this.scaleFactor_*t;var e=Math.floor(t),s=e-this.sincFilterSize_+1,r=e+this.sincFilterSize_;let a=0;for(let e=s;e<=r;e++)a+=this.kernel_(t-e)*this.getClippedInput_(e,i);return a}getTangent_(e,t){return this.tangentFactor_*(this.getClippedInput_(e+1,t)-this.getClippedInput_(e-1,t))/2}getClippedInput_(e,t){return 0<=e&&e<this.length_?t[e]:0}}function ht(e){return Math.exp(-e/2*e/2)}const lt={point:!1,linear:!1,cubic:!0,sinc:!0},ct={IIR:16,FIR:71},ut={IIR:class{constructor(t,i,s){let r=[];for(let e=0;e<t;e++)r.push(this.getCoeffs_({Fs:i,Fc:s,Q:.5/Math.sin(Math.PI/(2*t)*(e+.5))}));this.stages=[];for(let e=0;e<r.length;e++)this.stages[e]={b0:r[e].b[0],b1:r[e].b[1],b2:r[e].b[2],a1:r[e].a[0],a2:r[e].a[1],k:r[e].k,z:[0,0]}}filter(e){let i=e;for(let e=0,t=this.stages.length;e<t;e++)i=this.runStage_(e,i);return i}getCoeffs_(e){let t={a:[],b:[]};e=this.preCalc_(e,t);return t.k=1,t.b.push((1-e.cw)/(2*e.a0)),t.b.push(2*t.b[0]),t.b.push(t.b[0]),t}preCalc_(e,t){let i={};var s=2*Math.PI*e.Fc/e.Fs;return i.alpha=Math.sin(s)/(2*e.Q),i.cw=Math.cos(s),i.a0=1+i.alpha,t.a0=i.a0,t.a.push(-2*i.cw/i.a0),t.k=1,t.a.push((1-i.alpha)/i.a0),i}runStage_(e,t){var i=t*this.stages[e].k-this.stages[e].a1*this.stages[e].z[0]-this.stages[e].a2*this.stages[e].z[1],t=this.stages[e].b0*i+this.stages[e].b1*this.stages[e].z[0]+this.stages[e].b2*this.stages[e].z[1];return this.stages[e].z[1]=this.stages[e].z[0],this.stages[e].z[0]=i,t}reset(){for(let e=0;e<this.stages.length;e++)this.stages[e].z=[0,0]}},FIR:class{constructor(t,e,i){var s=2*Math.PI*i/e;let r=0;this.filters=[];for(let e=0;e<=t;e++)e-t/2==0?this.filters[e]=s:(this.filters[e]=Math.sin(s*(e-t/2))/(e-t/2),this.filters[e]*=.54-.46*Math.cos(2*Math.PI*e/t)),r+=this.filters[e];for(let e=0;e<=t;e++)this.filters[e]/=r;this.z=this.initZ_()}filter(e){this.z.buf[this.z.pointer]=e;let i=0;for(let e=0,t=this.z.buf.length;e<t;e++)i+=this.filters[e]*this.z.buf[(this.z.pointer+e)%this.z.buf.length];return this.z.pointer=(this.z.pointer+1)%this.z.buf.length,i}reset(){this.z=this.initZ_()}initZ_(){let t=[];for(let e=0;e<this.filters.length-1;e++)t.push(0);return{buf:t,pointer:0}}}};function dt(e,t,i,s=null){s=s||{};var r=new Float64Array(e.length*((i-t)/t+1));s.method=s.method||"cubic";var a=new ot(e.length,r.length,{method:s.method,tension:s.tension||0,sincFilterSize:s.sincFilterSize||6,sincWindow:s.sincWindow||void 0,clip:s.clip||"mirror"});if(void 0===s.LPF&&(s.LPF=lt[s.method]),s.LPF){s.LPFType=s.LPFType||"IIR";const n=ut[s.LPFType];t<i?function(i,s,r,a){for(let e=0,t=s.length;e<t;e++)s[e]=a.filter(r.interpolate(e,i));a.reset();for(let e=s.length-1;0<=e;e--)s[e]=a.filter(s[e])}(e,r,a,new n(s.LPForder||ct[s.LPFType],i,t/2)):function(i,e,t,s){for(let e=0,t=i.length;e<t;e++)i[e]=s.filter(i[e]);s.reset();for(let e=i.length-1;0<=e;e--)i[e]=s.filter(i[e]);gt(i,e,t)}(e,r,a,new n(s.LPForder||ct[s.LPFType],t,i/2))}else gt(e,r,a);return r}function gt(i,s,r){for(let e=0,t=s.length;e<t;e++)s[e]=r.interpolate(e,i)}class pt extends nt{toRIFF(){var e=new Float64Array(mt(this.data.samples.length,this.dataType.bits/8));Qe(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,this.bitDepth,e,{container:"RIFF"})}toRIFX(){var e=new Float64Array(mt(this.data.samples.length,this.dataType.bits/8));Qe(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,this.bitDepth,e,{container:"RIFX"})}toIMAADPCM(){if(8e3!==this.fmt.sampleRate)throw new Error("Only 8000 Hz files can be compressed as IMA-ADPCM.");if(1!==this.fmt.numChannels)throw new Error("Only mono files can be compressed as IMA-ADPCM.");this.assure16Bit_();var e=new Int16Array(mt(this.data.samples.length,2));Qe(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"4",Ce(e),{container:this.correctContainer_()})}fromIMAADPCM(e="16"){let r;if(1<this.fmt.numChannels){if(2<this.fmt.numChannels)throw new Error("Only 1 or 2 channels are supported");var a=this.data.samples.length/2;let t=new Uint8Array(a),i=new Uint8Array(a),s=0;for(let e=0;e<a;e++)e&&e%4==0&&(s+=4),t[e]=this.data.samples[s+e],i[e]=this.data.samples[s+e+4];r=[Ae(t,this.fmt.blockAlign/2),Ae(i,this.fmt.blockAlign/2)]}else r=Ae(this.data.samples,this.fmt.blockAlign);this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",r,{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toALaw(){this.assure16Bit_();var e=new Int16Array(mt(this.data.samples.length,2));Qe(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"8a",Pe(e),{container:this.correctContainer_()})}fromALaw(e="16"){this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",Ne(this.data.samples),{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toMuLaw(){this.assure16Bit_();var e=new Int16Array(mt(this.data.samples.length,2));Qe(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"8m",Fe(e),{container:this.correctContainer_()})}fromMuLaw(e="16"){this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",je(this.data.samples),{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toBitDepth(e,t=!0){let i=e,s=this.bitDepth;t||("32f"!=e&&(i=this.dataType.bits.toString()),s=""+this.dataType.bits),this.assureUncompressed_();var r=this.getSamples(!0),t=new Float64Array(r.length);Te(r,s,t,i),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,e,t,{container:this.correctContainer_()})}toSampleRate(t,i){this.validateResample_(t);var s=this.getSamples();let r=[];if(s.constructor===Float64Array)r=dt(s,this.fmt.sampleRate,t,i);else for(let e=0;e<s.length;e++)r.push(dt(s[e],this.fmt.sampleRate,t,i));this.fromExisting_(this.fmt.numChannels,t,this.bitDepth,r,{container:this.correctContainer_()})}validateResample_(e){if(!st(this.fmt.numChannels,this.fmt.bitsPerSample,e))throw new Error("Invalid sample rate.");if(-1<["4","8a","8m"].indexOf(this.bitDepth))throw new Error("wavefile can't change the sample rate of compressed files.")}assure16Bit_(){this.assureUncompressed_(),"16"!=this.bitDepth&&this.toBitDepth("16")}assureUncompressed_(){"8a"==this.bitDepth?this.fromALaw():"8m"==this.bitDepth?this.fromMuLaw():"4"==this.bitDepth&&this.fromIMAADPCM()}correctContainer_(){return"RF64"==this.container?"RIFF":this.container}fromExisting_(e,t,i,s,r){var a=new nt;Object.assign(this.fmt,a.fmt),Object.assign(this.fact,a.fact),Object.assign(this.ds64,a.ds64),Object.assign(this.data,a.data),this.newWavFile_(e,t,i,s,r)}}function mt(e,t){let i=e/t;return i%2&&i++,i}class ft extends pt{constructor(e){super(),e&&this.fromBuffer(e)}fromBase64(e){this.fromBuffer(function(i){let s=new Uint8Array(256);for(let e=0;e<we.length;e++)s[we.charCodeAt(e)]=e;let e=.75*i.length;"="===i[i.length-1]&&(e--,"="===i[i.length-2]&&e--);let r=new Uint8Array(e);for(let e=0,t=0;e<i.length;e+=4){var a=s[i.charCodeAt(e)],n=s[i.charCodeAt(e+1)],o=s[i.charCodeAt(e+2)],h=s[i.charCodeAt(e+3)];r[t++]=a<<2|n>>4,r[t++]=(15&n)<<4|o>>2,r[t++]=(3&o)<<6|63&h}return r}(e))}toBase64(){return function(t){let i="";for(let e=0;e<t.length;e+=3)i+=we[t[e]>>2],i+=we[(3&t[e])<<4|t[e+1]>>4],i+=we[(15&t[e+1])<<2|t[e+2]>>6],i+=we[63&t[e+2]];return t.length%3==2?i=i.substring(0,i.length-1)+"=":t.length%3==1&&(i=i.substring(0,i.length-2)+"=="),i}(this.toBuffer())}toDataURI(){return"data:audio/wav;base64,"+this.toBase64()}fromDataURI(e){this.fromBase64(e.replace("data:audio/wav;base64,",""))}}class yt{constructor(e){e instanceof Uint8Array?this.fromRawData(e):e instanceof i&&this.fromVirtualFile(e)}fromRawData(e){return this.rawData=e,this}fromVirtualFile(e){e=e.stream;return this.rawData=new Uint8Array(e.buffer,e.byteOffset,e.byteLength),this}getRawData(){return this.rawData}getData(){if(!this.decodedData){if(!this.rawData)throw new Error("No data loaded");this.decodedData=this.decodeData(this.rawData),this.rawData=void 0}return this.decodedData}setData(e){this.rawData=void 0,this.decodedData=e}decodeData(e){let t=new ft(e);return"4"===t.bitDepth&&t.fromIMAADPCM(),t.toBuffer()}isRawImaAdpcm(){return this.rawData&&"4"===new ft(this.rawData).bitDepth}}class wt{constructor(e,t=!0){this.resourceFactory=e,this.cache=t,this.resources=new Map}setDir(e){this.rfsDir=e}set(e,t){this.resources.set(e,t)}async has(e){return!!this.resources.has(e)||(await this.rfsDir?.containsEntry(e)??!1)}async get(e){let t;return t=this.resources.get(e),!t&&await this.rfsDir?.containsEntry(e)&&(t=await this.resourceFactory(await this.rfsDir.getRawFile(e)),this.cache&&this.resources.set(e,t)),t}clear(){this.resources.clear()}}class Tt{constructor(e){this.file=e}asFile(){return new File([this.file],this.file.name,{type:"audio/mp3"})}}const bt=(new Map).set("cameo.mix",["adogicon.shp","adoguico.shp","aengicon.shp","aenguico.shp","agapgen.shp","agisicon.shp","ahrvicon.shp","ahrvuico.shp","aparicon.shp","apchicon.shp","apcicon.shp","artyicon.shp","asaticon.shp","ayaricon.shp","batricon.shp","beagicon.shp","bggyicon.shp","bolticon.shp","brrkicon.shp","carricon.shp","ccomicon.shp","ccomuico.shp","chemicon.shp","chroicon.shp","clckicon.shp","clegicon.shp","cleguico.shp","clonicon.shp","cnsticon.shp","crryicon.shp","csphicon.shp","darken.shp","desoicon.shp","desouico.shp","desticon.shp","detnicon.shp","dlphicon.shp","dlphuico.shp","dogicon.shp","doguico.shp","dredicon.shp","dronicon.shp","e1icon.shp","e1uico.shp","e2icon.shp","e2uico.shp","e4icon.shp","empicon.shp","engnicon.shp","facticon.shp","falcicon.shp","fixicon.shp","flakicon.shp","flkticon.shp","flktuico.shp","forticon.shp","fsdicon.shp","fspicon.shp","fstdicon.shp","fvicon.shp","fvuico.shp","gapicon.shp","gat2icon.shp","gateicon.shp","gbayicon.shp","gcanicon.shp","giicon.shp","giuico.shp","gorep.shp","gtnkicon.shp","gtnkuico.shp","gwepicon.shp","handicon.shp","harvicon.shp","harvuico.shp","heliicon.shp","hindicon.shp","hmecicon.shp","hovricon.shp","htkicon.shp","htkuico.shp","htnkicon.shp","htnkuico.shp","ioncicon.shp","ircricon.shp","ironicon.shp","ivanicon.shp","ivanuico.shp","ivncicon.shp","ivncuico.shp","jjeticon.shp","jjetuico.shp","landicon.shp","lasricon.shp","liteicon.shp","lpsticon.shp","mcvicon.shp","mcvuico.shp","metricon.shp","mltiicon.shp","mmchicon.shp","msslicon.shp","mtnkicon.shp","mtnkuico.shp","mutcicon.shp","nga2icon.shp","ngaticon.shp","nhpdicon.shp","npsiicon.shp","npwricon.shp","nradicon.shp","nrcticon.shp","nreficon.shp","ntchicon.shp","nukeicon.shp","nwalicon.shp","nwepicon.shp","obliicon.shp","obmbicon.shp","orcaicon.shp","otrnicon.shp","paraicon.shp","pillicon.shp","plticon.shp","plugicon.shp","podsicon.shp","powricon.shp","prisicon.shp","proicon.shp","psicicon.shp","psicuico.shp","psisicon.shp","psiticon.shp","psituico.shp","rad1icon.shp","rad2icon.shp","rad3icon.shp","radricon.shp","rboticon.shp","reficon.shp","rfixicon.shp","rtnkicon.shp","rtnkuico.shp","samicon.shp","sapcicon.shp","sapicon.shp","sbagicon.shp","sealicon.shp","sealuico.shp","seekicon.shp","shadicon.shp","shaduico.shp","shkicon.shp","shkuico.shp","smchicon.shp","smcvicon.shp","smcvuico.shp","snipicon.shp","snipuico.shp","soniicon.shp","spoticon.shp","spyicon.shp","spyuico.shp","sqdicon.shp","sreficon.shp","srefuico.shp","stnkicon.shp","subicon.shp","subticon.shp","tanyicon.shp","tanyuico.shp","techicon.shp","tempicon.shp","teslaicon.shp","tickicon.shp","tnkdicon.shp","tnkduico.shp","towricon.shp","trkaicon.shp","trsticon.shp","trstuico.shp","tslaicon.shp","ttnkicon.shp","ttnkuico.shp","turbicon.shp","twr1icon.shp","twr2icon.shp","twr3icon.shp","v3icon.shp","v3uico.shp","wallicon.shp","weapicon.shp","weaticon.shp","weedicon.shp","wethicon.shp","xxicon.shp","yardicon.shp","yuriicon.shp","yuriuico.shp","yurpicon.shp","yurpuico.shp","zepicon.shp","zepuico.shp"]).set("theme.mix",["200meter.wav","blowitup.wav","burn.wav","destroy.wav","eaglehun.wav","fortific.wav","grinder.wav","hm2.wav","indeep.wav","industro.wav","jank.wav","motorize.wav","power.wav","ra2-opt.wav","ra2-sco.wav","tension.wav"]);r=["addon.shp","bkgdlg.shp","bkgdmd.shp","bkgdsm.shp","bttnbkgd.shp","button00.shp","button01.shp","button02.shp","button03.shp","button04.shp","button05.shp","button06.shp","button07.shp","button08.shp","button09.shp","button10.shp","button11.shp","credits.shp","diplobtn.shp","gclock2.shp","key.ini","lendcap.shp","lspacer.shp","optbtn.shp","pbeacon.shp","power.shp","powerp.shp","pwrlvl.shp","radar.shp","radar01.shp","radar02.shp","r-dn.shp","rdrbeacn.shp","rendcap.shp","repair.shp","r-up.shp","sell.shp","side1.shp","side2.shp","side2b.shp","side3.shp","sidebar.pal","sidebttn.shp","tab00.shp","tab01.shp","tab02.shp","tab03.shp","tabs.shp","top.shp","uibkgd.pal","wayp.shp"];bt.set("sidec01.mix",r).set("sidec02.mix",r);var vt,St,r=["reportbug.shp"];bt.set("sidec01cd.mix",r).set("sidec02cd.mix",r),(r=vt=vt||{})[r.Archive=0]="Archive",r[r.Cdn=1]="Cdn",r[r.Local=2]="Local";class kt{readIni(e){return this.minMoney=e.getNumber("MinMoney"),this.money=e.getNumber("Money"),this.maxMoney=e.getNumber("MaxMoney"),this.moneyIncrement=e.getNumber("MoneyIncrement"),this.minUnitCount=e.getNumber("MinUnitCount"),this.unitCount=e.getNumber("UnitCount"),this.maxUnitCount=e.getNumber("MaxUnitCount"),this.crates=e.getBool("Crates"),this.gameSpeed=e.getNumber("GameSpeed"),this.mcvRedeploys=e.getBool("MCVRedeploys"),this.shortGame=e.getBool("ShortGame"),this.superWeapons=e.getBool("SuperWeapons"),this.techLevel=e.getNumber("TechLevel"),this.alliesAllowed=e.getBool("AlliesAllowed",!0),this.allyChangeAllowed=e.getBool("AllyChangeAllowed",!0),this.mustAlly=e.getBool("MustAlly"),this.bridgeDestruction=e.getBool("BridgeDestruction",!0),this.multiEngineer=e.getBool("MultiEngineer"),this}}(r=St=St||{})[r.Battle=0]="Battle",r[r.ManBattle=1]="ManBattle",r[r.FreeForAll=2]="FreeForAll",r[r.Unholy=3]="Unholy",r[r.Cooperative=4]="Cooperative";class Ot{constructor(e,t){this.modeIniLoader=t,this.entries=new Map,this.loadIni(e)}loadIni(e){e.getOrderedSections().forEach(s=>{let r=St[s.name]??St.Battle;[...s.entries.keys()].forEach(e=>{let t=s.getArray(e);if(t.length<5)throw new Error(`Invalid format for mp mode entry "${e}".`);var i=Number(e),e=t[2].toLowerCase(),e={id:i,type:r,label:t[0],description:t[1],rulesOverride:e,mapFilter:t[3],randomMapsAllowed:t[4],aiAllowed:i<3,mpDialogSettings:(new kt).readIni(this.modeIniLoader(e).getOrCreateSection("MultiplayerDialogSettings"))};this.entries.set(i,e)})})}getById(e){if(!this.entries.has(e))throw new Error(`No game mode found with id ${e}`);return this.entries.get(e)}hasId(e){return this.entries.has(e)}getAll(){return[...this.entries.values()]}}class _t{fromIni(t,e){return this.fileName=t.getString("File")||t.name.toLowerCase()+".map",this.uiName=t.getString("Description"),this.maxSlots=t.getNumber("MaxPlayers"),this.official=!0,this.gameModes=e.filter(e=>t.getArray("GameMode").includes(e.mapFilter)),this}getFullMapTitle(e){return this.addTitleSlotsSuffix(e.get(this.uiName),this.maxSlots)}addTitleSlotsSuffix(e,t){return e.match(/(\(|()\s*\d(-\d)?\s*(\)|))\s*$/)||(e+=` (2${2<t?"-"+t:""})`),e}fromMapFile(e,t){var i=e.readAsString();let s=e.filename;const r=new D(this.extractIniSection("Basic",i)).getSection("Basic");if(!r)throw new Error(`Map "${s}" is missing the [Basic] section`);this.fileName=s,this.uiName="NOSTR:"+(r.getString("Name")||s.replace(/\.[^.]+$/,""));i=this.extractIniSection("Waypoints",i);let a=i?new D(i).getSection("Waypoints"):void 0;this.maxSlots=[...a?.entries.keys()??[]].filter(e=>Number(e)<8).length,this.official=r.getBool("Official");let n=r.getArray("GameMode",void 0,["standard"]);return this.gameModes=t.filter(e=>n.includes(e.mapFilter)),this}extractIniSection(t,i){t=i.indexOf(`[${t}]`);if(-1!==t){let e=t+1;for(;e<i.length&&("["!==i[e]||"\n"!==i[e-1]);e++);return i.slice(t,e)}}}class It{constructor(e){this.gameModes=e,this.manifests=[]}addFromIni(i){let e=i.getSection("MultiMaps");if(!e)throw new Error("Invalid map list. Missing [MultiMaps] section.");return this.manifests=this.manifests.concat([...e.entries.values()].map(e=>{var t=i.getSection(e);if(!t)throw new Error(`Invalid map list. Missing [${e}] section.`);return(new _t).fromIni(t,this.gameModes.getAll())})),this.dedupeEntries(),this}add(e){this.manifests.push(e)}addFromMapFile(e){this.add((new _t).fromMapFile(e,this.gameModes.getAll()))}getAll(){return this.manifests}getByName(t){return this.manifests.find(e=>e.fileName.toLowerCase()===t.toLowerCase())}sortByName(){this.manifests.sort((e,t)=>e.fileName.localeCompare(t.fileName))}clone(){let e=new It(this.gameModes);return e.manifests=[...this.manifests],e}mergeWith(e){return this.manifests.push(...e.manifests),this.dedupeEntries(),this}dedupeEntries(){this.manifests=[...new Map(this.manifests.map(e=>[e.fileName.toLowerCase(),e])).values()]}}class Ct{getMatrix(e){return this.matrices[e]}}var At,Bt,xt,Et,Pt=__webpack_require__(949);class Nt{constructor(e){e instanceof i&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let i=e.stream;this.sections=[],i.readCString(16);var s=i.readInt32(),r=i.readInt32();for(let e=0;e<r;++e){let e=new Ct;e.name=i.readCString(16),e.matrices=new Array(s),this.sections.push(e)}for(let t=0;t<s;++t)for(let e=0;e<r;++e)this.sections[e].matrices[t]=this.readMatrix(i)}readMatrix(t){let i=[];for(let e=0;e<3;++e)i.push(t.readFloat32(),t.readFloat32(),t.readFloat32(),t.readFloat32());return i.push(0,0,0,1),(new Pt.Matrix4).fromArray(i).transpose()}}At=At||{},At[At.NoDogEngiKills=0]="NoDogEngiKills",(r=xt=xt||{})[r.AutoDetect=0]="AutoDetect",r[r.TiberianSun=1]="TiberianSun",r[r.Firestorm=2]="Firestorm",r[r.RedAlert2=3]="RedAlert2",r[r.YurisRevenge=4]="YurisRevenge";class Dt{static getVersion(){return"0.78.0".split(".").slice(0,2).join(".")}static getModHash(){if(!this.modHash)throw new Error("Rules must be loaded first");return this.modHash}static getActiveMod(){return this.activeMod}static setActiveMod(e){this.activeMod=e}static initGameResSource(e){this.gameResSource=e}static async initRfs(e){let t=this.rfs=new fe;return t.addRootDirectoryHandle(e),t}static async initVfs(e,t){return this.vfs=new de(e,t),Bt.iniFiles.setVfs(this.vfs),Bt.palettes.setVfs(this.vfs),Bt.images.setVfs(this.vfs),Bt.voxels.setVfs(this.vfs),Bt.voxelAnims.setVfs(this.vfs),Bt.tileData.setVfs(this.vfs),Bt.sounds.setVfs(this.vfs),Bt.themes.setDir(await this.rfs?.findDirectory(Bt.rfsSettings.musicDir)),Bt.taunts.setDir(await this.rfs?.findDirectory(Bt.rfsSettings.tauntsDir)),this.vfs}static supportsTheater(t){var e=this.getActiveEngine();return this.theaterSettings.get(e)?.some(e=>e.type===t)||!1}static getTheaterSettings(e,t){if(!this.theaterSettings.has(e))throw new Error(`Unknown engineType "${e}`);e=this.theaterSettings.get(e).find(e=>e.type===t);if(!e)throw new Error(`Unsupported theater "${I[t]}"`);return e}static async loadTheater(e){if(!Bt.rules||!Bt.art)throw new Error("Rules and art should be loaded first");if(void 0===Bt.gameResSource)throw new Error("No gameResSource is set");var t=Bt.getActiveEngine();let i;var s,r=Bt.getTheaterSettings(t,e);if(Bt.gameResSource!==vt.Cdn)for(var a of r.mixes)await Bt.vfs.addMixFile(a);return Bt.theaters.has(e)?i=Bt.theaters.get(e):(s=Bt.getTheaterIni(t,e),t=Bt.getTileData(),i=class{static factory(e,t,i,s,r){var a=r.get(i.isoPaletteName);if(!a)throw new Error(`Missing palette "${i.isoPaletteName}"`);var n=r.get(i.overlayPaletteName);if(!n)throw new Error(`Missing palette "${i.overlayPaletteName}"`);var o=r.get(i.unitPaletteName);if(!o)throw new Error(`Missing palette "${i.unitPaletteName}"`);var h=r.get("anim.pal");if(!h)throw new Error("Missing anim palette");var l=r.get(i.libPaletteName);if(!l)throw new Error(`Missing lib palette ${i.libPaletteName}`);let c=new Y(t);return c.loadTileData(s,i.extension),new this(e,i,r,a,n,o,h,l,c)}constructor(e,t,i,s,r,a,n,o,h){this.type=e,this.settings=t,this.palettes=i,this.isoPalette=s,this.ovlPalette=r,this.unitPalette=a,this.animPalette=n,this.libPalette=o,this.tileSets=h}getPalette(e,t){switch(e){case _.Anim:return this.animPalette;case _.Overlay:return this.ovlPalette;case _.Unit:return this.unitPalette;case _.Custom:if("lib"===t)return this.libPalette;var i=this.palettes.get(t+".pal");if(!i)throw new Error(`Custom palette "${t}" not found`);return i;default:_.Iso;return this.isoPalette}}}.factory(e,s,r,t,Bt.palettes),Bt.theaters.set(e,i)),Bt.activeTheater=i,i}static unloadTheater(e){if(Bt.vfs){var t,i=Bt.getActiveEngine();for(t of Bt.getTheaterSettings(i,e).mixes)Bt.vfs.removeArchive(t)}}static unloadSideMixData(){for(var e of["sidec01.mix","sidec01cd.mix"]){var t,i=bt.get(e);if(!i)return void console.warn(`Mix "${e}" not found in mix database`);for(t of i)("pal"===t.split(".").pop()?Bt.palettes:Bt.images).clear(t)}}static getTheaterIni(e,t){t=Bt.getTheaterSettings(e,t).theaterIni;return Bt.getIni(t)}static loadRules(){var e=this.getFileNameVariant("rules.ini"),t=this.getFileNameVariant("art.ini"),i=this.getFileNameVariant("ai.ini");let s=this.iniFiles.get(e),r=this.iniFiles.get(t);var a=this.iniFiles.get(i);if(!s)throw new Error(`Rules "${e}" not found`);if(!r)throw new Error(`Art "${t}" not found`);if(!a)throw new Error(`AI "${i}" not found`);t=this.iniFiles.get(Bt.customRulesFileName),i=this.iniFiles.get(Bt.customArtFileName);if(!t)throw new Error(`Rules "${Bt.customRulesFileName}" not found`);if(!i)throw new Error(`Art "${Bt.customArtFileName}" not found`);Bt.art=r.clone().mergeWith(i),Bt.rules=s.clone().mergeWith(t),Bt.ai=a,Bt.modHash=Bt.computeModHash()}static computeModHash(){if(!this.vfs)throw new Error("VFS not initialized");let e=[this.customRulesFileName,this.customArtFileName,this.customMpModesFileName,this.shroudFileName,this.getFileNameVariant("rules.ini"),this.getFileNameVariant("art.ini"),this.getFileNameVariant("ai.ini"),...Bt.mixinRulesFileNames.values()];var t,i,s,r=this.theaterSettings.get(this.getActiveEngine());if(!r)throw new Error(`Unsupported engineType "${this.getActiveEngine()}`);for(t of r)e.push(this.getFileNameVariant(t.theaterIni));let a=this.getMpModes();for(i of a.getAll())e.push(i.rulesOverride);let n=new oe;for(s of e){if(!this.vfs.fileExists(s))throw new Error(`File ${s} not found`);var o=this.vfs.openFile(s).stream;n.append(new Uint8Array(o.buffer,o.byteOffset,o.byteLength))}return n.append(R(this.getVersion())),n.get()}static getRules(){if(!Bt.rules)throw new Error("Rules must be loaded first");return Bt.rules}static getArt(){if(!Bt.art)throw new Error("Art must be loaded first");return Bt.art}static getAi(){if(!Bt.ai)throw new Error("AI must be loaded first");return Bt.ai}static getFileNameVariant(e){var t=this.getActiveEngine();let i;if(t===xt.YurisRevenge)i="md";else{if(t!==xt.RedAlert2)throw new Error(`Unsupported engine type ${xt[t]}`);i=""}return i?e.replace(/\.([^.]+)$/,i+".$1"):e}static getMpModes(){return new Ot(this.getIni(this.customMpModesFileName),e=>this.getIni(e))}static getUiIni(){var e=this.getFileNameVariant("ui.ini");return this.getIni(e)}static getIni(e){if(!this.iniFiles.has(e))throw new Error(`INI file ${e} not found.`);return this.iniFiles.get(e)}static async loadMapList(){if(!this.vfs)throw new Error("File system not initialized");var e,i,s,t=this.getMpModes();let r=new It(t);r.addFromIni(this.getIni(this.getFileNameVariant("missions.pkt")));for(e of this.vfs.listArchives()){var a=e.toLowerCase().replace(/\.[^.]+$/,"")+".pkt";this.vfs.fileExists(a)&&r.addFromIni(new D(this.vfs.openFile(a)))}let n=new It(t);if(this.rfs)for await(var o of this.rfs.getEntries()){let t=o.toLowerCase();try{t.endsWith(".pkt")?(i=new D(await this.rfs.openFile(o,!0)),r.addFromIni(i)):this.supportedMapTypes.some(e=>t.endsWith("."+e))&&(s=await this.rfs.openFile(o,!0),n.addFromMapFile(s))}catch(e){console.warn(`Couldn't read file "${o}"`,e)}}return n.sortByName(),r.mergeWith(n),this.mapList=r,r}static getTileData(){return Bt.tileData}static getImages(){return Bt.images}static getVoxels(){return Bt.voxels}static getVoxelAnims(){return Bt.voxelAnims}static getPalettes(){return Bt.palettes}static getSounds(){return Bt.sounds}static getThemes(){return Bt.themes}static getTaunts(){return Bt.taunts}static getActiveEngine(){return xt.RedAlert2}static getLastTheaterType(){return Bt.activeTheater?.type}static getCacheDir(){try{return this.getOrCreateDir(this.rfsSettings.cacheDir,!0)}catch(e){return void console.error("Couldn't get cache directory",[e])}}static async getReplayDir(){var i=this.getActiveMod();if(i){let e=await this.getModDir(),t=await e?.getDirectory(i);return t?.getOrCreateDirectory(Bt.rfsSettings.replayDir)}return this.getOrCreateDir(this.rfsSettings.replayDir)}static getModDir(){return this.getOrCreateDir(Bt.rfsSettings.modDir)}static getMapDir(){return this.getOrCreateDir(Bt.rfsSettings.mapDir)}static async getOrCreateDir(e,t=!1){let i=this.rfs?.getRootDirectory();if(i)return await i.getOrCreateDirectory(e,t)}static getMapList(){return this.mapList}static destroy(){this.activeTheater=void 0,this.activeMod=void 0,this.modHash=void 0,this.mapList=void 0,this.rfs=void 0,this.vfs=void 0,this.art=void 0,this.iniFiles.clear(),this.images.clear(),this.palettes.clear(),this.rules=void 0,this.ai=void 0,this.theaters.clear(),this.tileData.clear(),this.voxels.clear(),this.voxelAnims.clear()}}(Bt=Dt).UI_ANIM_SPEED=2,Dt.rfsSettings={menuVideoFileName:"ra2ts_l.webm",splashImgFileName:"glsl.png",mapDir:"maps",modDir:"mods",musicDir:"music",tauntsDir:"Taunts",cacheDir:"cache",replayDir:"replays"},Dt.supportedMapTypes=["mpr","map"],Dt.images=new ye(e=>new s(e)),Dt.voxels=new ye(e=>new b(e)),Dt.voxelAnims=new ye(e=>new Nt(e)),Dt.sounds=new ye(e=>new yt(e)),Dt.themes=new wt(e=>new Tt(e),!1),Dt.taunts=new wt(async e=>new yt(new Uint8Array(await e.arrayBuffer()))),Dt.iniFiles=new ye(e=>new D(e)),Dt.tileData=new ye(e=>new E(e)),Dt.palettes=new ye(e=>new $(e)),Dt.theaters=new Map,Dt.theaterSettings=(new Map).set(xt.RedAlert2,[{type:I.Temperate,theaterIni:"temperat.ini",mixes:["isotemp.mix","temperat.mix","tem.mix"],extension:".tem",newTheaterChar:"T",isoPaletteName:"isotem.pal",unitPaletteName:"unittem.pal",overlayPaletteName:"temperat.pal",libPaletteName:"libtem.pal"},{type:I.Snow,theaterIni:"snow.ini",mixes:["isosnow.mix","snow.mix","sno.mix"],extension:".sno",newTheaterChar:"A",isoPaletteName:"isosno.pal",unitPaletteName:"unitsno.pal",overlayPaletteName:"snow.pal",libPaletteName:"libsno.pal"},{type:I.Urban,theaterIni:"urban.ini",mixes:["isourb.mix","urb.mix","urban.mix"],extension:".urb",newTheaterChar:"U",isoPaletteName:"isourb.pal",unitPaletteName:"uniturb.pal",overlayPaletteName:"urban.pal",libPaletteName:"liburb.pal"}]).set(xt.YurisRevenge,[{type:I.Temperate,theaterIni:"temperatmd.ini",mixes:["isotemp.mix","isotemmd.mix","temperat.mix","tem.mix"],extension:".tem",newTheaterChar:"T",isoPaletteName:"isotem.pal",unitPaletteName:"unittem.pal",overlayPaletteName:"temperat.pal",libPaletteName:"libtem.pal"},{type:I.Snow,theaterIni:"snowmd.ini",mixes:["isosnomd.mix","snowmd.mix","isosnow.mix","snow.mix","sno.mix"],extension:".sno",newTheaterChar:"A",isoPaletteName:"isosno.pal",unitPaletteName:"unitsno.pal",overlayPaletteName:"snow.pal",libPaletteName:"libsno.pal"},{type:I.Urban,theaterIni:"urbanmd.ini",mixes:["isourbmd.mix","isourb.mix","urb.mix","urban.mix"],extension:".urb",newTheaterChar:"U",isoPaletteName:"isourb.pal",unitPaletteName:"uniturb.pal",overlayPaletteName:"urban.pal",libPaletteName:"liburb.pal"},{type:I.NewUrban,theaterIni:"urbannmd.ini",mixes:["isoubnmd.mix","isoubn.mix","ubn.mix","urbann.mix"],extension:".ubn",newTheaterChar:"N",isoPaletteName:"isoubn.pal",unitPaletteName:"unitubn.pal",overlayPaletteName:"urbann.pal",libPaletteName:"libubn.pal"},{type:I.Desert,theaterIni:"desertmd.ini",mixes:["isodesmd.mix","desert.mix","des.mix","isodes.mix"],extension:".des",newTheaterChar:"D",isoPaletteName:"isodes.pal",unitPaletteName:"unitdes.pal",overlayPaletteName:"desert.pal",libPaletteName:"libdes.pal"},{type:I.Lunar,theaterIni:"lunarmd.ini",mixes:["isolunmd.mix","isolun.mix","lun.mix","lunar.mix"],extension:".lun",newTheaterChar:"L",isoPaletteName:"isolun.pal",unitPaletteName:"unitlun.pal",overlayPaletteName:"lunar.pal",libPaletteName:"liblun.pal"}]),Dt.customRulesFileName="rulescd.ini",Dt.customArtFileName="artcd.ini",Dt.customMpModesFileName="mpmodescd.ini",Dt.shroudFileName="shroud.shp",Dt.mixinRulesFileNames=(new Map).set(At.NoDogEngiKills,"nodogengikills.ini"),(r=Et=Et||{})[r.None=0]="None",r[r.Aircraft=1]="Aircraft",r[r.Building=2]="Building",r[r.Infantry=3]="Infantry",r[r.Overlay=4]="Overlay",r[r.Smudge=5]="Smudge",r[r.Terrain=6]="Terrain",r[r.Vehicle=7]="Vehicle",r[r.Animation=8]="Animation",r[r.Projectile=9]="Projectile",r[r.VoxelAnim=10]="VoxelAnim",r[r.Debris=11]="Debris";class Mt{constructor(e){this.type=e}isStructure(){return this.type===Et.Building}isVehicle(){return this.type===Et.Vehicle}isInfantry(){return this.type===Et.Infantry}isAircraft(){return this.type===Et.Aircraft}isTerrain(){return this.type===Et.Terrain}isSmudge(){return this.type===Et.Smudge}isOverlay(){return this.type===Et.Overlay}isNamed(){return"name"in this}isTechno(){return"health"in this}}class Rt extends Mt{}class Lt extends Rt{}class Ft extends Lt{constructor(){super(Et.Building)}}class jt extends Lt{constructor(){super(Et.Vehicle)}}class Ut extends Lt{constructor(){super(Et.Infantry)}}class Wt extends Lt{constructor(){super(Et.Aircraft)}}class zt extends Rt{constructor(){super(Et.Terrain)}}class Vt extends Rt{constructor(){super(Et.Smudge)}}class Ht extends Mt{constructor(){super(Et.Overlay)}}class Gt{static decode(e,t){t=new Uint8Array(t);return this.decodeInto(e,t),t}static decodeInto(e,t){let i=new k(new DataView(e.buffer,e.byteOffset,e.byteLength)),s=0;for(;;){var r=i.readUint8();if(0==(128&r)){var a=i.readUint8(),n=3+((112&r)>>4);this.replicatePrevious(t,s,s-(((15&r)<<8)+a),n),s+=n}else if(0==(64&r)){n=63&r;if(0==n)return s;t.set(i.readUint8Array(n),s),s+=n}else{r=63&r;if(62==r)for(var o=i.readInt16(),h=i.readUint8(),l=s+o;s<l;s++)t[s]=h;else if(63==r){o=i.readInt16();let e=i.readInt16();if(e>=s)throw new Error(`srcIndex >= destIndex ${e} ${s}`);for(var c=s+o;s<c;s++)t[s]=t[e++]}else{r=3+r;let e=i.readInt16();if(e>=s)throw new Error(`srcIndex >= destIndex ${e} ${s}`);for(var u=s+r;s<u;s++)t[s]=t[e++]}}}}static replicatePrevious(t,i,s,r){if(i<s)throw new Error(`srcIndex > destIndex ${s} ${i}`);if(i-s==1)for(let e=0;e<r;e++)t[i+e]=t[i-1];else for(let e=0;e<r;e++)t[i+e]=t[s+e]}}var $t,qt,Xt,Zt,Qt,Yt,Kt,Jt,ei,ti,ii,si,ri,ai,ni,oi,hi,li,ci,ui,di=__webpack_require__(251).default;class gi{static decompress(e,t){e={inputBuffer:e,outputBuffer:null},t=di.decompress(e,{outputSize:t});if(0!==t)throw new Error(`MiniLzo decode failed with code ${t}`);return e.outputBuffer}}class pi{static decode(e,t,i=5){t=new Uint8Array(t);return this.decodeInto(e,t,i),t}static decodeInto(e,i,s=5){var t=i.length;let r=0,a=0;for(;a<t;){var n=e[r+1]<<8|e[r];r+=2;var o=e[r+1]<<8|e[r];if(r+=2,!n||!o)break;let t;t=80===s?Gt.decode(e.subarray(r,r+n),o):gi.decompress(e.subarray(r,r+n),o);for(let e=0;e<o;++e)i[a+e]=t[e];r+=n,a+=o}}}function mi(e){switch(e){case $t.Indexed:return 1;case $t.Rgb:return 3;case $t.Rgba:return 4;default:throw new Error(`Unsupported pixel format ${e}`)}}(r=$t=$t||{})[r.Rgb=1]="Rgb",r[r.Rgba=2]="Rgba",r[r.Indexed=3]="Indexed";class fi{constructor(e,t,i,s=$t.Rgba){var r=mi(s);this.data=i||new Uint8Array(r*e*t),this.pixelFormat=s,this.width=e,this.height=t}drawIndexedImage(t,e,i){var s=mi(this.pixelFormat);const r=this.data;var a=this.width,n=s*a,o=s*a*this.height;let h=0+n*i+s*e,l=0;for(let e=0;e<t.height;e++){for(let e=0;e<t.width;e++){var c=t.data[l];0!==c&&0<=h&&h<o&&(r[h]=c,3<=s&&(r[h+1]=0,r[h+2]=0),4===s&&(r[h+3]=255)),h+=s,l++}h+=n-t.width*s}}}class yi extends fi{constructor(e,t,i){super(e,t,i,$t.Rgb)}}(r=qt=qt||{})[r.OnceAny=0]="OnceAny",r[r.OnceAll=1]="OnceAll",r[r.Repeat=2]="Repeat";class wi{read(e){let t=[];for(var[i,s]of e.entries){var r=s.split(",");r.length<3?console.warn(`Invalid tag ${i}=${s}. Skipping.`):(s=Number(r[0]),void 0!==qt[s]?(r={id:i,repeatType:s,name:r[1],triggerId:r[2]},t.push(r)):console.warn(`Invalid repeat value ${s} for tag id ${i}. Skipping.`))}return t}}(r=Xt=Xt||{})[r.NoEvent=0]="NoEvent",r[r.EnteredBy=1]="EnteredBy",r[r.SpiedBy=2]="SpiedBy",r[r.AttackedByAny=6]="AttackedByAny",r[r.DestroyedByAny=7]="DestroyedByAny",r[r.AnyEvent=8]="AnyEvent",r[r.DestroyedAllUnits=9]="DestroyedAllUnits",r[r.DestroyedAllBuildings=10]="DestroyedAllBuildings",r[r.DestroyedAll=11]="DestroyedAll",r[r.CreditsExceed=12]="CreditsExceed",r[r.ElapsedTime=13]="ElapsedTime",r[r.MissionTimerExpired=14]="MissionTimerExpired",r[r.DestroyedBuildings=15]="DestroyedBuildings",r[r.DestroyedUnits=16]="DestroyedUnits",r[r.NoFactoriesLeft=17]="NoFactoriesLeft",r[r.BuildBuilding=19]="BuildBuilding",r[r.BuildUnit=20]="BuildUnit",r[r.BuildInfantry=21]="BuildInfantry",r[r.BuildAircraft=22]="BuildAircraft",r[r.CrossesHorizontalLine=25]="CrossesHorizontalLine",r[r.CrossesVerticalLine=26]="CrossesVerticalLine",r[r.GlobalIsSet=27]="GlobalIsSet",r[r.GlobalIsCleared=28]="GlobalIsCleared",r[r.DestroyedOrCaptured=29]="DestroyedOrCaptured",r[r.LowPower=30]="LowPower",r[r.DestroyedBridge=31]="DestroyedBridge",r[r.BuildingExists=32]="BuildingExists",r[r.ComesNearWaypoint=34]="ComesNearWaypoint",r[r.LocalIsSet=36]="LocalIsSet",r[r.LocalIsCleared=37]="LocalIsCleared",r[r.FirstDamagedCombat=38]="FirstDamagedCombat",r[r.HalfHealthCombat=39]="HalfHealthCombat",r[r.QuarterHealthCombat=40]="QuarterHealthCombat",r[r.FirstDamagedAny=41]="FirstDamagedAny",r[r.HalfHealthAny=42]="HalfHealthAny",r[r.QuarterHealthAny=43]="QuarterHealthAny",r[r.AttackedByHouse=44]="AttackedByHouse",r[r.AmbientLightBelow=45]="AmbientLightBelow",r[r.AmbientLightAbove=46]="AmbientLightAbove",r[r.ElapsedScenarioTime=47]="ElapsedScenarioTime",r[r.DestroyedOrCapturedOrInfiltrated=48]="DestroyedOrCapturedOrInfiltrated",r[r.PickupCrate=49]="PickupCrate",r[r.PickupCrateAny=50]="PickupCrateAny",r[r.RandomDelay=51]="RandomDelay",r[r.CreditsBelow=52]="CreditsBelow",r[r.SpyEnteringAsHouse=53]="SpyEnteringAsHouse",r[r.SpyEnteringAsInfantry=54]="SpyEnteringAsInfantry",r[r.DestroyedAllUnitsNaval=55]="DestroyedAllUnitsNaval",r[r.DestroyedAllUnitsLand=56]="DestroyedAllUnitsLand",r[r.BuildingNotExists=57]="BuildingNotExists",(r=Zt=Zt||{})[r.NoAction=0]="NoAction",r[r.FireSale=9]="FireSale",r[r.TextTrigger=11]="TextTrigger",r[r.DestroyTrigger=12]="DestroyTrigger",r[r.ChangeHouse=14]="ChangeHouse",r[r.RevealMap=16]="RevealMap",r[r.RevealAroundWaypoint=17]="RevealAroundWaypoint",r[r.PlaySoundFx=19]="PlaySoundFx",r[r.PlaySpeech=21]="PlaySpeech",r[r.ForceTrigger=22]="ForceTrigger",r[r.TimerStart=23]="TimerStart",r[r.TimerStop=24]="TimerStop",r[r.TimerExtend=25]="TimerExtend",r[r.TimerShorten=26]="TimerShorten",r[r.TimerSet=27]="TimerSet",r[r.GlobalSet=28]="GlobalSet",r[r.GlobalClear=29]="GlobalClear",r[r.DestroyObject=32]="DestroyObject",r[r.AddOneTimeSuperWeapon=33]="AddOneTimeSuperWeapon",r[r.AddRepeatingSuperWeapon=34]="AddRepeatingSuperWeapon",r[r.AllChangeHouse=36]="AllChangeHouse",r[r.ResizePlayerView=40]="ResizePlayerView",r[r.PlayAnimAt=41]="PlayAnimAt",r[r.DetonateWarhead=42]="DetonateWarhead",r[r.ReshroudMap=51]="ReshroudMap",r[r.EnableTrigger=53]="EnableTrigger",r[r.DisableTrigger=54]="DisableTrigger",r[r.CreateRadarEvent=55]="CreateRadarEvent",r[r.LocalSet=56]="LocalSet",r[r.LocalClear=57]="LocalClear",r[r.SellBuilding=60]="SellBuilding",r[r.TurnOffBuilding=61]="TurnOffBuilding",r[r.TurnOnBuilding=62]="TurnOnBuilding",r[r.ApplyOneHundredDamage=63]="ApplyOneHundredDamage",r[r.ForceEnd=69]="ForceEnd",r[r.DestroyTag=70]="DestroyTag",r[r.SetAmbientStep=71]="SetAmbientStep",r[r.SetAmbientRate=72]="SetAmbientRate",r[r.SetAmbientLight=73]="SetAmbientLight",r[r.NukeStrike=95]="NukeStrike",r[r.PlaySoundFxAt=99]="PlaySoundFxAt",r[r.UnrevealAroundWaypoint=101]="UnrevealAroundWaypoint",r[r.LightningStrike=102]="LightningStrike",r[r.TimerText=103]="TimerText",r[r.CreateCrate=108]="CreateCrate",r[r.IronCurtainAt=109]="IronCurtainAt",r[r.EvictOccupiers=111]="EvictOccupiers",r[r.Cheer=113]="Cheer",r[r.StopSoundsAt=116]="StopSoundsAt";class Ti{read(e,t,i,s){let r=this.readTriggers(e),{events:a,unknownEventTypes:n}=this.readEvents(t),{actions:o,unknownActionTypes:h}=this.readActions(i),l=[...s.values()],c=new Set(r);for(let t of r.values()){var u=a.get(t.id);u&&t.events.push(...u);u=o.get(t.id);u&&t.actions.push(...u),!t.attachedTriggerId||(u=r.find(e=>e.id===t.attachedTriggerId))&&(t.attachedTrigger=u,c.delete(u))}for(let t of c){var d=l.find(e=>e.triggerId===t.id);if(d){let e=t;for(;e;)e.tag=d,e=e.attachedTrigger}else{let e=t;for(;e;){console.warn(`Trigger ${e.id} has no associated tag or valid root trigger. Skipping.`);var g=r.indexOf(e);-1!==g&&r.splice(g,1),e=e.attachedTrigger}}}return{triggers:r,unknownEventTypes:n,unknownActionTypes:h}}readTriggers(e){let t=[];for(var[i,s]of e.entries){var r=s.split(",");r.length<8?console.warn(`Invalid trigger ${i}=${s}. Skipping.`):(r={id:i,houseName:r[0],attachedTriggerId:"<none>"!==r[1]?r[1]:void 0,attachedTrigger:void 0,name:r[2],disabled:Boolean(Number(r[3])),difficulties:{easy:Boolean(Number(r[4])),medium:Boolean(Number(r[5])),hard:Boolean(Number(r[6]))},events:[],actions:[],tag:void 0},t.push(r))}return t}readEvents(e){let t=new Map,r=new Set;for(var[a,i]of e.entries){let s=i.split(",");if(s.length<4)console.warn(`Invalid event ${a}=${i}. Skipping.`);else{var n=Number(s.shift());let i=[];for(let t=0;t<n;t++){var o=Number(s.shift()),h=Number(s.shift());let e=s.splice(0,2===h?2:1);void 0!==Xt[o]?(h={triggerId:a,eventIndex:t,type:o,params:[h,...e.map(e=>e||"0")]},i.push(h)):(r.add(o),console.warn(`Unknown event type ${o} for trigger id ${a}. Skipping.`))}t.set(a,i)}}return{events:t,unknownEventTypes:r}}readActions(e){let s=new Map,r=new Set;for(var[a,t]of e.entries){let i=t.split(",");if(i.length<9)console.warn(`Invalid action ${a}=${t}. Skipping.`);else{var n=Number(i.shift());if(i.length<8*n)console.warn(`Invalid action ${a}=${t}. Skipping.`);else{let t=[];for(let e=0;e<n;e++){var o=Number(i.shift()),h=i.splice(0,7);void 0!==Zt[o]?(h={triggerId:a,index:e,type:o,params:[Number(h[0]||"0"),h[1]||"0",h[2]||"0",h[3]||"0",h[4]||"0",h[5]||"0",h[6]?this.readAZActionParam(h[6]):0]},t.push(h)):(r.add(o),console.warn(`Unknown action type ${o} for trigger id "${a}". Skipping.`))}s.set(a,t)}}}return{actions:s,unknownActionTypes:r}}readAZActionParam(e){var t="Z".charCodeAt(0),i="A".charCodeAt(0),t=t-i+1;return 1<e.length?e.charCodeAt(1)-i+(e.charCodeAt(0)-i+1)*t:e.charCodeAt(0)-i}}class bi{constructor(){this.level=0,this.ambient=1,this.red=1,this.green=1,this.blue=1,this.ground=0,this.forceTint=!1}read(e,t=""){return this.level=e.getNumber(t+"Level",.032),this.ambient=e.getNumber(t+"Ambient",1),this.red=e.getNumber(t+"Red",1),this.green=e.getNumber(t+"Green",1),this.blue=e.getNumber(t+"Blue",1),this.ground=e.getNumber(t+"Ground",0),this}copy(e){return this.level=e.level,this.ambient=e.ambient,this.red=e.red,this.green=e.green,this.blue=e.blue,this.ground=e.ground,this.forceTint=e.forceTint,this}}class vi{read(e,t){let i=[];for(var[s,r]of e.entries){s={tagId:r,coords:this.readCoords(Number(s),t)};i.push(s)}return i}readCoords(e,t){t=t<4?128:1e3;return{x:e%t,y:Math.floor(e/t)}}}class Si{constructor(e,t){this.name=e,this.value=t}clone(){return new Si(this.name,this.value)}}class ki{read(e){return this.initialVeteran=e.getBool("InitialVeteran"),this}}class Oi extends D{fromString(e){super.fromString(e);let t=this.getSection("Map");if(!t)throw new Error("[Map] section not found");e=t.getNumberArray("Size");if(this.fullSize={x:e[0],y:e[1],width:e[2],height:e[3]},e=t.getNumberArray("LocalSize"),this.localSize={x:e[0],y:e[1],width:e[2],height:e[3]},this.theaterType=t.getEnum("Theater",I,I.None,!0),this.theaterType===I.None)throw new Error(`Unsupported theater type "${t.getString("Theater")}"`);let i=this.getSection("Basic");e=this.iniFormat=i?.getNumber("NewINIFormat")??0;return this.readTiles(),this.readWaypoints(this.getOrCreateSection("Waypoints")),this.readStructures(this.getOrCreateSection("Structures")),this.readVehicles(),this.readInfantries(),this.readAircrafts(),this.readTerrains(this.getOrCreateSection("Terrain")),this.readOverlays(),this.readSmudges(),this.readLighting(),this.readTagsAndTriggers(),this.readCellTags(e),this.readVariableNames(),this.startingLocations=this.readStartingLocations(this.waypoints),this.specialFlags=(new ki).read(this.getOrCreateSection("SpecialFlags")),this}fromJson(i){if(i[Oi.artSectionPrefix]){let{[Oi.artSectionPrefix]:e,...t}=i;this.artOverrides=new D(e),i=t}return super.fromJson(i)}readStartingLocations(e){let t=[];var i;for(i of e.filter(e=>e.number<8).sort((e,t)=>e.number<t.number?-1:1))t.push({x:i.rx,y:i.ry});return t}readLighting(){var e=this.getOrCreateSection("Lighting");this.lighting=(new bi).read(e),this.ionLighting=(new bi).read(e,"Ion"),this.ionLighting.forceTint=!0}readTagsAndTriggers(){this.tags=(new wi).read(this.getOrCreateSection("Tags"));var e=this.getOrCreateSection("Triggers"),t=this.getOrCreateSection("Events"),i=this.getOrCreateSection("Actions"),{triggers:e,unknownEventTypes:t,unknownActionTypes:i}=(new Ti).read(e,t,i,this.tags);this.triggers=e,this.unknownEventTypes=t,this.unknownActionTypes=i}readCellTags(e){this.cellTags=(new vi).read(this.getOrCreateSection("CellTags"),e)}readVariableNames(){var e,t,i=this.getOrCreateSection("VariableNames");let s=new Map;for([e,t]of i.entries){var r,a,n=Number(e);Number.isNaN(n)?console.warn(`Map [VariableNames] contains non-numeric index "${e}". Skipping.`):([r,a]=t.split(","),a=new Si(r,Boolean(Number(a))),s.set(n,a))}this.variables=s}readTiles(){let e=this.getSection("IsoMapPack5");if(!e)throw new Error("[IsoMapPack5] section not found");var t=L(e.getConcatenatedValues()),i=(2*this.fullSize.width-1)*this.fullSize.height,s=new Uint8Array(11*i+4);pi.decodeInto(t,s);let r=new k(s.buffer),a=2*this.fullSize.width-1;var n,o,h,l,s=this.fullSize.height,c=(e,t)=>t*a+e;this.tiles=new Array(a*s);for(let e=this.maxTileNum=0;e<i;e++){var u=r.readUint16(),d=r.readUint16(),g=Math.max(0,r.readInt16());this.maxTileNum=Math.max(this.maxTileNum,g),r.readInt16();var p=r.readUint8(),m=r.readUint8();r.readUint8();var f=u-d+this.fullSize.width-1,y=u+d-this.fullSize.width-1;0<=f&&f<2*this.fullSize.width&&0<=y&&y<2*this.fullSize.height&&(p={dx:f,dy:y,rx:u,ry:d,z:m,tileNum:g,subTile:p},this.tiles[c(f,Math.floor(y/2))]=p)}for(let t=0;t<this.fullSize.height;t++)for(let e=0;e<=2*this.fullSize.width-2;e++)this.tiles[c(e,t)]||(n=e,l=(o=2*t+e%2)-(h=(n+o)/2+1)+this.fullSize.width+1,this.tiles[c(e,t)]={dx:n,dy:o,rx:h,ry:l,z:0,tileNum:0,subTile:0})}readWaypoints(e){this.waypoints=[];for(var[t,i]of e.entries){var s;let e;isNaN(s=parseInt(t,10))||isNaN(e=parseInt(i,10))||(t=Math.floor(e/1e3),i=e-1e3*t,this.waypoints.push({number:s,rx:i,ry:t}))}}readStructures(e){this.structures=[];for(var[,t]of e.entries){t=t.split(",");if(!(t.length<=15)){let e=new Ft;e.owner=t[0],e.name=t[1],e.health=Number(t[2]),e.rx=Number(t[3]),e.ry=Number(t[4]),e.tag=this.readTagId(t[6]),e.poweredOn=Boolean(Number(t[9])),this.structures.push(e)}}}readTagId(e){return"none"!==e.toLowerCase()?e:void 0}readVehicles(){this.vehicles=[];let e=this.getSection("Units");if(e)for(var t of e.entries.values()){var i=t.split(",");if(i.length<=11)console.warn(`Invalid Vehicle entry: "${t}"`);else{let e=new jt;e.owner=i[0],e.name=i[1],e.health=Number(i[2]),e.rx=Number(i[3]),e.ry=Number(i[4]),e.direction=Number(i[5]),e.tag=this.readTagId(i[7]),e.veterancy=Number(i[8]),e.onBridge="1"===i[10],this.vehicles.push(e)}}}readInfantries(){this.infantries=[];let e=this.getSection("Infantry");if(e)for(var t of e.entries.values()){var i=t.split(",");let e=new Ut;i.length<=8?console.warn(`Invalid Infantry entry: "${t}"`):(e.owner=i[0],e.name=i[1],e.health=Number(i[2]),e.rx=Number(i[3]),e.ry=Number(i[4]),e.subCell=Number(i[5]),e.direction=Number(i[7]),e.tag=this.readTagId(i[8]),e.veterancy=Number(i[9]),e.onBridge="1"===i[11],this.infantries.push(e))}}readAircrafts(){this.aircrafts=[];let e=this.getSection("Aircraft");if(e)for(var t of e.entries.values()){t=t.split(",");let e=new Wt;e.owner=t[0],e.name=t[1],e.health=Number(t[2]),e.rx=Number(t[3]),e.ry=Number(t[4]),e.direction=Number(t[5]),e.tag=this.readTagId(t[7]),e.veterancy=Number(t[8]),e.onBridge="1"===t[t.length-4],this.aircrafts.push(e)}}readTerrains(e){this.terrains=[];for(var[t,i]of e.entries){t=Number(t);if(!isNaN(t)){let e=new zt;e.name=i,e.rx=t%1e3,e.ry=Math.floor(t/1e3),this.terrains.push(e)}}}readOverlays(){this.overlays=[],this.maxOverlayId=0;let t=this.getSection("OverlayPack");if(t){var i=L(t.getConcatenatedValues()),s=new Uint8Array(1<<18);pi.decodeInto(i,s,80);let e=this.getSection("OverlayDataPack");if(e){var i=L(e.getConcatenatedValues()),r=new Uint8Array(1<<18);pi.decodeInto(i,r,80);for(let t=0;t<this.fullSize.height;t++)for(let e=2*this.fullSize.width-2;0<=e;e--){var a=e,n=2*t+e%2,o=(a+n)/2+1,h=n-o+this.fullSize.width+1,a=o+512*h,n=s[a];if(255!==n){a=r[a];let e=new Ht;e.id=n,e.value=a,e.rx=o,e.ry=h,this.overlays.push(e),this.maxOverlayId=Math.max(this.maxOverlayId,n)}}}else console.warn("[OverlayDataPack] section not found. Skipping.")}else console.warn("[Overlay] section not found. Skipping.")}readSmudges(){this.smudges=[];let e=this.getSection("Smudge");if(e)for(var t of e.entries.values()){var i=t.split(",");if(i.length<=2)console.warn(`Invalid Smudge entry: "${t}"`);else{let e=new Vt;e.name=i[0],e.rx=Number(i[1]),e.ry=Number(i[2]),this.smudges.push(e)}}}decodePreviewImage(){let e=this.getSection("Preview"),t=this.getSection("PreviewPack");if(e&&t){var[,,i,s]=e.getArray("Size").map(e=>Number(e)),r=L(t.getConcatenatedValues()),s=new yi(i,s);return pi.decodeInto(r,s.data),s}}}Oi.artSectionPrefix="ART",(r=Qt=Qt||{})[r.GDI=0]="GDI",r[r.Nod=1]="Nod",r[r.Civilian=2]="Civilian",r[r.Mutant=3]="Mutant";const _i=(new Map).set("GDI",Qt.GDI).set("Nod",Qt.Nod).set("Civilian",Qt.Civilian).set("Mutant",Qt.Mutant),Ii=new Map([["Americans","STT:PlayerSideAmerica"],["Alliance","STT:PlayerSideKorea"],["French","STT:PlayerSideFrance"],["Germans","STT:PlayerSideGermany"],["British","STT:PlayerSideBritain"],["Africans","STT:PlayerSideLibya"],["Arabs","STT:PlayerSideIraq"],["Confederation","STT:PlayerSideCuba"],["Russians","STT:PlayerSideRussia"]]);class Ci{constructor(e){this.id=e}readIni(e){this.name=e.name,this.uiName=e.getString("UIName"),this.uiTooltip=e.getString("UITooltip")||Ii.get(this.name);var t=e.getString("Side");if(!t)throw new Error(`Missing Side for country "${this.name}"`);var i=_i.get(t);if(void 0===i)throw new Error(`Unknown side "${t}" for country "${this.name}"`);this.side=i,this.multiplay=e.getBool("Multiplay"),this.multiplayPassive=e.getBool("MultiplayPassive"),this.veteranAircraft=e.getArray("VeteranAircraft"),this.veteranInfantry=e.getArray("VeteranInfantry"),this.veteranUnits=e.getArray("VeteranUnits")}}class Ai{static iniSpeedToLeptonsPerTick(e,t){return Math.min(256,256*e/t)}static iniRotToDegsPerTick(e){return e/256*360}constructor(e,t,i=-1,s){this.type=e,this.ini=t,this.index=i,this.generalRules=s,this.parse()}parse(){this.alphaImage=this.ini.getString("AlphaImage")||void 0,this.alternateArcticArt=this.ini.getBool("AlternateArcticArt"),this.crushable=this.ini.getBool("Crushable",this.type===Et.Infantry),this.crushSound=this.ini.getString("CrushSound")||void 0,this.dontScore=this.ini.getBool("DontScore"),this.insignificant=this.ini.getBool("Insignificant"),this.legalTarget=this.ini.getBool("LegalTarget",!0),this.noShadow=this.ini.getBool("NoShadow"),this.uiName=this.ini.getString("UIName")}get name(){return this.ini.name}get imageName(){let e=this.ini.getString("Image");return e&&"null"!==e||(e=this.name),e}}Ai.IMAGE_NONE="none";class Bi{constructor(e){this.rules=e,this.parse()}parse(){this.ambientDamage=this.rules.getNumber("AmbientDamage"),this.anim=this.rules.getArray("Anim"),this.areaFire=this.rules.getBool("AreaFire"),this.burst=this.rules.getNumber("Burst",1),this.cellRangefinding=this.rules.getBool("CellRangefinding"),this.damage=this.rules.getNumber("Damage"),this.decloakToFire=this.rules.getBool("DecloakToFire",!0),this.fireOnce=this.rules.getBool("FireOnce"),this.isAlternateColor=this.rules.getBool("IsAlternateColor"),this.isElectricBolt=this.rules.getBool("IsElectricBolt"),this.isHouseColor=this.rules.getBool("IsHouseColor"),this.isLaser=this.rules.getBool("IsLaser"),this.isRadBeam=this.rules.getBool("IsRadBeam"),this.isSonic=this.rules.getBool("IsSonic"),this.laserDuration=this.rules.getNumber("LaserDuration"),this.limboLaunch=this.rules.getBool("LimboLaunch"),this.minimumRange=this.rules.getNumber("MinimumRange"),this.name=this.rules.name,this.neverUse=this.rules.getBool("NeverUse"),this.omniFire=this.rules.getBool("OmniFire"),this.projectile=this.rules.getString("Projectile"),this.radLevel=this.rules.getNumber("RadLevel"),this.range=this.rules.getNumber("Range"),-2===this.range&&(this.range=Number.POSITIVE_INFINITY),this.report=this.rules.getArray("Report"),this.revealOnFire=this.rules.getBool("RevealOnFire",!0),this.rof=this.rules.getNumber("ROF"),this.sabotageCursor=this.rules.getBool("SabotageCursor"),this.spawner=this.rules.getBool("Spawner");var e=this.rules.getNumber("Speed");this.iniSpeed=e,this.speed=Ai.iniSpeedToLeptonsPerTick(e,100),this.suicide=this.rules.getBool("Suicide"),this.useSparkParticles=this.rules.getBool("UseSparkParticles"),this.warhead=this.rules.getString("Warhead")}}class xi{readIni(e){this.ini=e,this.ambientChangeRate=e.getNumber("AmbientChangeRate"),this.ambientChangeStep=e.getNumber("AmbientChangeStep"),this.behind=e.getString("Behind"),this.bridgeExplosions=e.getArray("BridgeExplosions"),this.chronoBeamColor=e.getNumberArray("ChronoBeamColor"),this.chronoBlast=e.getString("ChronoBlast"),this.chronoBlastDest=e.getString("ChronoBlastDest"),this.chronoPlacement=e.getString("ChronoPlacement"),this.chronoSparkle1=e.getString("ChronoSparkle1"),this.conditionRed=e.getNumber("ConditionRed"),this.conditionYellow=e.getNumber("ConditionYellow"),this.creditTicks=e.getArray("CreditTicks"),this.extraAircraftLight=e.getNumber("ExtraAircraftLight"),this.extraInfantryLight=e.getNumber("ExtraInfantryLight"),this.extraUnitLight=e.getNumber("ExtraUnitLight");let t=e.getString("DamageFireTypes");t=t||"FIRE01,FIRE02,FIRE03",this.fireNames=t.split(/\.|,/).filter(e=>""!==e),this.flyerHelper=e.getString("FlyerHelper"),this.gravity=e.getNumber("Gravity"),this.idleActionFrequency=60*e.getNumber("IdleActionFrequency"),this.impactLandSound=e.getString("ImpactLandSound")||void 0,this.impactWaterSound=e.getString("ImpactWaterSound")||void 0,this.infantryExplode=e.getString("InfantryExplode"),this.flamingInfantry=e.getString("FlamingInfantry"),this.infantryHeadPop=e.getString("InfantryHeadPop"),this.infantryNuked=e.getString("InfantryNuked"),this.ironCurtainInvokeAnim=e.getString("IronCurtainInvokeAnim"),this.messageDuration=e.getNumber("MessageDuration",10),this.metallicDebris=e.getArray("MetallicDebris"),this.nukeTakeOff=e.getString("NukeTakeOff"),this.deadBodies=e.getArray("DeadBodies"),this.wake=e.getString("Wake"),this.parachute=e.getString("Parachute"),this.moveFlash=e.getString("MoveFlash"),this.warpOut=e.getString("WarpOut"),this.warpAway=e.getString("WarpAway"),this.weaponNullifyAnim=e.getString("WeaponNullifyAnim"),this.weatherConClouds=e.getArray("WeatherConClouds"),this.weatherConBoltExplosion=e.getString("WeatherConBoltExplosion"),this.weatherConBolts=e.getArray("WeatherConBolts")}}(r=Yt=Yt||{})[r.GenericCombat=0]="GenericCombat",r[r.GenericNonCombat=1]="GenericNonCombat",r[r.DropZone=2]="DropZone",r[r.BaseUnderAttack=3]="BaseUnderAttack",r[r.HarvesterUnderAttack=4]="HarvesterUnderAttack",r[r.EnemyObjectSensed=5]="EnemyObjectSensed";class Ei{readIni(e){return this.eventSuppressionDistances=e.getNumberArray("RadarEventSuppressionDistances"),this.eventVisibilityDurations=e.getNumberArray("RadarEventVisibilityDurations"),this.eventDurations=e.getNumberArray("RadarEventDurations"),this.flashFrameTime=e.getNumber("FlashFrameTime"),this.combatFlashTime=e.getNumber("RadarCombatFlashTime"),this.eventMinRadius=e.getNumber("RadarEventMinRadius"),this.eventSpeed=e.getNumber("RadarEventSpeed"),this.eventRotationSpeed=e.getNumber("RadarEventRotationSpeed"),this.eventColorSpeed=e.getNumber("RadarEventColorSpeed"),this}getEventSuppresionDistance(e){if(e>this.eventSuppressionDistances.length-1)throw new RangeError(`No event suppression distance is defined for type ${Yt[e]}`);return this.eventSuppressionDistances[e]}getEventVisibilityDuration(e){if(e>this.eventVisibilityDurations.length-1)throw new RangeError(`No event visibility duration is defined for type ${Yt[e]}`);return this.eventVisibilityDurations[e]}getEventDuration(e){if(e>this.eventDurations.length-1)throw new RangeError(`No event duration is defined for type ${Yt[e]}`);return this.eventDurations[e]}}class Pi{readIni(e){return this.reloadRate=e.getNumber("ReloadRate"),this.repairPercent=e.getNumber("RepairPercent"),this.repairRate=e.getNumber("RepairRate"),this.repairStep=e.getNumber("RepairStep"),this.uRepairRate=e.getNumber("URepairRate"),this.iRepairRate=e.getNumber("IRepairRate"),this.iRepairStep=e.getNumber("IRepairStep"),this}}class Ni{readIni(e){return this.veteranRatio=e.getNumber("VeteranRatio",3),this.veteranCombat=e.getNumber("VeteranCombat",1),this.veteranSpeed=e.getNumber("VeteranSpeed",1),this.veteranSight=Math.max(1,e.getNumber("VeteranSight",1)),this.veteranArmor=e.getNumber("VeteranArmor",1),this.veteranROF=e.getNumber("VeteranROF",1),this.veteranCap=e.getNumber("VeteranCap",2),this.initialVeteran=e.getBool("InitialVeteran"),this}}class Di{readIni(e){return this.alliedCrew=e.getString("AlliedCrew"),this.alliedSurvivorDivisor=e.getNumber("AlliedSurvivorDivisor"),this.crewEscape=e.getNumber("CrewEscape"),this.sovietCrew=e.getString("SovietCrew"),this.sovietSurvivorDivisor=e.getNumber("SovietSurvivorDivisor"),this.survivorRate=e.getNumber("SurvivorRate"),this}}class Mi{readIni(e){return this.type=e.getString("PrismType"),this.supportHeight=e.getNumber("PrismSupportHeight"),this.supportMax=e.getNumber("PrismSupportMax"),this.supportModifier=e.getNumber("PrismSupportModifier",1),this}}class Ri{readIni(e){return this.myEffectivenessCoefficientDefault=e.getNumber("MyEffectivenessCoefficientDefault"),this.targetEffectivenessCoefficientDefault=e.getNumber("TargetEffectivenessCoefficientDefault"),this.targetSpecialThreatCoefficientDefault=e.getNumber("TargetSpecialThreatCoefficientDefault"),this.targetStrengthCoefficientDefault=e.getNumber("TargetStrengthCoefficientDefault"),this.targetDistanceCoefficientDefault=e.getNumber("TargetDistanceCoefficientDefault"),this}}class Li{readIni(e){if(this.allyParaDrop=this.readParadropSquad(e.getArray("AllyParaDropInf"),e.getNumberArray("AllyParaDropNum"),"Ally"),this.amerParaDrop=this.readParadropSquad(e.getArray("AmerParaDropInf"),e.getNumberArray("AmerParaDropNum"),"Amer"),this.sovParaDrop=this.readParadropSquad(e.getArray("SovParaDropInf"),e.getNumberArray("SovParaDropNum"),"Sov"),this.paradropPlane=e.getString("ParadropPlane"),!this.paradropPlane)throw new Error("Missing rules [General]->ParadropPlane");return this.paradropRadius=e.getNumber("ParadropRadius"),this}readParadropSquad(t,i,e){if(t.length!==i.length)throw new RangeError(`${e}ParaDropInf/Num size mismatch (${t.length}, ${i.length})`);let s=[];for(let e=0;e<t.length;++e)0<i[e]&&s.push({inf:t[e],num:i[e]});return s}getParadropSquads(e){switch(e){case Qt.GDI:return this.allyParaDrop;case Qt.Nod:return this.sovParaDrop;default:throw new Error(`Unhandled side type "${e}"`)}}}class Fi{readIni(e){return this.deferment=e.getNumber("LightningDeferment"),this.damage=e.getNumber("LightningDamage"),this.duration=e.getNumber("LightningStormDuration"),this.warhead=e.getString("LightningWarhead"),this.hitDelay=e.getNumber("LightningHitDelay"),this.scatterDelay=e.getNumber("LightningScatterDelay"),this.cellSpread=e.getNumber("LightningCellSpread"),this.separation=e.getNumber("LightningSeparation"),this}}class ji{}class Ui extends ji{readIni(e){return this.pauseFrames=e.getNumber("V3RocketPauseFrames"),this.tiltFrames=e.getNumber("V3RocketTiltFrames"),this.pitchInitial=e.getNumber("V3RocketPitchInitial"),this.pitchFinal=e.getNumber("V3RocketPitchFinal"),this.turnRate=e.getNumber("V3RocketTurnRate"),this.acceleration=e.getNumber("V3RocketAcceleration"),this.altitude=e.getNumber("V3RocketAltitude"),this.damage=e.getNumber("V3RocketDamage"),this.eliteDamage=e.getNumber("V3RocketEliteDamage"),this.bodyLength=e.getNumber("V3RocketBodyLength"),this.lazyCurve=e.getBool("V3RocketLazyCurve"),this.type=e.getString("V3RocketType"),this}}class Wi extends ji{readIni(e){return this.pauseFrames=e.getNumber("DMislPauseFrames"),this.tiltFrames=e.getNumber("DMislTiltFrames"),this.pitchInitial=e.getNumber("DMislPitchInitial"),this.pitchFinal=e.getNumber("DMislPitchFinal"),this.turnRate=e.getNumber("DMislTurnRate"),this.acceleration=e.getNumber("DMislAcceleration"),this.altitude=e.getNumber("DMislAltitude"),this.damage=e.getNumber("DMislDamage"),this.eliteDamage=e.getNumber("DMislEliteDamage"),this.bodyLength=e.getNumber("DMislBodyLength"),this.lazyCurve=e.getBool("DMislLazyCurve"),this.type=e.getString("DMislType"),this}}class zi{readIni(e){return this.height=e.getNumber("HoverHeight"),this.dampen=e.getNumber("HoverDampen"),this.bob=e.getNumber("HoverBob"),this.boost=e.getNumber("HoverBoost"),this.acceleration=e.getNumber("HoverAcceleration"),this.brake=e.getNumber("HoverBrake"),this}}(r=Kt=Kt||{})[r.Power=0]="Power",r[r.Factory=1]="Factory",r[r.Barracks=2]="Barracks",r[r.Radar=3]="Radar",r[r.Tech=4]="Tech",r[r.Proc=5]="Proc";const Vi=(new Map).set(Kt.Power,"PrerequisitePower").set(Kt.Factory,"PrerequisiteFactory").set(Kt.Barracks,"PrerequisiteBarracks").set(Kt.Radar,"PrerequisiteRadar").set(Kt.Tech,"PrerequisiteTech").set(Kt.Proc,"PrerequisiteProc");class Hi{constructor(){this.prereqCategories=new Map}readIni(e){this.aircraftFogReveal=e.getNumber("AircraftFogReveal"),this.alliedDisguise=e.getString("AlliedDisguise"),this.baseUnit=e.getArray("BaseUnit"),this.bridgeVoxelMax=e.getNumber("BridgeVoxelMax"),this.buildSpeed=e.getFixed("BuildSpeed"),this.buildupTime=e.getNumber("BuildupTime"),this.chronoDelay=e.getNumber("ChronoDelay"),this.chronoDistanceFactor=e.getNumber("ChronoDistanceFactor",32),this.chronoHarvTooFarDistance=e.getNumber("ChronoHarvTooFarDistance"),this.chronoMinimumDelay=e.getNumber("ChronoMinimumDelay"),this.chronoRangeMinimum=e.getNumber("ChronoRangeMinimum"),this.chronoTrigger=e.getBool("ChronoTrigger",!0),this.cliffBackImpassability=e.getNumber("CliffBackImpassability",2),this.cloakDelay=e.getNumber("CloakDelay"),this.closeEnough=e.getNumber("CloseEnough"),this.crew=(new Di).readIni(e),this.defaultMirageDisguises=e.getArray("DefaultMirageDisguises"),this.dMisl=(new Wi).readIni(e),this.dropPodWeapon=e.getString("DropPodWeapon"),this.engineer=e.getString("Engineer"),this.engineerCaptureLevel=e.getFixed("EngineerCaptureLevel",.25),this.engineerDamage=e.getFixed("EngineerDamage",.437),this.engineerAlwaysCaptureTech=e.getBool("EngineerAlwaysCaptureTech",!0),this.flightLevel=e.getNumber("FlightLevel"),this.guardAreaTargetingDelay=e.getNumber("GuardAreaTargetingDelay"),this.harvesterTooFarDistance=e.getNumber("HarvesterTooFarDistance"),this.harvesterUnit=e.getArray("HarvesterUnit"),this.hover=(new zi).readIni(e),this.infantryBlinkDisguiseTime=e.getNumber("InfantryBlinkDisguiseTime"),this.lightningStorm=(new Fi).readIni(e),this.lowPowerPenaltyModifier=e.getNumber("LowPowerPenaltyModifier",1),this.minLowPowerProductionSpeed=e.getFixed("MinLowPowerProductionSpeed",.5),this.maxLowPowerProductionSpeed=e.getFixed("MaxLowPowerProductionSpeed",1),this.maximumCheerRate=e.getNumber("MaximumCheerRate"),this.maximumQueuedObjects=e.getNumber("MaximumQueuedObjects"),this.maxWaypointPathLength=e.getNumber("MaxWaypointPathLength"),this.multipleFactory=e.getFixed("MultipleFactory",1),this.normalTargetingDelay=e.getNumber("NormalTargetingDelay"),this.padAircraft=e.getArray("PadAircraft"),this.parachuteMaxFallRate=e.getNumber("ParachuteMaxFallRate"),this.paradrop=(new Li).readIni(e),this.prism=(new Mi).readIni(e),this.purifierBonus=e.getNumber("PurifierBonus"),this.radar=(new Ei).readIni(e),this.refundPercent=z(e.getNumber("RefundPercent"),0,1),this.repair=(new Pi).readIni(e),this.returnStructures=e.getBool("ReturnStructures"),this.revealTriggerRadius=Math.min(10,e.getNumber("RevealTriggerRadius")),this.shipSinkingWeight=e.getNumber("ShipSinkingWeight"),this.sovietDisguise=e.getString("SovietDisguise"),this.spyMoneyStealPercent=e.getNumber("SpyMoneyStealPercent"),this.spyPowerBlackout=e.getNumber("SpyPowerBlackout"),this.technician=e.getString("Technician"),this.threat=(new Ri).readIni(e),this.treeStrength=e.getNumber("TreeStrength"),this.unitsUnsellable=e.getBool("UnitsUnsellable"),this.v3Rocket=(new Ui).readIni(e),this.veteran=(new Ni).readIni(e),this.wallBuildSpeedCoefficient=e.getFixed("WallBuildSpeedCoefficient"),this.readPrereqCategories(e)}readPrereqCategories(e){for(var[t,i]of Vi){if(!e.has(i))throw new Error(`Missing prerequisite category ${i} in [General] section`);this.prereqCategories.set(t,e.getArray(i))}}getMissileRules(e){switch(e){case this.v3Rocket.type:return this.v3Rocket;case this.dMisl.type:return this.dMisl;default:throw new Error(`Unsupported missile type "${e}"`)}}}(r=Jt=Jt||{})[r.Default=0]="Default",r[r.Tunnel=5]="Tunnel",r[r.Railroad=6]="Railroad",r[r.Rock1=7]="Rock1",r[r.Rock2=8]="Rock2",r[r.Water=9]="Water",r[r.Shore=10]="Shore",r[r.Pavement=11]="Pavement",r[r.Dirt=12]="Dirt",r[r.Clear=13]="Clear",r[r.Rough=14]="Rough",r[r.Cliff=15]="Cliff",(r=ei=ei||{})[r.Clear=0]="Clear",r[r.Road=1]="Road",r[r.Rock=2]="Rock",r[r.Beach=3]="Beach",r[r.Rough=4]="Rough",r[r.Railroad=5]="Railroad",r[r.Weeds=6]="Weeds",r[r.Water=7]="Water",r[r.Wall=8]="Wall",r[r.Tiberium=9]="Tiberium",r[r.Cliff=10]="Cliff";const Gi=new Map([[Jt.Default,ei.Clear],[Jt.Clear,ei.Clear],[Jt.Tunnel,ei.Cliff],[Jt.Railroad,ei.Railroad],[Jt.Rock1,ei.Rock],[Jt.Rock2,ei.Rock],[Jt.Water,ei.Water],[Jt.Shore,ei.Beach],[Jt.Pavement,ei.Road],[Jt.Dirt,ei.Road],[Jt.Rough,ei.Rough],[Jt.Cliff,ei.Cliff]]);function $i(e){if(!Gi.has(e))throw new Error(`Unknown terrain type ${e}`);return Gi.get(e)}(r=ti=ti||{})[r.Foot=0]="Foot",r[r.Track=1]="Track",r[r.Wheel=2]="Wheel",r[r.Hover=3]="Hover",r[r.Float=4]="Float",r[r.FloatBeach=5]="FloatBeach",r[r.Amphibious=6]="Amphibious",r[r.Winged=7]="Winged";class qi{constructor(){this.speedModifiers=new Map}readIni(t){return this.buildable=t.getBool("Buildable",!1),[...t.entries.keys()].forEach(e=>{void 0!==ti[e]&&this.speedModifiers.set(ti[e],t.getNumber(e))}),this}getSpeedModifier(e){if(e===ti.Foot&&0===this.speedModifiers.get(ti.Track))return 0;let t=this.speedModifiers.get(e);return void 0===t&&(t=1),e!==ti.Track&&e!==ti.Wheel&&0<t&&(t=1),t}}(r=ii=ii||{})[r.None=0]="None",r[r.Gunfire=1]="Gunfire",r[r.Explode=2]="Explode",r[r.ExplodeAlt=3]="ExplodeAlt",r[r.Fire=4]="Fire",r[r.Electro=5]="Electro",r[r.HeadExplode=6]="HeadExplode",r[r.Nuke=7]="Nuke";class Xi{constructor(e){this.rules=e,this.verses=new Map,this.parse()}get name(){return this.rules.name}parse(){this.affectsAllies=this.rules.getBool("AffectsAllies",!0),this.animList=this.rules.getArray("AnimList"),this.bombDisarm=this.rules.getBool("BombDisarm"),this.bullets=this.rules.getBool("Bullets"),this.causesDelayKill=this.rules.getBool("CausesDelayKill"),this.cellSpread=this.rules.getNumber("CellSpread"),this.conventional=this.rules.getBool("Conventional"),this.culling=this.rules.getBool("Culling"),this.delayKillAtMax=this.rules.getNumber("DelayKillAtMax"),this.delayKillFrames=this.rules.getNumber("DelayKillFrames"),this.electricAssault=this.rules.getBool("ElectricAssault"),this.emEffect=this.rules.getBool("EMEffect"),this.infDeath=this.rules.getEnumNumeric("InfDeath",ii,ii.None),this.ivanBomb=this.rules.getBool("IvanBomb"),this.makesDisguise=this.rules.getBool("MakesDisguise"),this.mindControl=this.rules.getBool("MindControl"),this.nukeMaker=this.rules.getBool("NukeMaker"),this.paralyzes=this.rules.getNumber("Paralyzes"),this.parasite=this.rules.getBool("Parasite"),this.percentAtMax=this.rules.getNumber("PercentAtMax",1),this.proneDamage=this.rules.getFixed("ProneDamage",1),this.psychicDamage=this.rules.getBool("PsychicDamage"),this.radiation=this.rules.getBool("Radiation"),this.rocker=this.rules.getBool("Rocker"),this.sonic=this.rules.getBool("Sonic"),this.temporal=this.rules.getBool("Temporal");let e=this.rules.getFixedArray("Verses");e.forEach((e,t)=>this.verses.set(t,e)),this.wallAbsoluteDestroyer=this.rules.getBool("WallAbsoluteDestroyer"),this.wall=this.rules.getBool("Wall"),this.wood=this.rules.getBool("Wood")}}class Zi extends Ai{parse(){super.parse();var e=this.ini.getNumber("ROT",0);let t=this.ini.getNumber("Acceleration");1!==e||t||(t=Number.POSITIVE_INFINITY),t=t||3,this.acceleration=t,this.arcing=this.ini.getBool("Arcing"),this.courseLockDuration=this.ini.getNumber("CourseLockDuration"),this.detonationAltitude=this.ini.getNumber("DetonationAltitude"),this.firersPalette=this.ini.getBool("FirersPalette"),this.flakScatter=this.ini.getBool("FlakScatter"),this.inaccurate=this.ini.getBool("Inaccurate"),this.inviso=this.ini.getBool("Inviso"),this.isAntiAir=this.ini.getBool("AA"),this.isAntiGround=this.ini.getBool("AG",!0),this.level=this.ini.getBool("Level"),this.rot=Ai.iniRotToDegsPerTick(e),this.iniRot=e,this.shadow=this.ini.getBool("Shadow",!0),this.shrapnelWeapon=this.ini.getString("ShrapnelWeapon")||void 0,this.shrapnelCount=this.ini.getNumber("ShrapnelCount"),this.subjectToCliffs=this.ini.getBool("SubjectToCliffs"),this.subjectToElevation=this.ini.getBool("SubjectToElevation"),this.subjectToWalls=this.ini.getBool("SubjectToWalls"),this.vertical=this.ini.getBool("Vertical")}}(r=si=si||{})[r.Green=0]="Green",r[r.Yellow=1]="Yellow",r[r.White=2]="White",r[r.Red=3]="Red",r[r.Blue=4]="Blue",(r=ri=ri||{})[r.Statue=0]="Statue",r[r.Aircraft=1]="Aircraft",r[r.Chrono=2]="Chrono",r[r.Hover=3]="Hover",r[r.Infantry=4]="Infantry",r[r.Jumpjet=5]="Jumpjet",r[r.Missile=6]="Missile",r[r.Ship=7]="Ship",r[r.Vehicle=8]="Vehicle";const Qi=new Map([["{4A582746-9839-11d1-B709-00A024DDAFD1}",ri.Aircraft],["{4A582747-9839-11d1-B709-00A024DDAFD1}",ri.Chrono],["{4A582742-9839-11d1-B709-00A024DDAFD1}",ri.Hover],["{4A582744-9839-11d1-B709-00A024DDAFD1}",ri.Infantry],["{92612C46-F71F-11d1-AC9F-006008055BB5}",ri.Jumpjet],["{B7B49766-E576-11d3-9BD9-00104B972FE8}",ri.Missile],["{2BEA74E1-7CCA-11d3-BE14-00104B62A16C}",ri.Ship],["{4A582741-9839-11d1-B709-00A024DDAFD1}",ri.Vehicle]]),Yi=new Map([[ri.Infantry,ti.Foot],[ri.Ship,ti.Float],[ri.Hover,ti.Hover],[ri.Jumpjet,ti.Winged],[ri.Aircraft,ti.Winged],[ri.Missile,ti.Winged]]);(r=ai=ai||{})[r.Amphibious=0]="Amphibious",r[r.AmphibiousCrusher=1]="AmphibiousCrusher",r[r.AmphibiousDestroyer=2]="AmphibiousDestroyer",r[r.Crusher=3]="Crusher",r[r.CrusherAll=4]="CrusherAll",r[r.Destroyer=5]="Destroyer",r[r.Fly=6]="Fly",r[r.Infantry=7]="Infantry",r[r.InfantryDestroyer=8]="InfantryDestroyer",r[r.Normal=9]="Normal",r[r.Subterranean=10]="Subterranean",r[r.Water=11]="Water",(r=ni=ni||{})[r.None=0]="None",r[r.Flak=1]="Flak",r[r.Plate=2]="Plate",r[r.Light=3]="Light",r[r.Medium=4]="Medium",r[r.Heavy=5]="Heavy",r[r.Wood=6]="Wood",r[r.Steel=7]="Steel",r[r.Concrete=8]="Concrete",r[r.Special_1=9]="Special_1",r[r.Special_2=10]="Special_2",(r=oi=oi||{})[r.LandOk=0]="LandOk",r[r.LandNotOk=1]="LandNotOk",r[r.LandSecondary=2]="LandSecondary",(r=hi=hi||{})[r.UnderwaterNever=0]="UnderwaterNever",r[r.UnderwaterSecondary=1]="UnderwaterSecondary",r[r.UnderwaterOnly=2]="UnderwaterOnly",r[r.OrganicSecondary=3]="OrganicSecondary",r[r.SealSpecial=4]="SealSpecial",r[r.NavalAll=5]="NavalAll",r[r.NavalNone=6]="NavalNone",(r=li=li||{})[r.Primary=0]="Primary",r[r.Secondary=1]="Secondary",r[r.DeathWeapon=2]="DeathWeapon",(r=ci=ci||{})[r.FASTER=0]="FASTER",r[r.STRONGER=1]="STRONGER",r[r.FIREPOWER=2]="FIREPOWER",r[r.SCATTER=3]="SCATTER",r[r.ROF=4]="ROF",r[r.SIGHT=5]="SIGHT",r[r.SELF_HEAL=6]="SELF_HEAL",r[r.CLOAK=7]="CLOAK",r[r.EXPLODES=8]="EXPLODES",r[r.RADAR_INVISIBLE=9]="RADAR_INVISIBLE",r[r.SENSORS=10]="SENSORS",r[r.FEARLESS=11]="FEARLESS",r[r.C4=12]="C4",r[r.GUARD_AREA=13]="GUARD_AREA",r[r.CRUSHER=14]="CRUSHER",(r=ui=ui||{})[r.None=0]="None",r[r.Normal=1]="Normal",r[r.Strong=2]="Strong";class Ki{static reverseSinTableLookup(e,t,i,s){for(;t<=i;){var r=Math.floor((t+i)/2),a=this.SIN_TABLE[r];if(a===e)return r;(s?e<a:a<e)?t=r+1:i=r-1}return Math.abs(e-this.SIN_TABLE[t])<Math.abs(e-this.SIN_TABLE[i])?t:i}static pow(e,t){if(!Number.isFinite(e)||!Number.isFinite(t)||Number.isSafeInteger(e)&&Number.isSafeInteger(t))return e**t;if(!Number.isSafeInteger(t))throw new Error("Exponent must be a safe integer");return Math.floor(e*this.EXP_10_PRECISION)**t/this.EXP_10_PRECISION**t}static sqrt(e){if(0===e)return 0;var t;let i=e/3;for(;t=i,i=(e/i+i)/2,5e-15<Math.abs(t-i););return i}static sin(e){if(!Number.isFinite(e))return NaN;if(!e)return e;e=e/(2*Math.PI)-Math.floor(e/(2*Math.PI)),e=Math.floor(e*this.SIN_TABLE.length);return this.SIN_TABLE[e]}static cos(e){return this.sin(e+Math.PI/2)}static asin(e){if(!V(e,-1,1))return NaN;if(!e)return 0;let t;var i=this.SIN_TABLE.length;return t=0<e?2*Math.PI*this.reverseSinTableLookup(e,0,i/4,!1)/i:Math.PI-2*Math.PI*this.reverseSinTableLookup(e,i/2,.75*i,!0)/i,t}static acos(e){return Math.PI/2-this.asin(e)}static atan2(e,t){if(Number.isNaN(t)||Number.isNaN(e))return NaN;let i;return i=Number.isFinite(e)||Number.isFinite(t)?Number.isFinite(t)&&0!==e?Number.isFinite(e)&&0!==t?this.atan2FiniteNonZero(e,t):this.signIncZero(e)*Math.PI*.5:this.signIncZero(e)*(this.signIncZero(t)<0?Math.PI:0):Math.sign(e)*Math.PI*(0<Math.sign(t)?.25:.75),i}static atan2FiniteNonZero(e,t){var i=Math.abs(t),s=Math.abs(e),r=Math.min(i,s)/Math.max(i,s),a=r*r;let n=((-.0464964749*a+.15931422)*a-.327622764)*a*r+r;return i<s&&(n=Math.PI/2-n),t<0&&(n=Math.PI-n),e<0&&(n=-n),n}static signIncZero(e){return e===-1/0||1/e<0?-1:1}}Ki.PRECISION=6,Ki.EXP_10_PRECISION=10**Ki.PRECISION,Ki.SIN_TABLE=[0,.004848117819001859,.009696121685978396,.014543897651582654,.01939133177182437,.024238310110748135,.0290847187431114,.03393044375706223,.03877537125681671,.043619387365336,.04846237822700296,.05330423001029823,.05814482891047582,.06298406115223795,.06782181299240934,.0726579707226106,.07749242067193093,.08232504920959989,.08715574274765817,.09198438774362744,.09681087070317909,.10163507818280187,.10645689679246824,.11127621319829964,.11609291412523022,.12090688635966935,.12571801675216268,.13052619222005157,.13533129975013108,.14013322640130627,.14493185930724672,.1497270856790396,.15451879280784048,.15930686806752256,.16409119891732396,.1688716729044928,.17364817766693033,.17842060093583212,.18318883053832663,.18795275440011186,.19271226054808968,.19746723711299752,.20221757233203794,.20696315455150538,.2117038722294107,.21643961393810288,.22117026836688775,.2258957243246448,.23061587074244014,.2353305966761376,.24003979130900588,.2447433439543238,.24944114405798126,.25413308120107847,.25881904510252074,.26349892562161076,.2681726127606373,.272839996667461,.27750096763809573,.28215541611928774,.2868032327110902,.29144430816943495,.2960785334086999,.3007057995042731,.3053259976951131,.30993901938630514,.31454475615161365,.31914309973603083,.323733942058321,.328317175213561,.33289269147567657,.3374603832999741,.3420201433256687,.34657186437840753,.3511154394727888,.3556507618148765,.3601777248047104,.36469622203881186,.3692061473126844,.3737073946233105,.3781998581716425,.3826834323650898,.3871580118200006,.3916234913641391,.3960797660391568,.4005267311030606,.4049642820326736,.4093923145260926,.4138107245051391,.4182194081178064,.42261826174069944,.4270071819814715,.4313860656812534,.4357548099170794,.4401133120043048,.44446146949902104,.4487991802004621,.4531263421534082,.4574428536505808,.4617486132350339,.46604351970253877,.4703274721039625,.4746003697476404,.4788621122017435,.4831125992966384,.48735173112724234,.49157940805537054,.49579553071207916,.49999999999999994,.5041927170956704,.5083735834518556,.5125425007998652,.5166993711518628,.5208440968031697,.5249765803345602,.5290967246145525,.5332044328016912,.5372996083468239,.5413821549953696,.5454519767895825,.549508978070806,.5535530634817223,.5575841379685927,.5616021067834929,.5656068754865385,.5695983499481065,.573576436351046,.5775410411928851,.5814920712880266,.5854294337699405,.5893530360933448,.593262786036382,.5971585917027862,.6010403615240428,.6049080042615417,.6087614290087207,.6126005451932028,.6164252625789254,.62023549126826,.6240311417041269,.6278121246720986,.6315783513024975,.6353297330724851,.6390661818081416,.6427876096865393,.6464939292378065,.6501850533471834,.6538608952570697,.6575213685690636,.6611663872459932,.6647958656139378,.6684097183642425,.6720078605555224,.6755902076156601,.6791566753437932,.6827071799122926,.6862416378687335,.6897599661378576,.6932620820235242,.696747903210655,.7002173477671685,.7036703341459059,.7071067811865475,.710526608117521,.713929734557899,.7173160805192894,.7206855664077146,.7240381130254825,.7273736415730487,.7306920736508674,.7339933312612352,.7372773368101241,.7405440131090046,.7437932833766612,.747025071240996,.7502393007408245,.7534358963276606,.7566147828674927,.7597758856425494,.7629191303530553,.766044443118978,.7691517504817651,.7722409794060692,.7753120572814658,.7783649119241599,.7813994715786823,.7844156649195757,.7874134210530723,.7903926695187593,.7933533402912352,.7962953637817558,.7992186708398696,.8021231927550437,.8050088612582783,.8078756085237111,.8107233671702122,.8135520702629676,.8163616513150519,.8191520442889918,.821923183598318,.8246750041091067,.8274074411415104,.8301204304712788,.8328139083312671,.8354878114129364,.8381420768678404,.8407766423091032,.8433914458128856,.845986425919841,.848561521636559,.8511166724369997,.8536518182639162,.8561668995302665,.8586618571206132,.8611366323925137,.8635911671778986,.8660254037844386,.8684392849969005,.870832754078492,.8732057547721958,.8755582313020908,.8778901283746645,.8802013911801111,.8824919653936212,.8847617971766577,.8870108331782216,.8892390205361062,.8914463068781385,.8936326403234122,.8957979694835052,.8979422434636881,.9000654118641211,.9021674247810376,.9042482328079179,.9063077870366499,.9083460390586793,.9103629409661466,.9123584453530141,.9143325053161794,.9162850744565779,.918216106880274,.9201255571995389,.9220133805339185,.9238795325112867,.9257239692688903,.9275466474543786,.9293475242268224,.9311265572577219,.9328837047320004,.9346189253489884,.9363321783233931,.9380234233862578,.9396926207859083,.9413397312888874,.942964716180876,.9445675372676047,.9461481568757504,.947706537853822,.9492426435730339,.9507564379281666,.9522478853384153,.9537169507482269,.955163599628123,.9565877979755122,.9579895123154889,.9593687097016201,.9607253577167205,.9620594244736131,.9633708786158803,.9646596893185995,.9659258262890683,.9671692597675166,.9683899605278059,.969587899878116,.97076304966162,.9719153822571454,.9730448705798238,.9741514880817275,.9752352087524931,.9762960071199334,.9773338582506355,.9783487377505475,.9793406217655515,.980309486982024,.9812553106273847,.9821780704706308,.98307774482286,.9839543125377807,.984807753012208,.9856380461865492,.9864451725452739,.987229113117374,.987989849476809,.9887273637429388,.9894416385809445,.9901326572022359,.9908004033648453,.9914448613738104,.9920660160815423,.9926638528881819,.993238357741943,.9937895171394426,.9943173181260184,.9948217482960331,.9953027957931658,.9957604493106914,.9961946980917455,.9966055319295779,.996992941167792,.9973569167005722,.9976974499728977,.9980145329807433,.9983081582712682,.9985783189429907,.9988250086459504,.9990482215818578,.99924795250423,.9994241967185149,.9995769500822006,.9997062090049132,.9998119704485015,.9998942319271075,.9999529915072262,.9999882478077495,1,.9999882478077495,.9999529915072262,.9998942319271075,.9998119704485015,.9997062090049132,.9995769500822006,.9994241967185149,.99924795250423,.9990482215818578,.9988250086459504,.9985783189429907,.9983081582712682,.9980145329807433,.9976974499728977,.9973569167005722,.996992941167792,.9966055319295779,.9961946980917455,.9957604493106914,.9953027957931658,.9948217482960331,.9943173181260184,.9937895171394426,.993238357741943,.9926638528881819,.9920660160815423,.9914448613738105,.9908004033648453,.9901326572022359,.9894416385809446,.9887273637429388,.987989849476809,.987229113117374,.9864451725452739,.9856380461865492,.984807753012208,.9839543125377807,.98307774482286,.9821780704706307,.9812553106273847,.9803094869820241,.9793406217655516,.9783487377505476,.9773338582506356,.9762960071199334,.9752352087524931,.9741514880817276,.9730448705798238,.9719153822571455,.9707630496616201,.969587899878116,.9683899605278059,.9671692597675166,.9659258262890683,.9646596893185995,.9633708786158803,.9620594244736133,.9607253577167205,.9593687097016202,.9579895123154889,.9565877979755123,.9551635996281231,.9537169507482269,.9522478853384153,.9507564379281666,.949242643573034,.9477065378538221,.9461481568757505,.9445675372676048,.942964716180876,.9413397312888873,.9396926207859084,.9380234233862579,.9363321783233931,.9346189253489885,.9328837047320006,.9311265572577219,.9293475242268225,.9275466474543786,.9257239692688904,.9238795325112867,.9220133805339185,.920125557199539,.918216106880274,.916285074456578,.9143325053161794,.9123584453530141,.9103629409661467,.9083460390586793,.90630778703665,.904248232807918,.9021674247810377,.9000654118641213,.8979422434636883,.8957979694835051,.8936326403234123,.8914463068781386,.8892390205361062,.8870108331782218,.8847617971766579,.8824919653936212,.8802013911801111,.8778901283746644,.8755582313020909,.8732057547721958,.8708327540784921,.8684392849969006,.8660254037844387,.8635911671778987,.8611366323925138,.858661857120613,.8561668995302665,.8536518182639163,.8511166724369997,.8485615216365591,.8459864259198412,.8433914458128856,.8407766423091031,.8381420768678404,.8354878114129364,.8328139083312672,.8301204304712789,.8274074411415107,.8246750041091069,.8219231835983182,.819152044288992,.8163616513150518,.8135520702629675,.8107233671702123,.8078756085237112,.8050088612582784,.802123192755044,.7992186708398695,.7962953637817556,.7933533402912352,.7903926695187593,.7874134210530723,.7844156649195758,.7813994715786824,.7783649119241601,.775312057281466,.7722409794060693,.769151750481765,.766044443118978,.7629191303530551,.7597758856425494,.756614782867493,.7534358963276608,.7502393007408243,.7470250712409959,.7437932833766611,.7405440131090045,.7372773368101241,.7339933312612353,.7306920736508675,.7273736415730488,.7240381130254827,.7206855664077148,.7173160805192896,.713929734557899,.710526608117521,.7071067811865476,.703670334145906,.7002173477671687,.6967479032106549,.6932620820235241,.6897599661378576,.6862416378687336,.6827071799122926,.6791566753437933,.6755902076156604,.6720078605555225,.6684097183642426,.6647958656139381,.6611663872459935,.6575213685690636,.6538608952570697,.6501850533471835,.6464939292378067,.6427876096865395,.6390661818081418,.635329733072485,.6315783513024975,.6278121246720986,.6240311417041269,.6202354912682602,.6164252625789255,.612600545193203,.6087614290087209,.6049080042615419,.6010403615240432,.5971585917027862,.593262786036382,.5893530360933449,.5854294337699406,.5814920712880268,.5775410411928852,.5735764363510459,.5695983499481064,.5656068754865385,.5616021067834929,.5575841379685929,.5535530634817224,.5495089780708062,.5454519767895827,.5413821549953699,.5372996083468241,.5332044328016912,.5290967246145525,.5249765803345602,.5208440968031698,.516699371151863,.5125425007998654,.5083735834518555,.5041927170956703,.49999999999999994,.49579553071207916,.49157940805537065,.48735173112724245,.48311259929663863,.4788621122017437,.47460036974764064,.47032747210396275,.46604351970253877,.4617486132350339,.45744285365058085,.4531263421534083,.44879918020046233,.4444614694990212,.4401133120043047,.43575480991707927,.43138606568125343,.4270071819814714,.4226182617406995,.4182194081178065,.4138107245051393,.40939231452609276,.4049642820326738,.40052673110306086,.3960797660391572,.39162349136413904,.38715801182000065,.3826834323650899,.37819985817164264,.3737073946233107,.3692061473126843,.36469622203881175,.3601777248047104,.3556507618148765,.35111543947278884,.34657186437840765,.3420201433256689,.3374603832999743,.33289269147567685,.32831717521356135,.3237339420583214,.31914309973603083,.3145447561516137,.30993901938630525,.30532599769511326,.30070579950427334,.29607853340870016,.2914443081694349,.2868032327110902,.28215541611928774,.2775009676380958,.2728399966674611,.26817261276063753,.263498925621611,.258819045102521,.2541330812010788,.24944114405798165,.24474334395432376,.24003979130900596,.2353305966761377,.23061587074244033,.225895724324645,.22117026836688802,.21643961393810274,.21170387222941067,.20696315455150538,.20221757233203796,.19746723711299763,.19271226054808982,.18795275440011205,.18318883053832688,.17842060093583242,.17364817766693072,.16887167290449276,.16409119891732402,.15930686806752267,.15451879280784062,.1497270856790398,.14493185930724697,.14013322640130613,.135331299750131,.13052619222005157,.12571801675216274,.12090688635966945,.11609291412523036,.11127621319829985,.1064568967924685,.10163507818280217,.09681087070317945,.09198438774362741,.0871557427476582,.08232504920959997,.07749242067193107,.07265797072261079,.0678218129924096,.06298406115223781,.05814482891047573,.0533042300102982,.04846237822700297,.04361938736533607,.038775371256816835,.03393044375706242,.029084718743111644,.02423831011074843,.01939133177182472,.014543897651583058,.009696121685978408,.004848117819001927,12246467991473532e-32,-.004848117819001238,-.009696121685978163,-.01454389765158237,-.019391331771824474,-.02423831011074774,-.029084718743111398,-.03393044375706173,-.03877537125681659,-.04361938736533583,-.048462378227003174,-.05330423001029795,-.05814482891047593,-.06298406115223758,-.06782181299240934,-.07265797072261056,-.07749242067193128,-.08232504920959974,-.08715574274765794,-.09198438774362716,-.09681087070317876,-.10163507818280193,-.10645689679246781,-.1112762131982996,-.11609291412523012,-.12090688635966965,-.1257180167521625,-.13052619222005177,-.13533129975013078,-.14013322640130632,-.14493185930724675,-.14972708567904,-.1545187928078404,-.15930686806752198,-.16409119891732377,-.16887167290449254,-.17364817766693047,-.17842060093583176,-.18318883053832663,-.1879527544001114,-.1927122605480896,-.19746723711299738,-.20221757233203816,-.20696315455150513,-.21170387222941087,-.21643961393810252,-.2211702683668878,-.22589572432464475,-.23061587074244053,-.23533059667613745,-.2400397913090053,-.2447433439543235,-.24944114405798098,-.2541330812010786,-.25881904510252035,-.2634989256216107,-.26817261276063686,-.2728399966674609,-.27750096763809556,-.2821554161192879,-.28680323271108993,-.29144430816943506,-.29607853340869994,-.30070579950427306,-.30532599769511304,-.3099390193863046,-.3145447561516135,-.3191430997360306,-.3237339420583211,-.3283171752135607,-.33289269147567657,-.3374603832999737,-.34202014332566866,-.3465718643784074,-.35111543947278906,-.35565076181487626,-.36017772480471055,-.3646962220388115,-.3692061473126845,-.3737073946233105,-.3781998581716428,-.38268343236508967,-.38715801182000004,-.3916234913641388,-.39607976603915657,-.40052673110306064,-.4049642820326732,-.40939231452609254,-.41381072450513867,-.4182194081178062,-.4226182617406993,-.4270071819814716,-.4313860656812532,-.43575480991707943,-.4401133120043045,-.444461469499021,-.4487991802004621,-.4531263421534085,-.4574428536505806,-.46174861323503374,-.46604351970253854,-.47032747210396214,-.4746003697476404,-.47886211220174313,-.4831125992966384,-.4873517311272422,-.4915794080553708,-.49579553071207894,-.5000000000000001,-.50419271709567,-.5083735834518556,-.5125425007998652,-.5166993711518633,-.5208440968031696,-.5249765803345596,-.5290967246145523,-.533204432801691,-.5372996083468239,-.5413821549953693,-.5454519767895825,-.5495089780708056,-.5535530634817222,-.5575841379685926,-.5616021067834931,-.5656068754865384,-.5695983499481065,-.5735764363510458,-.577541041192885,-.5814920712880266,-.5854294337699408,-.5893530360933448,-.5932627860363815,-.597158591702786,-.6010403615240426,-.6049080042615417,-.6087614290087203,-.6126005451932028,-.6164252625789249,-.6202354912682599,-.6240311417041268,-.6278121246720987,-.6315783513024973,-.6353297330724852,-.6390661818081416,-.6427876096865393,-.6464939292378065,-.6501850533471829,-.6538608952570695,-.6575213685690635,-.6611663872459933,-.6647958656139376,-.6684097183642425,-.6720078605555221,-.6755902076156601,-.6791566753437931,-.6827071799122927,-.6862416378687334,-.6897599661378577,-.693262082023524,-.696747903210655,-.7002173477671685,-.7036703341459061,-.7071067811865475,-.7105266081175206,-.7139297345578989,-.7173160805192892,-.7206855664077146,-.7240381130254823,-.7273736415730487,-.7306920736508671,-.7339933312612352,-.737277336810124,-.7405440131090048,-.743793283376661,-.747025071240996,-.7502393007408242,-.7534358963276607,-.7566147828674927,-.7597758856425493,-.7629191303530554,-.7660444431189779,-.7691517504817651,-.7722409794060688,-.7753120572814659,-.7783649119241597,-.7813994715786822,-.7844156649195754,-.7874134210530722,-.7903926695187589,-.7933533402912349,-.7962953637817558,-.79921867083987,-.8021231927550437,-.8050088612582785,-.8078756085237111,-.8107233671702119,-.8135520702629674,-.8163616513150515,-.8191520442889916,-.8219231835983181,-.8246750041091064,-.8274074411415104,-.830120430471279,-.8328139083312671,-.8354878114129365,-.8381420768678401,-.8407766423091032,-.8433914458128855,-.8459864259198411,-.8485615216365587,-.8511166724369996,-.8536518182639165,-.8561668995302664,-.8586618571206132,-.8611366323925135,-.8635911671778986,-.8660254037844385,-.8684392849969005,-.8708327540784918,-.8732057547721956,-.8755582313020905,-.8778901283746643,-.8802013911801112,-.8824919653936215,-.8847617971766578,-.8870108331782218,-.889239020536106,-.8914463068781383,-.8936326403234122,-.8957979694835049,-.897942243463688,-.9000654118641208,-.9021674247810375,-.9042482328079179,-.90630778703665,-.9083460390586792,-.9103629409661468,-.912358445353014,-.9143325053161795,-.9162850744565778,-.918216106880274,-.9201255571995388,-.9220133805339183,-.9238795325112865,-.9257239692688903,-.9275466474543786,-.9293475242268223,-.9311265572577219,-.9328837047320003,-.9346189253489884,-.9363321783233929,-.9380234233862578,-.9396926207859082,-.9413397312888873,-.9429647161808761,-.9445675372676049,-.9461481568757504,-.9477065378538222,-.9492426435730339,-.9507564379281666,-.9522478853384153,-.9537169507482267,-.9551635996281229,-.956587797975512,-.9579895123154888,-.9593687097016201,-.9607253577167205,-.9620594244736131,-.9633708786158804,-.9646596893185994,-.9659258262890683,-.9671692597675166,-.9683899605278059,-.9695878998781159,-.97076304966162,-.9719153822571452,-.9730448705798238,-.9741514880817276,-.975235208752493,-.9762960071199334,-.9773338582506355,-.9783487377505475,-.9793406217655514,-.980309486982024,-.9812553106273846,-.9821780704706307,-.98307774482286,-.9839543125377805,-.984807753012208,-.9856380461865493,-.9864451725452739,-.9872291131173742,-.9879898494768089,-.9887273637429387,-.9894416385809445,-.9901326572022358,-.9908004033648452,-.9914448613738104,-.9920660160815423,-.9926638528881818,-.993238357741943,-.9937895171394426,-.9943173181260184,-.994821748296033,-.9953027957931658,-.9957604493106913,-.9961946980917455,-.9966055319295779,-.996992941167792,-.9973569167005722,-.9976974499728977,-.9980145329807433,-.9983081582712682,-.9985783189429907,-.9988250086459504,-.9990482215818578,-.99924795250423,-.9994241967185149,-.9995769500822006,-.9997062090049132,-.9998119704485015,-.9998942319271076,-.9999529915072262,-.9999882478077495,-1,-.9999882478077495,-.9999529915072262,-.9998942319271076,-.9998119704485015,-.9997062090049132,-.9995769500822006,-.9994241967185149,-.99924795250423,-.9990482215818578,-.9988250086459504,-.9985783189429907,-.9983081582712682,-.9980145329807433,-.9976974499728977,-.9973569167005724,-.996992941167792,-.9966055319295779,-.9961946980917455,-.9957604493106914,-.9953027957931658,-.9948217482960331,-.9943173181260185,-.9937895171394426,-.993238357741943,-.9926638528881819,-.9920660160815424,-.9914448613738105,-.9908004033648453,-.9901326572022358,-.9894416385809446,-.9887273637429387,-.987989849476809,-.9872291131173742,-.986445172545274,-.9856380461865493,-.9848077530122081,-.9839543125377807,-.9830777448228601,-.9821780704706308,-.9812553106273846,-.9803094869820241,-.9793406217655515,-.9783487377505476,-.9773338582506355,-.9762960071199335,-.9752352087524931,-.9741514880817276,-.9730448705798239,-.9719153822571454,-.9707630496616201,-.969587899878116,-.968389960527806,-.9671692597675167,-.9659258262890684,-.9646596893185995,-.9633708786158806,-.9620594244736133,-.9607253577167206,-.9593687097016202,-.9579895123154889,-.9565877979755121,-.955163599628123,-.9537169507482268,-.9522478853384154,-.9507564379281668,-.949242643573034,-.9477065378538223,-.9461481568757506,-.944567537267605,-.9429647161808762,-.9413397312888874,-.9396926207859083,-.9380234233862579,-.936332178323393,-.9346189253489885,-.9328837047320004,-.9311265572577221,-.9293475242268224,-.9275466474543788,-.9257239692688904,-.9238795325112866,-.9220133805339186,-.9201255571995389,-.9182161068802742,-.9162850744565779,-.9143325053161796,-.9123584453530141,-.9103629409661469,-.9083460390586794,-.9063077870366503,-.9042482328079181,-.9021674247810376,-.9000654118641209,-.8979422434636882,-.895797969483505,-.8936326403234123,-.8914463068781384,-.8892390205361063,-.887010833178222,-.8847617971766579,-.8824919653936216,-.8802013911801113,-.8778901283746645,-.8755582313020907,-.8732057547721959,-.870832754078492,-.8684392849969007,-.8660254037844386,-.8635911671778989,-.8611366323925137,-.8586618571206134,-.8561668995302666,-.8536518182639167,-.8511166724369998,-.848561521636559,-.8459864259198413,-.8433914458128857,-.8407766423091034,-.8381420768678404,-.8354878114129367,-.8328139083312672,-.8301204304712791,-.8274074411415107,-.8246750041091067,-.8219231835983183,-.8191520442889918,-.8163616513150517,-.8135520702629676,-.8107233671702121,-.8078756085237113,-.8050088612582788,-.802123192755044,-.7992186708398701,-.796295363781756,-.7933533402912352,-.7903926695187591,-.7874134210530724,-.7844156649195756,-.7813994715786825,-.7783649119241599,-.7753120572814661,-.7722409794060691,-.7691517504817653,-.7660444431189781,-.7629191303530556,-.7597758856425495,-.7566147828674927,-.753435896327661,-.7502393007408246,-.7470250712409963,-.7437932833766612,-.740544013109005,-.7372773368101242,-.7339933312612357,-.7306920736508676,-.7273736415730492,-.7240381130254828,-.7206855664077145,-.7173160805192891,-.7139297345578991,-.7105266081175208,-.7071067811865477,-.7036703341459063,-.7002173477671687,-.6967479032106556,-.6932620820235246,-.6897599661378577,-.6862416378687334,-.6827071799122926,-.679156675343793,-.6755902076156605,-.6720078605555223,-.6684097183642427,-.6647958656139378,-.6611663872459935,-.6575213685690637,-.6538608952570701,-.6501850533471836,-.6464939292378064,-.6427876096865396,-.6390661818081416,-.6353297330724854,-.6315783513024976,-.627812124672099,-.624031141704127,-.6202354912682606,-.6164252625789255,-.6126005451932034,-.6087614290087209,-.6049080042615417,-.6010403615240425,-.5971585917027863,-.5932627860363818,-.589353036093345,-.585429433769941,-.5814920712880269,-.5775410411928856,-.5735764363510465,-.5695983499481065,-.5656068754865391,-.561602106783493,-.5575841379685926,-.5535530634817225,-.5495089780708059,-.5454519767895828,-.5413821549953696,-.5372996083468242,-.5332044328016913,-.5290967246145529,-.5249765803345603,-.5208440968031696,-.5166993711518632,-.5125425007998651,-.5083735834518559,-.5041927170956704,-.5000000000000004,-.49579553071207927,-.49157940805537115,-.48735173112724256,-.48311259929663913,-.4788621122017438,-.47460036974764036,-.4703274721039621,-.4660435197025389,-.46174861323503363,-.45744285365058096,-.4531263421534088,-.44879918020046244,-.4444614694990217,-.4401133120043052,-.43575480991708015,-.4313860656812539,-.42700718198147153,-.4226182617406992,-.4182194081178066,-.413810724505139,-.40939231452609287,-.40496428203267354,-.400526731103061,-.3960797660391569,-.39162349136413954,-.38715801182000076,-.3826834323650904,-.37819985817164276,-.3737073946233104,-.3692061473126848,-.36469622203881186,-.3601777248047109,-.3556507618148766,-.3511154394727894,-.34657186437840776,-.34202014332566943,-.3374603832999744,-.3328926914756765,-.32831717521356063,-.32373394205832107,-.31914309973603056,-.3145447561516138,-.3099390193863049,-.30532599769511337,-.30070579950427384,-.2960785334087003,-.29144430816943584,-.2868032327110907,-.28215541611928785,-.2775009676380955,-.2728399966674612,-.2681726127606372,-.2634989256216111,-.2588190451025207,-.2541330812010789,-.24944114405798135,-.24474334395432432,-.24003979130900607,-.23533059667613823,-.23061587074244044,-.2258957243246447,-.22117026836688813,-.21643961393810288,-.21170387222941123,-.2069631545515055,-.20221757233203852,-.19746723711299774,-.19271226054809037,-.1879527544001122,-.18318883053832655,-.17842060093583256,-.1736481776669304,-.16887167290449245,-.16409119891732413,-.15930686806752234,-.15451879280784075,-.14972708567904036,-.1449318593072471,-.14013322640130713,-.13533129975013158,-.13052619222005168,-.1257180167521624,-.12090688635966958,-.11609291412523004,-.11127621319829996,-.10645689679246818,-.10163507818280229,-.09681087070317913,-.09198438774362797,-.08715574274765832,-.08232504920960054,-.0774924206719312,-.07265797072261047,-.06782181299240972,-.06298406115223794,-.0581448289104763,-.05330423001029832,-.04846237822700354,-.043619387365336194,-.038775371256817404,-.03393044375706254,-.02908471874311221,-.02423831011074855,-.019391331771824397,-.014543897651582293,-.009696121685978531,-.004848117819001606];r=__webpack_require__(949);class Ji extends r.Quaternion{setFromEuler(e,t){if(!e||!e.isEuler)throw new Error("THREE.Quaternion: .setFromEuler() now expects an Euler rotation rather than a Vector3 and order.");var i=e.x,s=e.y,r=e.z,a=e.order,n=Ki.cos(i/2),o=Ki.cos(s/2),e=Ki.cos(r/2),i=Ki.sin(i/2),s=Ki.sin(s/2),r=Ki.sin(r/2);return"XYZ"===a?(this._x=i*o*e+n*s*r,this._y=n*s*e-i*o*r,this._z=n*o*r+i*s*e,this._w=n*o*e-i*s*r):"YXZ"===a?(this._x=i*o*e+n*s*r,this._y=n*s*e-i*o*r,this._z=n*o*r-i*s*e,this._w=n*o*e+i*s*r):"ZXY"===a?(this._x=i*o*e-n*s*r,this._y=n*s*e+i*o*r,this._z=n*o*r+i*s*e,this._w=n*o*e-i*s*r):"ZYX"===a?(this._x=i*o*e-n*s*r,this._y=n*s*e+i*o*r,this._z=n*o*r-i*s*e,this._w=n*o*e+i*s*r):"YZX"===a?(this._x=i*o*e+n*s*r,this._y=n*s*e+i*o*r,this._z=n*o*r-i*s*e,this._w=n*o*e-i*s*r):"XZY"===a&&(this._x=i*o*e-n*s*r,this._y=n*s*e-i*o*r,this._z=n*o*r+i*s*e,this._w=n*o*e+i*s*r),!1!==t&&this.onChangeCallback(),this}setFromAxisAngle(e,t){var i=t/2,t=Ki.sin(i);return this._x=e.x*t,this._y=e.y*t,this._z=e.z*t,this._w=Ki.cos(i),this.onChangeCallback(),this}setFromRotationMatrix(e){let t=e.elements,i=t[0],s=t[4],r=t[8],a=t[1],n=t[5],o=t[9],h=t[2],l=t[6],c=t[10],u=i+n+c,d;return 0<u?(d=.5/Ki.sqrt(u+1),this._w=.25/d,this._x=(l-o)*d,this._y=(r-h)*d,this._z=(a-s)*d):n<i&&c<i?(d=2*Ki.sqrt(1+i-n-c),this._w=(l-o)/d,this._x=.25*d,this._y=(s+a)/d,this._z=(r+h)/d):c<n?(d=2*Ki.sqrt(1+n-i-c),this._w=(r-h)/d,this._x=(s+a)/d,this._y=.25*d,this._z=(o+l)/d):(d=2*Ki.sqrt(1+c-i-n),this._w=(a-s)/d,this._x=(r+h)/d,this._y=(o+l)/d,this._z=.25*d),this.onChangeCallback(),this}length(){return Ki.sqrt(this._x*this._x+this._y*this._y+this._z*this._z+this._w*this._w)}slerp(e,t){if(0===t)return this;if(1===t)return this.copy(e);var i=this._x,s=this._y,r=this._z,a=this._w;let n=a*e._w+i*e._x+s*e._y+r*e._z;if(n<0?(this._w=-e._w,this._x=-e._x,this._y=-e._y,this._z=-e._z,n=-n):this.copy(e),1<=n)return this._w=a,this._x=i,this._y=s,this._z=r,this;var o=1-n*n;if(o<=Number.EPSILON){var h=1-t;return this._w=h*a+t*this._w,this._x=h*i+t*this._x,this._y=h*s+t*this._y,this._z=h*r+t*this._z,this.normalize()}e=Ki.sqrt(o),h=Ki.atan2(e,n),o=Ki.sin((1-t)*h)/e,e=Ki.sin(t*h)/e;return this._w=a*o+this._w*e,this._x=i*o+this._x*e,this._y=s*o+this._y*e,this._z=r*o+this._z*e,this.onChangeCallback(),this}}var es,ts,is,ss,rs,r=__webpack_require__(949);class as extends r.Vector3{applyEuler(e){return e&&e.isEuler||console.error("THREE.Vector3: .applyEuler() now expects an Euler rotation rather than a Vector3 and order."),this.applyQuaternion(ns.setFromEuler(e))}applyAxisAngle(e,t){return this.applyQuaternion(ns.setFromAxisAngle(e,t))}length(){return Ki.sqrt(this.x*this.x+this.y*this.y+this.z*this.z)}projectOnPlane(e){return os.copy(this).projectOnVector(e),this.sub(os)}reflect(e){return this.sub(os.copy(e).multiplyScalar(2*this.dot(e)))}angleTo(e){e=this.dot(e)/Ki.sqrt(this.lengthSq()*e.lengthSq());return Ki.acos(z(e,-1,1))}distanceTo(e){return Ki.sqrt(this.distanceToSquared(e))}setFromSpherical(e){var t=Ki.sin(e.phi)*e.radius;return this.x=t*Ki.sin(e.theta),this.y=Ki.cos(e.phi)*e.radius,this.z=t*Ki.cos(e.theta),this}setFromCylindrical(e){return this.x=e.radius*Ki.sin(e.theta),this.y=e.y,this.z=e.radius*Ki.cos(e.theta),this}}const ns=new Ji,os=new as;(r=es=es||{})[r.Combat=0]="Combat",r[r.Tech=1]="Tech",r[r.Resource=2]="Resource",r[r.Power=3]="Power",(r=ts=ts||{})[r.None=0]="None",r[r.BuildingType=1]="BuildingType",r[r.InfantryType=2]="InfantryType",r[r.UnitType=3]="UnitType",r[r.NavalUnitType=4]="NavalUnitType",r[r.AircraftType=5]="AircraftType";class hs extends Ai{constructor(e,t,i,s){super(e,t,i,s)}parse(){super.parse(),this.owner=this.ini.getArray("Owner");var e=this.ini.getNumber("AIBasePlanningSide");this.aiBasePlanningSide=-1!==e&&void 0!==Qt[e]?e:void 0,this.requiredHouses=this.ini.getArray("RequiredHouses"),this.forbiddenHouses=this.ini.getArray("ForbiddenHouses"),this.requiresStolenAlliedTech=this.ini.getBool("RequiresStolenAlliedTech"),this.requiresStolenSovietTech=this.ini.getBool("RequiresStolenSovietTech"),this.techLevel=this.ini.getNumber("TechLevel",-1),this.cost=this.ini.getNumber("Cost"),this.points=this.ini.getNumber("Points"),this.power=this.ini.getNumber("Power"),this.powered=this.ini.getBool("Powered"),this.prerequisite=this.ini.getArray("Prerequisite"),this.prerequisiteOverride=this.ini.getArray("PrerequisiteOverride"),this.soylent=this.ini.getNumber("Soylent"),this.crateGoodie=this.ini.getBool("CrateGoodie"),this.buildCat=this.ini.getEnum("BuildCat",es,es.Combat),this.adjacent=this.ini.getNumber("Adjacent",1),this.baseNormal=this.ini.getBool("BaseNormal",!0),this.buildLimit=this.ini.getNumber("BuildLimit",Number.POSITIVE_INFINITY),this.airRangeBonus=this.ini.getNumber("AirRangeBonus"),this.guardRange=this.ini.getNumber("GuardRange"),this.defaultToGuardArea=this.ini.getBool("DefaultToGuardArea"),this.eligibileForAllyBuilding=this.ini.getBool("EligibileForAllyBuilding"),this.numberImpassableRows=this.ini.getNumber("NumberImpassableRows"),this.bridgeRepairHut=this.ini.getBool("BridgeRepairHut"),this.constructionYard=this.ini.getBool("ConstructionYard"),this.refinery=this.ini.getBool("Refinery"),this.unitRepair=this.ini.getBool("UnitRepair"),this.unitReload=this.ini.getBool("UnitReload"),this.unitSell=this.ini.getBool("UnitSell"),this.isBaseDefense=this.ini.getBool("IsBaseDefense"),this.superWeapon=this.parseWeaponName(this.ini.getString("SuperWeapon")),this.chargedAnimTime=this.ini.getNumber("ChargedAnimTime");var t=this.ini.getBool("Naval");this.naval=t,this.underwater=this.ini.getBool("Underwater"),this.waterBound=this.ini.getBool("WaterBound"),this.orePurifier=this.ini.getBool("OrePurifier"),this.cloning=this.ini.getBool("Cloning"),this.grinding=this.ini.getBool("Grinding"),this.nukeSilo=this.ini.getBool("NukeSilo"),this.repairable=this.ini.getBool("Repairable",this.type===Et.Building),this.clickRepairable=this.ini.getBool("ClickRepairable",this.type===Et.Building),this.unsellable=this.ini.getBool("Unsellable",this.type!==Et.Building&&this.generalRules.unitsUnsellable),this.returnable=this.ini.getBool("Returnable",this.generalRules.returnStructures),this.gdiBarracks=this.ini.getBool("GDIBarracks"),this.nodBarracks=this.ini.getBool("NODBarracks"),this.numberOfDocks=this.ini.getNumber("NumberOfDocks"),this.unitRepair&&!this.numberOfDocks&&(this.numberOfDocks=1),this.factory=this.ini.getEnum("Factory",ts,ts.None),this.factory===ts.UnitType&&t&&(this.factory=ts.NavalUnitType),this.weaponsFactory=this.ini.getBool("WeaponsFactory"),this.helipad=this.ini.getBool("Helipad"),this.hospital=this.ini.getBool("Hospital"),this.landTargeting=this.ini.getEnumNumeric("LandTargeting",oi,oi.LandOk),this.navalTargeting=this.ini.getEnumNumeric("NavalTargeting",hi,hi.UnderwaterNever),this.tooBigToFitUnderBridge=this.ini.getBool("TooBigToFitUnderBridge",this.type===Et.Building),this.canBeOccupied=this.ini.getBool("CanBeOccupied"),this.maxNumberOccupants=this.ini.getNumber("MaxNumberOccupants"),this.leaveRubble=this.ini.getBool("LeaveRubble"),this.undeploysInto=this.ini.getString("UndeploysInto"),this.deploysInto=this.ini.getString("DeploysInto"),this.deployTime=this.ini.getNumber("DeployTime"),this.capturable=this.ini.getBool("Capturable"),this.spyable=this.ini.getBool("Spyable"),this.needsEngineer=this.ini.getBool("NeedsEngineer"),this.c4=this.ini.getBool("C4"),this.canC4=this.ini.getBool("CanC4",!0),this.eligibleForDelayKill=this.ini.getBool("EligibleForDelayKill"),this.produceCashStartup=this.ini.getNumber("ProduceCashStartup"),this.produceCashAmount=this.ini.getNumber("ProduceCashAmount"),this.produceCashDelay=this.ini.getNumber("ProduceCashDelay"),this.explosion=this.ini.getArray("Explosion"),this.explodes=this.ini.getBool("Explodes"),this.ifvMode=this.ini.getNumber("IFVMode"),this.turretIndexesByIfvMode=this.parseTurretIndexes(),this.turret=this.ini.getBool("Turret"),this.turretCount=this.ini.getNumber("TurretCount",this.turret?1:0),this.turretAnim=this.ini.getString("TurretAnim"),this.turretAnimIsVoxel=this.ini.getBool("TurretAnimIsVoxel"),this.turretAnimX=this.ini.getNumber("TurretAnimX"),this.turretAnimY=this.ini.getNumber("TurretAnimY"),this.turretAnimZAdjust=this.ini.getNumber("TurretAnimZAdjust"),this.isChargeTurret=this.ini.getBool("IsChargeTurret"),this.overpowerable=this.ini.getBool("Overpowerable"),this.freeUnit=this.ini.getString("FreeUnit"),this.primary=this.parseWeaponName(this.ini.getString("Primary")),this.secondary=this.parseWeaponName(this.ini.getString("Secondary")),this.elitePrimary=this.parseWeaponName(this.ini.getString("ElitePrimary")),this.eliteSecondary=this.parseWeaponName(this.ini.getString("EliteSecondary")),this.weaponCount=this.ini.getNumber("WeaponCount"),this.deathWeapon=this.parseWeaponName(this.ini.getString("DeathWeapon")),this.deathWeaponDamageModifier=this.ini.getNumber("DeathWeaponDamageModifier",1),this.occupyWeapon=this.parseWeaponName(this.ini.getString("OccupyWeapon")),this.eliteOccupyWeapon=this.parseWeaponName(this.ini.getString("EliteOccupyWeapon")),this.veteranAbilities=new Set(this.ini.getEnumArray("VeteranAbilities",ci)),this.eliteAbilities=new Set([...this.veteranAbilities,...this.ini.getEnumArray("EliteAbilities",ci)]),this.selfHealing=this.ini.getBool("SelfHealing"),this.wall=this.ini.getBool("Wall"),this.gate=this.ini.getBool("Gate"),this.armor=this.ini.getEnum("Armor",ni,ni.None,!0),this.strength=Math.floor(this.ini.getNumber("Strength")),this.immune=this.ini.getBool("Immune"),this.immuneToRadiation=this.ini.getBool("ImmuneToRadiation"),this.immuneToPsionics=this.ini.getBool("ImmuneToPsionics"),this.typeImmune=this.ini.getBool("TypeImmune"),this.warpable=this.ini.getBool("Warpable",!0),this.isTilter=this.ini.getBool("IsTilter",!0),this.walkRate=this.ini.getNumber("WalkRate",1),this.idleRate=this.ini.getNumber("IdleRate",0),this.noSpawnAlt=this.ini.getBool("NoSpawnAlt"),this.crusher=this.ini.getBool("Crusher"),this.consideredAircraft=this.ini.getBool("ConsideredAircraft"),this.crashable=this.ini.getBool("Crashable");var i=this.ini.getBool("Landable");this.landable=i,this.airportBound=this.ini.getBool("AirportBound"),this.balloonHover=this.ini.getBool("BalloonHover"),this.hoverAttack=this.ini.getBool("HoverAttack"),this.omniFire=this.ini.getBool("OmniFire"),this.fighter=this.ini.getBool("Fighter"),this.flightLevel=this.ini.getNumber("FlightLevel")||void 0;var s=this.ini.getString("Locomotor"),e=this.type===Et.Building?ri.Statue:ri.Chrono;if(s?(t=Qi.get(s))?this.locomotor=t:(console.warn(`Object rules "${this.name}" has invalid Locomotor "${s}"`),this.locomotor=e):this.locomotor=e,this.locomotor!==ri.Statue){let e=Yi.get(this.locomotor);void 0===e&&(this.type===Et.Aircraft||this.consideredAircraft?e=ti.Winged:this.type===Et.Vehicle?e=this.crusher?ti.Track:ti.Wheel:this.type===Et.Infantry&&(e=ti.Foot)),this.speedType=this.ini.getEnum("SpeedType",ti,e,!0)}e=[ri.Ship,ri.Vehicle,ri.Chrono].includes(this.locomotor)?65:100;this.speed=Ai.iniSpeedToLeptonsPerTick(this.ini.getNumber("Speed"),e),this.movementZone=this.ini.getEnum("MovementZone",ai,ai.Normal),this.fearless=this.ini.getBool("Fearless"),this.deployer=this.ini.getBool("Deployer"),this.deployFire=this.ini.getBool("DeployFire"),this.deployFireWeapon=this.ini.getNumber("DeployFireWeapon",li.Secondary),this.undeployDelay=this.ini.getNumber("UndeployDelay"),this.fraidycat=this.ini.getBool("Fraidycat",!1),this.isHuman=!this.ini.getBool("NotHuman"),this.organic=this.type===Et.Infantry||this.ini.getBool("Organic"),this.occupier=this.ini.getBool("Occupier"),this.engineer=this.ini.getBool("Engineer"),this.ivan=this.ini.getBool("Ivan"),this.civilian=this.ini.getBool("Civilian"),this.agent=this.ini.getBool("Agent"),this.infiltrate=this.ini.getBool("Infiltrate"),this.threatPosed=this.ini.getNumber("ThreatPosed"),this.specialThreatValue=this.ini.getNumber("SpecialThreatValue"),this.canPassiveAquire=this.ini.getBool("CanPassiveAquire",!0),this.canRetaliate=this.ini.getBool("CanRetaliate",!0),this.preventAttackMove=this.ini.getBool("PreventAttackMove"),this.opportunityFire=this.ini.getBool("OpportunityFire"),this.distributedFire=this.ini.getBool("DistributedFire"),this.radialFireSegments=this.ini.getNumber("RadialFireSegments"),this.attackCursorOnFriendlies=this.ini.getBool("AttackCursorOnFriendlies"),this.bombable=this.ini.getBool("Bombable",!0),this.trainable=this.ini.getBool("Trainable",this.type!==Et.Building),this.crewed=this.ini.getBool("Crewed"),this.parasiteable=this.ini.getBool("Parasiteable",this.type!==Et.Building),this.suppressionThreshold=this.ini.getNumber("SuppressionThreshold"),this.reselectIfLimboed=this.ini.getBool("ReselectIfLimboed"),this.rejoinTeamIfLimboed=this.ini.getBool("RejoinTeamIfLimboed"),this.weight=this.ini.getNumber("Weight"),this.accelerates=this.ini.getBool("Accelerates",!0),this.accelerationFactor=this.ini.getNumber("AccelerationFactor",.03),this.teleporter=this.ini.getBool("Teleporter"),this.canDisguise=this.ini.getBool("CanDisguise"),this.disguiseWhenStill=this.ini.getBool("DisguiseWhenStill"),this.permaDisguise=this.ini.getBool("PermaDisguise"),this.detectDisguise=this.ini.getBool("DetectDisguise"),this.detectDisguiseRange=this.ini.getNumber("DetectDisguiseRange"),this.cloakable=this.ini.getBool("Cloakable"),this.sensors=this.ini.getBool("Sensors"),this.sensorArray=this.ini.getBool("SensorArray"),this.sensorsSight=this.ini.getNumber("SensorsSight"),this.burstDelay=this.parseBurstDelay(),this.vhpScan=this.ini.getEnum("VHPScan",ui,ui.None,!0),this.pip=this.ini.getEnum("Pip",si,si.Green,!0),this.passengers=this.ini.getNumber("Passengers"),this.gunner=this.ini.getBool("Gunner"),this.ammo=this.ini.getNumber("Ammo",-1),this.initialAmmo=this.ini.getNumber("InitialAmmo",-1),this.manualReload=this.ini.getBool("ManualReload",this.type===Et.Aircraft),this.storage=this.ini.getNumber("Storage"),this.spawned=this.ini.getBool("Spawned"),this.spawns=this.ini.getString("Spawns"),this.spawnsNumber=this.ini.getNumber("SpawnsNumber"),this.spawnRegenRate=this.ini.getNumber("SpawnRegenRate"),this.spawnReloadRate=this.ini.getNumber("SpawnReloadRate"),this.missileSpawn=this.ini.getBool("MissileSpawn"),this.size=this.ini.getNumber("Size",1),this.sizeLimit=this.ini.getNumber("SizeLimit"),this.sight=Math.min(hs.MAX_SIGHT,this.needsEngineer?6:this.ini.getNumber("Sight",1)),this.spySat=this.ini.getBool("SpySat"),this.gapGenerator=this.ini.getBool("GapGenerator"),this.gapRadiusInCells=this.ini.getNumber("GapRadiusInCells"),this.psychicDetectionRadius=this.ini.getNumber("PsychicDetectionRadius"),this.hasRadialIndicator=this.ini.getBool("HasRadialIndicator"),this.harvester=this.ini.getBool("Harvester"),this.unloadingClass=this.ini.getString("UnloadingClass"),this.dock=this.ini.getArray("Dock"),this.radar=this.ini.getBool("Radar"),this.radarInvisible=this.ini.getBool("RadarInvisible"),this.revealToAll=this.ini.getBool("RevealToAll"),this.selectable=!(this.type===Et.Aircraft&&!i)&&this.ini.getBool("Selectable",!0),this.isSelectableCombatant=this.ini.getBool("IsSelectableCombatant"),this.invisibleInGame=this.ini.getBool("InvisibleInGame"),this.moveToShroud=this.ini.getBool("MoveToShroud",this.type!==Et.Aircraft),this.leadershipRating=this.ini.getNumber("LeadershipRating",5),this.unnatural=this.ini.getBool("Unnatural"),this.natural=this.ini.getBool("Natural"),this.buildTimeMultiplier=this.ini.getFixed("BuildTimeMultiplier",1),this.allowedToStartInMultiplayer=this.ini.getBool("AllowedToStartInMultiplayer",!0),this.rot=Ai.iniRotToDegsPerTick(this.ini.getNumber("ROT",0)),this.jumpjetAccel=this.ini.getNumber("JumpJetAccel",2),this.jumpjetClimb=this.ini.getNumber("JumpjetClimb",5),this.jumpjetCrash=this.ini.getNumber("JumpjetCrash",5),this.jumpjetDeviation=this.ini.getNumber("JumpjetDeviation",40),this.jumpjetHeight=this.ini.getNumber("JumpjetHeight",500),this.jumpjetNoWobbles=this.ini.getBool("JumpjetNoWobbles"),this.jumpjetSpeed=this.ini.getNumber("JumpjetSpeed",14),this.jumpjetTurnRate=Ai.iniRotToDegsPerTick(this.ini.getNumber("JumpJetTurnRate",4)),this.jumpjetWobbles=this.ini.getNumber("JumpjetWobbles",.15),this.pitchSpeed=this.ini.getNumber("PitchSpeed",.25),this.pitchAngle=1<=this.pitchSpeed?0:20,this.damageParticleSystems=this.ini.getArray("DamageParticleSystems");i=this.ini.getNumberArray("DamageSmokeOffset",void 0,[0,0,0]);this.damageSmokeOffset=new as(i[0],i[2]/Math.SQRT2,i[1]),this.minDebris=this.ini.getNumber("MinDebris"),this.maxDebris=this.ini.getNumber("MaxDebris"),this.debrisTypes=this.ini.getArray("DebrisTypes"),this.debrisAnims=this.ini.getArray("DebrisAnims"),this.isLightpost="GALITE"===this.imageName,this.lightVisibility=this.ini.getNumber("LightVisibility",5e3),this.lightIntensity=this.ini.getNumber("LightIntensity"),this.lightRedTint=this.ini.getNumber("LightRedTint",1),this.lightGreenTint=this.ini.getNumber("LightGreenTint",1),this.lightBlueTint=this.ini.getNumber("LightBlueTint",1),this.ambientSound=this.ini.getString("AmbientSound")||void 0,this.createSound=this.ini.getString("CreateSound")||void 0,this.deploySound=this.ini.getString("DeploySound")||void 0,this.undeploySound=this.ini.getString("UndeploySound")||void 0,this.voiceSelect=this.ini.getString("VoiceSelect")||void 0,this.voiceMove=this.ini.getString("VoiceMove")||void 0,this.voiceAttack=this.ini.getString("VoiceAttack")||void 0,this.voiceFeedback=this.ini.getString("VoiceFeedback")||void 0,this.voiceSpecialAttack=this.ini.getString("VoiceSpecialAttack")||void 0,this.voiceEnter=this.ini.getString("VoiceEnter")||void 0,this.voiceCapture=this.ini.getString("VoiceCapture")||void 0,this.voiceCrashing=this.ini.getString("VoiceCrashing")||void 0,this.crashingSound=this.ini.getString("CrashingSound")||void 0,this.impactLandSound=this.ini.getString("ImpactLandSound")||void 0,this.auxSound1=this.ini.getString("AuxSound1")||void 0,this.auxSound2=this.ini.getString("AuxSound2")||void 0,this.dieSound=this.ini.getString("DieSound")||void 0,this.moveSound=this.ini.getString("MoveSound")||void 0,this.enterWaterSound=this.ini.getString("EnterWaterSound")||void 0,this.leaveWaterSound=this.ini.getString("LeaveWaterSound")||void 0,this.turretRotateSound=this.ini.getString("TurretRotateSound")||void 0,this.workingSound=this.ini.getString("WorkingSound")||void 0,this.notWorkingSound=this.ini.getString("NotWorkingSound")||void 0,this.chronoInSound=this.ini.getString("ChronoInSound")||void 0,this.chronoOutSound=this.ini.getString("ChronoOutSound")||void 0,this.enterTransportSound=this.ini.getString("EnterTransportSound")||void 0,this.leaveTransportSound=this.ini.getString("LeaveTransportSound")||void 0}parseWeaponName(e){return e&&"none"!==e.toLowerCase()?e:void 0}parseTurretIndexes(){let i=new Map;return this.ini.getBool("Gunner")&&this.ini.entries.forEach((e,t)=>{t=t.match(/^(.*)TurretWeapon$/i);t&&(t=t[1]+"TurretIndex",this.ini.has(t)&&i.set(Number(e),this.ini.getNumber(t)))}),i}parseBurstDelay(){let t=[];for(let e=0;e<4;++e)t.push(this.ini.has(`BurstDelay${e}`)?this.ini.getNumber(`BurstDelay${e}`):void 0);return t}hasOwner(e){return!!this.owner.length&&-1!==this.owner.indexOf(e.name)}isAvailableTo(e){return(!this.requiredHouses.length||-1!==this.requiredHouses.indexOf(e.name))&&-1===this.forbiddenHouses.indexOf(e.name)}getWeaponAtIndex(e){return this.parseWeaponName(this.ini.getString(`Weapon${e+1}`))}getEliteWeaponAtIndex(e){return this.parseWeaponName(this.ini.getString(`EliteWeapon${e+1}`))}}hs.MAX_SIGHT=11;class ls extends Ai{parse(){super.parse(),this.armor=this.ini.getEnum("Armor",ni,ni.None,!0),this.crate=this.ini.getBool("Crate");var e=this.ini.getBool("IsARock");this.isARock=e,this.isRubble=this.ini.getBool("IsRubble"),this.isVeinholeMonster=this.ini.getBool("IsVeinholeMonster"),this.isVeins=this.ini.getBool("IsVeins"),this.land=this.ini.getEnum("Land",ei,ei.Clear),this.noUseTileLandType=!!this.ini.getString("NoUseTileLandType"),this.strength=this.ini.getNumber("Strength"),this.tiberium=this.ini.getBool("Tiberium");var t=this.ini.getBool("Wall");this.wall=t,this.radarInvisible=this.ini.getBool("RadarInvisible",!t&&!e)}}(r=is=is||{})[r.All=7]="All",r[r.Right=1]="Right",r[r.Left=2]="Left",r[r.Bottom=4]="Bottom";class cs extends Ai{parse(){super.parse(),this.animationRate=this.ini.getNumber("AnimationRate"),this.animationProbability=this.ini.getNumber("AnimationProbability"),this.gate=this.ini.getBool("Gate"),this.immune=this.ini.getBool("Immune"),this.isAnimated=this.ini.getBool("IsAnimated"),this.snowOccupationBits=this.normalizeOccupationBits(this.ini.getNumber("SnowOccupationBits",is.All)),this.spawnsTiberium=this.ini.getBool("SpawnsTiberium"),this.strength=this.ini.getNumber("Strength"),this.radarInvisible=this.ini.getBool("RadarInvisible"),this.temperateOccupationBits=this.normalizeOccupationBits(this.ini.getNumber("TemperateOccupationBits",is.All))}normalizeOccupationBits(e){return(e+8*Math.abs(Math.floor(e/8)))%8}getOccupationBits(e){return e!==I.Snow?this.temperateOccupationBits:this.snowOccupationBits}getOccupiedSubCells(e){var t,i=this.getOccupationBits(e),e=[0,1,2,3,4];if(i===is.All)return e;let s=[];for(t of e)!function(e,t){switch(e){case 0:case 1:return 1;case 2:return 0!=(t&is.Right);case 3:return 0!=(t&is.Left);case 4:return 0!=(t&is.Bottom);default:throw new Error(`Invalid subCell "${e}`)}}(t,i)||s.push(t);return s}}class us extends Ai{parse(){super.parse(),this.burn=this.ini.getBool("Burn"),this.crater=this.ini.getBool("Crater"),this.width=this.ini.getNumber("Width",1),this.height=this.ini.getNumber("Height",1)}}class ds extends Ai{parse(){super.parse(),this.damage=this.ini.getNumber("Damage"),this.damageRadius=this.ini.getNumber("DamageRadius"),this.duration=this.ini.getNumber("Duration"),this.elasticity=z(this.ini.getNumber("Elasticity",.75),0,1),this.expireAnim=this.ini.getString("ExpireAnim")||void 0,this.minAngularVelocity=this.ini.getNumber("MinAngularVelocity"),this.maxAngularVelocity=this.ini.getNumber("MaxAngularVelocity"),this.maxXYVel=this.ini.getNumber("MaxXYVel"),this.minZVel=this.ini.getNumber("MinZVel"),this.maxZVel=this.ini.getNumber("MaxZVel"),this.shareTurretData=this.ini.getBool("ShareTurretData"),this.shareBodyData=this.ini.getBool("ShareBodyData"),this.shareBarrelData=this.ini.getBool("ShareBarrelData"),this.shareSource=this.ini.getString("ShareSource")||void 0,this.trailerAnim=this.ini.getString("TrailerAnim")||void 0,this.trailerSeparation=this.ini.getNumber("TrailerSeperation"),this.warhead=this.ini.getString("Warhead")||void 0}}class gs{create(e,t,i,s){switch(e){case Et.Aircraft:case Et.Building:case Et.Infantry:case Et.Vehicle:return new hs(e,t,s,i);case Et.Overlay:return new ls(e,t,s);case Et.Terrain:return new cs(e,t,s);case Et.Smudge:return new us(e,t,s);case Et.VoxelAnim:return new ds(e,t,s);default:return new Ai(e,t,s)}}}class ps{readIni(e){this.ballisticScatter=e.getNumber("BallisticScatter"),this.bridgeStrength=e.getNumber("BridgeStrength"),this.c4Delay=e.getNumber("C4Delay"),this.c4Warhead=e.getString("C4Warhead"),this.deathWeapon=e.getString("DeathWeapon"),this.dMislEliteWarhead=e.getString("DMislEliteWarhead"),this.dMislWarhead=e.getString("DMislWarhead"),this.flameDamage=e.getString("FlameDamage"),this.ironCurtainDuration=e.getNumber("IronCurtainDuration"),this.ivanDamage=e.getNumber("IvanDamage"),this.ivanIconFlickerRate=e.getNumber("IvanIconFlickerRate"),this.ivanTimedDelay=e.getNumber("IvanTimedDelay"),this.ivanWarhead=e.getString("IvanWarhead"),this.splashList=e.getArray("SplashList"),this.v3EliteWarhead=e.getString("V3EliteWarhead"),this.v3Warhead=e.getString("V3Warhead")}}class ms{readIni(e){return this.value=e.getNumber("Value"),this}}class fs{readIni(e){this.buildPower=e.getArray("BuildPower"),this.buildRefinery=e.getArray("BuildRefinery"),this.buildTech=e.getArray("BuildTech"),this.tiberiumFarScan=e.getNumber("TiberiumFarScan",50),this.tiberiumNearScan=e.getNumber("TiberiumNearScan",5)}}class ys{readIni(e){return this.increment=e.getNumber("ElevationIncrement"),this.incrementBonus=e.getNumber("ElevationIncrementBonus",1),this.bonusCap=e.getNumber("ElevationBonusCap"),this}getBonus(e,t){return e<=t?0:Math.min(this.bonusCap,Math.floor((e-t)/this.increment))*this.incrementBonus}}class ws{readIni(e){this.radDurationMultiple=e.getNumber("RadDurationMultiple"),this.radApplicationDelay=e.getNumber("RadApplicationDelay"),this.radLevelMax=e.getNumber("RadLevelMax"),this.radLevelDelay=e.getNumber("RadLevelDelay"),this.radLightDelay=e.getNumber("RadLightDelay"),this.radLevelFactor=e.getNumber("RadLevelFactor"),this.radLightFactor=e.getNumber("RadLightFactor"),this.radTintFactor=e.getNumber("RadTintFactor"),this.radColor=e.getNumberArray("RadColor"),this.radSiteWarhead=e.getString("RadSiteWarhead")}}(r=ss=ss||{})[r.MultiMissile=0]="MultiMissile",r[r.IronCurtain=1]="IronCurtain",r[r.LightningStorm=2]="LightningStorm",r[r.ChronoSphere=3]="ChronoSphere",r[r.ChronoWarp=4]="ChronoWarp",r[r.ParaDrop=5]="ParaDrop",r[r.AmerParaDrop=6]="AmerParaDrop";class Ts{constructor(e){this.index=e}readIni(e){return this.disableableFromShell=e.getBool("DisableableFromShell"),this.isPowered=e.getBool("IsPowered",!0),this.name=e.name,this.preClick=e.getBool("PreClick"),this.preDependent=e.getEnum("PreDependent",ss,void 0),this.postClick=e.getBool("PostClick"),this.rechargeTime=e.getNumber("RechargeTime",5),this.showTimer=e.getBool("ShowTimer"),this.sidebarImage=e.getString("SidebarImage").toLowerCase(),this.type=e.getEnum("Type",ss,void 0),this.uiName=e.getString("UIName"),this.weaponType=e.getString("WeaponType")||void 0,this}}class bs{readIni(e){this.crateMaximum=e.getNumber("CrateMaximum"),this.crateMinimum=e.getNumber("CrateMinimum"),this.crateRadius=e.getNumber("CrateRadius"),this.crateRegen=e.getNumber("CrateRegen");let t=e.getString("UnitCrateType");return this.unitCrateType="none"!==t.toLowerCase()?t:void 0,this.healCrateSound=e.getString("HealCrateSound"),this.crateImg=e.getString("CrateImg"),this.waterCrateImg=e.getString("WaterCrateImg"),this.freeMCV=e.getBool("FreeMCV"),this}}(r=rs=rs||{})[r.Cheer=0]="Cheer",r[r.UnitDeployUndeploy=1]="UnitDeployUndeploy",r[r.WeaponFire=2]="WeaponFire",r[r.ObjectDestroy=3]="ObjectDestroy",r[r.ObjectSpawn=4]="ObjectSpawn",r[r.ObjectUnspawn=5]="ObjectUnspawn",r[r.ObjectMorph=6]="ObjectMorph",r[r.ObjectLiftOff=7]="ObjectLiftOff",r[r.ObjectLand=8]="ObjectLand",r[r.ObjectCrashing=9]="ObjectCrashing",r[r.ObjectDisguiseChange=10]="ObjectDisguiseChange",r[r.ObjectCloakChange=11]="ObjectCloakChange",r[r.ObjectAttacked=12]="ObjectAttacked",r[r.ShipSubmergeChange=13]="ShipSubmergeChange",r[r.BridgeRepair=14]="BridgeRepair",r[r.BuildStatusChange=15]="BuildStatusChange",r[r.BuildingPlace=16]="BuildingPlace",r[r.BuildingFailedPlace=17]="BuildingFailedPlace",r[r.ObjectSell=18]="ObjectSell",r[r.BuildingRepairFull=19]="BuildingRepairFull",r[r.BuildingCapture=20]="BuildingCapture",r[r.BuildingInfiltration=21]="BuildingInfiltration",r[r.BuildingGarrison=22]="BuildingGarrison",r[r.BuildingEvacuate=23]="BuildingEvacuate",r[r.BuildingRepairStart=24]="BuildingRepairStart",r[r.UnitRepairStart=25]="UnitRepairStart",r[r.UnitRepairFinish=26]="UnitRepairFinish",r[r.UnitRecycle=27]="UnitRecycle",r[r.InflictDamage=28]="InflictDamage",r[r.HealthChange=29]="HealthChange",r[r.WarheadDetonate=30]="WarheadDetonate",r[r.PlayerDefeated=31]="PlayerDefeated",r[r.PlayerResigned=32]="PlayerResigned",r[r.PlayerDropped=33]="PlayerDropped",r[r.DeployNotAllowed=34]="DeployNotAllowed",r[r.PowerChange=35]="PowerChange",r[r.PowerLow=36]="PowerLow",r[r.PowerRestore=37]="PowerRestore",r[r.RadarOnOff=38]="RadarOnOff",r[r.ObjectOwnerChange=39]="ObjectOwnerChange",r[r.RadarEvent=40]="RadarEvent",r[r.InsufficientFunds=41]="InsufficientFunds",r[r.RallyPointChange=42]="RallyPointChange",r[r.PrimaryFactoryChange=43]="PrimaryFactoryChange",r[r.FactoryProduceUnit=44]="FactoryProduceUnit",r[r.ObjectTeleport=45]="ObjectTeleport",r[r.AllianceChange=46]="AllianceChange",r[r.UnitPromote=47]="UnitPromote",r[r.EnterTransport=48]="EnterTransport",r[r.LeaveTransport=49]="LeaveTransport",r[r.EnterObject=50]="EnterObject",r[r.EnterTile=51]="EnterTile",r[r.SuperWeaponReady=52]="SuperWeaponReady",r[r.SuperWeaponActivate=53]="SuperWeaponActivate",r[r.LightningStormManifest=54]="LightningStormManifest",r[r.LightningStormCloud=55]="LightningStormCloud",r[r.CratePickup=56]="CratePickup",r[r.PingLocation=57]="PingLocation",r[r.StalemateDetect=58]="StalemateDetect",r[r.TriggerSoundFx=59]="TriggerSoundFx",r[r.TriggerStopSoundFx=60]="TriggerStopSoundFx",r[r.TriggerEva=61]="TriggerEva",r[r.TriggerAnim=62]="TriggerAnim",r[r.TriggerText=63]="TriggerText",r[r.TimerExpire=64]="TimerExpire";class vs{constructor(e,t,i,s){this.target=e,this.player=t,this.source=i,this.tile=s,this.type=rs.CratePickup}}var Ss,ks,r=__webpack_require__(949);class Os extends r.Vector2{length(){return Ki.sqrt(this.x*this.x+this.y*this.y)}angle(){let e=Ki.atan2(this.y,this.x);return e<0&&(e+=2*Math.PI),e}distanceTo(e){return Ki.sqrt(this.distanceToSquared(e))}rotateAround(e,t){var i=Ki.cos(t),s=Ki.sin(t),r=this.x-e.x,t=this.y-e.y;return this.x=r*i-t*s+e.x,this.y=r*s+t*i+e.y,this}}class _s{static tileToWorld(e,t){return{x:e*_s.LEPTONS_PER_TILE,y:t*_s.LEPTONS_PER_TILE}}static vecWorldToGround(e){return new Os(e.x,e.z)}static vecGroundToWorld(e){return new as(e.x,0,e.y)}static tileHeightToWorld(e){return e*(_s.LEPTONS_PER_TILE/2)*_s.zScale}static worldToTileHeight(e){return e/(_s.LEPTONS_PER_TILE/2*_s.zScale)}static tile3dToWorld(e,t,i){t=_s.tileToWorld(e,t),i=_s.tileHeightToWorld(i);return new as(t.x,i,t.y)}static screenDistanceToWorld(e,t){return{x:Math.floor((e+2*t)/2*_s.ISO_WORLD_SCALE),y:Math.floor((2*t-e)/2*_s.ISO_WORLD_SCALE)}}static getWorldTileSize(){return _s.LEPTONS_PER_TILE}}function Is(e){return[ei.Water,ei.Beach].includes(e)?Ss.Water:Ss.Ground}_s.ISO_TILE_SIZE=30,_s.LEPTONS_PER_TILE=256,_s.ISO_WORLD_SCALE=_s.LEPTONS_PER_TILE/_s.ISO_TILE_SIZE,_s.ISO_CAMERA_ALPHA=Math.PI/6,_s.ISO_CAMERA_BETA=Math.PI/4,_s.COS_ISO_CAMERA_BETA=Ki.cos(_s.ISO_CAMERA_BETA),_s.zScale=_s.COS_ISO_CAMERA_BETA/Ki.cos(_s.ISO_CAMERA_ALPHA),(r=Ss=Ss||{})[r.Ground=0]="Ground",r[r.Air=1]="Air",r[r.Water=2]="Water";const Cs=e=>void 0!==e.position,As=e=>void 0!==e.addScalar;class Bs{constructor(e){this.tileOccupation=e}isInWeaponRange(e,t,i,s,r){var a=r??e;if(i.rules.limboLaunch&&2<Math.abs((Cs(a)?a.position.tileElevation+a.tile.z:a.z)-(Cs(t)?t.position.tileElevation+t.tile.z:t.z)))return!1;var{minRange:r,range:s}=this.computeWeaponRangeVsTarget(a,t,i,s);return i.rules.cellRangefinding?this.isInTileRange(a,t,r,s):e.isUnit()&&e.rules.movementZone===ai.Fly?this.isInRange2(a,t,r,s):this.isInRange3(a,t,r,s)}computeWeaponRangeVsTarget(e,t,i,s){let r=0;var a,n;return!Cs(t)||!t.isBuilding()||i.projectileRules.arcing||i.projectileRules.vertical||i.warhead.rules.ivanBomb||1<(n=t.getFoundation()).width&&1<n.height&&(r+=Math.ceil(Math.min(n.width,n.height)/2)),!i.projectileRules.subjectToElevation||i.projectileRules.arcing&&!Cs(t)||(a=Cs(e)?e.tile.z+e.tileElevation:e.z,(n=Cs(t)?t.tile.z+t.tileElevation:t.z)<a&&(r+=s.elevationModel.getBonus(a,n))),i.projectileRules.isAntiAir&&Cs(e)&&e.isTechno()&&Cs(t)&&t.isUnit()&&t.zone===Ss.Air&&(r+=e.rules.airRangeBonus),{minRange:i.minRange,range:i.range+r}}isInRange(e,t,i,s,r=!1){return r?this.isInTileRange(e,t,i,s):e.isUnit()&&e.rules.movementZone===ai.Fly?this.isInRange2(e,t,i,s):this.isInRange3(e,t,i,s)}isInRange3(e,t,i,s){return V(this.distance3(e,t)/_s.LEPTONS_PER_TILE,i,s)}isInRange2(e,t,i,s){return V(this.distance2(e,t)/_s.LEPTONS_PER_TILE,i,s)}distance3(e,t){let i=Cs(e)?e.position.worldPosition:As(e)?e:_s.tile3dToWorld(e.rx+.5,e.ry+.5,e.z);t=Cs(t)?t.position.worldPosition:As(t)?t:_s.tile3dToWorld(t.rx+.5,t.ry+.5,t.z);return i.distanceTo(t)}distance2(e,t){let i=Cs(e)?new Os(e.position.worldPosition.x,e.position.worldPosition.z):As(e)?new Os(e.x,e.z):new Os(e.rx+.5,e.ry+.5).multiplyScalar(_s.LEPTONS_PER_TILE);t=Cs(t)?new Os(t.position.worldPosition.x,t.position.worldPosition.z):As(t)?new Os(t.x,t.z):new Os(t.rx+.5,t.ry+.5).multiplyScalar(_s.LEPTONS_PER_TILE);return i.distanceTo(t)}isInTileRange(e,t,i,s){return V(this.tileDistance(e,t),i,s)}tileDistance(e,t){var i,e=Cs(e)?this.tileOccupation.calculateTilesForGameObject(e.tile,e):Array.isArray(e)?e:[e],s=Cs(t)?this.tileOccupation.calculateTilesForGameObject(t.tile,t):Array.isArray(t)?t:[t];let r=new Os,a=new Os,n=Number.POSITIVE_INFINITY;for(i of e)for(var o of s){r.set(i.rx,i.ry),a.set(o.rx,o.ry);o=r.distanceTo(a);o<=n&&(n=o)}return n}}const xs=e=>"name"in e;(r=ks=ks||{})[r.Brutal=0]="Brutal",r[r.Medium=1]="Medium",r[r.Easy=2]="Easy";var Es,Ps,Ns,Ds,Ms,Rs,Ls,Fs,js;(new Map).set(ks.Easy,"GUI:AIDummy").set(ks.Medium,"GUI:AIEasyBeta"),new Map;class Us{static computeGameSpeed(e){let t;return t=6===e?60:5===e?45:60/(6-e),t/Us.BASE_TICKS_PER_SECOND}}Us.BASE_TICKS_PER_SECOND=15;class Ws{constructor(e,t,i,s,r,a,n,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.foundation=s,this.maxDistance=a,this.predicate=n,this.checkBounds=o,this.distance=r,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){var s=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t))return t};do{var r=this.startTile.rx-this.distance,a=this.startTile.ry-this.distance,n=this.startTile.rx+this.foundation.width-1+this.distance,o=this.startTile.ry+this.foundation.height-1+this.distance;let e,t,i;if(0<this.distance){for(e=n;e>=r;e--)i=s(e,o),i&&(yield i);for(t=o-1;t>=a;t--)i=s(n,t),i&&(yield i);for(e=r;e<n;e++)i=s(e,a),i&&(yield i);for(t=1+a;t<o;t++)i=s(r,t),i&&(yield i)}else this.predicate(this.startTile)&&(yield this.startTile)}while(this.distance++,this.distance<=this.maxDistance)}}(r=Es=Es||{})[r.Armor=0]="Armor",r[r.Firepower=1]="Firepower",r[r.HealBase=2]="HealBase",r[r.Money=3]="Money",r[r.Reveal=4]="Reveal",r[r.Speed=5]="Speed",r[r.Veteran=6]="Veteran",r[r.Unit=7]="Unit",r[r.Invulnerability=8]="Invulnerability",r[r.IonStorm=9]="IonStorm",r[r.Gas=10]="Gas",r[r.Tiberium=11]="Tiberium",r[r.Pod=12]="Pod",r[r.Cloak=13]="Cloak",r[r.Darkness=14]="Darkness",r[r.Explosion=15]="Explosion",r[r.ICBM=16]="ICBM",r[r.Napalm=17]="Napalm",r[r.Squad=18]="Squad",(Ps=Ps||{}).onTick=Symbol(),(Ns=Ns||{}).onChange=Symbol();class zs{constructor(e){this.target=e,this.type=rs.SuperWeaponReady}}(r=Ds=Ds||{})[r.Charging=0]="Charging",r[r.Paused=1]="Paused",r[r.Ready=2]="Ready";class Vs{constructor(e,t,i,s=!1){this.name=e,this.rules=t,this.owner=i,this.oneTimeOnly=s,this.status=Ds.Charging,this.isGift=!1,this.rechargeTicks=60*t.rechargeTime*Us.BASE_TICKS_PER_SECOND,this.chargeTicks=this.rechargeTicks,s&&(this.status=Ds.Ready,this.chargeTicks=0)}update(e){0<this.chargeTicks&&this.status!==Ds.Paused&&(this.chargeTicks--,0===this.chargeTicks&&(this.status=Ds.Ready,e.events.dispatch(new zs(this))))}pauseTimer(){this.status=Ds.Paused}resumeTimer(){this.status=0<this.chargeTicks?Ds.Charging:Ds.Ready}resetTimer(){this.chargeTicks=this.rechargeTicks,this.status===Ds.Ready&&(this.status=Ds.Charging)}getTimerSeconds(){return this.chargeTicks/Us.BASE_TICKS_PER_SECOND}getChargeProgress(){return(this.rechargeTicks-this.chargeTicks)/this.rechargeTicks}}(r=Ms=Ms||{})[r.NotStarted=0]="NotStarted",r[r.Running=1]="Running",r[r.Finished=2]="Finished";class Hs{constructor(e,t,i){this.type=e,this.owner=t,this.tile=i,this.status=Ms.NotStarted}onStart(e){}onTick(e){return!0}}(r=Rs=Rs||{}).onPowerLow=Symbol(),r.onPowerRestore=Symbol(),r.onPowerChange=Symbol(),(Ls=Ls||{}).onActivate=Symbol();class Gs{constructor(e,t,i,s,r){this.target=e,this.owner=t,this.atTile=i,this.atTile2=s,this.noSfxWarning=r,this.type=rs.SuperWeaponActivate}}(r=Fs=Fs||{})[r.None=0]="None",r[r.Guard=1]="Guard",r[r.Prone=2]="Prone",r[r.Deployed=3]="Deployed",r[r.Paradrop=4]="Paradrop",r[r.Cheer=5]="Cheer",(r=js=js||{})[r.NotStarted=0]="NotStarted",r[r.Running=1]="Running",r[r.Finished=2]="Finished",r[r.Cancelling=3]="Cancelling",r[r.Cancelled=4]="Cancelled";class $s{constructor(){this.status=js.NotStarted,this.children=[],this.cancellable=!0,this.useChildTargetLines=!1,this.blocking=!0,this.waitingForChildrenToFinish=!1,this.preventOpportunityFire=!0,this.preventLanding=!0,this.isAttackMove=!1}isRunning(){return this.status===js.Running}isCancelling(){return this.status===js.Cancelling}setCancellable(e){return this.cancellable=e,this}setBlocking(e){return this.blocking=e,this}onStart(e){}onEnd(e){}cancel(){if(this.cancellable)if(this.status===js.Running)this.status=js.Cancelling,this.children.length&&this.children.forEach(e=>e.cancel());else if(this.status===js.NotStarted&&(this.status=js.Cancelled,this.children.length))throw new Error("Should't have any children before starting a task")}getTargetLinesConfig(e){}}function qs(t,i){for(let e=t.length-1;0<=e;e--)if(i(t[e],e,t))return e;return-1}class Xs extends $s{constructor(e){super(),this.ticks=e}onTick(){return!!this.isCancelling()||!(0<this.ticks--)}}class Zs{constructor(e){this.map=e}findPositions(e,s,r,a){let n=new Map,t=this.clusterObjects(e);if(!t.length)throw new Error("We should have found at least one cluster");let i=t.reduce((e,t)=>t.objects.size>e.objects.size?t:e,t[0]);t.splice(t.indexOf(i),1);let o=[],h=this.findCenterTile([...i.objects]);i.objects.forEach(t=>{var i=this.map.tiles.getByMapCoords(s.rx+t.tile.rx-h.rx,s.ry+t.tile.ry-h.ry),e=i?.onBridgeLandType?this.map.tileOccupation.getBridgeOnTile(i):void 0;if(!i||!this.map.mapBounds.isWithinBounds(i)||n.has(i)&&!this.tileHasRoom(t,n.get(i))||t.rules.movementZone===ai.Fly&&!(t.rules.airportBound||a&&t.rules.balloonHover&&!t.rules.hoverAttack)&&!this.map.terrain.getPassableSpeed(i,ti.Amphibious,!1,!!e)||t.rules.movementZone!==ai.Fly&&!this.isEligibleTile(i,e,r,s))o.push(t);else{let e=n.get(i);void 0===e&&(e=[],n.set(i,e)),e.push(t)}}),t.forEach(e=>o.push(...e.objects));let l=new Ws(this.map.tiles,this.map.mapBounds,s,{width:1,height:1},1,5,()=>!0),c;for(;o.length&&(c=l.getNextTile());){var u=o[0],d=this.map.tileOccupation.getBridgeOnTile(c);if((!n.has(c)||this.tileHasRoom(u,n.get(c)))&&((u.rules.movementZone!==ai.Fly||u.rules.airportBound||this.map.terrain.getPassableSpeed(c,ti.Amphibious,!1,!!d))&&(u.rules.movementZone===ai.Fly||this.isEligibleTile(c,d,r,s)))){let e=n.get(c);void 0===e&&(e=[],n.set(c,e)),e.push(o.shift())}}let g=new Map;if(n.forEach((e,t)=>{e.forEach(e=>g.set(e,t))}),o.forEach(e=>g.set(e,s)),g.size!==e.length)throw new Error("We should have computed a number of positions equal to the number of input objects");return g}tileHasRoom(e,t){if(e.isInfantry()){if(t.find(e=>!e.isInfantry()))return!1;e=e.rules.movementZone===ai.Fly?1:3;return t.filter(e=>e.isInfantry()).length>=e?!1:!0}return!t.length}isEligibleTile(e,t,i,s){return i?.isHighBridge()||t?.isHighBridge()?e.z+(t?.tileElevation??0)===s.z+(i?.tileElevation??0):!(!i&&!t)||Math.abs(e.z-s.z)<2}clusterObjects(e){let r=new Map;e.forEach(e=>{var t=e.tile.rx+"_"+e.tile.ry;r.set(t,[...r.get(t)||[],e])});let t=[],a=new Set(e);for(;a.size;){let e=new Set,s=[];var i=[...a][0].tile;for(r.get(i.rx+"_"+i.ry).forEach(e=>{s.push(e)});s.length;){var n=s.shift();e.add(n),a.delete(n);for(let i=-1;i<=1;i++)for(let t=-1;t<=1;t++)if(i||t){let e=r.get(n.tile.rx+i+"_"+(n.tile.ry+t));e&&e.length&&e.forEach(e=>{a.has(e)&&(a.delete(e),s.push(e))})}}t.push({objects:e})}return t}findCenterTile(e){let t=0,i=0;e.forEach(e=>{t+=e.tile.rx,i+=e.tile.ry}),t=Math.round(t/e.length),i=Math.round(i/e.length);let s=this.map.tiles.getByMapCoords(t,i);if(!s&&(s=e.find(e=>Math.abs(e.tile.rx-t)<=1&&Math.abs(e.tile.ry-i)<=1)?.tile,!s))throw new Error("At least one adjacent object should have been found");return s}}r=__webpack_require__(949);class Qs extends r.Matrix4{extractRotation(e){let t=this.elements;var i=e.elements,s=1/Ys.setFromMatrixColumn(e,0).length(),r=1/Ys.setFromMatrixColumn(e,1).length(),e=1/Ys.setFromMatrixColumn(e,2).length();return t[0]=i[0]*s,t[1]=i[1]*s,t[2]=i[2]*s,t[3]=0,t[4]=i[4]*r,t[5]=i[5]*r,t[6]=i[6]*r,t[7]=0,t[8]=i[8]*e,t[9]=i[9]*e,t[10]=i[10]*e,t[11]=0,t[12]=0,t[13]=0,t[14]=0,t[15]=1,this}makeRotationFromEuler(e){e&&e.isEuler||console.error("THREE.Matrix4: .makeRotationFromEuler() now expects a Euler rotation rather than a Vector3 and order.");let t=this.elements;var i,s,r,a,n,o,h,l,c,u,d,g=e.x,p=e.y,m=e.z,f=Ki.cos(g),y=Ki.sin(g),w=Ki.cos(p),T=Ki.sin(p),g=Ki.cos(m),p=Ki.sin(m);return"XYZ"===e.order?(i=f*g,r=f*p,s=y*g,m=y*p,t[0]=w*g,t[4]=-w*p,t[8]=T,t[1]=r+s*T,t[5]=i-m*T,t[9]=-y*w,t[2]=m-i*T,t[6]=s+r*T,t[10]=f*w):"YXZ"===e.order?(a=w*g,i=w*p,s=T*g,r=T*p,t[0]=a+r*y,t[4]=s*y-i,t[8]=f*T,t[1]=f*p,t[5]=f*g,t[9]=-y,t[2]=i*y-s,t[6]=r+a*y,t[10]=f*w):"ZXY"===e.order?(h=w*g,a=w*p,n=T*g,o=T*p,t[0]=h-o*y,t[4]=-f*p,t[8]=n+a*y,t[1]=a+n*y,t[5]=f*g,t[9]=o-h*y,t[2]=-f*T,t[6]=y,t[10]=f*w):"ZYX"===e.order?(n=f*g,o=f*p,l=y*g,h=y*p,t[0]=w*g,t[4]=l*T-o,t[8]=n*T+h,t[1]=w*p,t[5]=h*T+n,t[9]=o*T-l,t[2]=-T,t[6]=y*w,t[10]=f*w):"YZX"===e.order?(u=f*w,l=f*T,c=y*w,d=y*T,t[0]=w*g,t[4]=d-u*p,t[8]=c*p+l,t[1]=p,t[5]=f*g,t[9]=-y*g,t[2]=-T*g,t[6]=l*p+c,t[10]=u-d*p):"XZY"===e.order&&(c=f*w,u=f*T,d=y*w,e=y*T,t[0]=w*g,t[4]=-p,t[8]=T*g,t[1]=c*p+e,t[5]=f*g,t[9]=u*p-d,t[2]=d*p-u,t[6]=y*g,t[10]=e*p+c),t[3]=0,t[7]=0,t[11]=0,t[12]=0,t[13]=0,t[14]=0,t[15]=1,this}lookAt(e,t,i){Ks.set(0,0,0),Js.set(0,0,0),er.set(0,0,0);const s=this.elements;return er.subVectors(e,t),0===er.lengthSq()&&(er.z=1),er.normalize(),Ks.crossVectors(i,er),0===Ks.lengthSq()&&(1===Math.abs(i.z)?er.x+=1e-4:er.z+=1e-4,er.normalize(),Ks.crossVectors(i,er)),Ks.normalize(),Js.crossVectors(er,Ks),s[0]=Ks.x,s[4]=Js.x,s[8]=er.x,s[1]=Ks.y,s[5]=Js.y,s[9]=er.y,s[2]=Ks.z,s[6]=Js.z,s[10]=er.z,this}getMaxScaleOnAxis(){var e=this.elements,t=e[0]*e[0]+e[1]*e[1]+e[2]*e[2],i=e[4]*e[4]+e[5]*e[5]+e[6]*e[6],e=e[8]*e[8]+e[9]*e[9]+e[10]*e[10];return Ki.sqrt(Math.max(t,i,e))}makeRotationX(e){var t=Ki.cos(e),e=Ki.sin(e);return this.set(1,0,0,0,0,t,-e,0,0,e,t,0,0,0,0,1),this}makeRotationY(e){var t=Ki.cos(e),e=Ki.sin(e);return this.set(t,0,e,0,0,1,0,0,-e,0,t,0,0,0,0,1),this}makeRotationZ(e){var t=Ki.cos(e),e=Ki.sin(e);return this.set(t,-e,0,0,e,t,0,0,0,0,1,0,0,0,0,1),this}makeRotationAxis(e,t){var i=Ki.cos(t),s=Ki.sin(t),r=1-i,a=e.x,n=e.y,o=e.z,t=r*a,e=r*n;return this.set(t*a+i,t*n-s*o,t*o+s*n,0,t*n+s*o,e*n+i,e*o-s*a,0,t*o-s*n,e*o+s*a,r*o*o+i,0,0,0,0,1),this}decompose(e,t,i){var s=this.elements;let r=Ys.set(s[0],s[1],s[2]).length();var a=Ys.set(s[4],s[5],s[6]).length(),n=Ys.set(s[8],s[9],s[10]).length();this.determinant()<0&&(r=-r),e.x=s[12],e.y=s[13],e.z=s[14],tr.copy(this);var o=1/r,e=1/a,s=1/n;return tr.elements[0]*=o,tr.elements[1]*=o,tr.elements[2]*=o,tr.elements[4]*=e,tr.elements[5]*=e,tr.elements[6]*=e,tr.elements[8]*=s,tr.elements[9]*=s,tr.elements[10]*=s,t.setFromRotationMatrix(tr),i.x=r,i.y=a,i.z=n,this}}const Ys=new as,Ks=new as,Js=new as,er=new as,tr=new Qs;var ir=__webpack_require__(949);function sr(e){return e*ir.Math.RAD2DEG}function rr(e){return e*ir.Math.DEG2RAD}const ar=new Os;function nr(e,t){t=rr(Math.floor(t));return e.rotateAround(ar,t)}function or(e){return Math.round(sr(e.angle()))}function hr(e,t){t=sr(2*Ki.acos(Math.abs(z(e.dot(t),-1,1))));return Math.round(t)}function lr(e,t){e=or(e),t=or(t);return Math.min((e-t+360)%360,(t-e+360)%360)}function cr(e,t){return hr(ur(e,fr),ur(t,yr))}function ur(e,t=new Ji){return t.setFromRotationMatrix(dr.lookAt(e,gr,pr))}const dr=new Qs,gr=new as(0,0,0),pr=new as(0,1,0);function mr(e,t,i){var s=e.length(),r=ur(t,fr),t=ur(e,yr);!function(e,t,i){var s=hr(e,t);if(0!==s){s=Math.min(1,i/s);e.slerp(t,s)}}(t,r,i),e.set(0,0,1).applyQuaternion(t).setLength(s)}const fr=new Ji,yr=new Ji;class wr extends $s{constructor(e,t){super(),this.game=e,this.fromDirection=t,this.resolved=!1,this.chainPushIssued=!1}onEnd(e){e.moveTrait.collisionState=Qr.Resolved}onTick(i){if(this.timeoutTicks=void 0===this.timeoutTicks?0:this.timeoutTicks+1,40<this.timeoutTicks||this.resolved||this.isCancelling())return!0;let s=this.game.map,t=new Zs(s);var r=i.onBridge?s.tileOccupation.getBridgeOnTile(i.tile):void 0;let a,n;for(let e=0;e<360;e+=45)if((0!==e||this.chainPushIssued)&&180!==e){var o=nr(this.fromDirection.clone(),e).round(),o=s.tiles.getByMapCoords(i.tile.rx+Math.sign(o.x),i.tile.ry+Math.sign(o.y));if(o&&s.mapBounds.isWithinBounds(o)&&(n=s.tileOccupation.getBridgeOnTile(o),i.rules.movementZone===ai.Fly||!s.terrain.findObstacles({tile:o,onBridge:n},i).length&&t.isEligibleTile(o,n,r,i.tile))){a=o;break}}if(a)return this.resolved=!0,i.isInfantry()&&i.deployerTrait&&i.deployerTrait.isDeployed()&&i.deployerTrait.setDeployed(!1),!!i.moveTrait.isDisabled()||(this.children.push(new _a(this.game,a,!!n,{closeEnoughTiles:0,strictCloseEnough:!0})),!1);{if(this.chainPushIssued)return this.children.push(new Xs(5)),!1;let t=s.tiles.getByMapCoords(i.tile.rx+Math.sign(this.fromDirection.x),i.tile.ry+Math.sign(this.fromDirection.y));if(!t||!s.mapBounds.isWithinBounds(t))return!0;n=s.tileOccupation.getBridgeOnTile(t);let e=s.tileOccupation.getGroundObjectsOnTile(t).filter(e=>e.isUnit()&&e.owner===i.owner&&e.tile===t&&e.onBridge===!!n&&!(e.isInfantry()&&e.stance===Fs.Paradrop)&&!(e.isAircraft()&&e.missileSpawnTrait));return e.find(e=>e.moveTrait.collisionState===Qr.Waiting||e.unitOrderTrait.hasTasks())?(this.children.push(new Xs(5)),i.moveTrait.collisionState=Qr.Waiting,i.moveTrait.moveState=Xr.PlanMove,!1):(e.forEach(e=>{e.unitOrderTrait.addTask(new wr(this.game,this.fromDirection))}),this.children.push(new Xs(1)),i.moveTrait.collisionState=Qr.Waiting,i.moveTrait.moveState=Xr.PlanMove,!(this.chainPushIssued=!0))}}}const Tr=__webpack_require__(163);class br{constructor(e){this.game=e,this.ignoresTerrain=!0,this.distanceToWaypoint=new Os}onNewWaypoint(e,t){}tick(e,t,i,s){if(s)return{distance:new as,done:!0};this.distanceToWaypoint.copy(t).sub(e.position.getMapPosition());s=this.game.rules.general;return s.chronoTrigger&&(s=(t=this.distanceToWaypoint.length())<s.chronoRangeMinimum?s.chronoMinimumDelay:t/s.chronoDistanceFactor,e.warpedOutTrait.setTimed(s,!1,this.game)),{distance:new as(this.distanceToWaypoint.x,0,this.distanceToWaypoint.y),done:!0,isTeleport:!0}}}class vr{static tick(e,t,i){if(e===t)return{facing:e,delta:0};var s=(e-t+360)%360,r=(t-e+360)%360;if(Math.min(s,r)<i)return{facing:t,delta:0};i*=r<=s?1:-1;return{facing:(e+i+360)%360,delta:i}}static fromMapCoords(e){return(-or(e)-90+720)%360}static toMapCoords(e){return nr(new Os(1e3,0),vr.toWorldDeg(e)).round().normalize()}static toWorldDeg(e){return-(e+90)}}class Sr extends $s{constructor(e){super(),this.direction=e,this.cancellable=!1}onTick(e){if(e.direction===this.direction)return!(e.spinVelocity=0);var t=e.rules.rot,{facing:i,delta:t}=vr.tick(e.direction,this.direction,t);return e.direction=i,e.spinVelocity=t,!1}}r=__webpack_require__(949);class kr extends r.LineCurve{constructor(e,t){super(e||new Os,t||new Os)}getPoint(e,t){return super.getPoint(e,t||new Os)}}r=__webpack_require__(949);class Or extends r.CurvePath{closePath(){let e=this.curves[0].getPoint(0);var t=this.curves[this.curves.length-1].getPoint(1);e.equals(t)||this.curves.push(new kr(t,e))}}var _r,Ir,r=__webpack_require__(949);class Cr extends r.QuadraticBezierCurve{constructor(e,t,i){super(e||new Os,t||new Os,i||new Os)}getPoint(e,t){return super.getPoint(e,t||new Os)}}(r=_r=_r||{})[r.None=0]="None",r[r.Start=1]="Start",r[r.Normal=2]="Normal",r[r.End=3]="End",r[r.Single=4]="Single";class Ar{constructor(e){this.game=e,this.hasMomentum=!1,this.moveOnCurve=!1,this.currentSpeed=0,this.distanceTravelled=0,this.carryOverDistance=0,this.currentWaypointType=_r.None}selectNextWaypoint(i,s){if(this.currentWaypointType=this.currentWaypointType&&this.currentWaypointType!==_r.End?_r.Normal:_r.Start,this.initialPosition=i.position.getMapPosition(),this.currentWaypointType!==_r.Start?i.moveTrait.speedPenalty=0:this.currentSpeed=0,1<s.length){var r=s[s.length-1],a=s[s.length-2],e=new Os(r.tile.rx-i.tile.rx,r.tile.ry-i.tile.ry),n=Math.abs(or(e)-or(new Os(a.tile.rx-r.tile.rx,a.tile.ry-r.tile.ry)));if(!Math.abs(vr.fromMapCoords(e)-i.direction)&&0<n&&n<90&&this.hasMomentum){this.moveOnCurve=!0,this.currentWaypointType=2===s.length?this.currentWaypointType===_r.Start?_r.Single:_r.End:_r.Normal;let e=this.initialPosition;i=new Os(r.tile.rx+.5,r.tile.ry+.5).multiplyScalar(_s.LEPTONS_PER_TILE);let t=new Os(a.tile.rx+.5,a.tile.ry+.5).multiplyScalar(_s.LEPTONS_PER_TILE);n=e.clone().lerp(i,.5),r=t.clone().lerp(i,.5);return this.steerCurve=new Or,this.steerCurve.add(new kr(e,n)),this.steerCurve.add(new Cr(n,i,r)),this.steerCurve.add(new kr(r,t)),this.lastPosition=e,a}}else this.currentWaypointType=this.currentWaypointType===_r.Start?_r.Single:_r.End;return this.hasMomentum=!0,this.moveOnCurve=!1,s[s.length-1]}onNewWaypoint(e,t,i){let s=(new Os).copy(t).sub(this.initialPosition);this.distanceTravelled=0,this.totalDistanceToTravel=this.moveOnCurve?this.steerCurve.getLength():s.length();t=vr.fromMapCoords(s);if(t!==e.direction&&(this.pointTurretToTarget(e,i),!this.moveOnCurve))return e.moveTrait.velocity.set(0,0,0),[new Sr(t)]}tick(i,s,r){this.pointTurretToTarget(i,r);let a=this.currentSpeed;a=i.rules.accelerates?(h=this.distanceTravelled/this.totalDistanceToTravel,this.currentSpeed=this.applyAcceleration(i,a,i.moveTrait.baseSpeed,h)):this.currentSpeed=i.moveTrait.baseSpeed,1<a&&(a=Math.floor(a));let e=this.game.map.terrain.getPassableSpeed(i.tile,i.rules.speedType,i.isInfantry(),i.onBridge,void 0,!0);e?i.moveTrait.lastTileSpeed=e:e=i.moveTrait.lastTileSpeed||1,a*=e,1<a&&(a=Math.floor(a)),this.carryOverDistance&&(a=this.carryOverDistance);var n=i.position.getMapPosition();let o;if(this.moveOnCurve){var r=this.steerCurve.getLength(),h=Math.min(this.distanceTravelled+a,r);this.carryOverDistance=Math.max(0,this.distanceTravelled+a-r),this.distanceTravelled=h;let e=this.steerCurve.getPointAt(this.distanceTravelled/r),t=this.steerCurve.getTangentAt(this.distanceTravelled/r);h=t.clone().setLength(a);i.moveTrait.velocity.set(h.x,0,h.y);var r=i.rules.rot,{facing:h,delta:r}=vr.tick(i.direction,vr.fromMapCoords(t),r);i.direction=h,i.spinVelocity=r;r=this.lastPosition;this.lastPosition=e.clone(),o=e.sub(r)}else{let e=(new Os).copy(s).sub(n);n=Math.min(e.length(),a);o=e.clone().setLength(n);let t=o.clone();this.carryOverDistance&&t.add(_s.vecWorldToGround(i.moveTrait.velocity)),i.moveTrait.velocity.set(t.x,0,t.y),this.distanceTravelled+=n,this.carryOverDistance=Math.max(0,a-e.length())}return{distance:new as(o.x,0,o.y),done:!o.length()||!!this.carryOverDistance}}pointTurretToTarget(t,i){if(t.turretTrait){t.attackTrait?.currentTarget?.obj&&(i=t.attackTrait.currentTarget.obj.position.getMapPosition());var s=t.position.getMapPosition();let e=(new Os).copy(i).sub(s);e.length()&&(s=vr.fromMapCoords(e),t.turretTrait.desiredFacing=s)}}applyAcceleration(e,t,i,s){if(this.currentWaypointType===_r.Single)return i/2;if(this.currentWaypointType!==_r.End)return Math.min(t+e.rules.accelerationFactor*i,i);return H(1,i,1-(s=this.moveOnCurve&&this.currentWaypointType===_r.End?s<=.5?0:2*(s-.5):s))}}class Br{constructor(e){this.game=e,this.currentMoveDirection=new Os,this.distanceToWaypoint=new Os,this.endPauseFrames=0}onNewWaypoint(e,t){this.currentMoveDirection.copy(t).sub(e.position.getMapPosition());t=vr.fromMapCoords(this.currentMoveDirection);t!==e.direction&&(e.direction=t),this.endPauseFrames=1}onWaypointUpdate(e,t){this.onNewWaypoint(e,t)}tick(e,t,i){let s=e.moveTrait.baseSpeed;s=Math.floor(s),e.stance===Fs.Prone&&(s*=e.art.crawls?.5:2),e.isPanicked&&(s*=2);let r=this.game.map.terrain.getPassableSpeed(e.tile,e.rules.speedType,e.isInfantry(),e.onBridge,void 0,!0);r?e.moveTrait.lastTileSpeed=r:r=e.moveTrait.lastTileSpeed||1,s*=r,s=Math.floor(s),this.distanceToWaypoint.copy(t).sub(e.position.getMapPosition());let a=this.distanceToWaypoint.clone().setLength(s);(a.length()||t.equals(i))&&e.moveTrait.velocity.set(a.x,0,a.y);i=Math.min(this.distanceToWaypoint.length(),s),e=!i&&0<this.endPauseFrames--;return this.distanceToWaypoint.setLength(i),{distance:new as(this.distanceToWaypoint.x,0,this.distanceToWaypoint.y),done:!this.distanceToWaypoint.length()&&!e}}}(r=Ir=Ir||{})[r.None=0]="None",r[r.Start=1]="Start",r[r.Normal=2]="Normal",r[r.End=3]="End",r[r.Single=4]="Single";class xr{constructor(e){this.hoverRules=e,this.currentSpeed=0,this.distanceTravelled=0,this.carryOverDistance=0,this.currentWaypointType=Ir.None,this.nextWaypointDir=new Os}selectNextWaypoint(e,t){var i;return this.currentWaypointType=this.currentWaypointType&&this.currentWaypointType!==Ir.End?Ir.Normal:Ir.Start,this.initialPosition=e.position.getMapPosition(),this.currentWaypointType===Ir.Start&&(this.currentSpeed=0),t.length<=1?(this.currentWaypointType=this.currentWaypointType===Ir.Start?Ir.Single:Ir.End,(i=t[t.length-1])&&this.nextWaypointDir.set(i.tile.rx-e.tile.rx,i.tile.ry-e.tile.ry)):(i=t[t.length-1],e=t[t.length-2],this.nextWaypointDir.set(e.tile.rx-i.tile.rx,e.tile.ry-i.tile.ry)),t[t.length-1]}onNewWaypoint(e,t,i){let s=(new Os).copy(t).sub(this.initialPosition);this.distanceTravelled=0,this.totalDistanceToTravel=s.length();t=this.maxSpeed=e.moveTrait.baseSpeed,e=60*this.hoverRules.acceleration*Us.BASE_TICKS_PER_SECOND;this.acceleration=t/e;e=60*this.hoverRules.brake*Us.BASE_TICKS_PER_SECOND;this.deceleration=t/e}tick(e,t){var i=e.position.getMapPosition();let s=t.clone().sub(i);t=s.length(),i=this.maxSpeed;this.currentWaypointType===Ir.Single?this.currentSpeed=i/2:this.currentWaypointType===Ir.End?(r=this.computeBrakeDistance(this.currentSpeed,this.deceleration),this.totalDistanceToTravel-this.distanceTravelled<=r&&(this.currentSpeed=Math.max(1,this.currentSpeed-this.deceleration))):this.currentSpeed=Math.min(this.currentSpeed+this.acceleration,i);var r=vr.fromMapCoords(s),i=vr.fromMapCoords(this.nextWaypointDir);let a=r,n=e.rules.rot;this.currentWaypointType===Ir.Normal&&r!==i&&(r=(o=lr(this.nextWaypointDir,vr.toMapCoords(e.direction)))/n,r=Math.max(this.currentSpeed*r,this.totalDistanceToTravel),this.totalDistanceToTravel-this.distanceTravelled<=r&&(a=i,n=o/((this.totalDistanceToTravel-this.distanceTravelled)/this.currentSpeed)));var o=vr.tick(e.direction,a,n)["facing"];e.direction=o;let h=this.currentSpeed;this.carryOverDistance&&(h=this.carryOverDistance);o=Math.min(h,t);let l=s.clone().setLength(o),c=l.clone();return this.carryOverDistance&&c.add(_s.vecWorldToGround(e.moveTrait.velocity)),e.moveTrait.velocity.set(c.x,0,c.y),this.distanceTravelled+=o,this.carryOverDistance=Math.max(0,h-t),{distance:new as(l.x,0,l.y),done:!l.length()||!!this.carryOverDistance}}computeBrakeDistance(e,t){var i=e/t;return Math.max(0,e*i-t*i*i/2)}}class Er{static computeInterceptPoint(e,t,i,s){let r=e.clone().sub(i);var a=s.length(),e=t*t-a*a,t=2*r.dot(s),a=-r.dot(r);if(t*t-4*e*a<0)return new as;e=(-t+Ki.sqrt(t*t-4*e*a))/(2*e);return s.clone().multiplyScalar(e).add(i)}static computeTurnCircle(e,t,i,s){s/=rr(Math.abs(i));let r=nr(t.clone(),90*-Math.sign(i));return{center:isFinite(s)?r.setLength(s).add(e):e.clone(),radius:s}}}var Pr=__webpack_require__(949);function Nr(e,t){var i=e.center;return(i.x-t.x)*(i.x-t.x)+(i.y-t.y)*(i.y-t.y)<=e.radius*e.radius}function Dr(e,t){let i=new Pr.Box2(new Pr.Vector2(e.x,e.y),new Pr.Vector2(e.x+e.width,e.y+e.height));return i.containsPoint(new Pr.Vector2(t.x,t.y))}class Mr{constructor(e){this.gameObject=e,this.type=rs.ObjectLiftOff}}class Rr{constructor(e){this.gameObject=e,this.type=rs.ObjectLand}}class Lr{static tickStationary(t,i){if(t.zone===Ss.Air){var s=t.tile.onBridgeLandType?i.map.tileOccupation.getBridgeOnTile(t.tile):void 0,r=!t.rules.balloonHover&&(!t.unitOrderTrait.getCurrentTask()?.preventLanding||!t.rules.hoverAttack)&&(i.map.getGroundObjectsOnTile(t.tile).find(e=>e.isBuilding()&&e.dockTrait?.isDocked(t))||i.map.getTileZone(t.tile)!==Ss.Water&&0<i.map.terrain.getPassableSpeed(t.tile,ti.Foot,!0,!!t.tile.onBridgeLandType)&&0===i.map.terrain.findObstacles({tile:t.tile,onBridge:s},t).length);let e;e=r?(a=t.tile.z+(s?.tileElevation??0),_s.tileHeightToWorld(a)):(n=t.tile.z+i.map.getGroundObjectsOnTile(t.tile).filter(e=>!(e.isInfantry()&&e.stance===Fs.Paradrop)).reduce((e,t)=>Math.max(e,t.tileElevation+t.art.height),0),_s.tileHeightToWorld(n)+t.rules.jumpjetHeight);var a,n,o=t.position.worldPosition.y;e!==o?(a=t.rules.jumpjetClimb,n=Math.abs(e-o),a=Math.sign(e-o)*Math.min(a,n),n=t.tileElevation,t.position.moveByLeptons3(new as(0,a,0)),t.moveTrait.handleElevationChange(n,i)):r&&(t.zone=Ss.Ground,t.onBridge=!!s,i.events.dispatch(new Rr(t)),(s=i.map.tileOccupation.getGroundObjectsOnTile(t.tile).find(e=>e.isOverlay()&&e.rules.crate))&&i.crateGeneratorTrait.pickupCrate(t,s,i))}}static tickCrash(e,t,i){var s=2*e.rules.jumpjetCrash;return e.direction=(e.direction-6+360)%360,new as(0,-s,0)}constructor(e){this.game=e,this.allowOutOfBounds=!0,this.currentMoveDir=new Os,this.currentHorizSpeed=0}onNewWaypoint(e,t,i){this.currentMoveDir=vr.toMapCoords(e.direction),this.cancelDestLeptons=void 0}tick(t,e,i,s){if(t.zone!==Ss.Air&&(t.onBridge=!1,t.zone=Ss.Air,this.game.events.dispatch(new Mr(t))),s){if(!this.cancelDestLeptons){let e=t.tile;this.game.map.isWithinBounds(e)||(e=this.game.map.clampWithinBounds(e)),this.cancelDestLeptons=this.computeCancelDest(e,i)}i=this.cancelDestLeptons}var r=t.position.getMapPosition();let a=i.clone().sub(r),n=this.findTilesToCheckForBlockers(t.tile,r,this.currentMoveDir,a.length());var o=n.map(e=>e.z+this.game.map.getGroundObjectsOnTile(e).filter(e=>!(e.isDestroyed||e.isInfantry()&&e.stance===Fs.Paradrop)).reduce((e,t)=>Math.max(e,t.tileElevation+t.art.height),0)).reduce((e,t)=>Math.max(e,t),0);let h=0;(void 0===this.lastClearZ||2<o-this.lastClearZ)&&(h=4);var l=_s.tileHeightToWorld(o),c=_s.tileHeightToWorld(o+h),u=t.position.worldPosition.y,d=vr.fromMapCoords(a),g=a.length()<t.rules.jumpjetSpeed;let p=0;l<=u&&!g&&({facing:T,delta:s}=vr.tick(t.direction,d,t.rules.jumpjetTurnRate),p=s,t.direction=T,this.currentMoveDir.copy(vr.toMapCoords(t.direction))),t.isVehicle()&&(t.spinVelocity=p);let m,f=!1,y=0,w=0;var T=t.rules.jumpjetClimb;u<c?(y=Math.min(T,c-u),m=!1,this.currentHorizSpeed=0):(this.lastClearZ=o,o=l+t.rules.jumpjetHeight,m=!0,o!==u&&(l=Math.abs(o-u),y=Math.sign(o-u)*Math.min(T,l),m=l<=T),T=this.currentHorizSpeed,this.currentHorizSpeed=Math.min(this.currentHorizSpeed+2,t.rules.jumpjetSpeed),f=d===t.direction?(w=Math.min(T,a.length()),T>=a.length()):((r=T||p?Er.computeTurnCircle(r,this.currentMoveDir,Math.sign(p)*t.rules.jumpjetTurnRate,T):void 0)&&Nr(r,i)?(w=0,this.currentHorizSpeed=0):w=T,!1));let b;b=g?(f=!0,a):this.currentMoveDir.clone().setLength(w);let v=new as(b.x,y,b.y);g=v.clone();return t.moveTrait.velocity.copy(g),{distance:v,done:f&&m}}findTilesToCheckForBlockers(e,t,i,s){s=i.clone().setLength(Math.min(s,_s.LEPTONS_PER_TILE)).add(t).multiplyScalar(1/_s.LEPTONS_PER_TILE).floor(),t=this.game.map.tiles.getByMapCoords(s.x,s.y);if(!t||t===e)return[e];s=Math.sign(t.rx-e.rx),t=Math.sign(t.ry-e.ry);let r=[e],a;return s&&(a=this.game.map.tiles.getByMapCoords(e.rx+s,e.ry),a&&r.push(a)),t&&(a=this.game.map.tiles.getByMapCoords(e.rx,e.ry+t),a&&r.push(a)),s&&t&&(a=this.game.map.tiles.getByMapCoords(e.rx+s,e.ry+t),a&&r.push(a)),r}computeCancelDest(e,t){var i=t.clone().multiplyScalar(1/_s.LEPTONS_PER_TILE).floor().multiplyScalar(_s.LEPTONS_PER_TILE),i=t.clone().sub(i);return new Os(e.rx,e.ry).multiplyScalar(_s.LEPTONS_PER_TILE).add(i)}}var Fr,jr,Ur,Wr,zr,Vr,Hr,Gr,$r,qr,Xr,Zr,Qr,Yr,Kr,Jr,ea,ta,ia,sa,ra,aa,na,oa,ha,la,ca,ua,da,ga,r=__webpack_require__(949);class pa extends r.CubicBezierCurve3{constructor(e,t,i,s){super(e||new as,t||new as,i||new as,s||new as)}getPoint(e,t){return super.getPoint(e,t||new as)}}(r=Fr=Fr||{})[r.Boost=0]="Boost",r[r.Midcourse=1]="Midcourse",r[r.Terminal=2]="Terminal";class ma{constructor(e,t){this.game=e,this.missileRules=t,this.flightPhase=Fr.Boost}selectNextWaypoint(e,t){var i=t[t.length-1],t=this.game.map.tileOccupation.getBridgeOnTile(i.tile),t=i.tile.z+(t?.tileElevation??0);return this.targetPosition=_s.tile3dToWorld(i.tile.rx+.5,i.tile.ry+.5,t),this.cruiseAltitude=_s.tileHeightToWorld(t)+this.missileRules.altitude,i}onNewWaypoint(e,t,i){}tick(i,e,t){let s=i.position.worldPosition.clone(),r=this.targetPosition.clone().sub(s);i.zone!==Ss.Air&&(i.onBridge=!1,i.zone=Ss.Air,this.game.events.dispatch(new Mr(i)));let a;var n;a=this.currentVelocity?(n=i.rules.speed,Math.min(this.currentVelocity.length()+this.missileRules.acceleration,n)):(g=this.missileRules.acceleration,this.missileRules.lazyCurve?this.currentVelocity=new as(r.x,0,r.z):this.currentVelocity=_s.vecGroundToWorld(vr.toMapCoords(i.direction)),mr(this.currentVelocity,new as(this.currentVelocity.x,1e8,this.currentVelocity.z),i.pitch),g),this.currentVelocity.setLength(a);let o=!1;switch(this.flightPhase){case Fr.Boost:if(!(i.position.worldPosition.y>=this.cruiseAltitude)){o=!1;break}this.flightPhase=Fr.Midcourse;case Fr.Midcourse:var h,l=new Os(r.x,r.z).length();if(!this.missileRules.lazyCurve){mr(this.currentVelocity,new as(this.currentVelocity.x,0,this.currentVelocity.z),i.rules.rot),this.currentVelocity.y<1&&(h=this.currentVelocity.length(),this.currentVelocity.y=0,this.currentVelocity.setLength(h)),mr(this.currentVelocity,new as(r.x,this.currentVelocity.y,r.z),i.rules.rot),i.direction=vr.fromMapCoords(_s.vecWorldToGround(this.currentVelocity)),i.pitch=Math.sign(this.currentVelocity.y)*cr(this.currentVelocity,new as(this.currentVelocity.x,0,this.currentVelocity.z)),l/(s.y-this.targetPosition.y)<1&&(this.flightPhase=Fr.Terminal);break}this.flightPhase=Fr.Terminal;var c=s.clone().add(this.currentVelocity.clone().setLength(l/3/Ki.cos(rr(i.pitch)))),u=this.targetPosition.clone().lerp(s,.15).setY(c.y);this.descentCurve=new pa(s,c,u,this.targetPosition);case Fr.Terminal:c=this.missileRules.bodyLength;if(this.missileRules.lazyCurve){var d=this.descentCurve.getLength();this.descentTravelled??(this.descentTravelled=0),this.descentTravelled+=Math.min(a,d-c-this.descentTravelled);u=this.descentTravelled/d;let e=this.descentCurve.getPointAt(u),t=this.descentCurve.getTangentAt(u);this.currentVelocity.copy(e.sub(s));u=t.clone().setY(0);i.pitch=Math.sign(t.y-u.y)*cr(u,t),o=1<=(this.descentTravelled+c)/d}else{mr(this.currentVelocity,r,i.rules.rot),i.direction=vr.fromMapCoords(_s.vecWorldToGround(this.currentVelocity)),i.pitch=Math.sign(this.currentVelocity.y)*cr(this.currentVelocity,new as(this.currentVelocity.x,0,this.currentVelocity.z));d=r.length()-c;(d<a||d<1)&&(this.currentVelocity.copy(r.clone().addScalar(-c)),o=!0)}break;default:throw new Error(`Unhandled flight phase "${this.flightPhase}"`)}var g=s.clone().add(this.currentVelocity);return this.game.map.isWithinHardBounds(g)?(i.moveTrait.velocity.copy(this.currentVelocity),{distance:this.currentVelocity,done:o}):(this.game.destroyObject(i),{done:!0,distance:new as})}}class fa extends Xs{constructor(e){super(Math.floor(Us.BASE_TICKS_PER_SECOND*e*60))}}class ya extends $s{constructor(e){super(),this.cb=e}onTick(e){return this.cb(e),!0}}(jr=jr||{}).onTick=Symbol(),(r=Ur=Ur||{})[r.Idle=0]="Idle",r[r.MoveToQueueingTile=1]="MoveToQueueingTile",r[r.WaitForTurn=2]="WaitForTurn",r[r.MoveToDock=3]="MoveToDock",r[r.Docking=4]="Docking",r[r.Docked=5]="Docked";class wa extends $s{constructor(e,t){super(),this.game=e,this.target=t,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.dockingStatus=Ur.Idle}onStart(e){if(!this.target.dockTrait)throw new Error(`Target object "${this.target.name}" is not a valid dock`);var t;this.target.dockTrait.hasReservedDockForUnit(e)?this.dockingStatus=Ur.MoveToDock:void 0!==(t=this.target.dockTrait.getFirstAvailableDockNumber())?(this.target.dockTrait.reserveDockAt(e,t),this.dockingStatus=Ur.MoveToDock):this.target.helipadTrait?this.cancel():this.dockingStatus=Ur.MoveToQueueingTile}onEnd(e){this.dockingStatus!==Ur.Docked&&this.target.isSpawned&&(this.target.dockTrait.undockUnit(e),this.target.dockTrait.unreserveDockForUnit(e)),this.dockingStatus=Ur.Idle}onTick(e){if(this.isCancelling())return!0;if(!this.isValidTarget(this.target,e))return!0;if(this.dockingStatus===Ur.MoveToQueueingTile){var t=this.findReachableQueueingTile(e);if(!t)return!0;if(e.tile!==t)return this.children.push(new _a(this.game,t,!1,{closeEnoughTiles:5}),new ya(()=>{e.moveTrait.lastMoveResult===Zr.Fail?this.cancel():e.moveTrait.lastMoveResult===Zr.CloseEnough&&(this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)||(this.dockingStatus=Ur.WaitForTurn))})),!1;this.dockingStatus=Ur.WaitForTurn}if(this.dockingStatus===Ur.WaitForTurn){var i=this.target.dockTrait.getFirstAvailableDockNumber();if(void 0===i)return this.children.push(new fa(1/60)),!1;this.target.dockTrait.reserveDockAt(e,i),this.dockingStatus=Ur.MoveToDock}if(this.dockingStatus===Ur.MoveToDock){var s=this.target.dockTrait.getReservedDockForUnit(e),i=this.target.dockTrait.getDockTile(s),s=_s.vecWorldToGround(this.target.dockTrait.getDockOffset(s)).add(this.target.position.getMapPosition()).sub(new Os(i.rx,i.ry).multiplyScalar(_s.LEPTONS_PER_TILE));if(e.tile!==i)return this.children.push(new _a(this.game,i,!1,{targetOffset:e.isAircraft()?s:void 0,closeEnoughTiles:0,strictCloseEnough:!0}),new ya(()=>{e.moveTrait.lastMoveResult===Zr.Fail&&this.cancel()})),this.game.afterTick(()=>e.unitOrderTrait[jr.onTick](e,this.game)),!1;this.dockingStatus=Ur.Docking}if(this.dockingStatus!==Ur.Docking)return!1;s=this.target.dockTrait.getReservedDockForUnit(e);return this.target.dockTrait.unreserveDockForUnit(e),this.target.dockTrait.dockUnitAt(e,s),e.isAircraft()&&e.airportBoundTrait&&this.target.helipadTrait&&(e.airportBoundTrait.preferredAirport=this.target),this.dockingStatus=Ur.Docked,!0}isValidTarget(e,t){return e.isSpawned&&this.game.areFriendly(e,t)}findReachableQueueingTile(t){var e=this.target.getFoundation(),e=new Os(this.target.tile.rx+e.width,this.target.tile.ry+e.height),e=this.game.map.tiles.getByMapCoords(e.x,e.y);return e&&this.isValidQueueingTile(e,t)?e:new Ws(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>this.isValidQueueingTile(e,t)).getNextTile()}isValidQueueingTile(e,t){var i=t.rules.movementZone===ai.Fly,s=t.rules.speedType,r=t.isInfantry();let a=!i&&this.game.map.terrain.getPassableSpeed(t.tile,s,r,t.onBridge)?this.game.map.terrain.getIslandIdMap(s,r):void 0;return(i||a?.get(e,!1)===a?.get(t.tile,t.onBridge)&&Math.abs(e.z-this.target.tile.z)<2&&!e.onBridgeLandType&&!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length)&&!this.game.map.tileOccupation.isTileOccupiedBy(e,this.target)}}(r=Wr=Wr||{})[r.None=0]="None",r[r.CircleStrafe=1]="CircleStrafe",r[r.HoverStrafe=2]="HoverStrafe";class Ta{static tickStationary(r,a){if(r.zone===Ss.Air){var n=r.tile.onBridgeLandType?a.map.tileOccupation.getBridgeOnTile(r.tile):void 0;let e=r.rules.landable&&!r.unitOrderTrait.getCurrentTask()?.preventLanding,i=r.spawnLinkTrait?.getParent();e&&i?e=!((!i.isUnit()||!i.onBridge)&&n||i.tile!==r.tile):e&&!r.airportBoundTrait&&(e=a.map.getTileZone(r.tile)!==Ss.Water&&0<a.map.terrain.getPassableSpeed(r.tile,ti.Foot,!0,!!r.tile.onBridgeLandType)&&0===a.map.terrain.findObstacles({tile:r.tile,onBridge:n},r).length);let s;if(e){let e=r.airportBoundTrait?.preferredAirport?.dockTrait;var o=e?.isDocked(r)||e?.hasReservedDockForUnit(r);if(!r.airportBoundTrait||o){var h=o?0:270;if(r.direction!==h)return void(r.direction=vr.tick(r.direction,h,r.rules.rot).facing)}if(r.airportBoundTrait){let e=r.airportBoundTrait.preferredAirport;if(!e?.dockTrait?.isDocked(r))return e?.dockTrait?.getAvailableDockCount()||(e=r.airportBoundTrait.findAvailableAirport(r),r.airportBoundTrait.preferredAirport=e,e&&(h=e.dockTrait.getFirstAvailableDockNumber(),e.dockTrait.reserveDockAt(r,h))),void(e?(r.unitOrderTrait.addTask(new wa(a,e)),r.unitOrderTrait[jr.onTick](r,a)):r.crashableTrait.crash(void 0))}let t;t=i?i.tile.z+i.tileElevation:r.tile.z+(n?.tileElevation??0),s=_s.tileHeightToWorld(t)}else{var t=r.tile.z+(n?.tileElevation??0),l=r.rules.flightLevel??a.rules.general.flightLevel;s=_s.tileHeightToWorld(t)+l}t=r.position.worldPosition.y;s!==t?(l=Math.abs(s-t),t=Math.sign(s-t)*Math.min(30,l),l=r.tileElevation,r.position.moveByLeptons3(new as(0,t,0)),r.moveTrait.handleElevationChange(l,a)):e&&(r.zone=Ss.Ground,i?i.airSpawnTrait.storeAircraft(r,a):r.onBridge=!!n,a.events.dispatch(new Rr(r)),(n=a.map.tileOccupation.getGroundObjectsOnTile(r.tile).find(e=>e.isOverlay()&&e.rules.crate))&&a.crateGeneratorTrait.pickupCrate(r,n,a))}}static tickCrash(e,t,i){i.rollDelta??(i.rollDelta=t.generateRandomInt(-15,15)),i.pitchDelta??(i.pitchDelta=t.generateRandomInt(0,15)),e.roll+=i.rollDelta,e.pitch+=i.pitchDelta;e=_s.vecWorldToGround(e.moveTrait.velocity);return new as(e.x,-30,e.y)}constructor(e){this.game=e,this.allowOutOfBounds=!0,this.lastDestLeptons=new Os,this.currentMoveDir=new Os,this.currentHorizSpeed=0,this.maneuverType=Wr.None,this.deceleratingToTurn=!1}onNewWaypoint(e,t,i){this.currentHorizSpeed=_s.vecWorldToGround(e.moveTrait.velocity).length(),this.cancelDestLeptons=void 0}tick(t,e,i,s){if(s){if(!this.cancelDestLeptons){let e=t.tile;this.game.map.isWithinBounds(e)||(e=this.game.map.clampWithinBounds(e)),this.cancelDestLeptons=this.computeCancelDest(e,i)}i=this.cancelDestLeptons}var r=t.position.getMapPosition();let a=i.clone().sub(r);var n=a.length();this.lastDestLeptons.equals(i)||(this.lastDestLeptons.copy(i),s?this.maneuverType=Wr.HoverStrafe:t.zone===Ss.Air&&this.currentHorizSpeed<5?this.maneuverType=n>_s.LEPTONS_PER_TILE?Wr.CircleStrafe:Wr.HoverStrafe:this.maneuverType=Wr.None,this.deceleratingToTurn=!1),t.zone!==Ss.Air&&(t.onBridge=!1,t.zone=Ss.Air,this.game.events.dispatch(new Mr(t)));var o=t.tile.onBridgeLandType?this.game.map.tileOccupation.getBridgeOnTile(t.tile):void 0,h=t.tile.z+(o?.tileElevation??0),l=t.rules.flightLevel??this.game.rules.general.flightLevel,s=_s.tileHeightToWorld(h)+l,o=t.position.worldPosition.y,c=vr.fromMapCoords(a);t.direction===c&&this.maneuverType===Wr.None&&n<=_s.LEPTONS_PER_TILE?this.maneuverType=Wr.HoverStrafe:t.direction===c&&this.maneuverType===Wr.CircleStrafe&&(this.maneuverType=Wr.None);let u;switch(this.maneuverType){case Wr.HoverStrafe:if(t.attackTrait?.currentTarget){let e=_s.vecWorldToGround(t.attackTrait.currentTarget.getWorldCoords());u=vr.fromMapCoords(e.sub(r))}else u=t.airportBoundTrait?.preferredAirport?.dockTrait?.hasReservedDockForUnit(t)?0:270;break;case Wr.CircleStrafe:case Wr.None:u=c;break;default:throw new Error(`Unknown maneuver type "${this.maneuverType}`)}var{facing:d,delta:g}=vr.tick(t.direction,u,t.rules.rot);t.direction=d,t.roll=Math.sign(g)*t.rules.pitchAngle;let p;switch(this.maneuverType){case Wr.HoverStrafe:p=c;break;case Wr.CircleStrafe:p=(d-90*Math.sign(g)+360)%360;break;case Wr.None:p=d;break;default:throw new Error(`Unknown maneuver type "${this.maneuverType}`)}void 0===this.thrustFacing&&(this.thrustFacing=p);var h=5<this.currentHorizSpeed?t.rules.rot:Number.POSITIVE_INFINITY,{facing:l,delta:h}=vr.tick(this.thrustFacing,p,h);this.thrustFacing=l,this.currentMoveDir.copy(vr.toMapCoords(this.thrustFacing));let m=!1,f=0,y=0;let w=!0;s!==o&&(b=Math.abs(s-o),f=Math.sign(s-o)*Math.min(30,b),w=b<=30);let T=t.rules.speed;n<=_s.LEPTONS_PER_TILE&&this.maneuverType!==Wr.CircleStrafe&&(T=H(1,T/2,Ki.sqrt(n/_s.LEPTONS_PER_TILE))),this.deceleratingToTurn?this.currentHorizSpeed=Math.max(0,this.currentHorizSpeed-2):this.currentHorizSpeed=Math.min(this.currentHorizSpeed+2,T);var b=this.currentHorizSpeed;this.deceleratingToTurn=!1,m=h?(h=b||h?Er.computeTurnCircle(r,this.currentMoveDir,Math.sign(h)*t.rules.rot,b):void 0,0!==b&&!Nr(h,i)||(this.maneuverType===Wr.HoverStrafe||n>_s.LEPTONS_PER_TILE?this.deceleratingToTurn=!0:this.maneuverType===Wr.None&&(this.maneuverType=Wr.HoverStrafe)),y=b,!1):(y=Math.min(b,n),n<=b);let v;v=n<1?(m=!0,a):m?a:this.currentMoveDir.clone().setLength(y);let S=new as(v.x,f,v.y);n=S.clone();return t.moveTrait.velocity.copy(n),{distance:S,done:m&&w}}computeCancelDest(e,t){var i=t.clone().multiplyScalar(1/_s.LEPTONS_PER_TILE).floor().multiplyScalar(_s.LEPTONS_PER_TILE),i=t.clone().sub(i);return new Os(e.rx,e.ry).multiplyScalar(_s.LEPTONS_PER_TILE).add(i)}}class ba{constructor(e){this.game=e}create(e){var t=e.rules.locomotor;switch(t){case ri.Infantry:return new Br(this.game);case ri.Jumpjet:return new Lr(this.game);case ri.Vehicle:case ri.Ship:return new Ar(this.game);case ri.Chrono:return e.isVehicle()&&e.harvesterTrait&&e.rules.teleporter?new Ar(this.game):new br(this.game);case ri.Aircraft:return new Ta(this.game);case ri.Missile:return new ma(this.game,this.game.rules.general.getMissileRules(e.name));case ri.Hover:return new xr(this.game.rules.general.hover);default:throw new Error(`Unhandled locomotor type ${t}`)}}}class va{constructor(e,t,i,s,r,a,n=!1,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=s,this.rng=r,this.predicate=a,this.includeStartTile=n,this.checkBounds=o,this.pool=[],this.pool=new Array(Ki.pow(2*this.maxDistance+1,2)).fill(0).map((e,t)=>t),this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){for(var e=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(this.includeStartTile||t!==this.startTile)return t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t)?t:void 0},t=2*this.maxDistance+1;this.pool.length;){var i=1<this.pool.length?this.rng.generateRandomInt(0,this.pool.length):0,s=this.pool.splice(i,1)[0],i=s%t,s=Math.floor(s/t),s=e(this.startTile.rx-this.maxDistance+i,this.startTile.ry-this.maxDistance+s);s&&(yield s)}}}class Sa{constructor(e,t,i){this.target=e,this.isChronoshift=t,this.prevTile=i,this.type=rs.ObjectTeleport}}(zr=zr||{}).onBeforeTeleport=Symbol();class ka{constructor(e){this.game=e,this.movePositionHelper=new Zs(e.map)}findPositions(e,t){let i=new Set,s=new Map;for(var r of e){var a=this.findFreeMovePosition(r,i,t);a&&(s.set(r,a),i.add(a.tile))}return s}findFreeMovePosition(i,e,{ignoredBlockers:t,excludedTiles:s,noSlopes:r}={}){let a=this.game.map,n=i.onBridge?a.tileOccupation.getBridgeOnTile(i.tile):void 0,o=new va(a.tiles,a.mapBounds,i.tile,1,this.game,e=>{if(s?.includes(e))return!1;var t=a.tileOccupation.getBridgeOnTile(e);return(t&&this.movePositionHelper.isEligibleTile(e,t,n,i.tile)||this.movePositionHelper.isEligibleTile(e,void 0,n,i.tile))&&(!r||0===e.rampType)}),h,l;for(;;){var c=o.getNextTile();if(!c)break;if(h=c,l=a.tileOccupation.getBridgeOnTile(c),l&&!this.movePositionHelper.isEligibleTile(c,l,n,i.tile)&&(l=void 0),!e.has(c)){let e=a.terrain.findObstacles({tile:c,onBridge:l},i);if(t&&t.length&&(e=e.filter(e=>!t.includes(e.obj))),!e.length)break}}if(h)return{tile:h,onBridge:l}}}class Oa extends $s{constructor(e,t,i){super(),this.game=e,this.target=t,this.options=i}onStart(i){if(!i.moveTrait.isDisabled()&&i.rules.movementZone!==ai.Fly){let e,t;if(this.target)({tile:e,toBridge:t}=this.target);else{i=new ka(this.game).findPositions([i],this.options).get(i);if(!i)return;e=i.tile,t=!!i.onBridge}this.children.push(new _a(this.game,e,t,{closeEnoughTiles:0,ignoredBlockers:this.options?.ignoredBlockers}))}}onTick(e){return!0}}class _a extends $s{constructor(e,t,i,s){super(),this.game=e,this.targetTile=t,this.toBridge=i,this.options=s,this.preventOpportunityFire=!1,this.logger=Tr.get("move"),this.destinationLeptons=new Os,this.currentWaypointLeptons=new Os,this.needsPathUpdate=!1,this.targetChangeRequested=!1,this.allObstaclesAreBlockers=!1,this.blockedPathNodes=[],this.unreachableTargets=[],this.pushTried=!1,this.cancelProcessed=!1,this.cancelRepositionPending=!1,this.targetLinesConfig={pathNodes:[]}}duplicate(){return new _a(this.game,this.targetTile,this.toBridge,this.options)}setForceMove(e){e?(this.options??(this.options={}),this.options.forceMove=!0):this.options?.forceMove&&(this.options.forceMove=void 0)}onStart(e){if(e.moveTrait.currentWaypoint)throw new Error("Nested move tasks are not supported");void 0===e.moveTrait.locomotor&&(e.moveTrait.locomotor=new ba(this.game).create(e)),e.moveTrait.lastTargetOffset?this.targetOffset=e.moveTrait.lastTargetOffset:this.targetOffset=this.computeTargetOffset(e),e.moveTrait.lastVelocity&&(e.moveTrait.velocity=e.moveTrait.lastVelocity),this.path||(this.groundPathPlan?(this.groundPathPlan.path[this.groundPathPlan.path.length-1].tile===e.tile?this.path=this.applyGroundPathPlan(this.groundPathPlan):this.computePath(e,e.moveTrait.locomotor),this.groundPathPlan=void 0):this.computePath(e,e.moveTrait.locomotor),this.targetLinesConfig.isRecalc=!1),this.updateDestination(this.path,this.targetOffset),e.moveTrait.moveState=Xr.ReachedNextWaypoint,e.moveTrait.lastMoveResult=void 0,e.moveTrait.lastTargetOffset=void 0,e.moveTrait.lastVelocity=void 0}computeTargetOffset(e){return this.options?.targetOffset??(e.isInfantry()?e.position.getTileOffset():e.position.computeSubCellOffset(0))}computePath(e,t){let i;i=this.options?.allowOutOfBoundsTarget||this.game.map.mapBounds.isWithinBounds(this.targetTile)?e.rules.movementZone===ai.Fly?this.computeAirPath(e):t.ignoresTerrain?this.computeDirectJumpPath(e):(t=this.computeGroundPath(e),this.applyGroundPathPlan(t)):[],e.rules.movementZone===ai.Fly?(this.targetLinesConfig.pathNodes=i.map(({tile:e,onBridge:t})=>({tile:e,onBridge:t})),i.length&&(this.targetLinesConfig.pathNodes[0].onBridge=this.toBridge?this.game.map.tileOccupation.getBridgeOnTile(this.targetTile):void 0)):this.targetLinesConfig.pathNodes=i,this.path=i}computeAirPath(e){return[{tile:this.targetTile,onBridge:void 0},{tile:e.tile,onBridge:void 0}]}computeDirectJumpPath(t){let i=this.game.map;var e=t.onBridge?i.tileOccupation.getBridgeOnTile(t.tile):void 0;let s=this.targetTile,r=this.toBridge?i.tileOccupation.getBridgeOnTile(this.targetTile):void 0,a=this.options?.ignoredBlockers;var n=new Ws(i.tiles,i.mapBounds,s,{width:1,height:1},0,5,e=>0<i.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!!e.onBridgeLandType,a)&&!i.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},t).find(e=>!a?.includes(e.obj))).getNextTile();return n?(n!==s&&(s=n,r=i.tileOccupation.getBridgeOnTile(s)),[{tile:s,onBridge:r},{tile:t.tile,onBridge:e}]):[]}computeGroundPath(t){let e=t.tile,i=t.onBridge?this.game.map.tileOccupation.getBridgeOnTile(e):void 0;t.moveTrait.moveState===Xr.Moving&&t.moveTrait.currentWaypoint&&(e=t.moveTrait.currentWaypoint.tile,i=t.moveTrait.currentWaypoint.onBridge);let s={path:[],ignoredBlockers:[],blockedPathNodes:[]};const r=this.game.map.getObjectsOnTile(e).find(e=>e.isBuilding());if(r&&!this.game.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)){var a=this.options?.ignoredBlockers?.includes(r);if(a||s.ignoredBlockers.push(r),!a&&r.dockTrait){let t=new Set(r.dockTrait?.getAllDockTiles()),e=this.game.map.tileOccupation.calculateTilesForGameObject(r.tile,r);e.filter(e=>!t.has(e)).forEach(e=>s.blockedPathNodes.push({node:{tile:e,onBridge:void 0},obj:r}))}}var n=this.game.map.getGroundObjectsOnTile(this.targetTile).find(e=>(e.isInfantry()||e.isVehicle())&&e.disguiseTrait?.hasTerrainDisguise()&&!(this.game.alliances.haveSharedIntel(t.owner,e.owner)||e.owner.sharedDetectDisguiseTrait?.has(t)));n&&(a=this.toBridge?this.game.map.tileOccupation.getBridgeOnTile(this.targetTile):void 0,s.blockedPathNodes.push({node:{tile:this.targetTile,onBridge:a},obj:n}));let o=[...new Set([...this.options?.ignoredBlockers??[],...s.ignoredBlockers])],h=[...this.blockedPathNodes,...s.blockedPathNodes];n=this.game.map.terrain.computePath(t.rules.speedType,t.isInfantry(),e,!!i,this.targetTile,this.toBridge,{maxExpandedNodes:this.allObstaclesAreBlockers?Math.min(300,this.options?.maxExpandedPathNodes??Number.POSITIVE_INFINITY):this.options?.maxExpandedPathNodes,bestEffort:!this.options?.strictCloseEnough,ignoredBlockers:[...new Set([...o,...this.options?.pathFinderIgnoredBlockers??[]])],excludeTiles:this.allObstaclesAreBlockers||h.length?e=>this.nodeIsBlockedForPathfinding(e,t,o,h):void 0});return s.path=n,s}nodeIsBlockedForPathfinding(t,e,i,s){return this.allObstaclesAreBlockers?!!this.game.map.terrain.findObstacles(t,e).find(e=>!i?.includes(e.obj)):!!s.find(({node:e})=>e.tile===t.tile&&e.onBridge===t.onBridge)}applyGroundPathPlan(e){var t;return this.blockedPathNodes=this.blockedPathNodes.filter(e=>e.obj.isSpawned&&e.node.tile===e.obj.tile),e.ignoredBlockers.length&&(this.options??(this.options={}),(t=this.options).ignoredBlockers??(t.ignoredBlockers=[]),this.options.ignoredBlockers.push(...e.ignoredBlockers)),this.blockedPathNodes.push(...e.blockedPathNodes),e.path}updateDestination(e,t){e=e.length?e[0].tile:this.targetTile;this.destinationLeptons.set(e.rx*_s.LEPTONS_PER_TILE,e.ry*_s.LEPTONS_PER_TILE).add(t)}canStopAtTile(t,i,s){if(t.zone===Ss.Air){if((!t.isAircraft()||!t.airportBoundTrait)&&!t.rules.spawned&&(!this.options?.forceMove||!t.rules.balloonHover||t.rules.hoverAttack)&&(!this.game.map.terrain.getPassableSpeed(i,ti.Amphibious,!1,s)||this.game.map.getObjectsOnTile(i).filter(e=>e.isBuilding()&&!e.isDestroyed&&!e.dockTrait?.hasReservedDockForUnit(t)&&!t.rules.dock.includes(e.name)||e.isUnit()&&e.tile===i&&e.moveTrait.moveState!==Xr.Moving&&e!==t).length))return!1}else if(t.isInfantry()){let e=this.game.map.getGroundObjectsOnTile(i).filter(e=>e.isInfantry()&&e.tile===i&&e.onBridge===s&&e.moveTrait.moveState!==Xr.Moving&&e!==t);if(2<e.length||e.find(e=>e.position.subCell===t.position.subCell))return!1}return!(t.zone!==Ss.Air&&t.rules.tooBigToFitUnderBridge&&!s&&i.onBridgeLandType&&this.game.map.tileOccupation.getBridgeOnTile(i)?.isHighBridge())&&!(!this.isCancelling()&&this.options?.strictCloseEnough&&void 0!==this.options?.closeEnoughTiles&&!this.isCloseEnoughToDest(t,i,this.options.closeEnoughTiles))}isCloseEnoughToDest(e,t,i){if(void 0===i)return!0;let s=new Bs(this.game.map.tileOccupation);return!(s.tileDistance(this.targetTile,t)>i)}hasReachedDestination(e){return!this.path.length}updateTarget(e,t){this.targetTile=e,this.toBridge=t,this.needsPathUpdate=!0,this.targetChangeRequested=!0}onEnd(e){e.moveTrait.collisionState=Qr.Resolved,e.moveTrait.currentWaypoint=void 0,this.targetOffset.equals(this.computeTargetOffset(e))||(e.moveTrait.lastTargetOffset=this.targetOffset)}forceCancel(e){return!(!this.cancellable||this.children.some(e=>!e.cancellable))&&(!(!this.options?.allowOutOfBoundsTarget&&!this.game.map.isWithinBounds(e.tile))&&(this.status!==js.Running&&this.status!==js.Cancelling||(e.moveTrait.unreservePathNodes(),e.moveTrait.lastMoveResult=Zr.Cancel,this.onEnd(e),e.moveTrait.lastTargetOffset=this.targetOffset,e.moveTrait.lastVelocity=e.moveTrait.velocity.clone()),this.status=js.Cancelled,!0))}onTick(r){if(r.moveTrait.isDisabled()&&r.moveTrait.moveState===Xr.ReachedNextWaypoint)return!!this.isCancelling()&&(r.moveTrait.lastMoveResult=Zr.Cancel,!0);this.needsPathUpdate&&(r.moveTrait.moveState===Xr.PlanMove&&(this.inPlanningForTicks=void 0,r.moveTrait.currentWaypoint=void 0,r.moveTrait.collisionState=Qr.Resolved,r.moveTrait.moveState=Xr.ReachedNextWaypoint,r.moveTrait.velocity.set(0,0,0)),this.computePath(r,r.moveTrait.locomotor),this.path.length||this.unreachableTargets.push({tile:this.targetTile,toBridge:this.toBridge}),this.updateDestination(this.path,this.targetOffset),this.targetLinesConfig.isRecalc=!this.targetChangeRequested,this.targetChangeRequested=!1,this.needsPathUpdate=!1,this.allObstaclesAreBlockers=!1);let i=this.game.map;if(r.moveTrait.moveState===Xr.ReachedNextWaypoint){r.moveTrait.unreservePathNodes();var s=this.path.findIndex(e=>e===r.moveTrait.currentWaypoint);if(-1!==s?this.path.splice(s):this.path.pop(),r.moveTrait.currentWaypoint=void 0,this.isCancelling()?!this.cancelProcessed:this.hasReachedDestination(r)){var a=!this.isCancelling()&&!this.isCloseEnoughToDest(r,r.tile,this.options?.closeEnoughTiles);if(!a&&this.canStopAtTile(r,r.tile,r.onBridge))return r.moveTrait.lastMoveResult=this.isCancelling()?Zr.Cancel:Zr.Success,!0;{if(5<this.unreachableTargets.length)return r.moveTrait.lastMoveResult=Zr.Fail,this.log(r,"bail_max_unreachable_dest"),!0;let e=r.tile,t=r.onBridge?i.tileOccupation.getBridgeOnTile(e):void 0;a&&(e=this.targetTile,t=this.toBridge?i.tileOccupation.getBridgeOnTile(e):void 0);s=this.findRelocationTile(e,t,r);if(!s)return r.moveTrait.lastMoveResult=a?Zr.Fail:Zr.CloseEnough,this.log(r,"bail_no_free_dest"),!0;a=!t||t.isHighBridge()?i.tileOccupation.getBridgeOnTile(s):void 0;return this.updateTarget(s,!!a),this.isCancelling()&&(this.cancelProcessed=!0,this.cancelRepositionPending=!0),!1}}if(this.cancelProcessed&&!this.path.length)return r.moveTrait.lastMoveResult=Zr.Cancel,!0;this.cancelProcessed=!1,r.moveTrait.moveState=Xr.PlanMove;let e=r.moveTrait.locomotor;r.moveTrait.currentWaypoint=e.selectNextWaypoint?e.selectNextWaypoint(r,this.path):this.path[this.path.length-1],this.currentWaypointLeptons.set(r.moveTrait.currentWaypoint.tile.rx,r.moveTrait.currentWaypoint.tile.ry).multiplyScalar(_s.LEPTONS_PER_TILE).add(this.targetOffset);a=e.onNewWaypoint(r,this.currentWaypointLeptons,this.destinationLeptons);if(a)return this.children.push(...a),!1}if(r.moveTrait.moveState===Xr.PlanMove){if(this.isCancelling()&&!this.cancelRepositionPending)return r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r);if(this.inPlanningForTicks=void 0===this.inPlanningForTicks?0:this.inPlanningForTicks+1,200<this.inPlanningForTicks)return this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,r.moveTrait.velocity.set(0,0,0),this.log(r,"repath_plan_timeout"),!1;if(r.rules.movementZone!==ai.Fly&&!r.moveTrait.locomotor.ignoresTerrain){let t=this.path.slice(this.path.indexOf(r.moveTrait.currentWaypoint)).reverse();var e,n,o,h=r.moveTrait.velocity.length();for(e of t)e.onBridge?.isDestroyed&&(e.onBridge=void 0);for(n of t){if(!i.terrain.getPassableSpeed(n.tile,r.rules.speedType,r.isInfantry(),!!n.onBridge,this.options?.ignoredBlockers))return this.options?.stopOnBlocker&&i.terrain.findObstacles(n,r).some(e=>e.obj===this.options.stopOnBlocker)?(r.moveTrait.lastMoveResult=Zr.CloseEnough,!0):(this.needsPathUpdate=!0,r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r));if(!n.onBridge){var l=i.getGroundObjectsOnTile(n.tile).find(e=>e.isOverlay()&&e.rules.crate);if(l)if(this.game.crateGeneratorTrait.peekInsideCrate(l)===Es.Unit){this.game.crateGeneratorTrait.pickupCrate(r,l,this.game);l=this.game.map.getGroundObjectsOnTile(n.tile).find(e=>e.isUnit()&&!e.onBridge);if(l)return this.needsPathUpdate=!0,this.blockedPathNodes.push({node:n,obj:l}),r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r)}}for(o of i.terrain.findObstacles(n,r).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj))){if(o.static)return this.needsPathUpdate=!0,r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r);if(o.obj.rules.crushable){if([ti.Track,ti.Hover].includes(r.rules.speedType)&&r.crusher&&(!o.obj.isTechno()||!this.game.areFriendly(o.obj,r)))continue;if(!o.obj.isTechno())return this.needsPathUpdate=!0,r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r)}if(o.obj.isTerrain()){if(!r.isInfantry())throw new Error(`Obstacle ${o.obj.name} should be a blocker for non infantry`);var c=this.findFreeSubCell(r,n);return void 0!==c?this.relocateToSubCell(r,c):(this.needsPathUpdate=!0,this.blockedPathNodes.push({node:n,obj:o.obj}),r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint),this.onTick(r)}if(!o.obj.isTechno())throw new Error(`Unexpected obstacle of type ${o.obj.type}`);const y=o.obj;var u=y.isUnit()?y.moveTrait.velocity.length():0;if(!y.isAircraft()||y.zone!==Ss.Ground||!this.options?.ignoredBlockers?.some(e=>e.isBuilding()&&e.dockTrait?.isDocked(y))){if(1===t.length&&y.isUnit()&&u&&h&&h<=u&&r.direction===y.direction&&y.tile===n.tile&&y.moveTrait.currentWaypoint?.tile!==n.tile)break;if(y.isBuilding()||y.moveTrait.moveState===Xr.Idle||y.moveTrait.collisionState!==Qr.Resolved){if(!h&&r.moveTrait.collisionState!==Qr.Resolved&&y.isUnit()&&y.moveTrait.collisionState!==Qr.Resolved)return 200<this.inPlanningForTicks+1&&(this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,this.log(r,"repath_waited_too_long_blocker "+y.id),r.moveTrait.velocity.set(0,0,0)),!1;{if(y.isInfantry()&&r.isInfantry()&&y.moveTrait.collisionState===Qr.Resolved){var d=this.findFreeSubCell(r,n);if(void 0!==d)return this.relocateToSubCell(r,d),this.onTick(r)}c=qs(this.path.slice(0,this.path.indexOf(n)),e=>!i.terrain.findObstacles(e,r).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj)).length);if(-1===c){if(this.canStopAtTile(r,r.tile,r.onBridge)&&this.isCloseEnoughToDest(r,r.tile,this.options?.closeEnoughTiles))return r.moveTrait.lastMoveResult=Zr.CloseEnough,this.log(r,"bail_waypoints_blocked_close_enough"),!0;if(!(0===this.options?.closeEnoughTiles||Math.abs(r.tile.rx-this.targetTile.rx)<=1&&Math.abs(r.tile.ry-this.targetTile.ry)<=1))return this.needsPathUpdate=!0,this.blockedPathNodes.push(...this.path.slice(0,this.path.indexOf(n)+1).map(e=>({node:e,obj:i.terrain.findObstacles(e,r)[0].obj}))),r.moveTrait.velocity.set(0,0,0),this.log(r,"repath_waypoints_blocked_too_far"),!1}let e;if(e=-1!==c?(d=this.path[c],i.terrain.computePath(r.rules.speedType,r.isInfantry(),r.tile,r.onBridge,d.tile,!!d.onBridge,{maxExpandedNodes:15,bestEffort:!1,excludeTiles:e=>!!i.terrain.findObstacles(e,r).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj)).length,ignoredBlockers:this.options?.ignoredBlockers})):[],e.length||y.owner!==r.owner||1!==t.length)return e.length?(this.path.splice(c,this.path.length,...e),r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r)):((g=this.selectWeaponVsObstacle(r,y))?(this.children.push(r.attackTrait.createAttackTask(this.game,y,y.tile,g,{passive:!0,holdGround:!0})),r.moveTrait.velocity.set(0,0,0)):this.options?.forceWaitOnPathBlocked?(this.children.push(new Xs(40)),this.inPlanningForTicks=0,r.moveTrait.velocity.set(0,0,0),r.moveTrait.collisionState=Qr.Waiting):(this.needsPathUpdate=!0,this.blockedPathNodes.push({node:n,obj:y}),y.isBuilding()&&(this.allObstaclesAreBlockers=!0),this.log(r,"repath_unavoidable_blocker "+y.id),r.moveTrait.velocity.set(0,0,0)),!1);g=y.unitOrderTrait.hasTasks();if(this.pushTried||y.isBuilding()||y.moveTrait.collisionState===Qr.Waiting||g||y.isAircraft()&&y.missileSpawnTrait)return!this.options?.forceWaitOnPathBlocked&&(y.isBuilding()||g&&y.moveTrait.moveState===Xr.Idle||200<this.inPlanningForTicks+40)?(this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,this.log(r,"repath_blocker_busy_wait_timeout "+y.id),r.moveTrait.velocity.set(0,0,0)):(this.children.push(new Xs(40)),this.options?.forceWaitOnPathBlocked?this.inPlanningForTicks=0:this.inPlanningForTicks+=40,r.moveTrait.velocity.set(0,0,0),r.moveTrait.collisionState=Qr.Waiting),!1;g=new Os(y.tile.rx-r.tile.rx,y.tile.ry-r.tile.ry);return this.pushTried=!0,y.unitOrderTrait.addTask(new wr(this.game,g)),this.children.push(new Xs(1)),r.moveTrait.velocity.set(0,0,0),r.moveTrait.collisionState=Qr.Waiting,this.log(r,"push "+y.id),!1}}if(y.isInfantry()&&r.isInfantry()){var g=this.findFreeSubCell(r,n);if(void 0!==g)return this.relocateToSubCell(r,g),this.onTick(r)}if(!h)return 40<this.inPlanningForTicks&&(r.moveTrait.collisionState=Qr.Waiting),!1;if(180===Math.abs(r.direction-y.direction))return r.moveTrait.velocity.set(0,0,0),r.moveTrait.collisionState=Qr.Waiting,!1;if(Math.abs(r.direction-y.direction)<=45&&1.5*u<h){u=this.path.indexOf(n);if(5<=u){let e=qs(this.path.slice(0,u-5),e=>!i.terrain.findObstacles(e,r).length);if(-1!==e){u=this.path[e],u=i.terrain.computePath(r.rules.speedType,r.isInfantry(),r.tile,r.onBridge,u.tile,!!u.onBridge,{maxExpandedNodes:15,bestEffort:!1,excludeTiles:t=>!!i.terrain.findObstacles(t,r).length||this.path.findIndex(e=>e.tile===t.tile&&e.onBridge===t.onBridge)>e});if(u.length)return this.path.splice(e,this.path.length,...u),r.moveTrait.currentWaypoint=void 0,r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r)}}return r.moveTrait.collisionState=Qr.Waiting,r.moveTrait.velocity.set(0,0,0),!1}return r.moveTrait.velocity.set(0,0,0),r.moveTrait.collisionState=Qr.Waiting,!1}}}if(r.rules.speedType===ti.Track&&h){var p,m=this.path.indexOf(r.moveTrait.currentWaypoint);if(0<m){let t=this.path[m-1];for(p of i.getGroundObjectsOnTile(t.tile).filter(e=>e.isUnit()&&e.onBridge===!!t.onBridge&&e.rules.crushable&&e.veteranTrait?.hasVeteranAbility(ci.SCATTER)&&!this.game.areFriendly(e,r)))p.unitOrderTrait.hasTasks()||p.unitOrderTrait.addTask(new Oa(this.game))}}r.moveTrait.reservedPathNodes.length||(r.moveTrait.reservedPathNodes.push(...t),t.forEach(e=>{i.tileOccupation.occupySingleTile(e.tile,r)}))}r.moveTrait.moveState=Xr.Moving,this.inPlanningForTicks=void 0,this.unreachableTargets.length=0,this.pushTried=!1,r.moveTrait.collisionState===Qr.Waiting&&(r.moveTrait.collisionState=Qr.Resolved)}if(r.moveTrait.moveState===Xr.Moving){let e=r.moveTrait.locomotor,{distance:t,done:i,isTeleport:s}=e.tick(r,this.currentWaypointLeptons,this.destinationLeptons,(this.isCancelling()||!this.path.length)&&!this.cancelRepositionPending);if(s&&r.traits.filter(zr).forEach(e=>{e[zr.onBeforeTeleport](r,this.game,!0,!0)}),t.length()){a=r.tile,m=e.allowOutOfBounds;if(t.y?(f=r.tileElevation,r.position.moveByLeptons3(t,m),r.moveTrait.handleElevationChange(f,this.game)):r.position.moveByLeptons(t.x,t.z,m),r.tile!==a){var f=r.onBridge?this.game.map.tileOccupation.getBridgeOnTile(a):void 0,m=function(t,i){for(let e=t.length-1;0<=e;e--)if(i(t[e],e,t))return t[e]}(this.path,e=>e.tile===r.tile);let e=m?m.onBridge:f||r.moveTrait.currentWaypoint.onBridge?this.game.map.tileOccupation.getBridgeOnTile(r.tile):void 0;if(e?.isDestroyed&&(e=void 0),r.moveTrait.handleTileChange(a,e,!1,this.game,s),s&&(r.moveTrait.lastTeleportTick=this.game.currentTick,this.game.events.dispatch(new Sa(r,!0,a))),r.isDestroyed)return!0}}if(i)return r.moveTrait.moveState=Xr.ReachedNextWaypoint,this.onTick(r)}return!1}selectWeaponVsObstacle(e,t){let i;if(!this.game.areFriendly(t,e)&&e.attackTrait&&!e.attackTrait.isDisabled()&&e.attackTrait.isIdle()&&(i=e.attackTrait.selectWeaponVersus(e,t,this.game,!1,!0))&&i.name!==e.armedTrait?.deathWeapon?.name&&(!i.rules.limboLaunch||!i.warhead.rules.parasite)&&!i.warhead.rules.mindControl)return i}findRelocationTile(a,n,o){let h=this.game.map,i;if(o.rules.movementZone===ai.Fly){var t=e=>!h.tileOccupation.getGroundObjectsOnTile(e).some(e=>e.isBuilding()&&!e.isDestroyed||e.isTerrain()||e.isOverlay()&&e.rules.isARock);let e=new va(h.tiles,h.mapBounds,a,1,this.game,t);if(i=e.getNextTile(),!i){let e=new Ws(h.tiles,h.mapBounds,a,o.getFoundation(),2,15,t);i=e.getNextTile()}}else{let e=!this.options?.ignoredBlockers?.length&&h.terrain.getPassableSpeed(o.tile,o.rules.speedType,o.isInfantry(),o.onBridge)?this.game.map.terrain.getIslandIdMap(o.rules.speedType,o.isInfantry()):void 0,s=e?.get(o.tile,o.onBridge),r=new Zs(h),t=new Ws(h.tiles,h.mapBounds,a,{width:1,height:1},0,5,t=>{let i=!n||n.isHighBridge()?h.tileOccupation.getBridgeOnTile(t):void 0;return!this.unreachableTargets.find(e=>e.tile===t&&e.toBridge===!!i)&&(o.zone===Ss.Air||e?.get(t,!!i)===s&&!h.terrain.findObstacles({tile:t,onBridge:i},o).length&&r.isEligibleTile(t,i,n,a))&&this.canStopAtTile(o,t,!!i)});i=t.getNextTile()}return i}findFreeSubCell(t,i){let e=this.game.map.getGroundObjectsOnTile(i.tile);var s=e.filter(e=>e.isInfantry()&&e.onBridge===!!i.onBridge&&e!==t).map(e=>e.position.desiredSubCell),r=e.filter(e=>e.isTerrain()).map(e=>e.rules.getOccupiedSubCells(this.game.map.getTheaterType())).flat();let a=[...s,...r];return Fa.SUB_CELLS.find(e=>-1===a.indexOf(e))}relocateToSubCell(e,t){e.position.desiredSubCell=t;t=e.position.computeSubCellOffset(t);this.targetOffset=t,this.currentWaypointLeptons.set(e.moveTrait.currentWaypoint.tile.rx,e.moveTrait.currentWaypoint.tile.ry).multiplyScalar(_s.LEPTONS_PER_TILE).add(this.targetOffset),this.updateDestination(this.path,this.targetOffset),e.moveTrait.locomotor.onWaypointUpdate?.(e,this.currentWaypointLeptons,this.destinationLeptons)}getTargetLinesConfig(e){var t,i;return this.path||(t=new ba(this.game).create(e),(this.options?.allowOutOfBoundsTarget||this.game.map.mapBounds.isWithinBounds(this.targetTile))&&e.rules.movementZone!==ai.Fly&&!t.ignoresTerrain&&e.unitOrderTrait.getCurrentTask()?.isCancelling()?this.groundPathPlan||(i=this.computeGroundPath(e),this.targetLinesConfig.pathNodes=i.path,i.path.length&&(this.groundPathPlan=i)):((i=e.moveTrait).locomotor??(i.locomotor=t),this.computePath(e,e.moveTrait.locomotor)),this.targetLinesConfig.isRecalc=!1),this.targetLinesConfig}log(e,t){this.logger.debug(`<${e.id}>: ${t}`)}}(Vr=Vr||{}).onDestroy=Symbol(),(r=Hr=Hr||{})[r.None=0]="None",r[r.Normal=1]="Normal",r[r.Demolish=2]="Demolish",r[r.Crush=3]="Crush",r[r.Temporal=4]="Temporal",r[r.Sink=5]="Sink",(Gr=Gr||{}).onTileChange=Symbol(),($r=$r||{}).onTileChange=Symbol();class Ia{constructor(e,t){this.target=e,this.source=t,this.type=rs.EnterTile}}(qr=qr||{}).onElevationChange=Symbol(),(r=Xr=Xr||{})[r.Idle=0]="Idle",r[r.ReachedNextWaypoint=1]="ReachedNextWaypoint",r[r.PlanMove=2]="PlanMove",r[r.Moving=3]="Moving",(r=Zr=Zr||{})[r.Success=0]="Success",r[r.Cancel=1]="Cancel",r[r.CloseEnough=2]="CloseEnough",r[r.Fail=3]="Fail",(r=Qr=Qr||{})[r.Waiting=0]="Waiting",r[r.Resolved=1]="Resolved";const Ca=e=>e instanceof _a||e.children[0]&&Ca(e.children[0]);class Aa{get baseSpeed(){return this.gameObject.rules.speed*(this.gameObject.veteranTrait?.getVeteranSpeedMultiplier()??1)*this.gameObject.crateBonuses.speed*(this.gameObject.isVehicle()&&this.gameObject.healthTrait.health<=50&&this.gameObject.rules.locomotor!==ri.Hover?.75:1)*(1-this.speedPenalty)}constructor(e,t){this.gameObject=e,this.tileOccupation=t,this.disabled=!1,this.speedPenalty=0,this.velocity=new as,this.reservedPathNodes=[],this.moveState=Xr.Idle,this.collisionState=Qr.Resolved}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}isMoving(){return this.moveState===Xr.Moving}isIdle(){return this.moveState===Xr.Idle}isWaiting(){return this.collisionState===Qr.Waiting}[jr.onTick](e,t){var i;this.moveState!==Xr.Idle&&this.collisionState===Qr.Resolved&&((i=e.unitOrderTrait.getCurrentTask())&&Ca(i)||(this.velocity.set(0,0,0),this.moveState=Xr.Idle,this.locomotor=void 0,!i&&!e.attackTrait?.currentTarget&&e.isVehicle()&&e.turretTrait&&(e.turretTrait.desiredFacing=e.direction))),this.moveState===Xr.Idle&&(e.rules.locomotor===ri.Jumpjet?Lr.tickStationary(e,t):e.isAircraft()&&e.rules.locomotor===ri.Aircraft&&Ta.tickStationary(e,t))}[Vr.onDestroy](e,t){this.unreservePathNodes()}teleportUnitToTile(e,t,i,s,r){let a=this.gameObject;var n=a.tile;a.traits.filter(zr).forEach(e=>{e[zr.onBeforeTeleport](a,r,i,s)}),a.position.tileElevation=a.tileElevation,a.position.tile=e,a.position.subCell=a.position.desiredSubCell,this.handleTileChange(n,t,!0,r,!0),s||(this.unreservePathNodes(),this.speedPenalty=0,this.velocity.set(0,0,0),this.moveState=Xr.Idle,this.collisionState=Qr.Resolved,this.locomotor=void 0,this.currentWaypoint=void 0,this.lastTargetOffset=void 0,this.lastVelocity=void 0,this.lastMoveResult=Zr.Cancel,a.isVehicle()&&(a.spinVelocity=0,a.turretTrait&&(a.turretTrait.desiredFacing=a.direction))),this.lastTeleportTick=r.currentTick,r.events.dispatch(new Sa(a,i,n))}handleTileChange(t,e,i,s,r=!1){const a=this.gameObject;if(s.map.tileOccupation.unoccupyTileRange(t,a),s.map.tileOccupation.occupyTileRange(a.tile,a),s.map.technosByTile.updateObject(a),a.zone!==Ss.Air){var n=a.onBridge?s.map.tileOccupation.getBridgeOnTile(t):void 0,o=a.onBridge?t.onBridgeLandType:t.landType,h=e?a.tile.onBridgeLandType:a.tile.landType;o!==h&&(0<s.rules.getLandRules(h).getSpeedModifier(a.rules.speedType)||a.rules.speedType===ti.Amphibious||r)&&(a.zone=Is(h)),e!==n&&(a.position.tileElevation+=-(n?.tileElevation??0)+(e?.tileElevation??0),a.onBridge=!!e);var l,e=a.moveTrait.reservedPathNodes.findIndex(e=>e.tile===a.tile);if(-1!==e&&a.moveTrait.reservedPathNodes.splice(e,1),a.crusher)for(l of s.map.getGroundObjectsOnTile(a.tile).filter(e=>(!e.isUnit()||e.onBridge===a.onBridge)&&e.rules.crushable&&!(e.isInfantry()&&e.stance===Fs.Paradrop)&&(!(e.isTechno()&&!i)||!s.areFriendly(e,a))))l.isDestroyed||(l.isInfantry()&&(l.infDeathType=ii.None),a.isVehicle()&&l.isOverlay()&&l.rules.wall&&a.applyRocking(0,.5),l.deathType=Hr.Crush,s.destroyObject(l,{player:a.owner,obj:a}));a.onBridge||(e=s.map.tileOccupation.getGroundObjectsOnTile(a.tile).find(e=>e.isOverlay()&&e.rules.crate))&&s.crateGeneratorTrait.pickupCrate(a,e,s)}s.traits.filter(Gr).forEach(e=>{e[Gr.onTileChange](a,s,t,r)}),a.traits.filter($r).forEach(e=>{e[$r.onTileChange](a,s,t,r)}),s.events.dispatch(new Ia(a.tile,a))}handleElevationChange(t,i){i.traits.filter(qr).forEach(e=>{e[qr.onElevationChange](this.gameObject,i,t)})}unreservePathNodes(){this.reservedPathNodes.forEach(e=>{e.tile!==this.gameObject.tile&&this.tileOccupation.unoccupySingleTile(e.tile,this.gameObject)}),this.reservedPathNodes.length=0}dispose(){this.gameObject=void 0}}class Ba{constructor(){this.suppressionTicks=0,this.enabled=!0}disable(){this.enabled=!1}isSuppressed(){return this.enabled&&0<this.suppressionTicks}suppress(){this.enabled&&(this.suppressionTicks=30)}[jr.onTick](){0<this.suppressionTicks&&this.suppressionTicks--}}class xa{constructor(){this.allTraits=[],this.traitsByTypeCache=new Map}add(e){this.allTraits.push(e),this.traitsByTypeCache.clear()}addToFront(e){this.allTraits.unshift(e),this.traitsByTypeCache.clear()}remove(e){e=this.allTraits.indexOf(e);-1!==e&&(this.allTraits.splice(e,1),this.traitsByTypeCache.clear())}filter(t){let e=this.traitsByTypeCache.get(t);return e||(e="function"==typeof t?this.allTraits.filter(e=>e instanceof t):this.allTraits.filter(e=>this.traitImplements(e,t)),this.traitsByTypeCache.set(t,e)),e}get(e){e=this.find(e);if(!e)throw new Error("No matching trait found");return e}find(e){return this.filter(e)[0]}getAll(){return this.allTraits}traitImplements(e,t){for(var i of Object.getOwnPropertyNames(t))if(void 0===e[t[i]])return!1;return!0}clear(){this.allTraits.length=0,this.traitsByTypeCache.clear()}dispose(){this.getAll().forEach(e=>e.dispose?.()),this.clear()}}(Yr=Yr||{}).onChange=Symbol(),(Kr=Kr||{}).onSpawn=Symbol(),(Jr=Jr||{}).onUnspawn=Symbol(),(ea=ea||{}).onAttack=Symbol();class Ea{get tile(){return this.position.tile}get tileElevation(){return this.position.tileElevation}constructor(e,t,i,s){this.traits=new xa,this.cachedTraits={tick:[]},this.isCrashing=!1,this.isDestroyed=!1,this.deathType=Hr.Normal,this.isDisposed=!1,this.isSpawned=!1,this.type=e,this.name=t,this.rules=i,this.art=s}getFoundation(){return{width:1,height:1}}isSmudge(){return this.type===Et.Smudge}isOverlay(){return this.type===Et.Overlay}isTerrain(){return this.type===Et.Terrain}isProjectile(){return this.type===Et.Projectile}isDebris(){return this.type===Et.Debris}isBuilding(){return!1}isInfantry(){return!1}isVehicle(){return!1}isAircraft(){return!1}isUnit(){return!1}isTechno(){return!1}update(e){for(var t of this.cachedTraits.tick)t[jr.onTick](this,e)}onSpawn(t){this.isSpawned=!0,this.traits.filter(Kr).forEach(e=>{e[Kr.onSpawn](this,t)})}onUnspawn(t){this.isSpawned=!1,this.traits.filter(Jr).forEach(e=>{e[Jr.onUnspawn](this,t)})}onDestroy(t,i,s){this.traits.filter(Vr).forEach(e=>{e[Vr.onDestroy](this,t,i,s)})}onOwnerChange(t,i){this.traits.filter(Yr).forEach(e=>{e[Yr.onChange](this,t,i)})}onAttack(t,i){this.traits.filter(ea).forEach(e=>{e[ea.onAttack](this,i,t)})}addTrait(e){this.traits.add(e),e[jr.onTick]&&this.cachedTraits.tick.push(e)}getUiName(){return this.rules.uiName}getHash(){var e=this.position.worldPosition;return G([this.id,...new Uint8Array(new Float64Array([e.x,e.y,e.z]).buffer),...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{id:this.id,position:this.position.worldPosition.toArray(),traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.isDisposed=!0,this.traits.dispose(),this.cachedTraits.tick.length=0}}(r=ta=ta||{})[r.None=0]="None",r[r.Veteran=1]="Veteran",r[r.Elite=2]="Elite";class Pa extends Ea{get primaryWeapon(){return this.armedTrait?.primaryWeapon}get secondaryWeapon(){return this.armedTrait?.secondaryWeapon}get ammo(){return this.ammoTrait?.ammo}get sight(){return Math.min(hs.MAX_SIGHT,this.rules.sight*(this.veteranTrait?.getVeteranSightMultiplier()??1))}get veteranLevel(){return this.veteranTrait?.veteranLevel??ta.None}constructor(e,t,i,s){super(e,t,i,s),this.explodes=this.rules.explodes,this.radarInvisible=this.rules.radarInvisible,this.c4=this.rules.c4,this.crusher=this.rules.crusher,this.defaultToGuardArea=this.rules.defaultToGuardArea,this.guardMode=this.rules.defaultToGuardArea,this.purchaseValue=this.rules.cost}resetGuardModeToIdle(){this.guardMode=this.defaultToGuardArea,this.guardArea=void 0}update(e){if(this.warpedOutTrait.isActive())for(var t of this.cachedTraits.tick)t.ticksWhenWarpedOut&&t[jr.onTick](this,e);else super.update(e)}isTechno(){return!0}}class Na{constructor(){this.cooldownTicks=Number.POSITIVE_INFINITY,this._actionDueThisTick=!1}[jr.onTick](e,t){this._actionDueThisTick=!1;var i=!e.unitOrderTrait.hasTasks();i&&!this.idle?this.resetCooldown(t):i?0===this.cooldownTicks?(this.doIdleAction(e,t),this.resetCooldown(t)):this.cooldownTicks--:this.cooldownTicks=Number.POSITIVE_INFINITY,this.idle=i}doIdleAction(e,t){if(e.isInfantry()){if(e.rules.fraidycat)if(.5<t.generateRandom())return void e.unitOrderTrait.addTask(new Oa(t,void 0,{noSlopes:!0}));this._actionDueThisTick=!0}}actionDueThisTick(){return this._actionDueThisTick}resetCooldown(e){var t=e.rules.audioVisual.idleActionFrequency,e=e.generateRandom()*t*.5,e=Math.max(0,t-e);this.cooldownTicks=Math.floor(e*Us.BASE_TICKS_PER_SECOND)}}class Da{constructor(e){this.gameObject=e,this.type=rs.ObjectCrashing}}(ia=ia||{}).onCrash=Symbol();class Ma{constructor(e){this.gameObject=e,this.crashingEvtSent=!1,this.crashState={}}[jr.onTick](i,s){if(i.isCrashing){if(this.crashingEvtSent||(this.crashingEvtSent=!0,i.traits.filter(ia).forEach(e=>e[ia.onCrash](i,s)),s.events.dispatch(new Da(i))),i.rules.locomotor!==ri.Jumpjet&&i.rules.locomotor!==ri.Aircraft)throw new Error(`Crashing logic not implemented for locomotor ${ri[i.rules.locomotor]}`);{let e;if(i.rules.locomotor===ri.Jumpjet)e=Lr.tickCrash(i,s,this.crashState);else{if(i.rules.locomotor!==ri.Aircraft)throw new Error(`Unhandled locomotor type "${i.rules.locomotor}"`);if(!i.isAircraft())throw new Error(`Obj "${i.name}#${i.id} is not an aircraft`);e=Ta.tickCrash(i,s,this.crashState)}let t=!1;var r,a,n=e.clone().add(i.position.worldPosition);s.map.isWithinHardBounds(n)?(a=i.tile,r=i.tileElevation,i.position.moveByLeptons3(e),i.tile!==a&&i.moveTrait.handleTileChange(a,void 0,!1,s),a=(n=i.tile.onBridgeLandType?s.map.tileOccupation.getBridgeOnTile(i.tile):void 0)?.tileElevation??0,i.position.tileElevation=Math.max(i.position.tileElevation,a),i.position.tileElevation===a&&(i.zone=s.map.getTileZone(i.tile),i.onBridge=!!n,t=!0),i.tileElevation!==r&&i.moveTrait.handleElevationChange(r,s)):t=!0,t&&s.destroyObject(i,this.attackerInfo)}}}crash(e){this.attackerInfo=e,this.gameObject.isCrashing=!0,this.gameObject.cachedTraits.tick.length=0,this.gameObject.cachedTraits.tick=[this]}dispose(){this.gameObject=void 0}}class Ra{infiltrate(e,t,i){var s;t.rules.radar&&![...t.owner.buildings].some(e=>e.rules.spySat)&&i.mapShroudTrait.resetShroud(t.owner,i),0<t.rules.power&&(s=i.rules.general.spyPowerBlackout,t.owner.powerTrait?.setBlackoutFor(s,i)),t.superWeaponTrait&&t.superWeaponTrait.getSuperWeapon(t)?.resetTimer(),0<t.rules.storage&&(s=z(i.rules.general.spyMoneyStealPercent,0,1),s=Math.floor(t.owner.credits*s),t.owner.credits-=s,e.owner.credits+=s),!i.rules.ai.buildTech.includes(t.name)||void 0!==(i=t.rules.aiBasePlanningSide)&&e.owner.production.addStolenTech(i),t.factoryTrait&&[ts.InfantryType,ts.UnitType].includes(t.factoryTrait.type)&&e.owner.production?.addVeteranType(t.factoryTrait.type)}}class La{constructor(){this.firepower=1,this.armor=1,this.speed=1}}class Fa extends Pa{get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,s){let r=new this(e,t,i);return r.moveTrait=new Aa(r,s),r.traits.add(r.moveTrait),r.rules.crashable&&(r.crashableTrait=new Ma(r),r.traits.add(r.crashableTrait)),r.rules.fearless||(r.suppressionTrait=new Ba,r.traits.add(r.suppressionTrait)),r.rules.agent&&(r.agentTrait=new Ra,r.traits.add(r.agentTrait)),r.idleActionTrait=new Na,r.traits.add(r.idleActionTrait),r}constructor(e,t,i){super(Et.Infantry,e,t,i),this.direction=0,this.onBridge=!1,this.zone=Ss.Ground,this._stance=Fs.None,this.isFiring=!1,this.isPanicked=!1,this.infDeathType=ii.Gunfire,this.crateBonuses=new La}get stance(){return this._stance===Fs.None&&this.suppressionTrait?.isSuppressed()?Fs.Prone:this._stance}set stance(e){this._stance=e,this.moveTrait.setDisabled([Fs.Deployed,Fs.Cheer].includes(e)),this.attackTrait?.setDisabled([Fs.Paradrop,Fs.Cheer].includes(e))}isUnit(){return!0}isInfantry(){return!0}}Fa.SUB_CELLS=[2,4,3];class ja extends $s{constructor(e){super(),this.game=e}onTick(e){var t=Math.abs(this.game.rules.general.parachuteMaxFallRate),i=e.tile.onBridgeLandType?this.game.map.tileOccupation.getBridgeOnTile(e.tile).tileElevation:0,s=_s.tileHeightToWorld(i),r=e.tileElevation,a=_s.tileHeightToWorld(r);return s<Math.max(s,a-t)?(e.position.moveByLeptons3(new as(0,-t,0)),e.moveTrait.handleElevationChange(r,this.game),!1):(e.position.tileElevation=i,e.stance=Fs.None,this.game.map.terrain.getPassableSpeed(e.tile,e.rules.speedType,e.isInfantry(),e.onBridge)||(e.infDeathType=ii.None,this.game.destroyObject(e,void 0,!0)),!0)}}function Ua(i,s,r,a,n){let o=[];n=n||((e,t)=>{o.push({x:e,y:t})});var e=r-i,t=a-s,h=Math.abs(e),l=Math.abs(t);let c=0;var u=0<e?1:-1,d=0<t?1:-1;if(l<h)for(let e=i,t=s;u<0?e>=r:e<=r;e+=u)n(e,t),c+=l,c<<1>=h&&(t+=d,c-=h);else for(let e=i,t=s;d<0?t>=a:t<=a;t+=d)n(e,t),c+=h,c<<1>=l&&(e+=u,c-=l);return o}function Wa(e){return null!=e}class za extends $s{constructor(...e){super(),this.children.push(...e)}onTick(e){return!0}}class Va{constructor(){this.enabled=!0}setEnabled(e){this.enabled=e}[jr.onTick](e,t){var i;this.enabled&&(e.owner.isNeutral||e.name===t.rules.general.paradrop.paradropPlane)&&e.unitOrderTrait.isIdle()&&(i=this.chooseExitTile(e.tile,t),e.unitOrderTrait.addTask(new za(new _a(t,i,!1,{allowOutOfBoundsTarget:!0}),new ya(e=>t.unspawnObject(e))).setCancellable(!1)))}chooseExitTile(e,t){var i=t.map.tiles.getMapSize(),i=.5<t.generateRandom()?new Os(Math.floor(i.width/2),0):new Os(0,Math.floor(i.height/2)),e=new Os(e.rx,e.ry),i=Ua(e.x,e.y,i.x,i.y).map(e=>t.map.tiles.getByMapCoords(e.x,e.y)).filter(Wa);if(!i.length)throw new Error("No valid exit tile found");return i[i.length-1]}}(r=sa=sa||{})[r.Spawning=0]="Spawning",r[r.EnRoute=1]="EnRoute",r[r.Dropping=2]="Dropping",r[r.TurningAround=3]="TurningAround";const Ha=5*Us.BASE_TICKS_PER_SECOND;class Ga extends Hs{constructor(e,t,i,s,r){super(e,t,i),this.paradropSquad=s,this.state=sa.Spawning,this.failedAttempts=0,this.spawnDelay=r*Ha}onStart(e){this.passengerRules=e.rules.getObject(this.paradropSquad.inf,Et.Infantry),this.passengerCount=this.paradropSquad.num}computeFlightPath(e,t,i){if(t.equals(e))throw new Error("Source and destination must be different");let s=e.clone().sub(t);e=i.rules.general.paradrop.paradropRadius/_s.LEPTONS_PER_TILE,e=t.clone().add(s.clone().setLength(s.length()+2*e)).floor();let r=Ua(t.x,t.y,e.x,e.y).map(e=>i.map.tiles.getByMapCoords(e.x,e.y)??i.map.tiles.getPlaceholderTile(e.x,e.y));for(;r.length;){var a=r[0],a=_s.tileToWorld(a.rx+.5,a.ry+.5);if(i.map.isWithinHardBounds(new Os(a.x,a.y)))break;r.shift()}if(!r.length)throw new Error("No valid paradrop path found");return{fromTile:r[0],toTile:r[r.length-1]}}onTick(r){if(this.state===sa.Spawning){if(0<this.spawnDelay)return this.spawnDelay--,!1;var a=r.map.tiles.getMapSize(),n=[new Os(0,0),new Os(Math.floor(a.width/2),0),new Os(0,Math.floor(a.height/2))][r.generateRandomInt(0,2)];let t=this.passengerRules.speedType,e=new Ws(r.map.tiles,r.map.mapBounds,this.tile,{width:1,height:1},0,50,e=>0<r.map.terrain.getPassableSpeed(e,t,!0,!!e.onBridgeLandType));var o=this.targetTile=e.getNextTile();if(!o)return!0;let i=new Os(o.rx,o.ry);var{fromTile:h,toTile:a}=this.computeFlightPath(i,n,r),o=r.rules.general.paradrop.paradropPlane,n=r.rules.getObject(o,Et.Aircraft);let s=this.pdPlane=r.createUnitForPlayer(n,this.owner);r.spawnObject(s,h),s.direction=vr.fromMapCoords(i.clone().sub(new Os(h.rx,h.ry))),s.position.tileElevation=_s.worldToTileHeight(s.rules.flightLevel??r.rules.general.flightLevel),s.zone=Ss.Air,s.onBridge=!1,s.unitOrderTrait.addTask(new _a(r,a,!1,{allowOutOfBoundsTarget:!0})),s.traits.get(Va).setEnabled(!1),this.state=sa.EnRoute}if(!this.pdPlane||this.pdPlane.isDestroyed||this.pdPlane.isCrashing)return!0;o=this.targetTile;if(!this.pdPlane.unitOrderTrait.hasTasks())return this.state=sa.TurningAround,this.pdPlane.unitOrderTrait.addTask(new _a(r,o,!1,{allowOutOfBoundsTarget:!0})),!1;n=r.rules.general.paradrop.paradropRadius/_s.LEPTONS_PER_TILE;let e=new Bs(r.map.tileOccupation);h=e.isInTileRange(this.pdPlane.tile,o,0,n);if(this.state===sa.EnRoute&&h&&(this.state=sa.Dropping),this.state===sa.Dropping)if(h&&0<this.passengerCount){a=this.pdPlane.tile;let t=!!a.onBridgeLandType;if(5<this.failedAttempts&&r.map.mapBounds.isWithinBounds(a))return this.passengerCount=0,!1;if(!r.map.terrain.getPassableSpeed(a,this.passengerRules.speedType,!0,t))return!1;let e=r.map.getGroundObjectsOnTile(a);if(e.some(e=>e.isVehicle()&&e.onBridge===t||e.isBuilding()&&!e.isDestroyed||e.isInfantry()&&e.stance===Fs.Paradrop))return!1;n=this.findFreeSubCell(r,a);if(!n)return!1;this.passengerCount--;let i=r.createUnitForPlayer(this.passengerRules,this.owner);i.stance=Fs.Paradrop,i.position.tileElevation=this.pdPlane.tileElevation,i.position.subCell=n,i.onBridge=t,i.rules.trainable&&this.owner.canProduceVeteran(i.rules)&&i.veteranTrait?.setVeteranLevel(ta.Veteran),r.spawnObject(i,a),i.unitOrderTrait.addTask(new ja(r).setCancellable(!1))}else{if(!(0<this.passengerCount))return this.pdPlane.unitOrderTrait.getCurrentTask().forceCancel(this.pdPlane),this.pdPlane.traits.get(Va).setEnabled(!0),!0;this.failedAttempts++,this.state=sa.TurningAround,this.pdPlane.unitOrderTrait.getCurrentTask().updateTarget(o,!!o.onBridgeLandType)}return this.state===sa.TurningAround&&h&&(o=this.computeFlightPath(new Os(o.rx,o.ry),new Os(this.pdPlane.tile.rx,this.pdPlane.tile.ry),r)["toTile"],this.pdPlane.unitOrderTrait.getCurrentTask().updateTarget(o,!1),this.state=sa.EnRoute),!1}findFreeSubCell(t,e){let i=t.map.getGroundObjectsOnTile(e).filter(e=>e.isTerrain()).map(e=>e.rules.getOccupiedSubCells(t.map.getTheaterType())).flat();e=Fa.SUB_CELLS.filter(e=>-1===i.indexOf(e));if(e.length)return 1<e.length?e[t.generateRandomInt(0,e.length-1)]:e[0]}}(r=ra=ra||{})[r.NotBridge=0]="NotBridge",r[r.Concrete=1]="Concrete",r[r.Wood=2]="Wood";class $a{static getOverlayBridgeType(e){return V(e,this.minHighBridgeConcreteId,this.maxHighBridgeConcreteId)||V(e,this.minLowBridgeConcreteId,this.maxLowBridgeConcreteId)?ra.Concrete:V(e,this.minHighBridgeWoodId,this.maxHighBridgeWoodId)||V(e,this.minLowBridgeWoodId,this.maxLowBridgeWoodId)?ra.Wood:ra.NotBridge}static isBridge(e){return this.isHighBridge(e)||this.isLowBridge(e)}static isBridgePlaceholder(e){return this.bridgePlaceholderIds.includes(e)}static isHighBridge(e){return V(e,this.minHighBridgeWoodId,this.maxHighBridgeWoodId)||V(e,this.minHighBridgeConcreteId,this.maxHighBridgeConcreteId)}static isLowBridge(e){return V(e,this.minLowBridgeWoodId,this.maxLowBridgeWoodId)||V(e,this.minLowBridgeConcreteId,this.maxLowBridgeConcreteId)}static isXBridge(e){return e===this.minHighBridgeWoodId||e===this.minHighBridgeConcreteId||V(e,this.minLowBridgeWoodId,this.minLowBridgeWoodId+8)||V(e,this.minLowBridgeWoodId+18,this.minLowBridgeWoodId+21)||V(e,this.minLowBridgeConcreteId,this.minLowBridgeConcreteId+8)||V(e,this.minLowBridgeConcreteId+18,this.minLowBridgeConcreteId+21)}static isLowBridgeHead(e){return V(e,this.minLowBridgeWoodId+18,this.minLowBridgeWoodId+25)||V(e,this.minLowBridgeConcreteId+18,this.minLowBridgeConcreteId+25)}static isLowBridgeHeadStart(e){return V(e,this.minLowBridgeWoodId+20,this.minLowBridgeWoodId+23)||V(e,this.minLowBridgeConcreteId+20,this.minLowBridgeConcreteId+23)}static calculateLowBridgeOverlayId(e,t){let i;if(e===ra.Concrete)i=this.minLowBridgeConcreteId;else{if(e!==ra.Wood)throw new Error("Not implemented");i=this.minLowBridgeWoodId}return i+(t?0:9)}static calculateHighBridgeOverlayId(e,t){let i;if(e===ra.Concrete)i=this.minHighBridgeConcreteId;else{if(e!==ra.Wood)throw new Error("Not implemented");i=this.minHighBridgeWoodId}return i+(t?0:1)}}$a.minLowBridgeWoodId=74,$a.maxLowBridgeWoodId=99,$a.minLowBridgeConcreteId=205,$a.maxLowBridgeConcreteId=230,$a.minHighBridgeConcreteId=24,$a.maxHighBridgeConcreteId=25,$a.minHighBridgeWoodId=237,$a.maxHighBridgeWoodId=238,$a.bridgePlaceholderIds=[100,101,231,232],(aa=aa||{}).onAttack=Symbol(),(r=na=na||{})[r.None=0]="None",r[r.Ground=1]="Ground",r[r.Wall=2]="Wall",r[r.Cliff=3]="Cliff",r[r.OnBridge=4]="OnBridge",r[r.UnderBridge=5]="UnderBridge",r[r.Shore=6]="Shore";class qa{constructor(e,t,i,s){this.target=e,this.position=t,this.explodeAnim=i,this.isLightningStrike=s,this.type=rs.WarheadDetonate}}(r=oa=oa||{})[r.Top=0]="Top",r[r.TopLeft=1]="TopLeft",r[r.TopRight=2]="TopRight",r[r.Left=3]="Left",r[r.Right=4]="Right",r[r.BottomLeft=5]="BottomLeft",r[r.Bottom=6]="Bottom",r[r.BottomRight=7]="BottomRight";class Xa{constructor(i,s,e,r){this.tileSets=s,this.generalRules=e;let a=this.rSize={width:0,height:0},n=this.dSize={width:0,height:0};for(let e=0,t=i.length;e<t;++e)a.width=Math.max(a.width,i[e].rx),a.height=Math.max(a.height,i[e].ry),n.width=Math.max(n.width,i[e].dx),n.height=Math.max(n.height,i[e].dy);a.width++,a.height++,n.width++,n.height++;let o=this.tilesByRxy=new Array(a.width*a.height);o.fill(void 0);let h=this.tilesByDxy=new Array(n.width*n.height);h.fill(void 0);let l=this.tiles=new Array(i.length),c=[],u=this.bridgeSetTiles=[],d=new Set(Object.values(Jt));this.minTileHeight=Number.POSITIVE_INFINITY;for(let e=this.maxTileHeight=0,t=i.length;e<t;++e){var g=i[e],p=s.getTileImage(g.tileNum,g.subTile,r),m=p.terrainType;if(!d.has(m))throw new Error(`Tile (${g.rx}, ${g.ry}) has unknown terrain type "${m}"`);var f={...g,terrainType:m,landType:$i(m),onBridgeLandType:void 0,rampType:p.rampType,id:g.rx+"_"+g.ry,occluded:!1},y=f.rx,w=f.ry,T=f.dx,m=f.dy;l[e]=f,o[y+w*a.width]=f,h[T+m*n.width]=f,this.minTileHeight=Math.min(this.minTileHeight,f.z),this.maxTileHeight=Math.max(this.maxTileHeight,f.z),4!==p.height||f.terrainType!==Jt.Cliff&&!s.isCliffTile(f.tileNum)||c.push(f),s.isHighBridgeBoundaryTile(g.tileNum)&&u.push(f)}this.computeLandBehindCliffTiles(c),this.cutoffTileHeight=this.computeCutoffTileHeight()}computeLandBehindCliffTiles(t){if(!(this.generalRules.cliffBackImpassability<2)){let e=[[-2,-2],[-1,-1],[-1,1],[1,-1],[0,1],[1,0]];t.forEach(t=>{for(var[i,s]of e){let e=this.getByMapCoords(t.rx+i,t.ry+s);e&&e.z<t.z&&e.terrainType!==Jt.Cliff&&e.terrainType!==Jt.Rough&&0===e.rampType&&(e.landType=ei.Rock)}})}}getTileRadarColor(e){let t=this.tileSets.getTileImage(e.tileNum,e.subTile,()=>0);return t.radarLeft.clone().multiplyScalar(.5)}getAll(){return[...this.tiles]}forEach(i){for(let e=0,t=this.tiles.length;e<t;++e)i(this.tiles[e],e)}reduce(t,e){let i=e;return this.forEach(e=>{i=t(i,e)}),i}getMinTileHeight(){return this.minTileHeight}getMaxTileHeight(){return this.maxTileHeight}getCutoffTileHeight(){return this.cutoffTileHeight}computeCutoffTileHeight(){var t=this.dSize.width-1;let i=this.dSize.height-1,s=0,r=!0;for(;r&&0<i;){for(let e=1;e<t-3;e++){var a=this.getByDisplayCoords(e,i);a&&(r=!1,a.z>s&&(s=a.z))}r&&i--}return s}getAllBridgeSetTiles(){return this.bridgeSetTiles}getAllNeighbourTiles(e){var t=e.rx,e=e.ry;return[this.getByMapCoords(t+1,e+1),this.getByMapCoords(t-1,e-1),this.getByMapCoords(t-1,e+1),this.getByMapCoords(t+1,e-1),this.getByMapCoords(t,e+1),this.getByMapCoords(t+1,e),this.getByMapCoords(t-1,e),this.getByMapCoords(t,e-1)].filter(Wa)}getNeighbourTile(e,t){var i=e.rx,s=e.ry;switch(t){case oa.Bottom:return this.getByMapCoords(i+1,s+1);case oa.Top:return this.getByMapCoords(i-1,s-1);case oa.Left:return this.getByMapCoords(i-1,s+1);case oa.Right:return this.getByMapCoords(i+1,s-1);case oa.BottomLeft:return this.getByMapCoords(i,s+1);case oa.BottomRight:return this.getByMapCoords(i+1,s);case oa.TopLeft:return this.getByMapCoords(i-1,s);case oa.TopRight:return this.getByMapCoords(i,s-1);default:throw new Error("Invalid direction")}}getByDisplayCoords(e,t){if(!(e>=this.dSize.width||t>=this.dSize.height))return this.tilesByDxy[e+t*this.dSize.width]}getByMapCoords(e,t){if(!(e>=this.rSize.width||t>=this.rSize.height))return this.tilesByRxy[e+t*this.rSize.width]}getMapSize(){return this.rSize}getDisplaySize(){return this.dSize}getInRectangle(e,t){let i,s,r,a;a=t?(i=e.rx,s=e.ry,r=t.width,t.height):(i=e.x,s=e.y,r=e.width,e.height);let n=[];for(let t=0;t<r;t++)for(let e=0;e<a;e++){var o=i+t,h=s+e,h=this.getByMapCoords(o,h);h&&n.push(h)}return n}getPlaceholderTile(e,t){var i=this.tiles[0],i=i.dx-i.rx+i.ry+1;return{rx:e,ry:t,dx:e-t+i-1,dy:e+t-i-1,z:0,id:`${e}_${t}`,landType:ei.Rock,terrainType:Jt.Rock1,rampType:0,subTile:0,tileNum:0,occluded:!1,onBridgeLandType:void 0}}}(r=ha=ha||{})[r.NotSpecial=0]="NotSpecial",r[r.Riparius=1]="Riparius",r[r.Cruentus=2]="Cruentus",r[r.Vinifera=4]="Vinifera",r[r.Aboreus=8]="Aboreus",r[r.Ore=1]="Ore",r[r.Gems=2]="Gems",r[r.All=15]="All";class Za{static getOverlayTibType(e){return this.isRiparius(e)?ha.Riparius:this.isCruentus(e)?ha.Cruentus:this.isVinifera(e)?ha.Vinifera:this.isAboreus(e)?ha.Aboreus:ha.NotSpecial}static isRiparius(e){return e>=this.minIdRiparius&&e<=this.maxIdRiparius}static isCruentus(e){return e>=this.minIdCruentus&&e<=this.maxIdCruentus}static isVinifera(e){return e>=this.minIdVinifera&&e<=this.maxIdVinifera}static isAboreus(e){return e>=this.minIdAboreus&&e<=this.maxIdAboreus}}Za.minIdRiparius=102,Za.maxIdRiparius=127,Za.minIdCruentus=27,Za.maxIdCruentus=38,Za.minIdVinifera=127,Za.maxIdVinifera=146,Za.minIdAboreus=147,Za.maxIdAboreus=166,(r=la=la||{})[r.Riparius=0]="Riparius",r[r.Cruentus=1]="Cruentus",r[r.Vinifera=2]="Vinifera",r[r.Aboreus=3]="Aboreus",r[r.Ore=0]="Ore",r[r.Gems=1]="Gems";class Qa{static canBePlacedOn(e,t){return[ei.Clear,ei.Road,ei.Rough].includes(e.landType)&&!t.getGroundObjectsOnTile(e).find(e=>!e.isSmudge()&&!e.isUnit())}constructor(e){this.gameObject=e}getTiberiumType(){var e=Za.getOverlayTibType(this.gameObject.overlayId);switch(e){case ha.Ore:return la.Ore;case ha.Gems:return la.Gems;case ha.Vinifera:return la.Ore;default:throw new Error(`Unsupported tiberium type ${e}`)}}collectBail(){var e=this.getBailCount();if(e<=0)throw new Error("Attempted to collect an ore bail, but there are none left");return this.gameObject.value--,1<e?this.getTiberiumType():void 0}spawnBails(e){this.gameObject.value=Math.min(Qa.maxBails,this.gameObject.value+e)}removeBails(e){this.gameObject.value=Math.max(-1,this.gameObject.value-e)}getBailCount(){return this.gameObject.value+1}dispose(){this.gameObject=void 0}}Qa.maxBails=11;class Ya{destroyOre(i,s,r){if(s.landType===ei.Tiberium&&(r.art.hasObject(i,Et.Animation)?r.art.getAnimation(i):void 0)?.crater){let t=r.map.getObjectsOnTile(s).find(e=>e.isOverlay()&&e.isTiberium());if(t){s=Math.ceil(Qa.maxBails/2),s=i.startsWith("S_CLSN")?s:r.generateRandomInt(1,s);let e=t.traits.get(Qa);e.removeBails(s),e.getBailCount()||r.unspawnObject(t)}}}spawnSmudges(e,r,a){if(r.landType===ei.Clear&&0===r.rampType&&a.map.mapBounds.isWithinBounds(r)&&!a.map.getObjectsOnTile(r).find(e=>!e.isUnit())){e=a.art.hasObject(e,Et.Animation)?a.art.getAnimation(e):void 0;if(e?.crater){let t=e?.forceBigCraters?2:1,i=e?.scorch,s=[oa.Bottom,oa.BottomLeft,oa.BottomRight].every(e=>a.map.tiles.getNeighbourTile(r,e));e=[...a.rules.smudgeRules.values()].filter(e=>(e.crater&&e.width===t&&e.height===t||i&&e.burn)&&!((1<e.width||1<e.height)&&!s));e.length&&(e=e[a.generateRandomInt(0,e.length-1)].name,e=a.createObject(Et.Smudge,e),a.spawnObject(e,r))}}}}class Ka{constructor(e,t,i){this.target=e,this.attacker=t,this.incidental=i,this.type=rs.ObjectAttacked}}(r=ca=ca||{})[r.None=0]="None",r[r.Shrapnel=1]="Shrapnel",r[r.LightningStrike=2]="LightningStrike",r[r.TntCharge=3]="TntCharge";class Ja{constructor(e){this.rules=e}canDamage(e,t,i){return!(!e.isSpawned||e.isDisposed||e.isDestroyed||e.isCrashing)&&(!(e.isTechno()&&e.warpedOutTrait.isInvulnerable()&&!this.rules.temporal)&&((!e.isUnit()||!e.moveTrait.reservedPathNodes.find(e=>e.tile===t))&&(!!e.healthTrait&&((!e.isUnit()||e.zone!==Ss.Air||i===Ss.Air)&&(!(!e.isUnit()&&i===Ss.Air)&&((!e.isBuilding()||!e.rules.invisibleInGame)&&(!((e.isTechno()||e.isTerrain())&&e.rules.immune&&!this.rules.temporal)&&(!(e.isTechno()&&!e.rules.warpable&&this.rules.temporal)&&(!(this.rules.radiation&&(!e.isUnit()||e.rules.immuneToRadiation))&&(!(this.rules.psychicDamage&&(!e.isUnit()||e.rules.immuneToPsionics))&&(!e.isOverlay()||!$a.isLowBridgeHead(e.overlayId))))))))))))}computeDamage(e,t,i,s=!1){let r=e;if(0<e&&t.isTechno()&&t.invulnerableTrait.isActive())return 0;if(t.isAircraft()&&t.missileSpawnTrait&&t.zone!==Ss.Air)return 0;if(!i.gameOpts.destroyableBridges&&t.isOverlay()&&t.bridgeTrait)return 0;if(this.rules.radiation||this.rules.temporal||!t.isInfantry()||t.stance!==Fs.Prone||(r*=this.rules.proneDamage),t.isTechno()||t.isOverlay()||t.isTerrain()){let e=t.isTerrain()?ni.Wood:t.rules.armor;t.isOverlay()&&t.isBridge()&&((i=$a.getOverlayBridgeType(t.overlayId))===ra.Wood?e=ni.Wood:i===ra.Concrete&&(e=ni.Concrete)),s&&t.isOverlay()&&(t.isBridge()||t.rules.wall)||(r*=this.rules.verses.get(e)),0<r&&t.isTechno()&&t.veteranTrait&&(r/=t.veteranTrait.getVeteranArmorMultiplier()),0<r&&t.isUnit()&&(r/=t.crateBonuses.armor)}return(t.isOverlay()||t.isBuilding())&&t.rules.wall&&(this.rules.wallAbsoluteDestroyer?r=Number.POSITIVE_INFINITY:this.rules.wall||this.rules.wood&&t.rules.armor===ni.Wood||(r=0)),t.isOverlay()&&t.isBridge()&&(this.rules.wall||(r=0)),r=0<r?Math.floor(r):Math.ceil(r),r}inflictDamage(e,t,i,s,r=!1){let a=t.healthTrait;return e===Number.POSITIVE_INFINITY&&(e=a.getHitPoints()),a.inflictDamage(e,i,s),s.traits.filter(aa).forEach(e=>{e[aa.onAttack](t,i?.obj,s)}),t.onAttack(s,i),s.events.dispatch(new Ka(t,i,r)),t.isTechno()&&!this.rules.temporal&&this.supressOrScatterTarget(t,s),!a.health&&(t.isInfantry()&&(t.infDeathType=this.rules.infDeath),this.rules.temporal&&(t.deathType=Hr.Temporal),t.isUnit()&&t.crashableTrait&&t.zone===Ss.Air&&!this.rules.temporal?t.crashableTrait.crash(i):s.destroyObject(t,i,void 0,r),!0)}supressOrScatterTarget(e,t){e.rules.fraidycat||e.isVehicle()&&!e.owner.isCombatant()&&e.rules.insignificant?e.unitOrderTrait.hasTasks()||(e.isInfantry()&&(e.isPanicked=!0),e.unitOrderTrait.addTask(new Oa(t)),e.isInfantry()&&e.unitOrderTrait.addTask(new ya(()=>e.isPanicked=!1).setCancellable(!1))):e.isInfantry()&&(e.moveTrait.isIdle()||e.suppressionTrait?.isSuppressed())&&e.suppressionTrait?.suppress()}createDummyWeaponInfo(){return{minRange:0,range:0,speed:Number.POSITIVE_INFINITY,type:li.Primary,rules:new Bi(new h("Dummy")),projectileRules:new Zi(Et.Projectile,new h("Dummy")),warhead:this}}detonate(s,e,t,i,r,a,n,o,h,l=ca.None,c,u,d=!1){var g,p,m,f,y,w=h?.weapon??this.createDummyWeaponInfo(),T=h?.obj,b=h?.player,v=l===ca.Shrapnel,S=l===ca.LightningStrike,k=l===ca.TntCharge,O=u?u/_s.LEPTONS_PER_TILE:this.rules.cellSpread,_=this.rules.percentAtMax;let I=new Set,C=new Map,A=new Bs(s.map.tileOccupation),B=new Ws(s.map.tiles,s.map.mapBounds,t,{width:1,height:1},0,Math.ceil(O),()=>!0);for(;g=B.getNextTile();)for(p of s.map.getObjectsOnTile(g))if((!I.has(p)||p.isBuilding())&&(n!==na.UnderBridge||!p.isUnit()||!p.onBridge)&&!(T&&p.isTechno()&&p.rules.typeImmune&&p.owner===b&&p.name===T.name)&&(!k||p!==T)&&this.canDamage(p,g,a)&&(!p.isOverlay()||!(!n&&.1<Math.abs(p.tileElevation-i)||n===na.OnBridge&&!p.isBridge()))){let e=p.isBuilding()?g===t?0:A.distance3(g,r)/_s.LEPTONS_PER_TILE:p.isTerrain()||p.isOverlay()?A.distance3(g,t)/_s.LEPTONS_PER_TILE:A.distance3(p,r)/_s.LEPTONS_PER_TILE;if(e<.001&&(e=0),!(v&&p.isInfantry()&&b)||p.owner!==b&&!s.alliances.areAllied(p.owner,b)){if(!O)if(p.isTerrain()){if(g!==t||!this.rules.wall)continue}else if(!v&&(g!==t||!p.isBuilding()&&p!==(o.obj||o.getBridge())))continue;O&&e>O||(I.add(p),C.set(p,p.isBuilding()?(C.get(p)||[]).concat(e):[e]))}}let x=!1,E;for(m of I)if(!m.isDestroyed&&!m.isCrashing){let i=this.computeDamage(e,m,s,S);if(0<e&&!this.rules.affectsAllies&&m.isTechno()&&b&&(s.alliances.areAllied(m.owner,b)||m.owner===b)&&(i=0),i)for(var P of C.get(m)){let t=i;if(0<O&&Number.isFinite(t)&&(t=H(t,_*t,P/O)),Math.abs(t)<1&&(!O||.25<=t/i)&&(t=+Math.sign(t)),t=0<t?Math.floor(t):Math.ceil(t),t){let e=m.healthTrait;if(t<0){if(!T)throw new Error("Expected healer object to be set");if(e.healBy(-t,T,s),100===e.health)break}else{if(m===o.obj&&P<1&&(E=m),this.rules.causesDelayKill&&m.isBuilding()&&m.delayedKillTrait&&(f=m.healthTrait.getHitPoints(),t>=f&&(t=f-1,m.delayedKillTrait.isActive()||(f=this.rules.delayKillAtMax,y=H(y=this.rules.delayKillFrames,f*y,P/O),m.delayedKillTrait.activate(y,h)))),this.inflictDamage(t,m,h,s,!E))break;m.isVehicle()&&this.rules.rocker&&(0<(P=z(i/300,0,1))&&(y=vr.fromMapCoords(m.position.getMapPosition().clone().sub(_s.vecWorldToGround(r)))-m.direction,m.applyRocking(y,P)))}}}else m.isTechno()&&m.invulnerableTrait.isActive()&&(x=!0)}w=w.rules.radLevel;w&&O&&s.mapRadiationTrait.createRadSite(t,w,O+1);d=d?void 0:x?s.rules.audioVisual.weaponNullifyAnim:this.pickExplodeAnim(e,E,a,s,S);if(!x&&a===Ss.Ground){let e=new Ya;d&&e.destroyOre(d,t,s),c&&e.spawnSmudges(c,t,s),d&&e.spawnSmudges(d,t,s)}s.events.dispatch(new qa(this,r,d,S))}pickExplodeAnim(t,i,s,r,a){if(t){if(a)return r.rules.audioVisual.weatherConBoltExplosion;if(this.rules.conventional&&s===Ss.Water&&(!i||i.isBuilding()||i.isVehicle()&&i.submergibleTrait)){var n=r.rules.combatDamage.splashList;return n[z(Math.floor(t/50),0,n.length-1)]}n=this.rules.animList.length;let e;return n?(e=r.rules.combatDamage.c4Warhead===this.rules.name?n-1:this.rules.emEffect?r.generateRandomInt(0,n-1):z(Math.floor(t/25),0,n-1),this.rules.animList[e]):void 0}}}Ja.SPECIAL_WARHEAD_NAME="Special",Ja.HE_WARHEAD_NAME="HE";class en{constructor(e){this.forward=0,this.lateral=0,this.vertical=0,e&&3===e.length&&this.fromArray(e)}fromArray(e){return this.forward=e[0],this.lateral=e[1],this.vertical=e[2],this}clone(){return new en([this.forward,this.lateral,this.vertical])}}class tn{constructor(e,t){this.weapon=e,this.gameObject=t,this.type=rs.WeaponFire}}class sn{constructor(e,t,i,s,r,a){this.weaponType=e,this.projectileRules=t,this.weaponRules=i,this.warheadRules=s,this.gameObject=r,this.generalRules=a,this.targetChecks=[],this.initConditions()}initConditions(){this.projectileRules.isAntiGround||this.targetChecks.push(e=>!!e);const a=this.generalRules.prism.type;this.gameObject.name===a&&this.weaponType===li.Secondary?this.targetChecks.push((e,t,i,s,r)=>!(!r||!e?.isBuilding()||e.name!==a||e.owner!==this.gameObject.owner)):this.warheadRules.electricAssault?this.targetChecks.push((e,t,i,s,r)=>!(!s&&!r||!e?.isBuilding()||!e.overpoweredTrait||e.owner!==this.gameObject.owner)):this.weaponRules.damage<0?this.targetChecks.push((e,t,i)=>!!(e!==this.gameObject&&e?.isUnit()&&i.areFriendly(e,this.gameObject)&&e.healthTrait.health<100&&this.gameObject.isAircraft()===e.isAircraft())):(this.gameObject.rules.attackCursorOnFriendlies||this.warheadRules.bombDisarm?this.targetChecks.push((e,t,i,s,r)=>!r&&!!(!this.warheadRules.bombDisarm||e?.isTechno()&&e.tntChargeTrait?.hasCharge())):this.targetChecks.push((e,t,i,s)=>!((!s||this.warheadRules.mindControl)&&e?.isTechno()&&i.areFriendly(e,this.gameObject))),this.targetChecks.push((e,t,i)=>!(e?.isTechno()&&e.cloakableTrait?.isCloaked()&&!i.alliances.haveSharedIntel(this.gameObject.owner,e.owner))),this.weaponRules.limboLaunch&&this.targetChecks.push((e,t,i,s,r)=>!(r&&e&&(e.isVehicle()||e.isAircraft())&&e.parasiteableTrait?.isInfested())),this.warheadRules.ivanBomb&&this.targetChecks.push(e=>!(!e?.isTechno()||!e.tntChargeTrait||e.tntChargeTrait.hasCharge())),this.warheadRules.parasite&&this.targetChecks.push((e,t,i,s)=>!!(!e&&s||e?.isInfantry()||(e?.isVehicle()||e?.isAircraft())&&e.parasiteableTrait)),this.warheadRules.mindControl&&this.targetChecks.push(e=>!(!e?.isTechno()||!e.mindControllableTrait)),this.warheadRules.temporal||this.targetChecks.push((e,t,i,s,r)=>!(r&&e?.isTechno()&&e.warpedOutTrait.isInvulnerable())),this.gameObject.rules.natural&&this.targetChecks.push(e=>!e?.isTechno()||!e.rules.unnatural)),this.targetChecks.push((e,t)=>this.canTargetZone(e,t))}canTarget(t,i,s,r,a){return this.targetChecks.every(e=>e(t,i,s,r,a))}canTargetZone(e,t){let i;if(e?.isUnit()){if(e?.isInfantry()&&e.stance===Fs.Paradrop&&2<e.tileElevation)return this.projectileRules.isAntiAir&&(this.projectileRules.isAntiGround||this.weaponType===li.Secondary);if(e.zone===Ss.Air)return this.projectileRules.isAntiAir;if(this.weaponType===li.Secondary&&this.projectileRules.isAntiAir&&!this.projectileRules.isAntiGround)return!1;i=e.zone}else i=t.landType===ei.Water?Ss.Water:Ss.Ground;return i===Ss.Water?this.canTargetNaval(this.gameObject.rules.navalTargeting,this.gameObject,e,this.weaponType):this.canTargetLand(this.gameObject.rules.landTargeting,this.weaponType)}canTargetLand(e,t){switch(e){case oi.LandOk:return!0;case oi.LandNotOk:return!1;case oi.LandSecondary:return t===li.Secondary;default:throw new Error(`Unhandled LandTargeting value "${e}"`)}}canTargetNaval(e,t,i,s){switch(e){case hi.UnderwaterNever:return!i||!(i.isVehicle()&&i.submergibleTrait?.isSubmerged());case hi.UnderwaterSecondary:return i&&i.isVehicle()&&i.submergibleTrait&&!t.rules.spawned?s===li.Secondary:s===li.Primary;case hi.UnderwaterOnly:return!!(i&&i.isVehicle()&&i.submergibleTrait);case hi.OrganicSecondary:return i?.isTechno()&&i.rules.organic?s===li.Secondary:s===li.Primary;case hi.SealSpecial:return i?.isTechno()&&i.rules.naval&&!i.rules.organic&&(i.isBuilding()||i.rules.speedType===ti.Float)?s===li.Secondary:s===li.Primary;case hi.NavalAll:return!0;case hi.NavalNone:return!1;default:throw new Error(`Unhandled NavalTargeting value "${e}"`)}}}class rn{static factory(e,t,i,s,r){var a=s.getWeapon(e);let n=a.warhead;n===Ja.SPECIAL_WARHEAD_NAME&&(n=rn.findSpecialWarheadName(a,i,s));var o=new Ja(s.getWarhead(n)),e=s.getProjectile(a.projectile),s=new sn(t,e,a,o.rules,i,s.general);return new this(t,i,a,o,e,r||new en,s)}static findSpecialWarheadName(e,t,i){let s;if(!e.spawner)throw new Error(`Weapon "${e.name} can't use "Special" warhead without Spawner=yes`);if(t.rules.spawns===i.general.v3Rocket.type)s=i.combatDamage.v3Warhead;else if(t.rules.spawns===i.general.dMisl.type)s=i.combatDamage.dMislWarhead;else{if(!t.rules.spawns)throw new Error(`Can't use "Special" warhead on unit type "${t.name}" without "Spawns"`);t=i.getObject(t.rules.spawns,Et.Aircraft);if(!t.primary)throw new Error(`Spawned unit "${t.name}" doesn't have a primary weapon`);s=i.getWeapon(t.primary).warhead}return s}static computeSpeed(e,t){return t.arcing?.75*Ai.iniSpeedToLeptonsPerTick(50,100):!t.rot||t.inviso||e.isLaser||e.isElectricBolt?Number.POSITIVE_INFINITY:e.speed}constructor(e,t,i,s,r,a,n){this.type=e,this.gameObject=t,this.rules=i,this.warhead=s,this.projectileRules=r,this.flh=a,this.targeting=n,this.cooldownTicks=0,this.burstsLeft=0,this.burstIndex=0,this.useBurstDelay=!1,this.lateralMuzzleMult=1,this.distributedFireAngle=t.rules.distributedFire&&t.rules.radialFireSegments?-90:0}get name(){return this.rules.name}get minRange(){return this.rules.minimumRange}get range(){return this.gameObject.isBuilding()&&!this.gameObject.overpoweredTrait&&this.type===li.Secondary&&this.gameObject.primaryWeapon?Math.min(this.gameObject.primaryWeapon.rules.range,this.rules.range):this.rules.range}get speed(){return rn.computeSpeed(this.rules,this.projectileRules)}get rof(){let e=this.rules.rof;return this.gameObject.isBuilding()&&this.gameObject.garrisonTrait?.isOccupied()&&(e/=this.gameObject.garrisonTrait.units.length),this.gameObject.veteranTrait&&(e*=this.gameObject.veteranTrait.getVeteranRofMultiplier()),Math.floor(e)}getCooldownTicks(){return this.cooldownTicks}expireCooldown(){this.cooldownTicks=0}resetCooldown(){this.cooldownTicks=this.rof}hasBurstsLeft(){return 0<this.burstsLeft}resetBursts(){this.burstsLeft=0,this.burstIndex=0,this.resetCooldown(),this.gameObject.ammoTrait&&0<this.gameObject.ammoTrait.ammo&&this.gameObject.ammoTrait.ammo--}tick(){0<this.cooldownTicks&&this.cooldownTicks--}getBurstsFired(){return this.burstIndex}fire(r,a,n=1){let o=this.gameObject,e,t=0;if(!o.airSpawnTrait||!this.rules.spawner||(e=o.airSpawnTrait.prepareLaunch(o,r,a),t=o.airSpawnTrait.availableSpawns,e)){this.burstsLeft?(this.burstsLeft--,this.burstIndex++,this.lateralMuzzleMult*=-1):(this.useBurstDelay=!1,this.burstIndex=0,e?this.burstsLeft=t:this.gameObject.isAircraft()?this.burstsLeft=this.projectileRules.iniRot<=1?4:this.gameObject.rules.fighter?0:1:(this.burstsLeft=this.rules.burst-1,this.useBurstDelay=!0),this.lateralMuzzleMult=1),0<this.burstsLeft&&(e&&0<t?this.cooldownTicks=this.rules.iniSpeed:this.gameObject.isAircraft()?this.cooldownTicks=this.rules.rof:this.cooldownTicks=this.useBurstDelay&&void 0!==this.gameObject.rules.burstDelay[this.burstIndex]?this.gameObject.rules.burstDelay[this.burstIndex]:a.generateRandomInt(3,5)),this.burstsLeft||this.resetBursts(),this.rules.limboLaunch&&(a.limboObject(this.gameObject,{selected:a.getUnitSelection().isSelected(this.gameObject),controlGroup:a.getUnitSelection().getOrCreateSelectionModel(this.gameObject).getControlGroupNumber()}),this.warhead.rules.parasite&&(r.obj?.isVehicle()||r.obj?.isAircraft())&&r.obj.parasiteableTrait&&(r.obj.parasiteableTrait.beingBoarded=!0));let i=e??a.createProjectile(this.projectileRules.name,this.gameObject,this,r,!1);i.isAircraft()||(i.baseDamageMultiplier=n*(this.gameObject.isUnit()?this.gameObject.crateBonuses.firepower:1));let s=this.flh.clone();s.lateral*=this.lateralMuzzleMult;var h=o.position.getMapPosition();if(a.map.isWithinHardBounds(h)){i.position.moveToLeptons(h),i.position.tileElevation=o.position.tileElevation;let e=new Os(s.lateral,s.forward);n=this.getMuzzleFacing()+this.distributedFireAngle;e=nr(e,n);var h=nr(h=new Os(0,o.art.turretOffset),o.direction);e.add(h),o.rules.radialFireSegments&&o.rules.distributedFire&&(h=Math.floor(180/o.rules.radialFireSegments),this.distributedFireAngle=(this.distributedFireAngle+h+90)%180-90),i.direction=n,o.isBuilding()&&o.rules.turretAnim&&(l=_s.screenDistanceToWorld(o.rules.turretAnimX,o.rules.turretAnimY),n=o.getFoundationCenterOffset(),i.position.moveByLeptons(-n.x+l.x,-n.y+l.y));let t=new as(e.x,s.vertical,-e.y);var l=t.clone().add(i.position.worldPosition);if(a.map.isWithinHardBounds(l)&&i.position.moveByLeptons3(t),i.tileElevation<0&&(i.position.tileElevation=0),i.isAircraft()?a.unlimboObject(i,i.position.tile):a.spawnObject(i,i.position.tile),this.rules.revealOnFire&&r.obj?.isTechno()){let e=a.mapShroudTrait.getPlayerShroud(r.obj.owner);e?.isShrouded(o.tile,o.tileElevation)&&e.revealTemporarily(o)}this.rules.decloakToFire&&this.gameObject.cloakableTrait?.uncloak(a),a.events.dispatch(new tn(this,this.gameObject))}else e&&(e.owner.removeOwnedObject(e),e.dispose())}}getMuzzleFacing(){let e=this.gameObject,t;return t=!e.isInfantry()&&!e.isAircraft()&&(e.isBuilding()||e.isVehicle())&&e.turretTrait?e.turretTrait.facing:e.direction,t}}rn.NUKE_PAYLOAD_NAME="NukePayload";class an extends Hs{constructor(e,t,i,s){super(e,t,i),this.weaponType=s}onStart(t){var i=t.rules.getWeapon(this.weaponType),s=t.createTarget(void 0,this.tile),r=this.owner.getOwnedObjectsByType(Et.Building).find(e=>e.rules.nukeSilo);if(r){let e=rn.factory(i.name,li.Primary,r,t.rules);e.fire(s,t)}else this.fireLooseNuke(i,s,t)}fireLooseNuke(t,i,s){var r=new Os(this.tile.rx+.5,this.tile.ry+.5).multiplyScalar(_s.LEPTONS_PER_TILE);if(s.map.isWithinHardBounds(r)){let e=s.createLooseProjectile(t.name,this.owner,i);e.position.moveToLeptons(r),e.position.tileElevation=_s.worldToTileHeight(e.rules.detonationAltitude),s.spawnObject(e,e.position.tile)}}onTick(e){return!0}}class nn{constructor(e){this.position=e,this.type=rs.LightningStormCloud}}class on{constructor(e){this.target=e,this.type=rs.LightningStormManifest}}(r=ua=ua||{})[r.Approaching=0]="Approaching",r[r.Manifesting=1]="Manifesting";class hn extends Hs{constructor(){super(...arguments),this.state=ua.Approaching,this.clouds=[]}onStart(e){e=e.rules.general.lightningStorm;this.manifestStartTimer=e.deferment,this.manifestEndTimer=e.duration,this.nextDirectHitTimer=0,this.nextRandomHitTimer=0}onTick(t){if(this.state===ua.Approaching&&(0<this.manifestStartTimer?this.manifestStartTimer--:(this.state=ua.Manifesting,t.events.dispatch(new on(this.tile)))),this.state===ua.Manifesting){var i,r=t.rules.general.lightningStorm;if(0<this.manifestEndTimer&&(this.manifestEndTimer--,0<this.nextDirectHitTimer&&this.nextDirectHitTimer--,this.nextDirectHitTimer<=0&&(this.nextDirectHitTimer=r.hitDelay,this.spawnCloudAt(this.tile,t)),0<this.nextRandomHitTimer&&this.nextRandomHitTimer--,this.nextRandomHitTimer<=0)){this.nextRandomHitTimer=r.scatterDelay;var a=Math.floor(r.cellSpread/2);let i=r.separation,s=new Bs(t.map.tileOccupation),e=new va(t.map.tiles,t.map.mapBounds,this.tile,a,t,t=>!this.clouds.some(e=>s.tileDistance(t,e.tile)<i),!1);a=e.getNextTile();a&&this.spawnCloudAt(a,t)}for(i of this.clouds.slice())if(0<i.ticksLeft){if(i.ticksLeft--,i.ticksLeft===Math.floor(i.durationTicks/2)){var s=r.warhead;let e=new Ja(t.rules.getWarhead(s));var n=i.tile,o=t.map.tileOccupation.getBridgeOnTile(n),h=o?.tileElevation??0,s=t.map.getTileZone(n);e.detonate(t,r.damage,n,h,_s.tile3dToWorld(n.rx+.5,n.ry+.5,n.z+h),s,o?na.OnBridge:na.None,t.createTarget(o,n),{player:this.owner,weapon:void 0},ca.LightningStrike)}}else this.clouds.splice(this.clouds.indexOf(i),1);if(!this.clouds.length&&this.manifestEndTimer<=0)return!0}return!1}spawnCloudAt(e,t){var i=t.rules.audioVisual.weatherConClouds,i=t.generateRandomInt(0,i.length-1);let s=t.art.getAnimation(t.rules.audioVisual.weatherConClouds[i]);i=s.art.getNumber("Rate",60*Us.BASE_TICKS_PER_SECOND)/60,i=Math.floor(Us.BASE_TICKS_PER_SECOND/i*60);this.clouds.push({tile:e,durationTicks:i,ticksLeft:i});i=(t.map.tileOccupation.getBridgeOnTile(e)?.tileElevation??0)+_s.worldToTileHeight(t.rules.general.flightLevel),i=_s.tile3dToWorld(e.rx+.5,e.ry+.5,e.z+i);t.events.dispatch(new nn(i))}}class ln extends Hs{onStart(e){var t,i,s=e.rules.combatDamage.ironCurtainDuration,r={player:this.owner};let a=new Ws(e.map.tiles,e.map.mapBounds,this.tile,{width:1,height:1},0,1,()=>!0);for(;t=a.getNextTile();)for(i of e.map.getGroundObjectsOnTile(t))!i.isTechno()||i.isUnit()&&i.tile!==t||i.rules.missileSpawn||(i.rules.organic?i.isDestroyed||e.destroyObject(i,r):(i.invulnerableTrait.setActiveFor(s,e.currentTick),(i.isVehicle()||i.isAircraft())&&i.parasiteableTrait?.isInfested()&&i.parasiteableTrait.destroyParasite(r,e)))}onTick(e){return!0}}class cn extends Hs{constructor(e,t,i,s){super(e,t,i),this.tile2=s,this.objectsToTeleport=[]}onStart(i){this.delayTicks=i.rules.general.chronoDelay;let s=i.map.tiles;for(let t=-1;t<=1;t++)for(let e=-1;e<=1;e++){var r=s.getByMapCoords(this.tile.rx+t,this.tile.ry+e);if(r){var a,n=!!r.onBridgeLandType,o=s.getByMapCoords(this.tile2.rx+t,this.tile2.ry+e);for(a of i.map.getGroundObjectsOnTile(r))!a.isUnit()||a.tile!==r||a.onBridge!==n||a.isInfantry()&&a.stance===Fs.Paradrop&&2<a.tileElevation||a.isDisposed||a.invulnerableTrait.isActive()||(a.rules.organic&&!a.rules.teleporter||!o?i.destroyObject(a,{player:this.owner}):a.warpedOutTrait.isActive()||(a.warpedOutTrait.setActive(!0,!0,i),this.objectsToTeleport.push({obj:a,destTile:o})))}}}onTick(c){if(0<this.delayTicks&&this.delayTicks--,this.delayTicks)return!1;for(let{obj:h,destTile:l}of this.objectsToTeleport)if(h.isSpawned){let i=!1,s=l?c.map.tileOccupation.getBridgeOnTile(l):void 0,r=c.map.getGroundObjectsOnTile(l),a=r.find(e=>e.isBuilding());var u=r.some(e=>c.rules.general.padAircraft.includes(e.name)),t=c.rules.general.padAircraft.includes(h.name)&&!!a?.helipadTrait&&!!a.dockTrait?.getAllDockTiles().includes(l)&&!a.dockTrait.hasReservedDockAt(a.dockTrait.getDockNumberByTile(l))&&a.owner===h.owner;let e=!1,n=h.rules.speedType,o=h.isInfantry();h.rules.movementZone===ai.Fly&&(n=ti.Wheel);var d=c.map.mapBounds.isWithinBounds(l);if(!(t||c.map.terrain.getPassableSpeed(l,n,o,!!s)&&d)){let t=!1;if(!u&&(0<c.map.terrain.getPassableSpeed(l,n,o,!!s,void 0,!0)||!d)){a&&(i=!0);let e=new Ws(c.map.tiles,c.map.mapBounds,l,{width:1,height:1},1,15,e=>0<c.map.terrain.getPassableSpeed(e,n,o,!!e.onBridgeLandType)&&!c.map.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},h).length);d=e.getNextTile();d&&(l=d,s=c.map.tileOccupation.getBridgeOnTile(l),r=c.map.getGroundObjectsOnTile(l),t=!0)}t||(h.moveTrait.teleportUnitToTile(l,s,!0,!1,c),h.warpedOutTrait.setActive(!1,!0,c),c.map.getTileZone(l)===Ss.Water&&(h.deathType=Hr.Sink),c.destroyObject(h,{player:this.owner}),e=!0)}for(let t of r)t.isDisposed||t.isUnit()&&(this.objectsToTeleport.some(({obj:e})=>e===t)||t.onBridge!==!!s&&t.tile===l||2<Math.abs(t.tileElevation-h.tileElevation)||(t.isInfantry()&&t.stance!==Fs.Paradrop&&(t.deathType=Hr.Crush),c.destroyObject(t,{player:this.owner,obj:h})));if(!e){if(h.moveTrait.teleportUnitToTile(l,s,!0,!1,c),t&&a?.dockTrait){t=a.dockTrait.getAllDockTiles().indexOf(l);if(a.dockTrait.undockUnitAt(t),a.dockTrait.hasReservedDockAt(t))throw new Error("Target building dock is already reserved by another unit");a.dockTrait.dockUnitAt(h,t)}i?h.warpedOutTrait.setTimed(c.rules.general.chronoDelay,!1,c):h.warpedOutTrait.setActive(!1,!0,c)}}return!0}}(da=da||{}).onDeactivate=Symbol();class un{constructor(){this.effects=[]}[Ps.onTick](i){for(var e of i.getCombatants()){var t;for(t of e.superWeaponsTrait.getAll())t.update(i)}for(let t of this.effects)t.status===Ms.NotStarted&&(t.onStart(i),t.status=Ms.Running),t.onTick(i)&&(t.status=Ms.Finished,i.traits.filter(da).forEach(e=>{e[da.onDeactivate](t.type,t.owner,i)}));this.effects=this.effects.filter(e=>e.status!==Ms.Finished)}[Rs.onPowerLow](e,t){e.superWeaponsTrait?.getAll()?.filter(e=>e.rules.isPowered).forEach(e=>{this.updateTimer(e,!1)})}[Rs.onPowerRestore](e,t){e.superWeaponsTrait?.getAll()?.filter(e=>e.rules.isPowered).forEach(e=>{this.updateTimer(e,!0)})}[Rs.onPowerChange](e,t){}[Ns.onChange](e,t){var i;e.owner.powerTrait&&e.isBuilding()&&e.superWeaponTrait&&((i=e.superWeaponTrait.getSuperWeapon(e))&&this.updateTimer(i,!e.owner.powerTrait.isLowPower()))}updateTimer(e,t){var i=this.superWeaponHasValidBuilding(e);t&&i?e.resumeTimer():e.pauseTimer()}superWeaponHasValidBuilding(t){return[...t.owner.buildings].find(e=>!(e.superWeaponTrait?.getSuperWeapon(e)!==t||e.warpedOutTrait.isActive()&&t.rules.isPowered))}addEffect(e){this.effects.push(e)}activateSuperWeapon(t,e,i,s,r){let a=e.superWeaponsTrait?.getAll().find(e=>e.rules.type===t);if(a&&a.status===Ds.Ready){if(a.oneTimeOnly){e.superWeaponsTrait.remove(a.name);for(var n of e.buildings)n.rules.superWeapon===a.name&&n.superWeaponTrait&&n.superWeaponTrait.addSuperWeaponToPlayerIfNeeded(e,i)}else a.resetTimer();this.activateEffect(a.rules,e,i,s,r)}}activateEffect(e,i,s,r,a,n=!1){const o=e.type;if(void 0!==o){let t=[];switch(o){case ss.AmerParaDrop:for(var[h,l]of s.rules.general.paradrop.amerParaDrop.entries())s.rules.hasObject(l.inf,Et.Infantry)?t.push(new Ga(o,i,r,l,h)):console.warn(`Can't paradrop unknown infantry type "${l.inf}"`);break;case ss.ParaDrop:{let e=s.rules.general.paradrop.getParadropSquads(i.country.side);for(var[c,u]of e.entries())s.rules.hasObject(u.inf,Et.Infantry)?t.push(new Ga(o,i,r,u,c)):console.warn(`Can't paradrop unknown infantry type "${u.inf}"`);break}case ss.MultiMissile:if(!e.weaponType)throw new Error("Missing WeaponType in super weapon rules");t.push(new an(o,i,r,e.weaponType));break;case ss.LightningStorm:t.push(new hn(o,i,r));break;case ss.IronCurtain:t.push(new ln(o,i,r));break;case ss.ChronoSphere:if(!a)throw new Error("Missing tile2 action param");t.push(new cn(o,i,r,a))}for(var d of t)this.addEffect(d);s.traits.filter(Ls).forEach(e=>{e[Ls.onActivate](o,i,s,r,a)}),s.events.dispatch(new Gs(o,i,r,a,n))}}}class dn{constructor(e){this.target=e,this.type=rs.ObjectCloakChange}}(ga=ga||{}).onDamage=Symbol();class gn{constructor(e,t){this.gameObject=e,this.cloakDelayMinutes=t,this.isActive=!1,this.resetCloakCooldown()}isCloaked(){return this.isActive}uncloak(e){var t=this.isActive;this.resetCloakCooldown(),t&&(this.isActive=!1,e.events.dispatch(new dn(this.gameObject)))}resetCloakCooldown(){this.cooldownTicks=Math.floor(60*this.cloakDelayMinutes*Us.BASE_TICKS_PER_SECOND)}[Kr.onSpawn](e,t){this.resetCloakCooldown()}[jr.onTick](e,t){0<this.cooldownTicks&&this.cooldownTicks--,!(this.cooldownTicks<=0)||this.isActive||e.isVehicle()&&e.submergibleTrait&&!e.submergibleTrait.isSubmerged()||e.temporalTrait.getTarget()||(this.isActive=!0,t.events.dispatch(new dn(this.gameObject)))}[ga.onDamage](e,t){this.uncloak(t)}dispose(){this.gameObject=void 0}}class pn{static calculateOverlayId(e,t){if(e!==ha.NotSpecial){var i=t.dx,t=t.dy,i=Math.floor((t-9)/2%12*((t-8)/2%12)%12-(i-13)/2%12*((i-12)/2%12)%12+12e4);return i%=12,e===ha.Ore?Za.minIdRiparius+i:e===ha.Gems?Za.minIdCruentus+i:e===ha.Vinifera?Za.minIdVinifera+i:e===ha.Aboreus?Za.minIdAboreus+i:void 0}}}var mn,fn,yn,wn,Tn,bn,vn,Sn,kn,On,_n,In,Cn,An,Bn,xn,En,Pn,Nn,Dn,Mn,Rn,Ln,Fn,jn,Un,Wn,zn,Vn,Hn,Gn,$n,qn,Xn,Zn,Qn,r=__webpack_require__(949);class Yn extends r.Box2{}const Kn=[Es.IonStorm,Es.Gas,Es.Pod,Es.Squad];class Jn{constructor(e){this.randomCrateSpawn=e,this.crates=[],this.availEdgeTiles=[],this.allTiles=[]}init(n){var o=n.map.tiles.getMapSize();let h=n.map.tiles,e=[],l=0;for(let a=0;a<o.width;++a){let t,i,s=!1,r=!1;for(let e=0;e<o.height;++e){var c=h.getByMapCoords(a,e);if(c&&this.canPlaceCrateOnTile(n,c)){var u=n.map.getTileZone(c)===Ss.Water;t?(u||(i=c),r=u):u?s=r=!0:t=i=c}else if(t&&!c)break}t&&(e.push(t),i&&i!==t&&e.push(i),s||r||l++)}this.availEdgeTiles=e,this.allTiles=h.getAll(),this.mapEdgeIsWater=0===l,this.minCrates=n.rules.crateRules.crateMinimum*n.gameOpts.humanPlayers.filter(e=>-3!==e.countryId).length}[Ps.onTick](t){for(var e of this.crates)e.ticksLeft--,e.ticksLeft<=0&&(t.unspawnObject(e.obj),e.obj.dispose());if(this.crates=this.crates.filter(e=>0<e.ticksLeft),this.randomCrateSpawn)for(let e=0;e<this.minCrates-this.crates.length&&this.spawnCrateAtRandom(this.allTiles,t);e++);}spawnCrateAtRandom(e,t){e=this.chooseSpawnTile(e,t);if(e)return this.spawnRandomCrateAt(e,t)}spawnRandomCrateAt(e,t){if(this.canPlaceCrateOnTile(t,e)){var i=t.map.getTileZone(e,!0)===Ss.Water,i=this.choosePowerup(i,t.rules.powerups.powerups,t);if(i)return this.spawnCrateAt(e,i,t)}}spawnCrateAt(t,i,s){if(this.canPlaceCrateOnTile(s,t)){var r=s.map.getTileZone(t,!0)===Ss.Water,a=s.rules.crateRules,r=r?a.waterCrateImg:a.crateImg;let e=s.createObject(Et.Overlay,r);e.overlayId=s.rules.getOverlayId(r),e.value=0,s.spawnObject(e,t);s=60*a.crateRegen*Us.BASE_TICKS_PER_SECOND*(.5+1.5*s.generateRandom());return this.crates.push({obj:e,powerup:i,ticksLeft:s}),e}}chooseSpawnTile(e,t){return t.generateRandom()<(this.mapEdgeIsWater?1/3:2/3)&&this.availEdgeTiles.length&&(e=this.availEdgeTiles),this.chooseRandomTile(e,t)}chooseRandomTile(e,t){let i;let s=0;for(;i=e[t.generateRandomInt(0,e.length-1)],s++,s<100&&!this.canPlaceCrateOnTile(t,i););if(100<=s){var r=t.map.tileOccupation.getEmptyTiles();if(!r.length)return;i=r[t.generateRandomInt(0,r.length-1)]}return i}canPlaceCrateOnTile(e,t){return e.map.mapBounds.isWithinBounds(t)&&!e.map.getGroundObjectsOnTile(t).length&&0<e.map.terrain.getPassableSpeed(t,ti.Amphibious,!1,!1)&&t.terrainType!==Jt.Shore&&0===t.rampType}choosePowerup(t,i,s){if((i=t?i.filter(e=>e.waterAllowed):i).length){var r,t=i.reduce((e,t)=>e+t.probShares,0),a=s.generateRandomInt(0,t);let e=0;for(r of i)if(e+=r.probShares,a<e)return r}}peekInsideCrate(t){return this.crates.find(e=>e.obj===t)?.powerup.type}pickupCrate(e,t,i){let s=this.crates.find(e=>e.obj===t);if(s){this.crates.splice(this.crates.indexOf(s),1),i.unspawnObject(s.obj),s.obj.dispose();let t=this.grantPowerup(e,s.powerup,s.obj.tile,i);var r;return void 0!==t&&(e.owner.cratesPickedUp++,r=i.rules.powerups.powerups.find(e=>e.type===t),i.events.dispatch(new vs(r,e.owner,e,s.obj.tile))),this.randomCrateSpawn&&this.spawnCrateAtRandom(this.allTiles,i),t}}grantPowerup(t,i,s,r){let a=t.owner,n=!1;if(a.isCombatant()){if(i.type===Es.Unit){let e;if(![...a.buildings].some(e=>e.rules.constructionYard)&&r.rules.crateRules.freeMCV){let t=r.rules.general.baseUnit;if(!a.getOwnedObjects(!0).some(e=>t.includes(e.name))&&a.credits>=[...r.rules.ai.buildPower,...r.rules.ai.buildRefinery].map(e=>r.rules.getBuilding(e)).filter(e=>e.aiBasePlanningSide===a.country.side).reduce((e,t)=>e+t.cost,0)){var o=t.find(e=>{let t=r.rules.getObject(e,Et.Vehicle);return t.isAvailableTo(a.country)&&t.hasOwner(a.country)});if(!o)throw new Error(`No suitable MCV found for player country ${a.country?.name}`);e=r.rules.getObject(o,Et.Vehicle)}}if(e||(o=(o=r.rules.crateRules.unitCrateType)?r.rules.hasObject(o,Et.Vehicle)?[r.rules.getObject(o,Et.Vehicle)]:[]:[...r.rules.vehicleRules.values()].filter(e=>e.crateGoodie&&0<r.map.terrain.getPassableSpeed(s,e.speedType,!1,!1))).length&&(e=o[r.generateRandomInt(0,o.length-1)]),e){let t=r.createUnitForPlayer(e,a);var h=new Ws(r.map.tiles,r.map.mapBounds,s,{width:1,height:1},0,3,e=>0<r.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)&&!r.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length).getNextTile();h?(r.spawnObject(t,h),n=!0):(a.removeOwnedObject(t),t.dispose())}}else if(i.type===Es.Money){if(!i.data)throw new Error("Money powerup missing data field");h=Math.floor(Number(i.data)*(.55+2*r.generateRandom()*.45));a.credits=Math.max(0,a.credits+h),0<h&&(a.creditsGained+=h),n=!0}else if(i.type===Es.HealBase){var e;for(e of a.getOwnedObjects(!0))e.isDestroyed||e.healthTrait.healToFull(void 0,r);n=!0}else if(i.type===Es.Reveal)r.mapShroudTrait.revealMap(a,r),n=!0;else if(i.type===Es.Darkness)r.mapShroudTrait.resetShroud(a,r),n=!0;else if(i.type===Es.Veteran){if(t.veteranTrait&&!t.veteranTrait.isMaxLevel()){n=!0;var l,c=Number(i.data);for(l of this.getUnitsInCrateRadius(r,s,a))l.veteranTrait?.promote(c,r)}}else if(i.type===Es.Armor){if(1===t.crateBonuses.armor){n=!0;var u,d=Number(i.data);for(u of this.getUnitsInCrateRadius(r,s,a))1===u.crateBonuses.armor&&(u.crateBonuses.armor=d)}}else if(i.type===Es.Firepower){if(1===t.crateBonuses.firepower){n=!0;var g,p=Number(i.data);for(g of this.getUnitsInCrateRadius(r,s,a))1===g.crateBonuses.firepower&&(g.crateBonuses.firepower=p)}}else if(i.type===Es.Speed){if(1===t.crateBonuses.speed){n=!0;var m,f=Number(i.data);for(m of this.getUnitsInCrateRadius(r,s,a))1===m.crateBonuses.speed&&(m.crateBonuses.speed=f)}}else if(i.type===Es.Cloak){if(!t.cloakableTrait){n=!0;for(var y of this.getUnitsInCrateRadius(r,s,a))y.cloakableTrait||(y.cloakableTrait=new gn(y,r.rules.general.cloakDelay),r.addObjectTrait(y,y.cloakableTrait))}}else if(i.type===Es.ICBM){var w=[...r.rules.superWeaponRules.values()].find(e=>e.type===ss.MultiMissile);if(w&&a.superWeaponsTrait&&!a.superWeaponsTrait.has(w.name)){let e=r.createSuperWeapon(w.name,a,!0);e.isGift=!0,a.superWeaponsTrait.add(e),n=!0}}else if(i.type===Es.Invulnerability){var T=[...r.rules.superWeaponRules.values()].find(e=>e.type===ss.IronCurtain);T&&(r.traits.get(un).activateEffect(T,a,r,s,void 0,!0),n=!0)}else if(i.type===Es.Explosion||i.type===Es.Napalm){n=!0;w=Number(i.data),T=i.type===Es.Napalm?r.rules.combatDamage.flameDamage:r.rules.combatDamage.c4Warhead;let e=new Ja(r.rules.getWarhead(T));e.detonate(r,w,t.tile,t.tileElevation,t.position.worldPosition,t.zone,na.None,r.createTarget(t,t.tile),{player:t.owner,weapon:void 0},ca.None,void 0,0)}else{if(i.type!==Es.Tiberium)return void console.warn(`Unhandled powerup type "${Es[i.type]}"`);{let e=new va(r.map.tiles,r.map.mapBounds,s,2,r,e=>Qa.canBePlacedOn(e,r.map)),t,i=0;for(;i++<6&&(t=e.getNextTile());){var b=pn.calculateOverlayId(ha.Ore,t);if(void 0===b)throw new Error("Expected an overlayId");let e=r.createObject(Et.Overlay,r.rules.getOverlayName(b));e.overlayId=b,e.value=3,r.spawnObject(e,t),n=!0}}}if(n)return i.type;i=r.rules.powerups.powerups.find(e=>e.type===Es.Money&&0<e.probShares);return i?this.grantPowerup(t,i,s,r):void 0}}getUnitsInCrateRadius(e,t,i){let s=e.rules.crateRules.crateRadius,r=new Bs(e.map.tileOccupation);return e.map.technosByTile.queryRange((new Yn).setFromCenterAndSize(new Os(t.rx,t.ry),new Os(s,s))).filter(e=>e.owner===i&&e.isUnit()&&r.tileDistance(e,t)<=s)}}class eo{constructor(){this.powerups=[]}readIni(e){for(var[r,a]of e.entries){let[e,t,i,s]=a.split(",");var n=Number(e),a=Es[r];void 0!==a?Kn.includes(a)||this.powerups.push({type:a,probShares:n,animName:"<none>"!==t.toLowerCase()?t:void 0,waterAllowed:"yes"===i,data:s}):console.warn(`Unknown powerup "${r}". Skipping.`)}return this}}const to=["Gold","DarkRed","DarkBlue","DarkGreen","Orange","DarkSky","Purple","Magenta"];class io{constructor(e,t){this.ini=e,this.logger=t,this.buildingTypes=new Map,this.vehicleTypes=new Map,this.infantryTypes=new Map,this.aircraftTypes=new Map,this.terrainTypes=new Map,this.overlayTypes=new Map,this.overlayIdsByType=new Map,this.animationTypes=new Map,this.animationNames=new Set,this.voxelAnimTypes=new Map,this.smudgeTypes=new Map,this.warheadTypes=new Map,this.tiberiumTypes=new Map,this.superWeaponTypes=new Map,this.countryTypes=new Map,this.weaponTypes=new Map,this.allObjectRules=new Map,this.buildingRules=new Map,this.infantryRules=new Map,this.vehicleRules=new Map,this.aircraftRules=new Map,this.terrainRules=new Map,this.overlayRules=new Map,this.smudgeRules=new Map,this.voxelAnimRules=new Map,this.countryRules=new Map,this.warheadRules=new Map,this.powerups=new eo,this.colors=new Map,this.general=new Hi,this.ai=new fs,this.crateRules=new bs,this.elevationModel=new ys,this.mpDialogSettings=new kt,this.audioVisual=new xi,this.combatDamage=new ps,this.radiation=new ws,this.landRules=new Map,this.tiberiumRules=new Map,this.superWeaponRules=new Map,this.cachedWeaponRules=new Map,this.cachedProjectileRules=new Map,this.init()}hasObject(e,t){return this.allObjectRules.get(t)?.has(e)}getObject(e,t){t=this.allObjectRules.get(t)?.get(e);if(!t)throw new Error(`Missing rules for object "${e}"`);return t}getTechnoByInternalId(e,t){let i;if(t===Et.Building)i=this.buildingTypes.get(e);else if(t===Et.Infantry)i=this.infantryTypes.get(e);else if(t===Et.Vehicle)i=this.vehicleTypes.get(e);else{if(t!==Et.Aircraft)throw new Error(`Type ${Et[t]} is not a techno type`);i=this.aircraftTypes.get(e)}if(void 0===i)throw new Error(`Object type "${Et[t]}" with ID "${e}" not found`);return this.getObject(i,t)}getBuilding(e){var t=this.buildingRules.get(e);if(!t)throw new Error(`Missing rules for building "${e}"`);return t}getWeapon(e){let t=this.cachedWeaponRules.get(e);if(!t){var i=this.ini.getSection(e);if(!i)throw new Error(`Weapon ${e} is missing ini section`);t=new Bi(i),this.cachedWeaponRules.set(e,t)}return t}getWeaponByInternalId(e){var t=this.weaponTypes.get(e);if(!t)throw new RangeError(`Weapon with internal ID "${e}" not found`);return this.getWeapon(t)}getWarhead(e){let t=this.warheadRules.get(e.toLowerCase());var i;if(t||(i=this.ini.getSection(e))&&(t=new Xi(i),this.warheadRules.set(e.toLowerCase(),t)),!t)throw new Error(`Unknown warhead ${e}`);return t}getProjectile(e){let t=this.cachedProjectileRules.get(e);if(!t){var i=this.ini.getSection(e);if(!i)throw new Error(`Projectile ${e} is missing ini section`);t=new Zi(Et.Projectile,i),this.cachedProjectileRules.set(e,t)}return t}getOverlayName(e){var t=this.overlayTypes.get(e);if(!t)throw new Error(`Invalid overlay id ${e}`);return t}hasOverlayId(e){return this.overlayTypes.has(e)}getOverlayId(e){var t=this.overlayIdsByType.get(e);if(void 0===t)throw new Error(`Invalid overlay name ${e}`);return t}getOverlay(e){var t=this.overlayRules.get(e);if(!t)throw new Error(`Missing rules for overlay "${e}"`);return t}getAnimationName(e){return this.animationTypes.get(e)}getCountry(e){if(!this.countryRules.has(e))throw new Error(`Unknown country ${e}`);return this.countryRules.get(e)}getMultiplayerCountries(){return[...this.countryRules.values()].filter(e=>e.multiplay)}getMultiplayerColors(){let t=new Map;return to.forEach(e=>{if(!this.colors.has(e))throw new Error(`Multiplayer color "${e}" does not exist in the rules [Colors] section.`);t.set(e,this.colors.get(e))}),t}getLandRules(e){let t=this.landRules.get(e);var i;return t||(i=e===ei.Cliff?"Rock":ei[e],t=(new qi).readIni(this.ini.getOrCreateSection(i)),this.landRules.set(e,t)),t}getTiberium(e){var t=this.tiberiumTypes.get(e);if(!t)throw new Error(`Unknown tiberium type ${e}`);return this.tiberiumRules.get(t)}getSuperWeapon(e){if(!this.superWeaponRules.has(e))throw new Error(`Unknown superweapon type "${e}"`);return this.superWeaponRules.get(e)}getIni(){return this.ini}applySpecialFlags(e){e.initialVeteran&&(this.general.veteran.initialVeteran=!0)}init(){this.readAudioVisual(),this.readCombatDamage(),this.readRadiation(),this.readGeneral(),this.readAi(),this.readCrateRules(),this.readElevationModel(),this.readMpDialogSettings(),this.readObjectTypes("BuildingTypes",this.buildingTypes),this.readObjectTypes("InfantryTypes",this.infantryTypes),this.readObjectTypes("VehicleTypes",this.vehicleTypes),this.readObjectTypes("AircraftTypes",this.aircraftTypes),this.readObjectTypes("TerrainTypes",this.terrainTypes),this.readObjectTypes("SmudgeTypes",this.smudgeTypes),this.readObjectTypes("Animations",this.animationTypes),this.animationNames=new Set(this.animationTypes.values()),this.readObjectTypes("VoxelAnims",this.voxelAnimTypes),this.readObjectTypes("OverlayTypes",this.overlayTypes),this.overlayTypes.forEach((e,t)=>this.overlayIdsByType.set(e,t)),this.readColors(),this.readObjectTypes("Countries",this.countryTypes),this.readObjectTypes("Warheads",this.warheadTypes),this.readObjectTypes("Tiberiums",this.tiberiumTypes),this.readObjectTypes("SuperWeaponTypes",this.superWeaponTypes),this.allObjectRules.set(Et.Building,this.buildingRules).set(Et.Infantry,this.infantryRules).set(Et.Vehicle,this.vehicleRules).set(Et.Aircraft,this.aircraftRules).set(Et.Terrain,this.terrainRules).set(Et.Overlay,this.overlayRules).set(Et.Smudge,this.smudgeRules).set(Et.VoxelAnim,this.voxelAnimRules),this.readObjects(Et.Building,this.buildingTypes,this.buildingRules),this.readObjects(Et.Infantry,this.infantryTypes,this.infantryRules),this.readObjects(Et.Vehicle,this.vehicleTypes,this.vehicleRules),this.readObjects(Et.Aircraft,this.aircraftTypes,this.aircraftRules),this.readObjects(Et.Terrain,this.terrainTypes,this.terrainRules),this.readObjects(Et.Overlay,this.overlayTypes,this.overlayRules),this.readObjects(Et.Smudge,this.smudgeTypes,this.smudgeRules),this.readObjects(Et.VoxelAnim,this.voxelAnimTypes,this.voxelAnimRules),this.readCountries(),this.readWarheads(),this.readPowerups(),this.readTiberiums(),this.readSuperWeapons(),this.buildWeaponsList()}readAudioVisual(){var e=this.ini.getSection("AudioVisual");if(!e)throw new Error("Missing [AudioVisual] section");this.audioVisual.readIni(e)}readCombatDamage(){var e=this.ini.getSection("CombatDamage");if(!e)throw new Error("Missing [CombatDamage] section");this.combatDamage.readIni(e)}readRadiation(){var e=this.ini.getSection("Radiation");if(!e)throw new Error("Missing [Radiation] section");this.radiation.readIni(e)}readGeneral(){var e=this.ini.getSection("General");if(!e)throw new Error("Missing [General] section");this.general.readIni(e)}readAi(){var e=this.ini.getSection("AI");if(!e)throw new Error("Missing [AI] section");this.ai.readIni(e)}readCrateRules(){var e=this.ini.getSection("CrateRules");if(!e)throw new Error("Missing [CrateRules] section");this.crateRules.readIni(e)}readElevationModel(){var e=this.ini.getSection("ElevationModel");if(!e)throw new Error("Missing [ElevationModel] section");this.elevationModel.readIni(e)}readMpDialogSettings(){var e=this.ini.getSection("MultiplayerDialogSettings");if(!e)throw new Error("Missing [MultiplayerDialogSettings] section");this.mpDialogSettings.readIni(e)}readObjectTypes(i,s){let e=this.ini.getSection(i);if(!e)throw new Error(`Missing [${i}] section`);let r=0,a=new Set;e.entries.forEach((e,t)=>{"string"==typeof e?Number.isNaN(Number(t))?this.logger?.debug(`Non-numeric id "${t}" found in rules section [${i}]. Skipping.`):a.has(e)?this.logger?.debug(`Duplicate type "${e}" in rules section [${i}]. Skipping.`):(s.set(r++,e),a.add(e)):this.logger?.debug(`Non-string type found in rules section [${i}]. Skipping.`)})}readColors(){let e=this.ini.getSection("Colors");if(!e)throw new Error("Missing [Colors] section");e.entries.forEach((e,t)=>{var[i,s,e]=e.split(","),e=W.fromHsv(parseInt(i,10),parseInt(s,10),parseInt(e,10));this.colors.set(t,e)})}readObjects(s,e,r){e.forEach((e,t)=>{var i=this.ini.getSection(e);i?(t=(new gs).create(s,i,this.general,t),r.set(e,t)):this.logger?.debug(`${Et[s]} type "${e}" has no rules section`)})}readCountries(){this.countryTypes.forEach((e,t)=>{var i=this.ini.getSection(e);if(!i)throw new Error(`Missing ini section for country ${e}`);let s=new Ci(t);s.readIni(i),this.countryRules.set(e,s)})}readWarheads(){this.warheadTypes.forEach(e=>{var t=this.ini.getSection(e);t?(t=new Xi(t),this.warheadRules.set(e.toLowerCase(),t)):this.logger?.debug(`Warhead "${e}" has no rules section`)})}readPowerups(){var e=this.ini.getSection("Powerups");if(!e)throw new Error("Missing [Powerups] section");this.powerups.readIni(e)}readTiberiums(){this.tiberiumTypes.forEach(e=>{var t=this.ini.getSection(e);if(!t)throw new Error(`Missing rules section for tiberium type ${e}`);this.tiberiumRules.set(e,(new ms).readIni(t))})}readSuperWeapons(){this.superWeaponTypes.forEach((e,t)=>{var i=this.ini.getSection(e);if(!i)throw new Error(`Missing rules section for superweapon type ${e}`);this.superWeaponRules.set(e,new Ts(t).readIni(i))})}buildWeaponsList(){let e=new Set;e.add(this.general.dropPodWeapon);for(var t of this.superWeaponRules.values())t.weaponType&&e.add(t.weaponType);var s,i;e.add(rn.NUKE_PAYLOAD_NAME);for(let i of[...this.buildingRules.values(),...this.aircraftRules.values(),...this.vehicleRules.values(),...this.infantryRules.values()])for(s of[i.deathWeapon,i.primary,i.secondary,i.elitePrimary,i.eliteSecondary,i.occupyWeapon,i.eliteOccupyWeapon,...i.weaponCount?new Array(i.weaponCount).fill(0).map((e,t)=>[i.getWeaponAtIndex(t),i.getEliteWeaponAtIndex(t)]).flat():[]].filter(Wa).filter(e=>""!==e))e.add(s);let r=0;for(i of e)this.weaponTypes.set(r++,i)}}(r=mn=mn||{})[r.Ready=0]="Ready",r[r.Guard=1]="Guard",r[r.Prone=2]="Prone",r[r.Walk=3]="Walk",r[r.FireUp=4]="FireUp",r[r.Down=5]="Down",r[r.Crawl=6]="Crawl",r[r.Up=7]="Up",r[r.FireProne=8]="FireProne",r[r.Idle1=9]="Idle1",r[r.Idle2=10]="Idle2",r[r.Die1=11]="Die1",r[r.Die2=12]="Die2",r[r.Hover=13]="Hover",r[r.Fly=14]="Fly",r[r.FireFly=15]="FireFly",r[r.Tumble=16]="Tumble",r[r.AirDeathStart=17]="AirDeathStart",r[r.AirDeathFalling=18]="AirDeathFalling",r[r.AirDeathFinish=19]="AirDeathFinish",r[r.Tread=20]="Tread",r[r.Swim=21]="Swim",r[r.WetAttack=22]="WetAttack",r[r.WetIdle1=23]="WetIdle1",r[r.WetIdle2=24]="WetIdle2",r[r.WetDie1=25]="WetDie1",r[r.WetDie2=26]="WetDie2",r[r.Deploy=27]="Deploy",r[r.Deployed=28]="Deployed",r[r.DeployedFire=29]="DeployedFire",r[r.DeployedIdle=30]="DeployedIdle",r[r.Undeploy=31]="Undeploy",r[r.Paradrop=32]="Paradrop",r[r.Cheer=33]="Cheer",r[r.Panic=34]="Panic";const so=new Map([["E",5],["S",3],["W",1],["N",7]]);class ro{readIni(e){let t=new Map;for(var[i,s]of e.entries){i=mn[i];void 0!==i&&(s=s.split(","),s={type:i,startFrame:Number(s[0]),frameCount:Number(s[1]),facingMult:Number(s[2]),onlyFacing:s[3]?so.get(s[3]):void 0},t.set(i,s))}return t}}(r=fn=fn||{})[r.None=0]="None",r[r.Global=1]="Global",r[r.Level=2]="Level",r[r.Ambient=3]="Ambient",r[r.Full=4]="Full",r[r.Default=5]="Default";class ao{static getDefaultPalette(e){switch(e){case Et.Building:case Et.Aircraft:case Et.Infantry:case Et.Vehicle:case Et.Projectile:case Et.VoxelAnim:return _.Unit;case Et.Overlay:return _.Overlay;case Et.Smudge:case Et.Terrain:return _.Iso;default:Et.Animation;return _.Anim}}static getDefaultLighting(e){switch(e){case Et.Animation:return fn.None;case Et.Aircraft:case Et.Building:case Et.Infantry:case Et.Vehicle:return fn.Ambient;case Et.Projectile:case Et.VoxelAnim:return fn.Global;case Et.Overlay:case Et.Smudge:case Et.Terrain:default:return fn.Full}}static getDefaultRemapability(e){switch(e){case Et.Aircraft:case Et.Building:case Et.Infantry:case Et.Vehicle:return!0;case Et.Overlay:case Et.Smudge:case Et.Terrain:case Et.Animation:case Et.Projectile:case Et.VoxelAnim:return!1;default:throw new Error(`Unknown object type ${e}`)}}static getDefaultDrawOffset(e){switch(e){case Et.Animation:case Et.Building:case Et.Vehicle:case Et.Infantry:case Et.Overlay:case Et.Smudge:case Et.Projectile:case Et.VoxelAnim:return new Os(0,0);case Et.Terrain:case Et.Aircraft:return new Os(0,(_s.ISO_TILE_SIZE+1)/2);default:throw new Error(`Unknown object type ${e}`)}}static getDefaultShadow(e){switch(e){case Et.Overlay:case Et.Building:case Et.Infantry:case Et.Terrain:case Et.Vehicle:case Et.Aircraft:return!0;default:case Et.Smudge:case Et.Animation:case Et.Projectile:case Et.VoxelAnim:return!1}}static getDefaultHeight(e){switch(e){case Et.Building:return 2;case Et.Infantry:case Et.Vehicle:case Et.Aircraft:return 1;default:return 0}}static factory(e,t,i,s){let r=new this(e,t,s);return e===Et.Infantry&&(!(s=s.getString("Sequence"))||(s=i.getSection(s))&&(r.sequences=(new ro).readIni(s))),r}constructor(e,t,i){this.sequences=new Map,this.dockingOffsets=[],this.type=e,this.rules=t,this.art=i,this.init()}init(){this.image=[Et.Infantry,Et.Vehicle,Et.Aircraft].includes(this.type)?"":this.art.getString("Image"),this.report=this.art.getString("Report")||void 0,this.readRotors(),this.noHva=this.art.getBool("NoHVA"),this.startSound=this.art.getString("StartSound")||void 0,this.readMuzzleFlash(),this.readPaletteAndLightingTypes(),this.readRemapability(),this.readFlatness(),this.readDockingOffsets();var e=this.art.getNumberArray("QueueingCell");this.queueingCell=e.length?new Os(e[0],e[1]):void 0,this.demandLoad=this.art.getBool("DemandLoad");var t=this.art.getBool("UseLineTrail"),i=this.art.getNumberArray("LineTrailColor"),e=this.art.getNumber("LineTrailColorDecrement",ao.DEFAULT_LINE_TRAIL_DEC);t&&i.length?(this.useLineTrail=!0,this.lineTrailColor=i,this.lineTrailColorDecrement=e):this.useLineTrail=!1,this.crater=this.art.getBool("Crater"),this.forceBigCraters=this.art.getBool("ForceBigCraters"),this.scorch=this.art.getBool("Scorch"),this.height=this.art.getNumber("Height",ao.getDefaultHeight(this.type)),this.isVoxel=this.art.getBool("Voxel"),this.occupyHeight=this.art.getNumber("OccupyHeight",this.height),this.type===Et.Building?this.canHideThings=this.art.getBool("CanHideThings",!0):this.canHideThings=!1,this.canBeHidden=this.art.getBool("CanBeHidden",!0),this.addOccupy=this.readAddRemoveOccupy("AddOccupy"),this.removeOccupy=this.readAddRemoveOccupy("RemoveOccupy"),this.rotates=this.art.getBool("Rotates")}get imageName(){return(this.image||this.rules.imageName)+(this.rules.alternateArcticArt?"A":"")}get cameo(){let e=this.art.getString("Cameo")||ao.MISSING_CAMEO;return e.toLowerCase()}get altCameo(){let e=this.art.getString("AltCameo")||this.cameo;return e.toLowerCase()}get useTheaterExtension(){return this.art.getBool("Theater")}readPaletteAndLightingTypes(){this.paletteType=_.Default,this.lightingType=fn.Default,(this.rules instanceof ls?this.rules.noUseTileLandType:void 0)&&(this.paletteType=_.Iso,this.lightingType=fn.Full),this.art.getBool("TerrainPalette")||this.art.getBool("ShouldUseCellDrawer")?this.paletteType=_.Iso:this.art.getBool("AnimPalette")?(this.paletteType=_.Anim,this.lightingType=fn.None):this.art.getString("Palette")&&(this.paletteType=_.Custom,this.customPaletteName=this.art.getString("Palette")),this.art.getBool("AltPalette")&&(this.paletteType=_.Unit),(this.rules instanceof ls||this.rules instanceof hs)&&this.rules.wall&&(this.paletteType=_.Unit,this.lightingType=fn.Ambient),(this.rules instanceof cs||this.rules instanceof hs)&&this.rules.gate&&(this.paletteType=_.Unit),this.rules instanceof cs&&this.rules.spawnsTiberium&&(this.paletteType=_.Unit,this.lightingType=fn.None),this.rules instanceof ls&&(this.rules.isVeins&&(this.paletteType=_.Unit,this.lightingType=fn.None),this.rules.isVeinholeMonster&&(this.paletteType=_.Unit,this.lightingType=fn.None),this.rules.tiberium&&(this.lightingType=fn.None),this.rules.land===ei.Railroad&&(this.paletteType=_.Iso,this.lightingType=fn.Full),this.rules.crate&&(this.paletteType=_.Iso,this.lightingType=fn.Full)),this.paletteType===_.Default&&(this.paletteType=ao.getDefaultPalette(this.type)),this.lightingType===fn.Default&&(this.lightingType=ao.getDefaultLighting(this.type))}readRemapability(){this.remapable=ao.getDefaultRemapability(this.type),this.art.getBool("TerrainPalette")||this.art.getBool("AnimPalette")?this.remapable=!1:this.rules instanceof Zi&&this.rules.firersPalette&&(this.remapable=!0)}readFlatness(){let e=!1;this.type===Et.Building||this.type===Et.Animation?e=this.art.getBool("Flat"):this.type===Et.Smudge&&(e=!0),this.rules instanceof ls&&(this.rules.wall||this.rules.crate||this.rules.isARock||(e=!0)),this.flat=e}readRotors(){var i=this.art.getArray("Rotors");if(i.length){let t=[];for(let e=0;e<i.length;++e){var s=this.art.getNumberArray(`Rotor${e+1}Axis`,void 0,[0,1,0]),s=new as(-s[2],-s[0],s[1]).normalize();t.push({name:i[e],axis:s,speed:this.art.getNumber(`Rotor${e+1}Rate`)||void 0,idleSpeed:this.art.getNumber(`Rotor${e+1}IdleRate`)||void 0})}t.length&&(this.rotors=t)}}readMuzzleFlash(){let e=0,t=`MuzzleFlash${e}`,i=[];for(;this.art.has(t);){var[s,r]=this.art.getNumberArray(t);i.push({x:s,y:r}),e++,t=`MuzzleFlash${e}`}this.muzzleFlash=i.length?i:void 0}readDockingOffsets(){if(this.type===Et.Building){var t=this.rules.numberOfDocks;for(let e=0;e<t;e++){var[i,s,r]=this.art.getNumberArray(`DockingOffset${e}`,/,\s*/,[0,0,0]);this.dockingOffsets.push(new as(i,r,s))}}}readAddRemoveOccupy(e){let t=0,i=[];for(;;){var s=this.art.getNumberArray(e+ ++t);if(!s.length)break;i.push(new Os(s[0],s[1]))}return i}get bibShape(){return this.art.getString("BibShape")}get foundation(){let e=this.art.getString("Foundation","1x1");var[t,i]=e.split("x");return{width:parseInt(t,10),height:parseInt(i,10)}}get foundationCenter(){return new Os(Math.floor(this.foundation.width/2-.5),Math.floor(this.foundation.height/2-.5))}getDrawOffset(){if(this.rules instanceof cs&&this.rules.spawnsTiberium)return new Os(0,0);let e=ao.getDefaultDrawOffset(this.type);return this.rules instanceof ls&&this.rules.isARock&&(e.y+=(_s.ISO_TILE_SIZE+1)/2),e}get hasShadow(){return this.art.getBool("Shadow",ao.getDefaultShadow(this.type))&&!this.rules.noShadow}get turretOffset(){return this.art.getNumber("TurretOffset")}get facings(){return this.art.getNumber("Facings",8)}get walkFrames(){return this.art.getNumber("WalkFrames")}get firingFrames(){return this.art.getNumber("FiringFrames")}get standingFrames(){return this.art.getNumber("StandingFrames",1)}get startWalkFrame(){return this.art.getNumber("StartWalkFrame",0)}get startStandFrame(){return this.art.getNumber("StartStandFrame",this.walkFrames*this.facings)}get startFiringFrame(){return this.art.getNumber("StartFiringFrame",(this.walkFrames+this.standingFrames)*this.facings)}get isFlamingGuy(){return this.art.getBool("IsFlamingGuy")}get runningFrames(){return this.art.getNumber("RunningFrames")}get crawls(){return this.art.getBool("Crawls",!0)}get primaryFireFlh(){return new en(this.art.getNumberArray("PrimaryFireFLH"))}get elitePrimaryFireFlh(){var e=this.art.getNumberArray("ElitePrimaryFireFLH");return e.length?new en(e):this.primaryFireFlh}get primaryFirePixelOffset(){return this.art.getNumberArray("PrimaryFirePixelOffset")}get secondaryFirePixelOffset(){return this.art.getNumberArray("SecondaryFirePixelOffset")}get secondaryFireFlh(){return new en(this.art.getNumberArray("SecondaryFireFLH"))}get eliteSecondaryFireFlh(){var e=this.art.getNumberArray("EliteSecondaryFireFLH");return e.length?new en(e):this.secondaryFireFlh}getSpecialWeaponFlh(e){return new en(this.art.getNumberArray(`Weapon${e+1}FLH`))}get fireUp(){return this.art.getNumber("FireUp")||this.art.getNumber("DelayedFireDelay")}get isAnimDelayedFire(){return this.art.getBool("IsAnimDelayedFire")}get zShapePointMove(){return this.art.getNumberArray("ZShapePointMove")}get zAdjust(){return this.art.getNumber("ZAdjust")}get trailer(){return this.art.getString("Trailer")}get spawnDelay(){return this.art.getNumber("SpawnDelay",1)}get translucent(){return this.art.getBool("Translucent")}get translucency(){var e=(e=this.art.getNumber("Translucency",0))/25*25;return e/=100}}ao.DEFAULT_LINE_TRAIL_DEC=16,ao.MISSING_CAMEO="xxicon";class no{constructor(e,t,i,s){this.rules=e,this.artIni=t,this.mapFile=i,this.logger=s,this.objectArt=new Map,this.parse()}hasObject(e,t){return this.objectArt.get(t)?.has(e)}getObject(e,t){if(!e)throw new Error(`Must specify an art name for type "${Et[t]}"`);var i=this.objectArt.get(t)?.get(e);return i||(this.logger?.debug(`Missing art for object "${e}"`),new ao(t,this.rules.hasObject(e,t)?this.rules.getObject(e,t):new Ai(t,new h(e)),new h(e)))}getAnimation(e){return this.getObject(e,Et.Animation)}getProjectile(e){var t=this.rules.getProjectile(e),i=t.imageName;let s=this.artIni.getSection(i);return s||(this.logger?.debug(`Image ${i} (Projectile: ${e}) has no section in art.ini`),s=new h(i)),ao.factory(t.type,t,this.artIni,s)}getIni(){return this.artIni}parse(){this.rules.allObjectRules.forEach((e,t)=>{let s=new Map;this.objectArt.set(t,s),e.forEach(e=>{var t=this.artIni.getSection(e.imageName),i=this.artIni.getSection(e.name);(t=this.applyUnitMapOverrides(e,this.mapFile,i,t))?(t=ao.factory(e.type,e,this.artIni,t),s.set(e.name,t)):this.logger?.debug(`${Et[e.type]} "${e.name}" has no art section "${e.imageName}"`)})});let e=[[Et.Animation,this.rules.animationNames]];e.forEach(([s,e])=>{let r=new Map;this.objectArt.set(s,r),e.forEach(e=>{var t,i=this.artIni.getSection(e);i?(t=new Ai(s,new h(e)),i=new ao(s,t,i),r.set(e,i)):this.logger?.debug(`${Et[s]} "${e}" has no art section`)})})}applyUnitMapOverrides(e,t,s,r){if([Et.Infantry,Et.Vehicle,Et.Aircraft].includes(e.type)&&!!t?.getSection(e.name)?.getString("Image")&&s){let i=s.clone();r?.entries.forEach((e,t)=>{i.set(t,e)}),r=i,this.logger?.debug(`${Et[e.type]} "${e.name}": `+`Using merged art sections ${e.name} and ${e.imageName}`)}return r}}class oo{static factory(e,t){return new this(t.getCountry(e))}constructor(e){this.rules=e}get id(){return this.rules.id}get side(){return this.rules.side}get name(){return this.rules.name}isPlayable(){return this.rules.multiplay&&!this.rules.multiplayPassive}hasVeteranUnit(e,t){let i=[];switch(e){case Et.Aircraft:i=this.rules.veteranAircraft;break;case Et.Infantry:i=this.rules.veteranInfantry;break;case Et.Vehicle:i=this.rules.veteranUnits;break;default:throw new Error(`Unsupported object type "${Et[e]}"`)}return i.includes(t)}}class ho{constructor(e,t){this.target=e,this.player=t,this.type=rs.BuildingEvacuate}}class lo{constructor(e,t,i){this.building=e,this.evacThreshold=t,this.maxOccupants=i,this.units=[]}isOccupied(){return!!this.units.length}canBeOccupied(){return this.building.healthTrait.health>100*this.evacThreshold}[ga.onDamage](e,t){e.healthTrait.health<=100*this.evacThreshold&&this.evacuate(t)}[Vr.onDestroy](e,t,i,s){if(s){for(var r of this.units)r.deathType=e.deathType,t.destroyObject(r,i,!0);this.units=[]}else this.evacuate(t)}getHash(){return G(this.units.map(e=>e.getHash()))}debugGetState(){return{units:this.units.map(e=>e.debugGetState())}}dispose(){this.building=void 0}evacuate(s,r=!1){let a=this.building,n=this.units;if(n.length){let e=new Map;for(var t of n)e.set(t.rules.speedType,(e.get(t.rules.speedType)||[]).concat(t));for(let[t,i]of e){var o,h=new Ws(s.map.tiles,s.map.mapBounds,a.tile,a.art.foundation,1,1,e=>0<s.map.terrain.getPassableSpeed(e,t,!0,!1)&&Math.abs(e.z-a.tile.z)<2&&!s.map.terrain.findObstacles({tile:e,onBridge:void 0},i[0]).length).getNextTile();for(o of i){var l=n.indexOf(o);h?(n.splice(l,1),s.unlimboObject(o,h),o.onBridge=s.map.tileOccupation.getBridgeOnTile(h)?.isLowBridge()??!1,o.position.tileElevation=0,o.unitOrderTrait.addTask(new Oa(s))):r||(s.destroyObject(o,{player:o.owner}),n.splice(l,1))}}var i=a.owner;n.length||a.isDestroyed||s.changeObjectOwner(a,s.getCivilianPlayer()),s.events.dispatch(new ho(a,i))}}}class co{constructor(){this.facing=0,this.desiredFacing=0}isRotating(){return this.facing!==this.desiredFacing}[Kr.onSpawn](e){e.isUnit()&&(this.facing=this.desiredFacing=e.direction)}[jr.onTick](e){this.desiredFacing!==this.facing&&(e=e.rules.rot,this.facing=vr.tick(this.facing,this.desiredFacing,e||Number.POSITIVE_INFINITY).facing)}}class uo{constructor(e,t){this.target=e,this.status=t,this.type=rs.BuildStatusChange}}class go{constructor(e){this.target=e,this.type=rs.PowerLow}}class po{constructor(e){this.target=e,this.type=rs.PowerRestore}}class mo{constructor(e,t,i){this.target=e,this.power=t,this.drain=i,this.type=rs.PowerChange}}(r=yn=yn||{})[r.Low=0]="Low",r[r.Normal=1]="Normal";class fo{constructor(e){this.player=e,this.power=0,this.drain=0,this.level=yn.Normal,this.blackoutFrames=0,this.powerByObject=new Map}isLowPower(){return this.level===yn.Low}setBlackoutFor(e,t){var i=0<this.blackoutFrames;this.blackoutFrames=e,i||this.updateLevel(t)}updateBlackout(e){0<this.blackoutFrames&&(this.blackoutFrames--,this.blackoutFrames<=0&&this.updateLevel(e))}getBlackoutDuration(){return this.blackoutFrames}updateFrom(t,i,s){var r=t.rules.power;if(r){if(r<0)"add"!==i&&"remove"!==i||(this.drain+="add"===i?-r:r);else{let e=0;if("add"===i){var a=Math.ceil(r*t.healthTrait.health/100);this.powerByObject.set(t,a),e=a}else if("update"===i||"remove"===i){a=this.powerByObject.get(t);if(void 0===a)throw new Error("Cannot update power before add.");e="update"===i?(r=Math.ceil(r*t.healthTrait.health/100),this.powerByObject.set(t,r),r-a):(this.powerByObject.delete(t),-a)}this.power+=e}this.updateLevel(s),s.traits.filter(Rs).forEach(e=>{e[Rs.onPowerChange](this.player,s)}),s.events.dispatch(new mo(this.player,this.power,this.drain))}}updateLevel(t){var e=this.level;this.level=this.power>=this.drain&&!this.blackoutFrames?yn.Normal:yn.Low,this.level!==e&&(e===yn.Normal&&this.level===yn.Low&&(t.traits.filter(Rs).forEach(e=>{e[Rs.onPowerLow](this.player,t)}),t.events.dispatch(new go(this.player))),e===yn.Low&&this.level===yn.Normal&&(t.traits.filter(Rs).forEach(e=>{e[Rs.onPowerRestore](this.player,t)}),t.events.dispatch(new po(this.player))))}getHash(){return G([this.power,this.drain])}debugGetState(){return{power:this.power,drain:this.drain}}dispose(){this.player=void 0,this.powerByObject.clear()}}class yo{constructor(e){this.obj=e,this.turnedOn=!0}setTurnedOn(e){this.turnedOn=e}isCharged(){return!!this.obj.isBuilding()&&!!this.obj.overpoweredTrait?.hasChargersToPowerOn()}isPoweredOn(e=!1){return!(!this.obj||!this.turnedOn)&&(!(e||!this.isCharged())||(!this.obj.rules.power&&this.obj.rules.needsEngineer?!this.obj.owner.isNeutral:!!this.obj.owner.powerTrait&&this.obj.owner.powerTrait?.level!==yn.Low))}dispose(){this.obj=void 0}}class wo{constructor(){this.listeners=new Set}subscribe(e){this.listeners.add(e)}subscribeOnce(i){let s=(e,t)=>{i(e,t),this.unsubscribe(s),s=void 0};this.subscribe(s)}unsubscribe(e){this.listeners.delete(e)}dispatch(t,i){this.listeners.forEach(e=>e(i,t))}asEvent(){return this}}(r=wn=wn||{})[r.Structures=0]="Structures",r[r.Armory=1]="Armory",r[r.Infantry=2]="Infantry",r[r.Vehicles=3]="Vehicles",r[r.Aircrafts=4]="Aircrafts",r[r.Ships=5]="Ships",(r=Tn=Tn||{})[r.Idle=0]="Idle",r[r.Active=1]="Active",r[r.OnHold=2]="OnHold",r[r.Ready=3]="Ready";class To{get onUpdate(){return this._onUpdate.asEvent()}constructor(e,t,i){this.type=e,this._maxSize=t,this.maxItemQuantity=i,this.items=[],this.size=0,this._status=Tn.Idle,this._onUpdate=new wo}get status(){return this._status}set status(e){var t=this._status;(this._status=e)!==t&&this._onUpdate.dispatch(this)}get maxSize(){return this._maxSize}set maxSize(e){var t=this.size;this.size=Math.min(e,this.size);let i=0,s=0;for(;i<=this.size&&s<this.items.length;){let e=this.items[s];i+=e.quantity,i>this.size&&(e.quantity-=i-this.size),0<e.quantity&&s++}this._maxSize=e,this.items[s]&&this.items.splice(s),t!==this.size&&(this.size||(this._status=Tn.Idle),this._onUpdate.dispatch(this))}get currentSize(){return this.size}find(t){return this.items.filter(e=>e.rules===t)}getFirst(){return this.items[0]}getAll(){return[...this.items]}push(e,t,i){t=Math.min(this.maxSize-this.size,t);var s=this.find(e).reduce((e,t)=>e+t.quantity,0);t=Math.min(this.maxItemQuantity-s,t),this.items[this.items.length-1]?.rules===e?this.items[this.items.length-1].quantity+=t:this.items.push({rules:e,quantity:t,creditsEach:i,creditsSpent:0,creditsSpentLeftover:0,progress:0}),this.size+=t,t&&(this._status===Tn.Idle&&(this._status=Tn.Active),this._onUpdate.dispatch(this))}pop(e,t){this.remove(e,t,!1)}shift(e,t){this.remove(e,t,!0)}remove(e,t,i){let s=this.find(e);if(!s.length)throw new Error(`Can't remove non-existent item ${e.name} from queue ${wn[this.type]}`);var r;if(s.reduce((e,t)=>e+t.quantity,0)<t)throw new Error(`Attempted to remove a quantity larger than the one in queue (${e.name})`);let a=t;for(;0<a;){let e=i?s.shift():s.pop();e.quantity<=a?(r=this.getFirst()===e,this.items.splice(this.items.indexOf(e),1),r&&(this._status=Tn.Active),a-=e.quantity):(e.quantity-=a,a=0)}this.size-=t,t&&(this.size||(this._status=Tn.Idle),this._onUpdate.dispatch(this))}notifyUpdated(){this._onUpdate.dispatch(this)}}const bo=e=>void 0!==e.position;class vo{constructor(e,t){this.tiles=e,this.tileOccupation=t}hasLineOfSight(t,i,s){var r=s.warhead.rules.wall||!s.projectileRules.subjectToWalls,a=s.projectileRules.subjectToCliffs,n=s.rules.spawner;let o=0,h=!1;if(!r||a||n){var l,c,s=bo(t)?t.tile:t,i=bo(i)?i.isBuilding()?i.centerTile:i.tile:i;let e=s.z;a&&bo(t)&&t.isUnit()&&t.onBridge&&(e+=this.tileOccupation.getBridgeOnTile(s)?.tileElevation??0);for({x:l,y:c}of Ua(s.rx,s.ry,i.rx,i.ry)){var u=this.tiles.getByMapCoords(l,c);if(!u)return!1;if(!r&&u.landType===ei.Wall)return!1;if(a)if(u.landType===ei.Cliff){if(u.z>e)return!1;h=!0}else{if(u.z>e&&h)return!1;h=!1}if(n&&o<2&&this.tileOccupation.getBridgeOnTile(u)?.isHighBridge())return!1;o++}}return!0}}class So extends _a{constructor(e,t,i,s){super(e,t instanceof Ea?t.isBuilding()?t.centerTile:t.tile:t,i,{pathFinderIgnoredBlockers:t instanceof Ea&&0<s.range?[t]:void 0}),this.target=t,this.weapon=s,this.recalcMinRange=!0,this.cancelRequested=!1,this.bomberInitialLock=!1,this.rangeHelper=new Bs(e.map.tileOccupation),this.losHelper=new vo(e.map.tiles,e.map.tileOccupation)}onStart(i){let e=this.target,s=this.game.map;if(e instanceof Ea&&e.isBuilding()&&i.rules.movementZone!==ai.Fly){let t=e.tile;var r=e instanceof Ea?e.getFoundation():{width:1,height:1},r=new Ws(s.tiles,s.mapBounds,t,r,1,5,e=>0<s.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-t.z)<2).getNextTile();r&&this.rangeHelper.tileDistance(e,r)>Math.SQRT2&&this.updateTarget(r,!1)}this.bomberInitialLock=this.isCloseEnoughToDest(i,i.tile),super.onStart(i)}cancel(){this.bomberManeuverTile?this.cancelRequested=!0:super.cancel()}shouldAirStrafe(e){return e.rules.movementZone===ai.Fly&&e.rules.locomotor===ri.Aircraft&&e.rules.fighter&&1<this.weapon.projectileRules.iniRot}isBombingRun(e){return e.rules.movementZone===ai.Fly&&e.rules.locomotor===ri.Aircraft&&this.weapon.projectileRules.iniRot<=1}isAirStrafeCloseEnough(e){return this.rangeHelper.tileDistance(e,this.targetTile)<Math.min(this.weapon.range,2)}bomberCanReturn(e){return!this.bomberManeuverTile||this.rangeHelper.tileDistance(e,this.bomberManeuverTile)<=1}findStrafeDestination(t,i){let e=new va(this.game.map.tiles,this.game.map.mapBounds,i,this.weapon.range,this.game,e=>this.rangeHelper.isInWeaponRange(t,i,this.weapon,this.game.rules,e));return e.getNextTile()}hasReachedDestination(e){return super.hasReachedDestination(e)||this.canStopAtTile(e,e.tile,e.onBridge)}canStopAtTile(t,e,i){if(t.zone!==Ss.Air&&this.target instanceof Ea&&this.game.map.tileOccupation.isTileOccupiedBy(e,this.target)&&(!this.target.isUnit()||this.target.tile===e&&this.target.moveTrait.moveState!==Xr.Moving))return!1;if(t.zone!==Ss.Air){if(!super.canStopAtTile(t,e,i))return!1}else if(this.game.map.tileOccupation.getAirObjectsOnTile(e).filter(e=>e.isUnit()&&e.moveTrait.moveState!==Xr.Moving&&e!==t).length)return!1;return!(this.isBombingRun(t)&&!this.bomberCanReturn(e))&&(!!this.isCancelling()||this.isCloseEnoughToDest(t,e))}isCloseEnoughToDest(e,t){if(e.rules.balloonHover&&!e.rules.hoverAttack)return this.rangeHelper.isInTileRange(t,this.target,0,0);if(this.weapon.rules.cellRangefinding||!e.isInfantry())return this.rangeHelper.isInWeaponRange(e,this.target,this.weapon,this.game.rules,t)&&this.losHelper.hasLineOfSight(t,this.target,this.weapon);var i=e.zone===Ss.Air?e.position.computeSubCellOffset(e.position.desiredSubCell):e.position.getTileOffset(),{minRange:s,range:r}=this.rangeHelper.computeWeaponRangeVsTarget(t,this.target,this.weapon,this.game.rules),i=_s.tile3dToWorld(t.rx+i.x/_s.LEPTONS_PER_TILE,t.ry+i.y/_s.LEPTONS_PER_TILE,t.z+e.position.tileElevation);return(e.isUnit()&&e.rules.movementZone===ai.Fly?this.rangeHelper.isInRange2(i,this.target,s,r):this.rangeHelper.isInRange3(i,this.target,s,r))&&this.losHelper.hasLineOfSight(t,this.target,this.weapon)}findRelocationTile(t,i,s){if(s.rules.movementZone!==ai.Fly)return super.findRelocationTile(t,i,s);{i=this.game.map;let e=new va(i.tiles,i.mapBounds,t,1,this.game,e=>this.isCancelling()||this.isCloseEnoughToDest(s,e));return e.getNextTile()}}retarget(e,t){var i=e instanceof Ea?e.isBuilding()?e.centerTile:e.tile:e;this.bomberManeuverTile?this.bomberQueuedTargetTile=i:(this.updateTarget(i,t),this.recalcMinRange=!0),this.target=e,this.options?.ignoredBlockers&&(this.options.ignoredBlockers=e instanceof Ea?[e]:void 0),this.options??(this.options={}),this.options.pathFinderIgnoredBlockers=e instanceof Ea?[e]:void 0}onTick(r){if(this.recalcMinRange){this.recalcMinRange=!1;var e=this.findMinRangeRelocationTile(r,this.targetTile);if(e!==this.targetTile){if(!e)return this.cancel(),!1;this.updateTarget(e,!!e.onBridgeLandType)}}if(this.shouldAirStrafe(r)&&!this.isCancelling()&&(this.updateTarget(this.target instanceof Ea?this.target.isBuilding()?this.target.centerTile:this.target.tile:this.target,!1),!this.isAirStrafeCloseEnough(r)||(a=this.findStrafeDestination(r,this.targetTile))&&this.updateTarget(a,!1)),this.isBombingRun(r)&&!this.isCancelling()&&(!r.ammo||this.weapon.getBurstsFired()||this.bomberInitialLock)&&!this.bomberManeuverTile){this.bomberInitialLock=!1;let e=r.position.getMapPosition();var a=this.target instanceof Ea?this.target.isBuilding()?this.target.centerTile:this.target.tile:this.target;let t=new Os(a.rx+.5,a.ry+.5).clone().multiplyScalar(_s.LEPTONS_PER_TILE).sub(e),i=t.length();i||(t.copy(vr.toMapCoords(r.direction)),i=Number.EPSILON);let s=e.clone().add(t.setLength(i+7*_s.LEPTONS_PER_TILE));a=s.multiplyScalar(1/_s.LEPTONS_PER_TILE).floor(),a=Ua(a.x,a.y,r.tile.rx,r.tile.ry);if(!a.length)throw new Error("Bresenham returned no tiles");a=a[0];this.bomberManeuverTile=this.game.map.tiles.getByMapCoords(a.x,a.y)??this.game.map.tiles.getPlaceholderTile(a.x,a.y),this.options.allowOutOfBoundsTarget=!0,this.updateTarget(this.bomberManeuverTile,!1)}return this.bomberManeuverTile&&this.bomberCanReturn(r.tile)&&(this.bomberManeuverTile=void 0,this.bomberQueuedTargetTile&&(this.updateTarget(this.bomberQueuedTargetTile,!1),this.recalcMinRange=!0,this.bomberQueuedTargetTile=void 0)),this.cancelRequested&&(this.bomberManeuverTile||(this.cancelRequested=!1,this.cancel())),!!(this.isBombingRun(r)&&this.isCancelling()&&this.forceCancel(r))||super.onTick(r)}forceCancel(e){return!this.bomberManeuverTile&&super.forceCancel(e)}findMinRangeRelocationTile(e,t){var{minRange:i,range:s}=this.rangeHelper.computeWeaponRangeVsTarget(e,this.target,this.weapon,this.game.rules);return e.rules.locomotor===ri.Chrono?this.rangeHelper.isInRange(e,this.target,s-1,s,this.weapon.rules.cellRangefinding)?t:this.findTileInRange(e,t,s-1,2*s)??t:this.rangeHelper.isInRange(e,this.target,i,Number.POSITIVE_INFINITY,this.weapon.rules.cellRangefinding)?t:this.findTileInRange(e,t,2*i,s-i)}findTileInRange(t,e,i,s){let r=this.game.map;var a,i=new Os(t.tile.rx-e.rx,t.tile.ry-e.ry).setLength(i).floor().add(new Os(e.rx,e.ry));let n;for(a of Ua(i.x,i.y,e.rx,e.ry))if(n=r.tiles.getByMapCoords(a.x,a.y),n)break;if(n){let e=new Ws(r.tiles,r.mapBounds,n,{width:1,height:1},0,s,e=>this.rangeHelper.isInWeaponRange(t,this.target,this.weapon,this.game.rules,e)&&this.losHelper.hasLineOfSight(e,this.target,this.weapon)&&0<r.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!!e.onBridgeLandType)&&!r.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},t).length);return e.getNextTile()}}}class ko{tick(e,t){this.tickChildren(e,t)}startTask(e,t){if(e.status!==js.NotStarted)throw new Error(`Attempted to start a task with status ${e.status}`);e.status=js.Running,e.onStart(t)}tickTask(e,t){let i=this.tickChildren(e.children,t);var s=e.children.find(e=>e.blocking);if(!i&&s)return!1;if(!t.isSpawned)return!1;if(e.status===js.NotStarted)throw new Error("Attempted tick on a non-started task");if(e.isRunning()||e.isCancelling()){var r=e.isCancelling(),a=!!e.waitingForChildrenToFinish||e.onTick(t);e.children.length&&!s&&a&&(i=e.children.every(e=>e.status===js.Cancelled||e.status===js.Finished),e.waitingForChildrenToFinish=!i);a=a&&i;return a&&(e.onEnd(t),e.status=r?js.Cancelled:js.Finished),a}return!0}tickChildren(s,r){let a=!0;if(s.length){let t=new Set,i;for(;r.isSpawned&&(i=s.find(e=>!t.has(e)));){let e;if(i.status===js.NotStarted&&this.startTask(i,r),i.status===js.Running||i.status===js.Cancelling)e=!0===this.tickTask(i,r);else{if(i.status!==js.Cancelled)throw new Error(`Unhandled task status ${js[i.status]}`);e=!0}if(e){var n=s.indexOf(i);-1!==n&&s.splice(n,1)}else{if(a=!1,i.blocking)break;t.add(i)}}}return a}}class Oo{constructor(e,t,i){this.tileOccupation=i,this.isOre=!1,e?e.isOverlay()&&e.isBridge()?(this.bridge=e,this.tile=t):e.isOverlay()&&e.isTiberium()?(this.isOre=!0,this.tile=e.tile):(this.obj=e,this.tile=e.isBuilding()?e.centerTile:e.tile):(t.landType===ei.Tiberium&&(this.isOre=!0),this.tile=t)}equals(e){return this.obj===e.obj&&this.tile===e.tile&&this.bridge===e.bridge&&this.isOre===e.isOre}getWorldCoords(){return this.obj?this.obj.position.worldPosition:_s.tile3dToWorld(this.tile.rx+.5,this.tile.ry+.5,this.tile.z+(this.bridge?.tileElevation??0))}isBridge(){return!this.obj&&!!this.bridge}getBridge(){return this.bridge||(this.obj?.isUnit()&&this.obj.onBridge?this.tileOccupation.getBridgeOnTile(this.obj.tile):void 0)}}(r=bn=bn||{})[r.Idle=0]="Idle",r[r.CheckRange=1]="CheckRange",r[r.PrepareToFire=2]="PrepareToFire",r[r.FireUp=3]="FireUp",r[r.Firing=4]="Firing",r[r.JustFired=5]="JustFired";class _o{constructor(e,t){this.disabled=!1,this.attackState=bn.Idle,this.passiveScanCooldownTicks=0,this.taskRunner=new ko,this.distributedFireHistory=new Map,this.rangeHelper=new Bs(t),this.losHelper=new vo(e,t)}isIdle(){return this.attackState===bn.Idle}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}isOnCooldown(e){let t=[e.primaryWeapon,e.secondaryWeapon],i=e.armedTrait?.getDeployFireWeapon();return i?.rules.areaFire&&!i.rules.fireOnce&&(t=t.filter(e=>e!==i)),t.some(e=>0<(e?.getCooldownTicks()??0))}expirePassiveScanCooldown(){this.passiveScanCooldownTicks=0}increasePassiveScanCooldown(e){this.passiveScanCooldownTicks+=e}cancelOpportunityFire(){this.opportunityFireTask?.cancel()}selectDefaultWeapon(e){let i;if((e.isInfantry()||e.isVehicle())&&e.rules.deployFire){let t=e.armedTrait?.getDeployFireWeapon();i=e.deployerTrait?.isDeployed()?t&&!t.rules.areaFire?t:void 0:[e.primaryWeapon,e.secondaryWeapon].find(e=>e!==t)}else i=e.isBuilding()&&e.garrisonTrait?e.garrisonTrait.isOccupied()?e.owner.country.side===Qt.GDI?e.primaryWeapon:e.secondaryWeapon??e.primaryWeapon:void 0:e.isBuilding()&&e.overpoweredTrait?e.overpoweredTrait.getWeapon():e.primaryWeapon;return i}selectWeaponVersus(e,t,i,s=!1,r=!1){var a=t.tile;const n=t instanceof Oo?t.obj:t;t=this.getAvailableWeapons(e,r,n?.isOverlay()||s&&!n);return this.selectWeaponFromList(e,n,a,t,i,s,r,!1)}selectWeaponFromList(e,t,i,s,r,a,n,o){if((!t?.isInfantry()&&!t?.isVehicle()||!t.disguiseTrait||this.canAttackThroughDisguise(e,t,t.disguiseTrait,r,a,n,o))&&(t?.isBuilding()&&t.overpoweredTrait&&t.owner===e.owner&&s.find(e=>e.warhead.rules.electricAssault)&&(s=s.filter(e=>e.warhead.rules.electricAssault)),!(n&&t?.isAircraft()&&t.missileSpawnTrait&&t.zone!==Ss.Air))){var h=t?.isTechno()?t.rules.armor:void 0;for(const l of s)if(l.targeting.canTarget(t,i,r,a,n)&&(void 0===h||this.checkArmor(l.warhead.rules,h,n)))return l}}getAvailableWeapons(e,t,i){let s;var r;return s=(e.isInfantry()||e.isVehicle())&&e.rules.deployFire&&e.armedTrait?(r=e.armedTrait.getDeployFireWeapon(),[e.deployerTrait?.isDeployed()?r.rules.areaFire?void 0:r:r===e.secondaryWeapon?e.primaryWeapon:e.secondaryWeapon]):e.isBuilding()&&e.garrisonTrait?e.garrisonTrait.isOccupied()?[e.owner.country.side===Qt.GDI?e.primaryWeapon:e.secondaryWeapon??e.primaryWeapon]:[]:e.isBuilding()&&e.overpoweredTrait?[e.overpoweredTrait.getWeapon()]:i||t?[e.primaryWeapon,!i&&t&&e.secondaryWeapon?e.secondaryWeapon:void 0]:[e.primaryWeapon,e.secondaryWeapon],s.filter(e=>e&&!e.rules.neverUse)}canAttackThroughDisguise(e,t,i,s,r,a,n){if(!r&&i.hasTerrainDisguise()&&!s.areFriendly(e,t)&&!e.owner.sharedDetectDisguiseTrait?.has(t))return!1;if(a){if(n&&t.moveTrait.isIdle()&&!e.rules.detectDisguise&&!e.owner.sharedDetectDisguiseTrait?.has(t)&&!s.areFriendly(t,e))return!1;i=i.getDisguise();if(i?.owner&&!e.rules.detectDisguise&&!e.owner.sharedDetectDisguiseTrait?.has(t)&&(i.owner===e.owner||s.alliances.areAllied(e.owner,i.owner)))return!1}return!0}checkArmor(e,t,i){var s=e.ivanBomb||e.bombDisarm||e.nukeMaker?1:e.verses.get(t);return void 0===s?(console.warn(`Unhandled ArmorType ${ni[t]} in warhead ${e.name} verses`),!1):!(100*s<=(i?1:0))}createAttackTask(e,t,i,s,r){return new Io(e,e.createTarget(t,i),s,r)}[jr.onTick](a,n){if(!this.isDisabled()){if(this.opportunityFireTask&&(!a.unitOrderTrait.hasTasks()||a.isUnit()&&!a.unitOrderTrait.getTasks()[0].preventOpportunityFire||(a.unitOrderTrait.getTasks()[0]instanceof Io?this.opportunityFireTask=void 0:this.opportunityFireTask.cancel()),this.opportunityFireTask&&(c=[this.opportunityFireTask],this.taskRunner.tick(c,a),c.length||(this.opportunityFireTask=void 0))),!this.opportunityFireTask&&this.retaliateTarget){var o=this.retaliateTarget;this.retaliateTarget=void 0;let e;!a.unitOrderTrait.hasTasks()&&n.isValidTarget(o)&&(e=this.selectWeaponVersus(a,o,n,!1))&&a.unitOrderTrait.addTask(this.createAttackTask(n,o,o.tile,e,{holdGround:a.rules.movementZone===ai.Fly}))}if(!this.opportunityFireTask&&this.shouldPassiveAcquire(a))if(0<this.passiveScanCooldownTicks)this.passiveScanCooldownTicks--;else{this.passiveScanCooldownTicks=a.guardMode?n.rules.general.guardAreaTargetingDelay:n.rules.general.normalTargetingDelay;let e=this.selectDefaultWeapon(a);var h,l,c=a.unitOrderTrait.hasTasks();let t=void 0,i,s;!c&&a.guardMode&&e&&a.owner.isCombatant()&&(t=a.armedTrait?.computeGuardScanRange(e),i=a.guardArea?.tile,s=50);let r=!1;!e||(o=this.scanForTarget(a,e,n,t,i)).target&&({target:h,weapon:l}=o,h=this.createAttackTask(n,h,h.tile,l,{holdGround:c||!a.guardMode,disallowTurning:c,leashTiles:s,passive:!0}),c?this.opportunityFireTask=h:a.unitOrderTrait.addTask(h),r=!0,c||!a.guardMode||a.guardArea||(a.guardArea={tile:a.tile,onBridge:!!a.isUnit()&&a.onBridge}),r&&!c&&a.unitOrderTrait[jr.onTick](a,n)),r||c||!a.secondaryWeapon?.warhead.rules.electricAssault||(e=a.secondaryWeapon,(l=this.scanForTarget(a,e,n,void 0,void 0,!0)).target&&({target:h,weapon:l}=l,l=this.createAttackTask(n,h,h.tile,l,{passive:!0}),a.unitOrderTrait.addTask(l),r=!0)),!r&&!c&&a.guardArea&&a.isUnit()&&a.moveTrait&&!a.moveTrait.isDisabled()&&a.guardArea.tile!==a.tile&&a.unitOrderTrait.addTasks(new _a(n,a.guardArea.tile,a.guardArea.onBridge),new ya(()=>{[Zr.Success,Zr.CloseEnough].includes(a.moveTrait.lastMoveResult)||a.resetGuardModeToIdle(),a.guardArea=void 0}))}}}[ga.onDamage](e,t,i,s){this.isDisabled()||!this.retaliateTarget&&!this.opportunityFireTask&&s&&s.obj&&s.weapon&&this.shouldRetaliate(e,t,i,s.obj,s.weapon.warhead)&&(this.retaliateTarget=s.obj)}[zr.onBeforeTeleport](e,t,i,s){s||(this.attackState=bn.Idle,this.currentTarget=void 0,this.retaliateTarget=void 0,this.opportunityFireTask=void 0)}shouldPassiveAcquire(e){if(!e.owner.isCombatant()&&e.rules.needsEngineer||!e.rules.canPassiveAquire||!e.primaryWeapon||e.ammoTrait&&!e.ammoTrait.ammo&&e.rules.manualReload)return!1;if(e.mindControllerTrait?.isAtCapacity())return!1;var t=e.rules.opportunityFire||e.rules.balloonHover&&e.unitOrderTrait.getCurrentTask()?.isAttackMove;if(e.isUnit()&&t){if(e.unitOrderTrait.hasTasks()&&e.unitOrderTrait.getTasks()[0].preventOpportunityFire)return!1}else if(e.unitOrderTrait.hasTasks())return!1;return!0}shouldRetaliate(e,t,i,s,r){if(i<1||t.areFriendly(e,s)||!e.rules.canRetaliate||!e.primaryWeapon||e.ammoTrait&&!e.ammoTrait.ammo&&e.rules.manualReload||r.rules.temporal||s.rules.missileSpawn||e.unitOrderTrait.hasTasks()||!t.isValidTarget(s)||(s.isInfantry()||s.isVehicle())&&s.disguiseTrait&&!e.rules.detectDisguise||e.mindControllerTrait?.isAtCapacity())return!1;t=this.selectWeaponVersus(e,s,t,!1);return!(!t||(e.isBuilding()||s.isBuilding()?this.rangeHelper.tileDistance(e,s):this.rangeHelper.distance2(e,s)/_s.LEPTONS_PER_TILE)>Math.max(t.range,e.sight))}scanForTarget(e,t,i,s,r,a=!1){let n={},o=Number.NEGATIVE_INFINITY;var h=this.getAvailableWeapons(e,!0,!1),t=s??(e.rules.guardRange||t.range)+1+3+i.rules.elevationModel.bonusCap+(t.projectileRules.isAntiAir?e.rules.airRangeBonus:0);for(const u of this.scanTechnosAround(e,t,i)){var l,c=this.selectWeaponFromList(e,u,u.tile,h,i,!1,!0,!0);c&&this.canPassiveAcquire(u,i)&&i.isValidTarget(u)&&(s?this.rangeHelper.isInRange(e,u,c.minRange,s,c.rules.cellRangefinding)&&(!r||this.rangeHelper.isInRange2(r,u,0,s)):this.rangeHelper.isInWeaponRange(e,u,c,i.rules))&&(a||this.losHelper.hasLineOfSight(e,u,c))&&(l=this.rangeHelper.distance3(e,u)/_s.LEPTONS_PER_TILE,(l=this.computeThreat(u,e,c,l,i.rules.general.threat))>o&&(n={target:u,weapon:c},o=l))}return n.target&&e.rules.distributedFire&&this.updateDistributedFireHistory(n),n}scanTechnosAround(e,t,i){var s=e.getFoundation();const r=new Os(e.tile.rx,e.tile.ry),a=new Os(e.tile.rx+s.width-1,e.tile.ry+s.height-1);r.addScalar(-t),a.addScalar(t);t=new Yn(r,a);return i.map.technosByTile.queryRange(t)}canPassiveAcquire(e,t){return!e.owner.isNeutral&&!e.rules.civilian&&!e.rules.insignificant&&(1<e.rules.threatPosed||0<e.rules.specialThreatValue&&!e.isBuilding()||e.rules.harvester||e.name===t.rules.general.paradrop.paradropPlane)}computeThreat(e,t,i,s,r){let a=[e.primaryWeapon,e.secondaryWeapon].filter(Wa).map(e=>e.warhead.rules.verses.get(t.rules.armor)??0).reduce((e,t)=>Math.max(e,t),0)*r.targetEffectivenessCoefficientDefault;return e.attackTrait?.currentTarget?.obj===t&&(a*=-1),a+=e.rules.specialThreatValue*r.targetSpecialThreatCoefficientDefault,a+=(i.warhead.rules.verses.get(e.rules.armor)??0)*r.myEffectivenessCoefficientDefault,a+=e.healthTrait.health/100*r.targetStrengthCoefficientDefault,a+=s*r.targetDistanceCoefficientDefault,a+=1e5,t.rules.vhpScan!==ui.None&&(r=e.healthTrait.getProjectedHitPoints(),t.rules.vhpScan===ui.Strong?r<=0&&(a=Number.NEGATIVE_INFINITY):t.rules.vhpScan===ui.Normal&&(r<=0?a/=2:r<=e.healthTrait.maxHitPoints/2&&(a*=2))),t.rules.distributedFire&&(a-=1e6*(this.distributedFireHistory.get(e)??0)),a}updateDistributedFireHistory(e){if(50!==this.distributedFireHistory.get(e.target)){for(var[t,i]of this.distributedFireHistory)i--,i<=0?this.distributedFireHistory.delete(t):this.distributedFireHistory.set(t,i);this.distributedFireHistory.set(e.target,50)}}dispose(){this.distributedFireHistory.clear()}}class Io extends $s{constructor(e,t,i,s={}){super(),this.game=e,this.target=t,this.weapon=i,this.options=s,this.moveExecuted=!1,this.moveAttempts=0,this.rangeCheckCooldown=0,this.lastInRangeTargetPosition=new as,this.lastInRangeSelfPosition=new as,this.initialIndirectTarget=!1,this.forceDropTarget=!1,this.rangeHelper=new Bs(e.map.tileOccupation),this.losHelper=new vo(e.map.tiles,e.map.tileOccupation),this.targetLinesConfig={pathNodes:[]},this.updateTargetLines(this.target,!0)}duplicate(){return new Io(this.game,this.target,this.weapon,this.options)}getWeapon(){return this.weapon}setWeapon(e){this.weapon=e}setForceAttack(e){this.options.force=e}requestTargetUpdate(e){this.target.equals(e)||(this.needsTargetUpdate=e)}onTargetChange(e){let t=e.attackTrait,i=this.target;t.currentTarget=i,this.lastValidTargetPosition=i.obj?{tile:i.tile,onBridge:i.getBridge()}:void 0,this.initialTargetOwner=i.obj?.isTechno()?i.obj.owner:void 0,this.initialIndirectTarget=!i.obj&&this.game.map.tileOccupation.getObjectsOnTile(i.tile).some(e=>e.isOverlay()&&!e.isBridgePlaceholder()||e.isTerrain()),this.updateTargetLines(i,!0)}updateTargetLines(e,t){this.targetLinesConfig.target=e.obj,this.targetLinesConfig.pathNodes=e.obj?[]:[{tile:e.tile,onBridge:e.getBridge()}],this.targetLinesConfig.isAttack=t}onStart(t){if(!t.attackTrait)throw new Error(`Object ${t.name} has no attack trait`);if(0!==t.ammo){let e=this.game.map.tileOccupation;var i,s;t.attackTrait.attackState=bn.CheckRange,this.onTargetChange(t),this.initialSelfPosition={tile:t.tile,onBridge:t.isUnit()&&t.onBridge?e.getBridgeOnTile(t.tile):void 0},this.weapon.rules.limboLaunch&&t.isUnit()&&!this.target.obj&&(this.forceDropTarget=!0,{reachable:i,fallback:s}=this.findReachableMeleePosition(this.target.tile,!!this.target.getBridge(),{width:1,height:1},t),!i&&s&&(this.lastValidTargetPosition=s,this.updateTargetLines(this.game.createTarget(s.onBridge,s.tile),!1))),this.weapon.rules.limboLaunch&&this.target.obj?.isTechno()&&t.isUnit()&&!this.rangeHelper.isInWeaponRange(t,this.target.obj,this.weapon,this.game.rules)&&({reachable:i,fallback:s}=this.findReachableMeleePosition(this.target.obj.tile,this.target.obj.isUnit()&&this.target.obj.onBridge,this.target.obj.getFoundation(),t),i||(1<(t.unitOrderTrait.waypointPath?.waypoints?.length??0)?this.cancel():(this.forceDropTarget=!0,s&&(this.lastValidTargetPosition=s,this.updateTargetLines(this.game.createTarget(s.onBridge,s.tile),!1))))),this.rangeHelper.isInWeaponRange(t,this.target.obj??this.target.tile,this.weapon,this.game.rules)&&t.isUnit()&&t.rules.movementZone===ai.Fly&&t.zone!==Ss.Air&&(t.rules.hoverAttack||t.isAircraft())&&this.children.push(new _a(this.game,t.tile,!1).setCancellable(!1))}else this.cancel()}findReachableMeleePosition(s,e,t,r){let i=this.game.map,a=i.tileOccupation,n=e?a.getBridgeOnTile(s):void 0,o=new Zs(i),h=r.rules.movementZone===ai.Fly,l=(e,t)=>h||0<i.terrain.getPassableSpeed(e,r.rules.speedType,r.isInfantry(),!!t)&&o.isEligibleTile(e,t,n,s)&&!i.terrain.findObstacles({tile:e,onBridge:t},r).length,c,u=new Ws(i.tiles,i.mapBounds,s,t,1,Math.ceil(this.weapon.rules.range),e=>{let t=!1;var i;return l(e,void 0)&&(c=c??{tile:e,onBridge:void 0},t=!0),void 0!==e.onBridgeLandType&&(i=a.getBridgeOnTile(e),l(e,i)&&(c=c??{tile:e,onBridge:i},t=!0)),!!t&&this.rangeHelper.isInWeaponRange(r,s,this.weapon,this.game.rules,e)});return{reachable:u.getNextTile(),fallback:c}}onEnd(e){e.isVehicle()&&e.turretTrait&&(e.turretTrait.desiredFacing=e.direction),e.attackTrait.attackState=bn.Idle,e.attackTrait.currentTarget=void 0;var t=this.game.rules.general.prism.type;e.isBuilding()&&e.name===t&&this.weapon.type!==li.Secondary&&this.countSupportBeamsAndFireDownTowers(e,t),this.weapon.rules.limboLaunch&&e.attackTrait.expirePassiveScanCooldown(),(e.isInfantry()||e.isVehicle())&&(e.isFiring=!1),this.weapon.hasBurstsLeft()&&this.weapon.resetBursts()}forceCancel(t){if(t.rules.movementZone!==ai.Fly)return!1;if(!this.cancellable||this.children.some(e=>!e.cancellable))return!1;if(this.status===js.Running||this.status===js.Cancelling){if(this.children.filter(e=>e instanceof _a).some(e=>!e.forceCancel(t)))return!1;this.onEnd(t),(t.isInfantry()||t.isVehicle())&&(t.isFiring=!1)}return this.status=js.Cancelled,!0}onTick(s){let t=s.attackTrait;(s.isInfantry()||s.isVehicle())&&t.attackState!==bn.Firing&&(s.isFiring=!1);let r=this.target.obj,a=this.children.find(e=>e instanceof So);if(this.isCancelling()&&t.attackState!==bn.FireUp)return!s.airSpawnTrait?.isLaunchingMissiles()&&(a?.cancel(),!0);let n=!1;if(t.attackState===bn.FireUp){if(t.isDisabled())return!0;t.attackState=bn.Firing,n=!0}if(t.attackState===bn.Firing){if(this.initialIndirectTarget&&!this.game.map.getObjectsOnTile(this.target.tile).find(e=>e.isOverlay()&&!e.isBridgePlaceholder()||e.isTerrain()))return this.cancel(),this.onTick(s);if(n){var o=this.target.obj||this.target.tile;if(!this.game.isValidTarget(this.target.obj)||this.shouldDropTarget(this.target.obj)||!this.weapon.targeting.canTarget(this.target.obj,this.target.tile,this.game,!!this.options.force,!!this.options.passive)||!this.rangeHelper.isInWeaponRange(s,o,this.weapon,this.game.rules)||!this.losHelper.hasLineOfSight(s,o,this.weapon))return t.attackState=bn.CheckRange,this.onTick(s)}if(this.weapon.rules.limboLaunch){if((r?.isVehicle()||r?.isAircraft())&&r.parasiteableTrait?.isInfested())return!0;if(s.rules.movementZone!==ai.Fly&&r?.isUnit()&&r.zone===Ss.Air)return!0}if(this.target.tile.onBridgeLandType&&s.tile.onBridgeLandType&&s.isUnit()&&(this.game.map.tileOccupation.getBridgeOnTile(this.target.tile)?.isHighBridge()||this.game.map.tileOccupation.getBridgeOnTile(s.tile)?.isHighBridge()))if((r?r.isUnit()&&(r.zone===Ss.Air||r.onBridge):this.target.isBridge())!==(s.zone===Ss.Air||s.onBridge))return!0;let e=1;o=this.game.rules.general.prism.type;if(s.isBuilding()&&s.name===o&&this.weapon.type!==li.Secondary&&(o=this.countSupportBeamsAndFireDownTowers(s,o),e=1+o*this.game.rules.general.prism.supportModifier),this.weapon.rules.spawner&&(s.isVehicle()||s.isAircraft())&&s.parasiteableTrait?.isParalyzed())return!0;if(0===s.ammo)return s.isAircraft()&&(s.rules.fighter||s.rules.spawned)&&a?.cancel(),!0;let i=!1;if(this.weapon.rules.limboLaunch){let t=a;if(!t){let e=s.unitOrderTrait.getCurrentTask();if(e&&e!==this){if(!(e instanceof _a))return e.cancel(),!1;t=e}}if(t){if(!t.forceCancel(s))return!1;s.moveTrait.lastTargetOffset=void 0,s.moveTrait.lastVelocity=void 0}i=!0}return(this.weapon.fire(this.target,this.game,e),i)?!0:!!this.weapon.rules.fireOnce||(!(!this.options.passive||!s.rules.distributedFire)||(t.attackState=bn.JustFired,!1))}if(t.attackState===bn.JustFired)return t.attackState=bn.PrepareToFire,this.onTick(s);this.needsTargetUpdate&&(this.target=this.needsTargetUpdate,r=this.target.obj,this.needsTargetUpdate=void 0,this.onTargetChange(s),r||a?.retarget(this.target.tile,!!this.target.getBridge())),r?.isTechno()&&r.replacedBy&&(h=this.game.createTarget(r.replacedBy,r.replacedBy.tile),this.target=h,r=r.replacedBy,this.onTargetChange(s));let i=this.game.isValidTarget(r)&&!this.shouldDropTarget(r);if(i){let e=this.weapon.targeting.canTarget(r,this.target.tile,this.game,!!this.options.force,!!this.options.passive);if(!e||!s.armedTrait.isEquippedWithWeapon(this.weapon)){var h=t.selectWeaponVersus(s,this.target,this.game,this.options.force,this.options.passive);if(h){if(this.setWeapon(h),t.attackState!==bn.CheckRange)return t.attackState=bn.CheckRange,this.onTick(s);e=!0}else e=!1}i=e}if(i&&(l=this.lastTargetTpCheck,r?.isUnit()&&l&&r.moveTrait.lastTeleportTick>=l?(i=!1,this.rangeCheckCooldown=0):this.lastTargetTpCheck=this.game.currentTick),i&&r&&(this.lastValidTargetPosition={tile:r.tile,onBridge:this.target.getBridge()}),i||(this.targetLinesConfig.isAttack=!1),t.attackState===bn.CheckRange){if(0<this.rangeCheckCooldown)return this.rangeCheckCooldown--,!1;let e=this.target.obj?i?this.target.obj:this.lastValidTargetPosition.tile:this.target.tile;var l=this.target.obj?i?this.target.obj.isBuilding()?this.target.obj.centerTile:this.target.obj.tile:this.lastValidTargetPosition.tile:this.target.tile;if(!this.rangeHelper.isInWeaponRange(s,e,this.weapon,this.game.rules)||!this.losHelper.hasLineOfSight(s,e,this.weapon)||s.isUnit()&&s.rules.balloonHover&&!s.rules.hoverAttack&&!a&&s.tile!==l&&!this.options.holdGround||s.isAircraft()&&this.weapon.projectileRules.iniRot<=1&&!a){if(s.isUnit()&&!this.options.holdGround&&this.game.map.isWithinBounds(l)){if(a){if(a.target!==this.target.obj||i)if(i&&this.target.obj&&this.rangeHelper.tileDistance(this.target.obj,this.lastSelfMoveTargetTile)>this.weapon.range)a.retarget(this.target.obj,!!this.target.getBridge()),this.lastSelfTileBeforeMove=s.tile,this.lastSelfMoveTargetTile=this.target.obj?.tile??this.target.tile;else{if(void 0!==this.options.leashTiles&&this.rangeHelper.tileDistance(this.initialSelfPosition.tile,s.tile)>this.options.leashTiles)return a.cancel(),!0;var c=e instanceof Ea&&e.isUnit()?e.moveTrait.baseSpeed:0,u=Math.ceil((this.rangeHelper.tileDistance(s,e)-(this.weapon.range+1))/((s.moveTrait.baseSpeed+c)/_s.LEPTONS_PER_TILE));0<u&&(this.rangeCheckCooldown=Math.min(Us.BASE_TICKS_PER_SECOND,u))}else{let e;e=void 0!==this.options.leashTiles?this.game.createTarget(this.initialSelfPosition.onBridge,this.initialSelfPosition.tile):this.game.createTarget(this.lastValidTargetPosition.onBridge,this.lastValidTargetPosition.tile),t.currentTarget=e,a.retarget(e.tile,e.isBridge()),this.updateTargetLines(e,!1)}return!1}if(!s.moveTrait||s.moveTrait.isDisabled())return!0;if(this.isCancelling())return!0;if(s.tile===this.lastSelfTileBeforeMove||this.moveExecuted&&s.moveTrait.lastMoveResult===Zr.Fail?this.moveAttempts++:this.moveAttempts=0,this.weapon.rules.limboLaunch&&s.defaultToGuardArea&&r&&this.moveExecuted&&s.moveTrait.lastMoveResult===Zr.Fail&&this.rangeHelper.isInRange(s,r,0,s.armedTrait.computeGuardScanRange(this.weapon),!0))return!0;if(3<this.moveAttempts)return!0;0<this.moveAttempts&&this.children.push(new fa(1/60));c=e,u=r&&!i?this.lastValidTargetPosition.onBridge:this.target.getBridge();return a=new So(this.game,c,!!u,this.weapon),a.blocking=!1,this.children.push(a),this.moveExecuted=!0,this.lastSelfTileBeforeMove=s.tile,this.lastSelfMoveTargetTile=c instanceof Ea?c.tile:c,this.onTick(s)}return!0}if(this.moveExecuted=!1,this.moveAttempts=0,a&&(s.rules.balloonHover&&!s.rules.hoverAttack||s.rules.fighter||s.rules.spawned||s.rules.movementZone===ai.Fly&&!this.rangeHelper.isInRange2(s,this.target.obj??this.target.tile,this.weapon.minRange,this.weapon.range-1)||a.cancel()),a&&(s.isInfantry()||this.weapon.rules.spawner))return!1;if(a?.children.some(e=>!e.cancellable)&&this.weapon.rules.limboLaunch)return!1;if(a&&a.shouldAirStrafe(s)&&this.target.obj?.isUnit()&&this.target.obj.moveTrait.isMoving()&&1<this.weapon.range&&!this.rangeHelper.isInRange2(s,this.target.obj,this.weapon.minRange,this.weapon.range-1))return!1;t.attackState=bn.PrepareToFire}if(t.attackState!==bn.PrepareToFire)return!1;if(!i||t.isDisabled())return a?.cancel(),!0;u=this.target.getWorldCoords(),c=s.position.worldPosition;if(!(this.lastInRangeTargetPosition.length()&&this.lastInRangeTargetPosition.equals(u)&&this.lastInRangeSelfPosition.length()&&this.lastInRangeSelfPosition.equals(c)))return this.lastInRangeTargetPosition.copy(u),this.lastInRangeSelfPosition.copy(c),t.attackState=bn.CheckRange,this.onTick(s);if(!(this.weapon.rules.omniFire||s.rules.omniFire&&s.rules.fighter)){var c=(new as).copy(u).sub(c),e=vr.fromMapCoords(new Os(c.x,c.z)),c=this.weapon.projectileRules.rot?45:11.25;if((s.isVehicle()||s.isBuilding())&&s.turretTrait){if(s.turretTrait.desiredFacing=e,Math.abs(e-s.turretTrait.facing)>=c)return!1}else if(Math.abs(e-s.direction)>=c){if(s.isAircraft())return s.direction=vr.tick(s.direction,e,s.rules.rot).facing,!1;if(a)return!1;if(this.options.disallowTurning)return!0;if(s.isVehicle())return this.children.push(new Sr(e)),!1;s.direction=e}}if(!this.losHelper.hasLineOfSight(s,this.target.obj||this.target.tile,this.weapon))return t.attackState=bn.CheckRange,this.onTick(s);if(t.isOnCooldown(s))return!1;if(this.weapon.warhead.rules.temporal&&s.temporalTrait.getTarget()===this.target.obj)return!1;if(this.weapon.rules.suicide&&this.weapon.type!==li.DeathWeapon)return this.game.destroyObject(s,{player:s.owner,obj:s,weapon:this.weapon}),!0;e=this.game.rules.general.prism.type;return s.isBuilding()&&s.name===e&&this.weapon.type!==li.Secondary&&this.fireUpPrismSupportTowers(s,e),(s.isInfantry()||s.isVehicle())&&(s.isFiring=!0),s.art.fireUp?(this.children.push(new Xs(s.art.fireUp).setCancellable(!1)),t.attackState=bn.FireUp,!1):(t.attackState=bn.Firing,this.onTick(s))}shouldDropTarget(e){return this.forceDropTarget||e?.isTechno()&&(this.weapon.rules.limboLaunch&&((e.isVehicle()||e.isAircraft())&&e.parasiteableTrait?.isInfested()||e.invulnerableTrait.isActive())||e.warpedOutTrait.isInvulnerable()&&!this.weapon.warhead.rules.temporal||this.initialTargetOwner!==e.owner)}fireUpPrismSupportTowers(t,i){var e;for(e of t.owner.getOwnedObjectsByType(Et.Building).filter(e=>e.name===i&&e.secondaryWeapon&&!e.unitOrderTrait.hasTasks()&&e.attackTrait&&!e.attackTrait.isDisabled()&&!e.attackTrait.isOnCooldown(e)).filter(e=>this.rangeHelper.isInWeaponRange(e,t,e.secondaryWeapon,this.game.rules)).slice(0,this.game.rules.general.prism.supportMax))e.unitOrderTrait.addTask(e.attackTrait.createAttackTask(this.game,t,t.centerTile,e.secondaryWeapon,{passive:!0}))}countSupportBeamsAndFireDownTowers(t,i){var e,s=t.owner.getOwnedObjectsByType(Et.Building).filter(e=>e.name===i&&e.attackTrait?.currentTarget?.obj===t);for(e of s)e.unitOrderTrait.getCurrentTask()?.cancel();return Math.min(this.game.rules.general.prism.supportMax,s.length)}getTargetLinesConfig(){return this.targetLinesConfig}}class Co extends Io{constructor(e,t,i){if(super(e,t,i),this.isAttackMove=!0,this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.internalTargetUpdateRequested=!1,this.scanCooldownTicks=0,!t.obj?.isTechno())throw new Error("Target must be a techno object");this.initialTarget=t,this.initialWeapon=i,this.requestedTarget=t}duplicate(){return new Co(this.game,this.initialTarget,this.initialWeapon)}requestTargetUpdate(e){this.internalTargetUpdateRequested?(this.requestedTarget=e,this.internalTargetUpdateRequested=!1):(this.requestedTarget===this.initialTarget?this.requestedTarget=e:this.attackPerformed=!0,this.initialTarget=e),super.requestTargetUpdate(e)}onTargetChange(e){super.onTargetChange(e);e=e.attackTrait.currentTarget;e&&e.obj!==this.initialTarget.obj&&e.obj!==this.requestedTarget.obj&&(this.requestedTarget===this.initialTarget&&(this.requestedTarget=e),this.initialTarget=e)}onTick(t){if(t.moveTrait.moveState===Xr.Moving&&(this.passedFirstWaypoint=!0),this.scanCooldownTicks=Math.max(0,this.scanCooldownTicks-1),t.attackTrait&&!t.attackTrait.isDisabled()&&!this.isCancelling()&&(this.requestedTarget===this.initialTarget||this.attackPerformed)){if(!(t.moveTrait.isIdle()||t.tile===this.lastScanTile&&this.scanCooldownTicks)){this.lastScanTile=t.tile,this.scanCooldownTicks=this.game.rules.general.normalTargetingDelay;let e=t.attackTrait.selectDefaultWeapon(t);if(e&&(this.passedFirstWaypoint||!e.getCooldownTicks())){var i=t.attackTrait.scanForTarget(t,e,this.game);if(i.target){let{target:e,weapon:t}=i;if(!t.getCooldownTicks()){this.options.holdGround=!0,this.options.passive=!0,this.setWeapon(t);var s=this.game.createTarget(e,e.tile);return this.internalTargetUpdateRequested=!0,this.requestTargetUpdate(s),this.attackPerformed=!1}}}}if(this.attackPerformed){if(!t.isSpawned){if(!this.forceCancel(t))throw new Error("Force cancel failed");return!0}this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.options.holdGround=!1,this.options.passive=!1,this.setWeapon(this.initialWeapon),this.internalTargetUpdateRequested=!0,this.requestTargetUpdate(this.initialTarget)}}s=super.onTick(t);return s&&this.requestedTarget!==this.initialTarget?(this.attackPerformed=!0,this.isCancelling()||t.attackTrait.isDisabled()):s}}class Ao extends _a{constructor(){super(...arguments),this.isAttackMove=!0,this.attackPerformed=!1,this.passedFirstWaypoint=!1}duplicate(){return new Ao(this.game,this.targetTile,this.toBridge,this.options)}onTick(i){if(i.moveTrait.moveState===Xr.Moving&&(this.passedFirstWaypoint=!0),i.moveTrait.moveState===Xr.ReachedNextWaypoint&&i.attackTrait&&!i.attackTrait.isDisabled()&&(i.rules.movementZone!==ai.Fly||!i.rules.balloonHover)&&(!i.ammoTrait||i.ammoTrait.ammo||!i.rules.manualReload)&&!this.isCancelling()){let e=i.attackTrait.selectDefaultWeapon(i);if(e&&(this.passedFirstWaypoint||e&&!e.getCooldownTicks())){var s=i.attackTrait.scanForTarget(i,e,this.game);if(s.target){let{target:e,weapon:t}=s;if(!t.getCooldownTicks()){s=i.attackTrait.createAttackTask(this.game,e,e.tile,t,{holdGround:!0,passive:!0});return this.children.push(s),this.useChildTargetLines=!0,this.attackPerformed=!0,i.moveTrait.velocity.set(0,0,0),i.moveTrait.currentWaypoint=void 0,i.moveTrait.collisionState=Qr.Waiting,!1}}}if(this.attackPerformed){if(!i.isSpawned){if(!this.forceCancel(i))throw new Error("Force cancel failed");return!0}this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.useChildTargetLines=!1,i.moveTrait.collisionState=Qr.Resolved,this.updateTarget(this.targetTile,this.toBridge)}}return super.onTick(i)}}class Bo extends _a{constructor(e,t,i,s){super(e,i,!1,{ignoredBlockers:[t],closeEnoughTiles:0,strictCloseEnough:!0,forceWaitOnPathBlocked:t.factoryTrait?.type!==ts.InfantryType}),this.factory=t,this.rallyPoint=s,this.preventOpportunityFire=!0,this.rampBlockersPushed=!1,this.cancellable=!1}onStart(t){super.onStart(t),this.factory.factoryTrait?.type===ts.UnitType&&(this.checkRampTiles=this.game.map.tileOccupation.calculateTilesForGameObject(this.factory.tile,this.factory).filter(e=>0<this.game.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)))}canStopAtTile(e,t,i){return!this.game.map.tileOccupation.isTileOccupiedBy(t,this.factory)&&super.canStopAtTile(e,t,i)}onTick(e){if(this.checkRampTiles){for(var t of this.checkRampTiles){var i,s;for(i of this.game.map.tileOccupation.getGroundObjectsOnTile(t))if(i.isUnit()){if(this.rampBlockersPushed)return!1;let e=new Oa(this.game,void 0,{excludedTiles:this.checkRampTiles});e.setCancellable(!1);let t=i.unitOrderTrait.getCurrentTask();t?t.constructor!==_a&&t.constructor!==Io&&t.constructor!==Ao&&t.constructor!==Co||(s=t.duplicate(),t.cancel(),i.unitOrderTrait.addTaskNext(s),i.unitOrderTrait.addTaskNext(e)):i.unitOrderTrait.addTask(e)}}if(!this.rampBlockersPushed)return!(this.rampBlockersPushed=!0);this.checkRampTiles=void 0}return e.moveTrait.moveState===Xr.ReachedNextWaypoint&&this.options?.ignoredBlockers&&!this.game.map.terrain.isBlockerObject(this.factory,e.tile,!1,e.rules.speedType,e.isInfantry())&&(this.options.ignoredBlockers=void 0,this.preventOpportunityFire=!1,this.rallyPoint&&(this.updateTarget(this.rallyPoint.tile,!!this.rallyPoint.onBridge),this.cancellable=!0,this.options.closeEnoughTiles=this.game.rules.general.closeEnough,this.options.strictCloseEnough=!1,this.options.forceWaitOnPathBlocked=!1)),super.onTick(e)}}class xo{constructor(e,t,i,s,r,a=()=>!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=r,this.predicate=a,this.dirVec=new Os(10,0),this.finished=!1,this.diagonal=!0,this.distance=s}getNextTile(){if(!this.finished){let t;do{let e={x:this.startTile.rx,y:this.startTile.ry};e.x+=this.distance*Math.sign(this.dirVec.x),e.y+=this.distance*Math.sign(this.dirVec.y),this.dirVec.rotateAround(new Os,Math.PI/4*(this.diagonal?1:2)).round();var i=this.tiles.getByMapCoords(e.x,e.y);if(i&&this.mapBounds.isWithinBounds(i)&&this.predicate(i)&&(t=i),!this.dirVec.angle()){if(this.maxDistance&&this.distance>=this.maxDistance)return this.finished=!0,t;this.distance++}}while(!t);return t}}}(vn=vn||{}).onSell=Symbol();class Eo{[Jr.onUnspawn](e){this.undock(e),this.reservedDock?.dockTrait.unreserveDockForUnit(e)}[Yr.onChange](e){e.owner!==this.dock?.owner&&this.undock(e),e.owner!==this.reservedDock?.owner&&this.reservedDock?.dockTrait.unreserveDockForUnit(e)}[zr.onBeforeTeleport](e,t,i,s){s||this.undock(e)}undock(e){this.dock&&!this.dock.isDisposed&&this.dock.dockTrait.undockUnit(e)}dispose(){this.dock=void 0,this.reservedDock=void 0}}class Po{constructor(e,t,i,s){this.building=e,this.tiles=t,this.numberOfDocks=i,this.dockingOffsets=s,this.ticksWhenWarpedOut=!0,this.unitsByDockNumber=new Array(i).fill(void 0),this.reservedDocks=new Array(i).fill(void 0)}[Kr.onSpawn](){this.dockTiles=[];for(let e=0;e<this.numberOfDocks;e++){var t=this.findDockTile(e);if(!t)throw new Error(`Docking tile ${e} not found for object "${this.building.name}"`);this.dockTiles[e]=t}}[Jr.onUnspawn](){for(let e=0;e<this.numberOfDocks;e++)this.unreserveDockAt(e)}[jr.onTick](){for(let e=0;e<this.numberOfDocks;e++){var t=this.unitsByDockNumber[e];t&&t.tile!==this.getDockTile(e)&&this.undockUnit(t)}}[Vr.onDestroy](e,t,i,s){var r=(e.rules.unitRepair||e.helipadTrait)&&!e.rules.naval&&!i?.weapon?.warhead.rules.temporal;if(r)for(var a of this.unitsByDockNumber)a&&!a.isDestroyed&&(r?t.destroyObject(a,i,s):this.undockUnit(a))}[vn.onSell](s,r){if(s.helipadTrait&&this.hasDockedUnits()){var a,e,n;let t=[],i=0;for(a of[...s.owner.buildings].filter(e=>e.helipadTrait&&(e.dockTrait?.getAvailableDockCount()??!1)&&e!==s)){let e=a.dockTrait?.getAvailableDockCount()??0;for(;0<e&&i<this.unitsByDockNumber.length;)t.push(a),e--,i++;if(i===this.unitsByDockNumber.length)break}i=0;for(e of this.unitsByDockNumber)e&&((n=t[i])?e.unitOrderTrait.addTask(new wa(r,n)):e.unitOrderTrait.addTask(new za(new _a(r,e.tile,!1),new ya(e=>{e.crashableTrait?e.crashableTrait.crash({player:s.owner}):r.destroyObject(e,{player:s.owner})})).setCancellable(!1))),i++}else{var t,i=s.rules.unitRepair&&!s.rules.naval;for(t of this.unitsByDockNumber)t&&(i?r.sellTrait.sell(t):this.undockUnit(t))}}[Yr.onChange](e,t,i){for(var s of this.unitsByDockNumber)s&&i.changeObjectOwner(s,e.owner)}getFirstAvailableDockNumber(){if(!this.building?.warpedOutTrait.isActive()){var e=this.unitsByDockNumber.findIndex((e,t)=>!e&&!this.reservedDocks[t]);if(-1!==e)return e}}getAvailableDockCount(){return this.building?.warpedOutTrait.isActive()?0:this.unitsByDockNumber.filter((e,t)=>!e&&!this.reservedDocks[t]).length}getFirstEmptyDockNumber(){if(!this.building?.warpedOutTrait.isActive()){var e=this.unitsByDockNumber.findIndex(e=>!e);if(-1!==e)return e}}getDockOffset(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);return this.dockingOffsets[e]}getDockTile(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);return this.dockTiles[e]}getDockNumberByTile(e){e=this.dockTiles.indexOf(e);if(-1!==e)return e}getAllDockTiles(){return[...this.dockTiles]}findDockTile(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);var t=this.building.position.getMapPosition(),e=this.getDockOffset(e);return this.tiles.getByMapCoords(Math.floor((t.x+e.x)/_s.LEPTONS_PER_TILE),Math.floor((t.y+e.z)/_s.LEPTONS_PER_TILE))}isValidUnitForDock(e){return(this.building.unitRepairTrait&&e.isVehicle()&&!this.building.helipadTrait&&(!e.rules.consideredAircraft||e.rules.landable)||e.rules.dock.includes(this.building.name)&&!(e.isAircraft()&&!this.building.helipadTrait))&&this.building.rules.naval===e.rules.naval}dockUnitAt(e,t){if(t>this.numberOfDocks-1)throw new RangeError(`Index ${t} exceeds available docks (${this.numberOfDocks})`);if(this.unitsByDockNumber[t])throw new Error(`Another unit is already docked at dock #${t}`);let i=e.traits.find(Eo);if(!i)throw new Error(`Unit "${e.name}" cannot be docked to ${this.building.name}`);this.unitsByDockNumber[t]=e,i.dock=this.building}undockUnitAt(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);let t=this.unitsByDockNumber[e];t&&(this.unitsByDockNumber[e]=void 0,t.traits.get(Eo).dock=void 0)}undockUnit(e){e=this.unitsByDockNumber.indexOf(e);-1!==e&&this.undockUnitAt(e)}isDocked(e){return this.unitsByDockNumber.includes(e)}hasDockedUnits(){return!!this.unitsByDockNumber.find(e=>e)}getDockedUnits(){return this.unitsByDockNumber.filter(Wa)}reserveDockAt(e,t){if(t>this.numberOfDocks-1)throw new RangeError(`Index ${t} exceeds available docks (${this.numberOfDocks})`);if(this.reservedDocks[t])throw new Error(`Dock #${t} is already reserved by ${this.reservedDocks[t].name}`);(this.reservedDocks[t]=e).traits.get(Eo).reservedDock?.dockTrait.unreserveDockForUnit(e),e.traits.get(Eo).reservedDock=this.building}unreserveDockAt(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);let t=this.reservedDocks[e];t&&(this.reservedDocks[e]=void 0,t.traits.get(Eo).reservedDock=void 0)}unreserveDockForUnit(e){e=this.reservedDocks.indexOf(e);-1!==e&&this.unreserveDockAt(e)}hasReservedDockForUnit(e){return!!this.reservedDocks.includes(e)}hasReservedDockAt(e){return!!this.reservedDocks[e]}getReservedDockForUnit(e){e=this.reservedDocks.indexOf(e);if(-1!==e)return e}dispose(){this.building=void 0}}class No{constructor(e){this.target=e,this.type=rs.FactoryProduceUnit}}(r=Sn=Sn||{})[r.All=0]="All",r[r.Ground=1]="Ground",r[r.Air=2]="Air";class Do{get onChange(){return this._onChange.asEvent()}constructor(e){this.tiles=e,this.tileOccupation=[],this.emptyTiles=new Set,this._onChange=new wo;let t=this.tileOccupation;for(var i of e.getAll())t[i.rx]=t[i.rx]||[],t[i.rx][i.ry]=new Set,this.emptyTiles.add(i)}occupyTileRange(e,t){let i=this.calculateTilesForGameObject(e,t);i.forEach(e=>this.occupyTile(e,t)),this._onChange.dispatch(this,{tiles:i,object:t,type:"added"})}unoccupyTileRange(e,t){let i=this.calculateTilesForGameObject(e,t);i.forEach(e=>this.unoccupyTile(e,t)),this._onChange.dispatch(this,{tiles:i,object:t,type:"removed"})}occupySingleTile(e,t){this.occupyTile(e,t),this._onChange.dispatch(this,{tiles:[e],object:t,type:"added"})}unoccupySingleTile(e,t){this.unoccupyTile(e,t),this._onChange.dispatch(this,{tiles:[e],object:t,type:"removed"})}calculateTilesForGameObject(e,t){return this.tiles.getInRectangle(e,t.getFoundation())}occupyTile(e,t){let i=this.tileOccupation[e.rx]?.[e.ry];i&&(i.add(t),this.emptyTiles.delete(e),e.landType=this.computeTileLandType(e),e.onBridgeLandType=this.computeOnBridgeLandType(e))}unoccupyTile(e,t){let i=this.tileOccupation[e.rx]?.[e.ry];i&&(i.delete(t),i.size||this.emptyTiles.add(e),e.landType=this.computeTileLandType(e),e.onBridgeLandType=this.computeOnBridgeLandType(e))}isTileOccupiedBy(e,t){return!!this.tileOccupation[e.rx]?.[e.ry]?.has(t)}computeTileLandType(e){if(e.landType===ei.Rock)return ei.Rock;var t,i=$i(e.terrainType);for(t of this.tileOccupation[e.rx]?.[e.ry]??[]){if((t.isOverlay()||t.isBuilding())&&t.rules.wall)return ei.Wall;if(t.isOverlay()&&t.isTiberium())return ei.Tiberium;if(t.isOverlay()&&t.rules.land!==ei.Clear&&!t.isBridge()&&!t.isBridgePlaceholder())return t.rules.land}return i}computeOnBridgeLandType(e){for(var t of this.tileOccupation[e.rx]?.[e.ry]??[])if(t.isOverlay()&&t.isBridge())return t.isHighBridge()?ei.Road:t.rules.land}getTileZone(e,t=!1){return Is(t?e.landType:e.onBridgeLandType??e.landType)}getBridgeOnTile(e){for(var t of this.tileOccupation[e.rx]?.[e.ry]??[])if(t.isOverlay()&&t.isBridge())return t}getObjectsOnTile(e){return[...this.tileOccupation[e.rx]?.[e.ry]??[]]}getGroundObjectsOnTile(e){let t=[];for(var i of this.tileOccupation[e.rx]?.[e.ry]??[])i.isTechno()&&!i.isBuilding()&&i.zone===Ss.Air||t.push(i);return t}getAirObjectsOnTile(e){let t=[];for(var i of this.tileOccupation[e.rx]?.[e.ry]??[])i.isUnit()&&i.zone===Ss.Air&&t.push(i);return t}getObjectsOnTileByLayer(e,t){if(t===Sn.Ground)return this.getGroundObjectsOnTile(e);if(t===Sn.Air)return this.getAirObjectsOnTile(e);if(t===Sn.All)return this.getObjectsOnTile(e);throw new Error(`Unhandled layer type "${t}"`)}getEmptyTiles(){return[...this.emptyTiles]}}(kn=kn||{}).onChange=Symbol(),(On=On||{}).onProduce=Symbol(),(r=_n=_n||{})[r.Idle=0]="Idle",r[r.Delivering=1]="Delivering";class Mo{constructor(e,t=!1){this.type=e,this.isCloningVats=t,this.status=_n.Idle}[Kr.onSpawn](e,t){this.resetRallyPoint(e,t)}resetRallyPoint(e,t){var i;[ts.BuildingType,ts.AircraftType].includes(this.type)||(i=this.computeDefaultRallyPoint(e,this.type,t.map),e.rallyTrait?.changeRallyPoint(i,e,t))}[kn.onChange](t,e,i){if(t.owner.production){let e=[];e=this.type===ts.BuildingType?[wn.Structures,wn.Armory]:[t.owner.production.getQueueTypeForFactory(this.type)];for(var s of e)t.owner.production.getQueue(s).notifyUpdated()}}[Yr.onChange](e,t,i){this.status===_n.Delivering&&e.rules.deployTime&&this.deliveringUnit&&!this.deliveringUnit.isDestroyed&&this.unitIsInsideFactory(this.deliveringUnit,e,i)&&i.changeObjectOwner(this.deliveringUnit,e.owner)}[Vr.onDestroy](e,t,i,s){this.status===_n.Delivering&&e.rules.deployTime&&this.deliveringUnit&&!this.deliveringUnit.isDestroyed&&e.deathType!==Hr.Temporal&&this.unitIsInsideFactory(this.deliveringUnit,e,t)&&t.destroyObject(this.deliveringUnit,i,s)}[jr.onTick](i,s){if(this.status===_n.Delivering){if(!this.deliveringUnit||this.deliveringUnit.isDestroyed){if(this.buildingProductionTicks=this.buildingProductionTicks??1,0<this.buildingProductionTicks--)return;this.buildingProductionTicks=void 0}else if(!this.unitHasClearedFactory(this.deliveringUnit,i,s))return;return this.status=_n.Idle,void(this.deliveringUnit=void 0)}if(i.owner.production&&!i.warpedOutTrait.isActive()){let e=i.owner.production.getPrimaryFactory(this.type);if((e?.warpedOutTrait.isActive()||e===i||e?.factoryTrait?.deliveringUnit&&e.factoryTrait.type===ts.UnitType)&&this.type!==ts.BuildingType){let e=i.owner.production.getQueueForFactory(this.type);if(e&&e.status===Tn.Ready){let t=e.getFirst();if(this.type===ts.AircraftType){let e=this.produceAircraftAt(i,t,s);var r;if(!e)for(r of[...i.owner.buildings].filter(e=>e.factoryTrait?.type===ts.AircraftType&&e.helipadTrait)){if(e)break;e=this.produceAircraftAt(r,t,s)}if(!e)return}else{var a;if(this.produceGroundUnitAt(i,t,s),!this.isCloningVats&&this.type===ts.InfantryType)for(a of[...i.owner.buildings].filter(e=>e.factoryTrait&&e.rules.cloning))a.factoryTrait.status===_n.Idle&&a.factoryTrait.produceGroundUnitAt(a,t,s)}i.owner.addUnitsBuilt(t.rules,1),t.creditsSpent=0,t.progress=0,e.shift(t.rules,1),e.currentSize&&(e.status=Tn.Active)}}}}unitIsInsideFactory(e,t,i){return i.map.tileOccupation.isTileOccupiedBy(e.tile,t)&&e.zone!==Ss.Air}unitHasClearedFactory(e,t,i){return!i.map.tileOccupation.isTileOccupiedBy(e.tile,t)||e.rules.consideredAircraft&&e.position.tileElevation>=t.art.height}produceGroundUnitAt(t,e,i){let s=i.createUnitForPlayer(e.rules,t.owner);e.rules.trainable&&t.owner.canProduceVeteran(s.rules)&&s.veteranTrait?.setVeteranLevel(ta.Veteran),s.isInfantry()&&(s.position.subCell=Fa.SUB_CELLS[0]);let r=this.computeInternalRallyPoint(t,this.type,t.rallyTrait.getRallyPoint(),i.map);this.type!==ts.UnitType&&(r=t.rallyTrait.findRallyPointforUnit(s,r,i.map,!1,t.tile.z));let a;a=this.type===ts.NavalUnitType?r:(e=this.computeExitCoords(t,this.type),i.map.tiles.getByMapCoords(Math.floor(e.rx),Math.floor(e.ry))),s.rules.consideredAircraft&&(r=a);let n;if(t.rallyTrait.getRallyPoint()!==r&&(n=t.rallyTrait.findRallyNodeForUnit(s,i.map)),s.isInfantry()){let t=i.map.tileOccupation.getObjectsOnTileByLayer(n?.tile??r,s.rules.consideredAircraft?Sn.Air:Sn.Ground).filter(e=>e.isInfantry()&&e.moveTrait.moveState!==Xr.Moving).map(e=>e.position.subCell);s.position.subCell=Fa.SUB_CELLS.find(e=>!t.includes(e))??Fa.SUB_CELLS[0]}function o(){var e;s.rules.consideredAircraft?(e=n??{tile:r,onBridge:void 0},s.unitOrderTrait.addTaskNext(new _a(i,e.tile,!!e.onBridge,{closeEnoughTiles:i.rules.general.closeEnough}))):s.unitOrderTrait.addTaskNext(new Bo(i,t,r,n))}s.direction=270,i.spawnObject(s,a),i.traits.filter(On).forEach(e=>{e[On.onProduce](s,i)}),i.events.dispatch(new No(s)),t.rules.deployTime?s.unitOrderTrait.addTask(new za(new fa(t.rules.deployTime),new ya(()=>{t.isSpawned&&t.buildStatus!==xn.BuildDown&&o()})).setCancellable(!1)):o(),this.status=_n.Delivering,this.deliveringUnit=s}produceAircraftAt(e,t,i){let s=e.traits.find(Po);if(!s)return!1;var r=s.getFirstAvailableDockNumber();if(void 0===r)return!1;let a=i.createUnitForPlayer(t.rules,e.owner);t.rules.trainable&&e.owner.canProduceVeteran(a.rules)&&a.veteranTrait?.setVeteranLevel(ta.Veteran);t=s.getDockOffset(r);return a.position.moveToLeptons(e.position.getMapPosition()),a.position.moveByLeptons3(t),i.spawnObject(a,a.position.tile),s.dockUnitAt(a,r),a.isAircraft()&&a.airportBoundTrait&&(a.airportBoundTrait.preferredAirport=e),i.traits.filter(On).forEach(e=>{e[On.onProduce](a,i)}),i.events.dispatch(new No(a)),!0}computeExitCoords(e,t){if(t===ts.InfantryType)return this.computeBarracksDefaultExitCoords(e);if(t===ts.UnitType)return this.computeWarFactoryExitCoords(e);throw new Error(`Unsupported factory type ${ts[t]}`)}computeInternalRallyPoint(e,t,i,s){let r,a;if(t===ts.NavalUnitType)a=this.computeNavalInternalRallyPoint(e,i,s);else{if(t===ts.InfantryType)r=this.computeBarracksInternalRallyCoords(e);else{if(t!==ts.UnitType)throw new Error(`Unsupported factory type ${ts[t]}`);r=this.computeWarFactoryInternalRallyCoords(e)}a=s.tiles.getByMapCoords(r.rx,r.ry)}return a??this.findTileAdjacentToBuilding(e,s)}computeDefaultRallyPoint(e,t,i){let s,r;if(t===ts.NavalUnitType)r=this.computeNavalDefaultRallyPoint(e,i);else{if(t===ts.InfantryType)s=this.computeBarracksInternalRallyCoords(e);else{if(t!==ts.UnitType)throw new Error(`Unsupported factory type ${ts[t]}`);s=this.computeWarFactoryDefaultRallyCoords(e)}r=i.tiles.getByMapCoords(s.rx,s.ry)}return r??this.findTileAdjacentToBuilding(e,i)}findTileAdjacentToBuilding(e,t){return new Ws(t.tiles,t.mapBounds,e.tile,e.getFoundation(),1,1,()=>!0).getNextTile()}computeBarracksDefaultExitCoords(e){var t=e.getFoundation();let i,s;return t.width<=2||t.height<=2?(i=t.width-1,s=t.height-1,e.rules.gdiBarracks&&2<t.width&&(i=Math.floor(t.width/2))):(i=0,s=t.height-1),{rx:e.tile.rx+i,ry:e.tile.ry+s}}computeBarracksInternalRallyCoords(e){var t=e.getFoundation();let{rx:i,ry:s}=this.computeBarracksDefaultExitCoords(e);return!(t.width<=2||t.height<=2)||e.rules.gdiBarracks?s+=1:e.rules.nodBarracks&&(i+=t.width<=2?1:0,s+=t.height<=2?1:0),{rx:i,ry:s}}computeWarFactoryExitCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+Math.floor(t.width/2),ry:e.tile.ry+Math.floor(t.height/2)}}computeWarFactoryInternalRallyCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+t.width-1,ry:e.tile.ry+Math.floor(t.height/2)}}computeWarFactoryDefaultRallyCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+t.width,ry:e.tile.ry+Math.floor(t.height/2)}}computeNavalDefaultRallyPoint(e,t){let i=new xo(t.tiles,t.mapBounds,e.centerTile,5,5,e=>e.terrainType===Jt.Water&&!t.getObjectsOnTile(e).find(e=>e.isBuilding()||e.isOverlay()&&e.isBridge()));return i.diagonal=!1,i.getNextTile()??t.tiles.getByMapCoords(e.tile.rx+e.getFoundation().width,e.tile.ry+e.getFoundation().height)}computeNavalInternalRallyPoint(e,t,i){t=new Os(t.rx,t.ry).sub(new Os(e.centerTile.rx,e.centerTile.ry));return i.tiles.getByMapCoords(e.centerTile.rx+Math.sign(t.x)*(Math.floor(e.getFoundation().width/2)+1),e.centerTile.ry+Math.sign(t.y)*(Math.floor(e.getFoundation().height/2)+1))}}(In=In||{}).onStatusChange=Symbol();class Ro{constructor(e,t,i,s,r,a,n,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.foundation=s,this.maxDistance=a,this.predicate=n,this.checkBounds=o,this.distance=r,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){var s=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t))return t};do{var r=this.startTile.rx-this.distance,a=this.startTile.ry-this.distance,n=this.startTile.rx+this.foundation.width-1+this.distance,o=this.startTile.ry+this.foundation.height-1+this.distance;let e,t,i;if(0<this.distance){for(t=1+a;t<o;t++)i=s(r,t),i&&(yield i);for(e=r;e<n;e++)i=s(e,a),i&&(yield i);for(t=o-1;t>=a;t--)i=s(n,t),i&&(yield i);for(e=n;e>=r;e--)i=s(e,o),i&&(yield i)}else this.predicate(this.startTile)&&(yield this.startTile)}while(this.distance++,this.distance<=this.maxDistance)}}class Lo{[In.onStatusChange](t,r,a){if(r.buildStatus===xn.Ready&&t===xn.BuildUp&&!r.owner.isNeutral){let e;if(a.rules.hasObject(r.rules.freeUnit,Et.Vehicle))e=a.rules.getObject(r.rules.freeUnit,Et.Vehicle);else{if(!a.rules.hasObject(r.rules.freeUnit,Et.Infantry))return void console.warn(`Free unit "${r.rules.freeUnit}" is not a vehicle or infantry type.`);e=a.rules.getObject(r.rules.freeUnit,Et.Infantry)}let i=a.createUnitForPlayer(e,r.owner),s;t=new Ro(a.map.tiles,a.map.mapBounds,r.tile,r.getFoundation(),1,1,e=>{var t=0<a.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-r.tile.z)<2&&!a.map.terrain.findObstacles({tile:e,onBridge:void 0},i).length;return!s&&t&&(s=e),t&&!a.map.getObjectsOnTile(e).find(e=>e.isOverlay())}).getNextTile()??s;if(!t)return r.owner.removeOwnedObject(i),i.dispose(),void(r.owner.credits+=i.purchaseValue);a.spawnObject(i,t)}}}class Fo{[vn.onSell](e,t){this.spawnSurvivors(e,t)}[Vr.onDestroy](e,t,i,s){s||i?.obj===e&&i.weapon?.rules.suicide||e.isVehicle()&&e.moveTrait.isMoving()||e.crashableTrait||this.spawnSurvivors(e,t)}spawnSurvivors(s,r){var e=r.rules.general.crew,t=s.owner.country.side;let i,a;if(t===Qt.GDI)i=e.alliedSurvivorDivisor,a=e.alliedCrew;else{if(t!==Qt.Nod)return;i=e.sovietSurvivorDivisor,a=e.sovietCrew}let n=r.sellTrait.computeRefundValue(s)/i;n=0<n&&n<1?1:Math.floor(n),n=s.isVehicle()?Math.min(1,n):Math.min(5,n);let o=[];for(let e=0;e<n;e++)o.push(a);if(0<o.length){s.rules.constructionYard&&(o[o.length-1]=r.rules.general.engineer);var h,l=r.map.tiles.getInRectangle(s.tile,s.getFoundation()).filter(e=>r.map.isWithinBounds(e));let i=[...l];for(h of o){var c=r.rules.getObject(h,Et.Infantry);if(r.map.terrain.getPassableSpeed(s.tile,c.speedType,!0,!s.isBuilding()&&s.onBridge,void 0,!0)){let e=r.createUnitForPlayer(c,s.owner),t=i.length?i.splice(r.generateRandomInt(0,i.length-1),1)[0]:void 0;t=t||l[r.generateRandomInt(0,l.length-1)],e.isInfantry()&&(e.position.subCell=Fa.SUB_CELLS[0]),e.veteranTrait&&s.owner.canProduceVeteran(e.rules)&&e.veteranTrait.setVeteranLevel(ta.Veteran),r.spawnObject(e,t),s.isBuilding()&&e.unitOrderTrait.addTask(new Oa(r,void 0,{ignoredBlockers:s.isDestroyed?void 0:[s]}))}}}}}class jo{constructor(e,t){this.gameObject=e,this.bridges=t,this.checkedClosestBridge=!1}canRepairBridge(){var e=this.findClosestBridgeBounds();return e?this.bridges.canBeRepaired(e):(console.warn(`No bridge associated with hut at ${this.gameObject.tile.rx}, ${this.gameObject.tile.ry}.`),!1)}repairBridge(t,i){var s=this.findClosestBridgeBounds();if(!s)throw new Error("No bridge bounds found");var e=this.bridges.findDestroyedPieceTiles(s),r=s.start.rx!==s.end.rx;let a;a=s.isHigh?$a.calculateHighBridgeOverlayId(s.type,r):$a.calculateLowBridgeOverlayId(s.type,r);var n,o,h=t.rules.getOverlayName(a);for(n of e){let e=t.createObject(Et.Overlay,h);e.overlayId=a,e.value=0,e.position.tileElevation=s.isHigh?4:0,t.spawnObject(e,n),this.updateUnitsUnderBridgePiece(n,s,t,i)}for(o of this.bridges.findBridgePieces(s))o.obj.bridgeTrait.bridgeSpec=s}updateUnitsUnderBridgePiece(e,i,s,r){var a;for(let t of this.bridges.getPieceTiles(this.bridges.getPieceAtTile(e)))if(i.isHigh){let e=s.map.getGroundObjectsOnTile(t).filter(e=>e.tile===t&&e.isUnit()&&!e.unitOrderTrait.hasTasks()&&e.rules.tooBigToFitUnderBridge);e.forEach(e=>e.unitOrderTrait.addTask(new Oa(s)))}else for(a of s.map.getGroundObjectsOnTile(t))a.isUnit()&&(s.map.terrain.getPassableSpeed(t,a.rules.speedType,a.isInfantry(),!0)?(a.zone=Ss.Ground,a.onBridge=!0):a.isDestroyed||s.destroyObject(a,{player:r}))}demolishBridge(e,t){var i=this.getBridgePieces();if(i)for(var s of i)s.obj.isLowBridge()&&e.map.getTileZone(s.obj.tile,!0)!==Ss.Water||s.obj.isDestroyed||(s.obj.deathType=Hr.Demolish,e.destroyObject(s.obj,t,!0))}getBridgePieces(){var e=this.findClosestBridgeBounds();if(e)return this.bridges.findBridgePieces(e)}findClosestBridgeBounds(){return this.checkedClosestBridge||(this.checkedClosestBridge=!0,this.closestBridge=this.bridges.findClosestBridgeSpec(this.gameObject.tile)),this.closestBridge}dispose(){this.gameObject=void 0}}class Uo{constructor(){this.isActive=!1,this.produceCashCooldown=0}[Kr.onSpawn](e){e.owner.isNeutral||(this.isActive=!0)}[Yr.onChange](e,t){t.isNeutral&&!e.owner.isNeutral&&(e.owner.credits=Math.max(0,e.owner.credits+e.rules.produceCashStartup),0<e.rules.produceCashStartup&&(e.owner.creditsGained+=e.rules.produceCashStartup),this.isActive=!0,this.produceCashCooldown=e.rules.produceCashDelay)}[jr.onTick](e){this.isActive&&(this.produceCashCooldown--,this.produceCashCooldown<=0&&(this.produceCashCooldown=e.rules.produceCashDelay,e.owner.credits=Math.max(0,e.owner.credits+e.rules.produceCashAmount),0<e.rules.produceCashAmount&&(e.owner.creditsGained+=e.rules.produceCashAmount)))}}const Wo=[[0,0,0,0],[1,0,0,0],[0,1,0,0],[1,1,0,0],[0,0,1,0],[1,0,1,0],[0,1,1,0],[1,1,1,0],[0,0,0,1],[1,0,0,1],[0,1,0,1],[1,1,0,1],[0,0,1,1],[1,0,1,1],[0,1,1,1],[1,1,1,1]];class zo{constructor(){this.linkedDamageHandled=!1,this.wallType=0}[Kr.onSpawn](e,t){e.isBuilding()?this.connectWall(e,t.map):this.wallType=e.value}[Jr.onUnspawn](e,t){this.updateAdjacentWalls(e,t.map)}[ga.onDamage](e,t,i,s){if(!this.linkedDamageHandled){var r=Math.floor(i/2);if(r)for(var a of t.map.tiles.getAllNeighbourTiles(e.tile))if(a.landType===ei.Wall){let e=t.map.getObjectsOnTile(a).find(e=>(e.isBuilding()||e.isOverlay())&&e.wallTrait);e.wallTrait.linkedDamageHandled=!0,e.healthTrait.inflictDamage(r,s,t),e.wallTrait.linkedDamageHandled=!1,e.healthTrait.health||t.destroyObject(e,s)}}}updateAdjacentWalls(t,e){let i=new xo(e.tiles,e.mapBounds,t.tile,1,1);for(i.diagonal=!1;s=i.getNextTile();){var s=e.getObjectsOnTile(s).find(e=>(e.isBuilding()||e.isOverlay())&&e.name===t.rules.name);s&&this.connectWall(s,e)}}connectWall(e,i){let t=this.getAdjacentWallData(e.tile,e.name,i);this.updateWallType(e,t.map(e=>e.direction)),t.forEach(e=>{let t=this.getAdjacentWallData(e.tile,e.wall.name,i);this.updateWallType(e.wall,t.map(e=>e.direction))})}updateWallType(e,t){let i=[0,0,0,0];for(var s of t)0===s[0]&&-1===s[1]&&(i[0]=1),1===s[0]&&0===s[1]&&(i[1]=1),0===s[0]&&1===s[1]&&(i[2]=1),-1===s[0]&&0===s[1]&&(i[3]=1);t=this.findWallType(i);e.wallTrait.wallType=t,e.isOverlay()&&(e.value=t)}findWallType(t){for(let e=0;e<Wo.length;++e){var i=Wo[e];if(i[0]===t[0]&&i[1]===t[1]&&i[2]===t[2]&&i[3]===t[3])return e}return console.warn("Invalid wall directions",t),0}getAdjacentWallData(e,t,i){var s;let r=[];for(s of[[0,1],[0,-1],[1,0],[-1,0]]){var a={x:e.rx+s[0],y:e.ry+s[1]},n=i.tiles.getByMapCoords(a.x,a.y);n&&((a=i.getObjectsOnTile(n).find(e=>(e.isBuilding()||e.isOverlay())&&e.name===t))&&r.push({direction:s,tile:n,wall:a}))}return r}}class Vo{constructor(e){this.obj=e,this.chargers=new Set}isOverpowered(){let e=1;return this.obj?.poweredTrait?.isPoweredOn(!0)||(e+=2),this.chargers.size>=e}hasChargersToPowerOn(){return 2<=this.chargers.size}chargeFrom(e){this.chargers.add(e),this.swapAttackTaskWeapon()}[jr.onTick](i){if(0<this.chargers.size){let t=!1;this.chargers.forEach(e=>{(e.isDestroyed||e.isCrashing||e.owner!==i.owner||e.attackTrait?.currentTarget?.obj!==i)&&(this.chargers.delete(e),t=!0)}),t&&this.swapAttackTaskWeapon()}}swapAttackTaskWeapon(){let e=this.obj?.unitOrderTrait.getCurrentTask();var t;e instanceof Io&&((t=this.getWeapon())?e.setWeapon(t):e.cancel())}getWeapon(){return this.isOverpowered()?this.obj?.secondaryWeapon:this.obj?.primaryWeapon}dispose(){this.obj=void 0,this.chargers.clear()}}class Ho{constructor(e,t){this.target=e,this.from=t,this.type=rs.UnitRepairFinish}}class Go{constructor(e){this.target=e,this.type=rs.UnitRepairStart}}(r=Cn=Cn||{})[r.Idle=0]="Idle",r[r.Repairing=1]="Repairing";class $o{constructor(){this.status=Cn.Idle,this.cooldownTicks=0,this.lastRepairTickSuccessful=!1}[Kr.onSpawn](e,t){this.resetRallyPoint(e,t)}resetRallyPoint(e,t){var i;e.factoryTrait||(i=this.computeDefaultRallyPoint(e,t.map),e.rallyTrait.changeRallyPoint(i,e,t))}[jr.onTick](t,i){if(t.dockTrait&&(!t.rules.needsEngineer||!t.owner.isNeutral))if(!t.dockTrait.hasDockedUnits()||t.dockTrait.getDockedUnits().some(e=>e.zone===Ss.Air)||t.poweredTrait&&!t.poweredTrait.isPoweredOn())this.status=Cn.Idle;else if(this.cooldownTicks<=0){var s,r,a=i.rules.general.repair,a=t.rules.unitReload?a.reloadRate:a.uRepairRate;this.cooldownTicks+=Us.BASE_TICKS_PER_SECOND*a*60;let e=!1;for(s of t.dockTrait.getDockedUnits())s.zone!==Ss.Air&&(s.healthTrait.health<100&&i.areFriendly(s,t)?(this.tickRepair(s,i,t)&&(e=!0),!e||this.status!==Cn.Idle&&this.lastRepairTickSuccessful||t.helipadTrait||i.events.dispatch(new Go(s))):((r=t.rallyTrait.findRallyNodeForUnit(s,i.map))&&(t.dockTrait.undockUnit(s),s.unitOrderTrait.addTask(new _a(i,r.tile,!!r.onBridge,{closeEnoughTiles:i.rules.general.closeEnough}))),t.helipadTrait||i.events.dispatch(new Ho(s,t))));this.lastRepairTickSuccessful=e,this.status=e?Cn.Repairing:Cn.Idle}else this.cooldownTicks--}tickRepair(e,t,i){var s=t.rules.general.repair,r=Math.floor(s.repairStep),a=s.repairPercent;let n;if(a){s=a*e.purchaseValue/e.healthTrait.maxHitPoints,a=Math.min(i.owner.credits,Math.max(1,Math.floor(s*r)));if(n=s&&a?Math.floor(a/s):r,!a)return!1;i.owner.credits-=a}else n=r;return n=Math.min(n,e.healthTrait.maxHitPoints-e.healthTrait.getHitPoints()),!!n&&(e.healthTrait.healBy(n,i,t),!0)}computeDefaultRallyPoint(e,t){var i=e.getFoundation(),i=new Os(e.tile.rx,e.tile.ry+i.height);return t.tiles.getByMapCoords(i.x,i.y)??e.tile}}class qo{getRallyPoint(){return this.rallyPoint}changeRallyPoint(e,t,i){i=this.findValidRallyPoint(t,e,i.map);i&&(this.rallyPoint=i)}findValidRallyPoint(i,e,s){let t=new Ws(s.tiles,s.mapBounds,e,{width:1,height:1},0,20,e=>i.rules.naval===(e.terrainType===Jt.Water)&&!s.tileOccupation.isTileOccupiedBy(e,i)),r=t.getNextTile();if(!r&&i.factoryTrait?.type===ts.NavalUnitType){var{width:a,height:n}=i.getFoundation();for(let t=0;t<a;t++)for(let e=0;e<n;e++){var o=s.tiles.getByMapCoords(i.tile.rx+t,i.tile.ry+e);if(!o)break;if(0<s.terrain.getPassableSpeed(o,ti.Float,!1,!1)){r=o;break}}}return r}findRallyNodeForUnit(e,t){if(this.rallyPoint){var i=this.findRallyPointforUnit(e,this.rallyPoint,t,!0);return{tile:i,onBridge:e.rules.naval?void 0:t.tileOccupation.getBridgeOnTile(i)}}}findRallyPointforUnit(i,e,s,r,a){let n=i.rules.naval?void 0:s.tileOccupation.getBridgeOnTile(e),o=i.rules.movementZone===ai.Fly,t=new Ws(s.tiles,s.mapBounds,e,{width:1,height:1},0,5,e=>{var t=!n||n.isHighBridge()?s.tileOccupation.getBridgeOnTile(e):void 0;return!(o?[]:s.terrain.findObstacles({tile:e,onBridge:t},i)).length&&(void 0===a||Math.abs(a-(e.z+(t?.tileElevation??0)))<4)&&(!r||!s.getObjectsOnTile(e).find(e=>e.isBuilding()&&!e.isDestroyed))&&(o||0<s.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!!t))});return t.getNextTile()??e}}class Xo{constructor(){this.activeTicks=0}isActive(){return 0<this.activeTicks}setActiveFor(e,t){this.activeTicks=e,this.activeFor=e,this.activeSince=t}reset(){this.activeTicks=0,this.activeSince=void 0,this.activeFor=void 0}getTicksLeft(){return this.activeTicks}getInitialTicks(){return this.activeFor??0}tick(e){return 0<this.activeTicks&&(this.activeTicks--,this.activeTicks<=0||void 0!==this.activeSince&&e-this.activeSince>this.activeFor)&&(this.reset(),!0)}}class Zo{constructor(){this.timer=new Xo}hasCharge(){return this.timer.isActive()}setCharge(e,t){this.hasCharge()||(this.timer.setActiveFor(e),this.attackerInfo=t)}[jr.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.invulnerableTrait.isActive()||(e.isBuilding()&&e.cabHutTrait?e.cabHutTrait.demolishBridge(t,this.attackerInfo):(e.deathType=Hr.Demolish,t.destroyObject(e,this.attackerInfo,!0))))}}class Qo{[Yr.onChange](e,t,i){this.checkAircraftsForPlayer(t,i)}[Jr.onUnspawn](e,t){this.checkAircraftsForPlayer(e.owner,t)}checkAircraftsForPlayer(e,t){let i=t.rules.general.padAircraft;var s;for(s of e.getOwnedObjectsByType(Et.Aircraft).filter(e=>i.includes(e.name)))s.airportBoundTrait&&(s.airportBoundTrait.preferredAirport=void 0)}}class Yo{[jr.onTick](t,i){if(t.dockTrait&&t.dockTrait.hasDockedUnits()&&!t.dockTrait.getDockedUnits().every(e=>!this.canReloadUnit(e)))if(void 0===this.cooldownTicks&&(this.cooldownTicks=Us.BASE_TICKS_PER_SECOND*i.rules.general.repair.reloadRate*60),this.cooldownTicks<=0){this.cooldownTicks=Us.BASE_TICKS_PER_SECOND*i.rules.general.repair.reloadRate*60;let e=t.dockTrait.getDockedUnits();var s;for(s of 0===e[0].ammo?e.slice(0,1):e)this.canReloadUnit(s)&&s.ammoTrait.ammo++}else this.cooldownTicks--}canReloadUnit(e){return!(!e.ammoTrait||!e.rules.manualReload||e.ammoTrait.isFull()||e.zone===Ss.Air)}}class Ko extends za{constructor(e,t){super(new fa(e),new ya(e=>e.setBuildStatus(xn.Ready,t))),this.cancellable=!1}}class Jo{constructor(e){this.name=e}getSuperWeapon(e){return e.owner.superWeaponsTrait?.get(this.name)}[Kr.onSpawn](e,t){this.addSuperWeaponToPlayerIfNeeded(e.owner,t)}[Jr.onUnspawn](e,t){this.removeSuperWeaponFromPlayerIfNeeded(e.owner)}[Yr.onChange](e,t,i){this.removeSuperWeaponFromPlayerIfNeeded(t),this.addSuperWeaponToPlayerIfNeeded(e.owner,i)}addSuperWeaponToPlayerIfNeeded(t,i){if(t.superWeaponsTrait&&!t.superWeaponsTrait.has(this.name)){let e=i.createSuperWeapon(this.name,t);t.superWeaponsTrait.add(e),e.rules.isPowered&&t.powerTrait?.isLowPower()&&e.pauseTimer()}}removeSuperWeaponFromPlayerIfNeeded(e){let t=e.superWeaponsTrait;t&&(e.getOwnedObjectsByType(Et.Building).some(e=>e.superWeaponTrait?.name===this.name)||(e=t.get(this.name))&&!e.isGift&&t.remove(this.name))}}(r=An=An||{})[r.Unexplored=0]="Unexplored",r[r.TemporaryReveal=1]="TemporaryReveal",r[r.Explored=2]="Explored",Bn=Bn||{},Bn[Bn.Darken=8]="Darken";class eh{constructor(){this.invalidations=new Map,this.temporaryReveals=new Map,this.fullInvalidation=!1,this._onChange=new wo}get onChange(){return this._onChange.asEvent()}fromTiles(e){var t,i=e.getMapSize(),s=e.getMaxTileHeight(),s=this.padding=(s+s%2)/2;this.size={width:i.width+s,height:i.height+s},this.tiles=new Uint8Array(this.size.width*this.size.height),this.tiles.fill(An.Unexplored),this.tileElevation=new Uint8Array(this.size.width*this.size.height);for(t of e.getAll()){var r=this.getTileIndex(t);this.tileElevation[r]=Math.max(this.tileElevation[r],t.terrainType===Jt.Cliff&&0<t.z?t.z-1:t.z)}return this}getSize(){return this.size}getTileIndex(e){var{sx:t,sy:e}=this.rxyzToSxy(e.rx,e.ry,e.z);return t+e*this.size.width}rxyzToSxy(e,t,i){i=(i|=0)+i%2;return{sx:e-i/2+this.padding,sy:t-i/2+this.padding}}sxyzToRxy(e,t,i){return{rx:e+Math.ceil(i/2)-this.padding,ry:t+Math.ceil(i/2)-this.padding}}shroudCoordsToWorld({sx:e,sy:t}){return this.sxyzToRxy(e,t,0)}findTilesAtShroudCoords({sx:t,sy:i},s){var e=s.getMaxTileHeight(),r=e+e%2;let a=[];for(let e=0;e<=r;e+=2){var n=e+e%2,{rx:o,ry:n}=this.sxyzToRxy(t,i,n),n=s.getByMapCoords(o,n);n?.z===e&&a.push(n)}return a}clone(){let e=new eh;return e.tiles=this.tiles.slice(),e.size=this.size,e.padding=this.padding,e.tileElevation=this.tileElevation,e}copy(e){this.tiles=e.tiles.slice(),this.size=e.size,this.padding=e.padding,this.tileElevation=e.tileElevation}merge(e){if(this.size.width!==e.size.width||this.size.height!==e.size.height)throw new Error("Size mismatch");var i=e.tiles;for(let e=0,t=this.tiles.length;e<t;e++)this.tiles[e]=Math.max(7&i[e],7&this.tiles[e])|(i[e]|this.tiles[e])>>3<<3}isShrouded(e,t=0){t=this.rxyzToSxy(e.rx,e.ry,e.z+t);return this.getShroudTypeByShroudCoords(t)===An.Unexplored}getShroudType(e){return 7&this.tiles[this.getTileIndex(e)]}isFlagged(e,t){return 0!=(this.tiles[this.getTileIndex(e)]&t)}getShroudTypeByTileCoords(e,t,i){return this.getShroudTypeByShroudCoords(this.rxyzToSxy(e,t,i))}getShroudTypeByShroudCoords({sx:e,sy:t}){return e<0||t<0||e>=this.size.width||t>=this.size.height?An.Unexplored:7&this.tiles[e+t*this.size.width]}invalidateFull(){this.fullInvalidation=!0}invalidate(e,t,i){var s=e.sx+e.sy*this.size.width;let r=this.invalidations.get(s);r||(r={center:e,elevation:0,radius:0},this.invalidations.set(s,r)),r.elevation=Math.max(r.elevation,t),r.radius=Math.max(r.radius,i)}revealFrom(e){var t,i;e.isBuilding()&&e.wallTrait||(t=e.sight)&&(i=e.tile.z+e.tileElevation,e=this.rxyzToSxy(e.tile.rx,e.tile.ry,i),this.invalidate(e,i,t))}revealAround(e,t){e=this.rxyzToSxy(e.rx,e.ry,e.z);this.invalidate(e,Number.POSITIVE_INFINITY,t)}unrevealAround(e,t){var i=[],e=this.rxyzToSxy(e.rx,e.ry,e.z);this.setValueAround(e,t,Number.POSITIVE_INFINITY,i,An.Unexplored,An.Explored),this._onChange.dispatch(this,{type:"incremental",coords:i})}revealTemporarily(e){e=this.rxyzToSxy(e.tile.rx,e.tile.ry,e.tile.z+e.tileElevation);this.temporaryReveals.set(e,5*Us.BASE_TICKS_PER_SECOND)}revealObject(e){e=this.rxyzToSxy(e.tile.rx,e.tile.ry,e.tile.z+e.tileElevation);this.invalidate(e,Number.POSITIVE_INFINITY,4.25)}toggleFlagsAround(e,t,i,s){var r=[],e=this.rxyzToSxy(e.rx,e.ry,e.z);this.setValueAround(e,t,Number.POSITIVE_INFINITY,r,void 0,void 0,s?{setFlags:i}:{clearFlags:i}),this._onChange.dispatch(this,{type:"incremental",coords:r})}update(){let i=[];if(this.invalidations.size){for(var e of this.invalidations.values())this.setValueAround(e.center,e.radius,e.elevation,i,An.Explored,[An.Unexplored,An.TemporaryReveal]);this.invalidations.clear()}this.temporaryReveals.size&&this.temporaryReveals.forEach((e,t)=>{e<=0?(this.setValueAround(t,3,Number.POSITIVE_INFINITY,i,An.Unexplored,An.TemporaryReveal),this.temporaryReveals.delete(t)):(e===5*Us.BASE_TICKS_PER_SECOND&&this.setValueAround(t,3,Number.POSITIVE_INFINITY,i,An.TemporaryReveal,An.Unexplored),this.temporaryReveals.set(t,e-1))}),this.fullInvalidation?(this.fullInvalidation=!1,this._onChange.dispatch(this,{type:"full"})):i.length&&this._onChange.dispatch(this,{type:"incremental",coords:i})}setValueAround(s,r,a,n,o,h=void 0,{setFlags:l,clearFlags:c}={}){var e=Math.ceil(r),t=z(s.sx-e,0,this.size.width-1),u=z(s.sx+e,0,this.size.width-1),d=z(s.sy-e,0,this.size.height-1),g=z(s.sy+e,0,this.size.height-1),p=this.size.width;for(let i=t;i<=u;i++)for(let t=d;t<=g;t++){var m=i+t*p,f=7&this.tiles[m],y=this.tiles[m]>>3<<3;let e=y;void 0!==l&&(e|=l),void 0!==c&&(e&=~c),void 0!==h&&("number"!=typeof h?!h.includes(f):h!==f)||((i-s.sx)*(i-s.sx)+(t-s.sy)*(t-s.sy)>r*r+1||this.tileElevation[m]>=a+4||(this.tiles[m]=(o??f)|e,f===o&&y===e||n.push({sx:i,sy:t})))}}revealAll(){this.tiles.fill(An.Explored),this._onChange.dispatch(this,{type:"clear"})}reset(){this.tiles.fill(An.Unexplored),this._onChange.dispatch(this,{type:"cover"})}}class th{constructor(e){this.radiusTiles=e,this.refreshTicks=0}[jr.onTick](e,t){0<this.refreshTicks&&this.refreshTicks--,this.refreshTicks<=0&&this.update(e,t)}[Kr.onSpawn](e,t){this.markGapTilesForFriendlies(e,e.owner,t,!0)}[Jr.onUnspawn](e,t){this.markGapTilesForFriendlies(e,e.owner,t,!1),this.update(e,t)}[Yr.onChange](e,t,i){this.markGapTilesForFriendlies(e,t,i,!1),this.markGapTilesForFriendlies(e,e.owner,i,!0),this.update(e,i)}[kn.onChange](e,t,i){this.markGapTilesForFriendlies(e,e.owner,t,!i),i&&this.update(e,t)}markGapTilesForFriendlies(i,e,s,t){let r=[e,...s.alliances.getAllies(e)],a;for(var n of r){let e=s.mapShroudTrait.getPlayerShroud(n);if(e&&(e.toggleFlagsAround(i.tile,this.radiusTiles,Bn.Darken,t),!t)){if(!a){let t=new Bs(s.map.tileOccupation);a=r.map(e=>[...e.buildings]).flat().filter(e=>e.gapGeneratorTrait&&e!==i&&t.tileDistance(e,i)<=e.gapGeneratorTrait.radiusTiles+this.radiusTiles)}for(var o of a)e.toggleFlagsAround(o.tile,o.gapGeneratorTrait.radiusTiles,Bn.Darken,!0)}}}update(t,i){this.refreshTicks=5*Us.BASE_TICKS_PER_SECOND;let s;var r,a,n,o,h=t.owner.buildings.has(t)&&t.poweredTrait?.isPoweredOn();for(r of i.getCombatants())if(r!==t.owner&&!i.alliances.areAllied(t.owner,r)){let e=i.mapShroudTrait.getPlayerShroud(r);if(e)if(h){e.unrevealAround(t.tile,this.radiusTiles),s||(n=this.radiusTiles+hs.MAX_SIGHT,a=new Os(t.tile.rx,t.tile.ry).addScalar(-n),n=new Os(t.tile.rx,t.tile.ry).addScalar(n),s=i.map.technosByTile.queryRange(new Yn(a,n)));for(o of s)o.owner===r||i.alliances.areAllied(o.owner,r)?e.revealFrom(o):o.rules.revealToAll&&e.revealObject(o)}else[...r.buildings].some(e=>e.rules.spySat)&&e.revealAround(t.tile,this.radiusTiles)}}}const ih=Us.BASE_TICKS_PER_SECOND;class sh{constructor(e){this.radiusTiles=e,this.detectionLines=[],this.nextScan=ih}[jr.onTick](e,t){e.owner.powerTrait?.isLowPower()?this.disable():(0<this.nextScan&&this.nextScan--,this.nextScan<=0&&(this.nextScan=ih,this.detectionLines=this.scan(e,t)))}[kn.onChange](e,t,i){i&&this.disable()}disable(){this.detectionLines.length&&(this.detectionLines=[],this.nextScan=0)}scan(t,i){var e=i.getCombatants().filter(e=>e!==t.owner&&!i.alliances.areAllied(e,t.owner));let s=[],r=new Bs(i.map.tileOccupation);var a,n,o,h=e=>r.distance2(e,t)/_s.LEPTONS_PER_TILE<=this.radiusTiles;for(a of e)for(var l of a.getOwnedObjects())l.attackTrait?.currentTarget?h((n=l.attackTrait.currentTarget).obj??n.tile)&&s.push({source:l,target:n}):l.isUnit()&&l.unitOrderTrait.targetLinesConfig&&((o=l.unitOrderTrait.targetLinesConfig).target?h(o.target)&&(n=i.createTarget(o.target,o.target.tile),s.push({source:l,target:n})):(o=o.pathNodes[0])&&h(o.tile)&&(o=i.createTarget(o.onBridge,o.tile),s.push({source:l,target:o})));return s}}class rh{constructor(){this.healQueue=[]}addToHealQueue(e){return this.healQueue.push(e),this.healQueue.length-1}unitIsFirstInHealQueue(e){return this.healQueue[0]===e}removeFromHealQueue(e){e=this.healQueue.indexOf(e);-1!==e&&this.healQueue.splice(e,1)}startHealing(e){if(this.unit)throw new Error(`Already busy healing unit ${Et[this.unit.type]}#${this.unit.id}}`);this.unit=e,this.healTicks=5*Us.BASE_TICKS_PER_SECOND}[jr.onTick](e,t){var i;this.healQueue=this.healQueue.filter(e=>!e.isDestroyed&&!e.isCrashing),this.unit&&void 0!==this.healTicks&&(0<this.healTicks&&this.healTicks--,this.healTicks<=0&&(this.healTicks=void 0,this.removeFromHealQueue(this.unit),this.unit.healthTrait.healToFull(e,t),e.ammoTrait&&e.ammoTrait.ammo--,this.evacuate(this.unit,e,t),i=this.unit,this.unit=void 0,t.events.dispatch(new Ho(i,e))))}[Vr.onDestroy](e,t,i){this.unit&&(this.unit.deathType=e.deathType,t.destroyObject(this.unit,i,!0),this.unit=void 0)}evacuate(t,i,s){let e;var r={x:i.tile.rx,y:i.tile.ry+i.art.foundation.height},r=s.map.tiles.getByMapCoords(r.x,r.y);r&&s.map.isWithinBounds(r)&&this.canEvacuateTo(r,t,i,s)&&(e=r),e=e||new Ws(s.map.tiles,s.map.mapBounds,i.tile,i.art.foundation,1,1,e=>this.canEvacuateTo(e,t,i,s)).getNextTile(),e?(s.unlimboObject(t,e),t.unitOrderTrait.addTask(new Oa(s))):s.destroyObject(t,{player:t.owner})}canEvacuateTo(e,t,i,s){return 0<s.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)&&Math.abs(e.z-i.tile.z)<2&&!s.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length}}class ah{constructor(){this.timer=new Xo}isActive(){return this.timer.isActive()}activate(e,t){this.isActive()||(this.timer.setActiveFor(e),this.attackerInfo=t)}[jr.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.invulnerableTrait.isActive()||e.isBuilding()&&e.cabHutTrait||t.destroyObject(e,this.attackerInfo,!0,!0))}}(r=xn=xn||{})[r.BuildUp=0]="BuildUp",r[r.Ready=1]="Ready",r[r.BuildDown=2]="BuildDown";class nh extends Pa{get buildStatus(){return this._buildStatus}static factory(e,t,i,s,r,a){let n=new this(e,t,s);return t.canBeOccupied&&(n.garrisonTrait=new lo(n,i.audioVisual.conditionRed,t.maxNumberOccupants),n.traits.add(n.garrisonTrait)),t.canC4&&!t.wall&&(n.c4ChargeTrait=new Zo,n.traits.add(n.c4ChargeTrait)),t.eligibleForDelayKill&&(n.delayedKillTrait=new ah,n.traits.add(n.delayedKillTrait)),t.bridgeRepairHut&&(n.cabHutTrait=new jo(n,a),n.traits.add(n.cabHutTrait)),t.crewed&&(n.crewedTrait=new Fo,n.traits.add(n.crewedTrait)),t.turret&&(n.turretTrait=new co,n.traits.add(n.turretTrait)),t.overpowerable&&(n.overpoweredTrait=new Vo(n),n.traits.add(n.overpoweredTrait)),(t.powered&&0!==t.power||t.needsEngineer)&&(n.poweredTrait=new yo(n),n.traits.add(n.poweredTrait)),(t.factory||t.cloning)&&(n.factoryTrait=new Mo(t.cloning?ts.InfantryType:t.factory,t.cloning),n.traits.add(n.factoryTrait)),t.superWeapon&&(n.superWeaponTrait=new Jo(t.superWeapon),n.traits.add(n.superWeaponTrait)),t.numberOfDocks&&(n.dockTrait=new Po(n,r,t.numberOfDocks,s.dockingOffsets),n.traits.add(n.dockTrait),t.helipad&&(n.helipadTrait=new Qo,n.traits.add(n.helipadTrait)),(t.unitRepair||t.unitReload)&&(n.unitRepairTrait=new $o,n.traits.add(n.unitRepairTrait)),t.unitReload&&(n.unitReloadTrait=new Yo,n.traits.add(n.unitReloadTrait))),t.hospital&&(n.hospitalTrait=new rh,n.traits.add(n.hospitalTrait)),(t.factory||t.cloning||t.numberOfDocks)&&(n.rallyTrait=new qo,n.traits.add(n.rallyTrait)),t.freeUnit&&n.traits.add(new Lo),t.produceCashStartup&&n.traits.add(new Uo),t.wall&&(n.wallTrait=new zo,n.traits.add(n.wallTrait)),t.gapGenerator&&(n.gapGeneratorTrait=new th(t.gapRadiusInCells),n.traits.add(n.gapGeneratorTrait)),t.psychicDetectionRadius&&(n.psychicDetectorTrait=new sh(t.psychicDetectionRadius),n.traits.add(n.psychicDetectorTrait)),n}constructor(e,t,i){super(Et.Building,e,t,i),this.showWeaponRange=!1,this.direction=0,this._buildStatus=xn.BuildUp,this.lastBuildStatus=this.buildStatus}isBuilding(){return!0}getFoundation(){return this.art.foundation}getFoundationCenterOffset(){var e=this.getFoundation();return new Os(e.width/2*_s.LEPTONS_PER_TILE,e.height/2*_s.LEPTONS_PER_TILE)}update(e){this.buildStatus!==xn.BuildUp||this.unitOrderTrait.hasTasks()||this.unitOrderTrait.addTask(new Ko(e.rules.general.buildupTime,e)),this.attackTrait?.setDisabled(this.buildStatus!==xn.Ready||!!this.poweredTrait&&!this.poweredTrait.isPoweredOn()),super.update(e)}setBuildStatus(e,t){this._buildStatus=e;let i=this.lastBuildStatus;this.buildStatus!==i&&(this.lastBuildStatus=this.buildStatus,this.traits.filter(In).forEach(e=>{e[In.onStatusChange](i,this,t)}),t.events.dispatch(new uo(this,this.buildStatus)))}}class oh extends Ea{static factory(e,t,i){return new this(e,t,i)}constructor(e,t,i){super(Et.Terrain,e,t,i),this.radarInvisible=this.rules.radarInvisible}}class hh extends Ea{static factory(e,t,i){let s=new this(e,t,i);return t.wall&&(s.wallTrait=new zo,s.traits.add(s.wallTrait)),s}constructor(e,t,i){super(Et.Overlay,e,t,i),this.radarInvisible=this.rules.radarInvisible}isTiberium(){return Za.getOverlayTibType(this.overlayId)!==ha.NotSpecial}isBridge(){return $a.isBridge(this.overlayId)}isXBridge(){return $a.isXBridge(this.overlayId)}isHighBridge(){return $a.isHighBridge(this.overlayId)}isLowBridge(){return $a.isLowBridge(this.overlayId)}isBridgePlaceholder(){return $a.isBridgePlaceholder(this.overlayId)}getFoundation(){let e={width:1,height:1};return this.isBridge()&&(this.isXBridge()?e.height+=2:e.width+=2),e}}class lh extends Ea{static factory(e,t,i){return new this(e,t,i)}constructor(e,t,i){super(Et.Smudge,e,t,i)}getFoundation(){return{width:this.rules.width,height:this.rules.height}}}class ch extends _a{constructor(e,t,i,s){super(e,i??t,!1,{closeEnoughTiles:i?void 0:0,strictCloseEnough:!i}),this.teleportTile=t,this.teleportCondition=s}onStart(e){if(super.onStart(e),!e.harvesterTrait||e.rules.locomotor!==ri.Chrono)throw new Error(`Vehicle ${e.name} is not a chrono miner`)}onTick(e){return!e.moveTrait.isDisabled()&&(!(this.isCancelling()||e.moveTrait.moveState!==Xr.ReachedNextWaypoint||e.tile===this.teleportTile||!this.tryTeleportToRefinery(e))||!0===super.onTick(e)&&(this.isCancelling()||e.tile===this.teleportTile||this.tryTeleportToRefinery(e),!0))}tryTeleportToRefinery(e){return(!this.teleportCondition||!1!==this.teleportCondition(e,this.teleportTile))&&(!this.game.map.terrain.findObstacles({tile:this.teleportTile,onBridge:void 0},e).length&&(e.moveTrait.teleportUnitToTile(this.teleportTile,void 0,!0,!0,this.game),e.zone===Ss.Air&&(e.zone=Ss.Ground,e.position.tileElevation=0),!0))}}const uh=[[8,5,6],[3,0,2],[7,4,1]];class dh extends $s{constructor(e,t,i=!1){super(),this.game=e,this.initialTarget=t,this.explicitOrder=i,this.forceMoveTried=!1,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.rangeHelper=new Bs(e.map.tileOccupation),this.scanNearRadius=e.rules.ai.tiberiumNearScan,this.scanFarRadius=e.rules.ai.tiberiumFarScan}onStart(e){if(!e.isVehicle()||!e.harvesterTrait)throw new Error(`Unit ${e.name} is not a harvester.`);e.harvesterTrait.status=Nn.MovingToOreSite,e.harvesterTrait.lastGatherExplicit=this.explicitOrder}onEnd(e){e.harvesterTrait.status!==Nn.LookingForOreSite&&(e.harvesterTrait.status=Nn.Idle)}onTick(i){if(this.isCancelling())return!0;let s=i.harvesterTrait;if(s.status===Nn.MovingToOreSite){var e=this.target;if(this.target=this.findClosestReachableOreSite(i,this.target||this.initialTarget?.landType!==ei.Tiberium?s.lastOreSite??i.tile:this.initialTarget,!0),s.lastOreSite=this.target,!this.target){s.status=Nn.LookingForOreSite;let e=this.getRefineryOnTile(i.tile);if(e&&1===i.unitOrderTrait.getTasks().length){let t=i.rules.movementZone===ai.Fly;var r=new Ws(this.game.map.tiles,this.game.map.mapBounds,e.tile,e.getFoundation(),1,5,e=>t||0<this.game.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-i.tile.z)<2&&!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},i).length).getNextTile();r&&i.unitOrderTrait.addTasks(new _a(this.game,r,!1),new ya(()=>{[Zr.Success,Zr.CloseEnough,Zr.Cancel].includes(i.moveTrait.lastMoveResult)||this.children.push(new fa(1/60))}))}return!0}r=this.game.rules.general.closeEnough,e=e&&this.rangeHelper.tileDistance(i.tile,this.target)<=r;if(!(i.tile===this.target||i.tile.landType===ei.Tiberium&&e)){if(i.tile!==this.target&&e&&i.tile.landType!==ei.Tiberium){e=this.findClosestReachableOreSite(i,i.tile,!1,!0);if(e)this.target=e,s.lastOreSite=this.target;else{if(!this.forceMoveTried)return this.forceMoveTried=!0,this.children.push(new _a(this.game,this.target,!1,{closeEnoughTiles:0,strictCloseEnough:!0})),!1;if(this.forceMoveTried=!1,!s.isEmpty())return this.returnOreIfPossible(i),!0;e=this.findClosestReachableOreSite(i,i.tile,!0,!0);if(!e)return s.status=Nn.LookingForOreSite,!0;this.target=e,s.lastOreSite=this.target}}return this.children.push(new _a(this.game,this.target,!1,{closeEnoughTiles:r}),new ya(()=>{[Zr.Success,Zr.CloseEnough,Zr.Cancel].includes(i.moveTrait.lastMoveResult)||this.children.push(new fa(5/60))})),!1}this.target=i.tile,s.lastOreSite=this.target,s.status=Nn.Harvesting,this.forceMoveTried=!1}if(s.status!==Nn.Harvesting)return!1;{if(s.isFull())return this.returnOreIfPossible(i),!0;let e=this.game.map.getObjectsOnTile(i.tile).find(e=>e.isOverlay()&&e.isTiberium());if(!e)return this.findClosestReachableOreSite(i,s.lastOreSite??i.tile,!1)||s.isEmpty()?(s.status=Nn.MovingToOreSite,this.onTick(i)):(this.returnOreIfPossible(i),!0);let t=e.traits.get(Qa);r=t.collectBail();if(t.getBailCount()||this.game.unspawnObject(e),void 0!==r)if(r===la.Ore)s.ore++;else{if(r!==la.Gems)throw new Error(`Unsupported tiberium type ${r}`);s.gems++}return[...i.owner.buildings].some(e=>e.rules.refinery)||this.explicitOrder?(this.children.push(new fa(1/60)),!1):!0}}findClosestReachableOreSite(t,i,e,s=!1){let r=t.rules.movementZone===ai.Fly;var a=t.rules.speedType,n=t.isInfantry();let o=!r&&this.game.map.terrain.getPassableSpeed(t.tile,a,n,t.onBridge)?this.game.map.terrain.getIslandIdMap(a,n):void 0,h=o?.get(t.tile,t.onBridge);var l,n=e=>e.landType===ei.Tiberium&&o?.get(e,!1)===h&&(!s||(r||!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length));if(n(i))return i;let c=1;if(!e){let e=new Ws(this.game.map.tiles,this.game.map.mapBounds,i,{width:1,height:1},c,c,n),t=[];for(;l=e.getNextTile();)t.push(l);if(t.length){let e=t.map(e=>{var t=this.game.map.getObjectsOnTile(e).find(e=>e.isOverlay()&&e.isTiberium());if(!t)throw new Error(`Ore should exist on tile ${e.rx},${e.ry} b/c of landType`);return{tile:e,ore:t}});return e.sort((e,t)=>1e3*(t.ore.value-e.ore.value)+(uh[1+t.tile.ry-i.ry][1+t.tile.rx-i.rx]-uh[1+e.tile.ry-i.ry][1+e.tile.rx-i.rx])),e[0].tile}c=2}e=e?this.scanFarRadius:this.scanNearRadius;let u=new Ws(this.game.map.tiles,this.game.map.mapBounds,i,{width:1,height:1},c,e,n);return u.getNextTile()}getRefineryOnTile(e){return this.game.map.getObjectsOnTile(e).find(e=>e.isBuilding()&&e.rules.refinery)}returnOreIfPossible(e){1===e.unitOrderTrait.getTasks().length&&e.unitOrderTrait.addTask(new gh(this.game))}getTargetLinesConfig(e){return{pathNodes:this.initialTarget?[{tile:this.initialTarget,onBridge:void 0}]:[]}}}class gh extends $s{constructor(e,t,i=!1,s=!1){super(),this.game=e,this.forceTarget=t,this.resetLastOreSite=i,this.explicitOrder=s,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.rangeHelper=new Bs(e.map.tileOccupation)}onStart(e){if(!e.isVehicle()||!e.harvesterTrait)throw new Error(`Unit ${e.name} is not a harvester.`);e.harvesterTrait.status=Nn.MovingToRefinery,this.resetLastOreSite&&(e.harvesterTrait.lastOreSite=void 0)}onEnd(e){this.target?.isSpawned&&(this.target.dockTrait.undockUnit(e),this.target.dockTrait.unreserveDockForUnit(e)),e.harvesterTrait.status!==Nn.LookingForRefinery&&(e.harvesterTrait.status=Nn.Idle)}onTick(s){if(this.isCancelling())return!0;let r=s.harvesterTrait;if(r.status===Nn.LookingForRefinery)return!0;if(r.status===Nn.MovingToRefinery){if(!this.target||!this.isValidTargetRefinery(this.target,s)||s.tile!==this.findRefineryDockingTile(this.target)){var a=this.forceTarget??this.findClosestReachableRefinery(s);if(!a)return r.status=Nn.LookingForRefinery,!0;this.target&&this.target!==a&&this.target.dockTrait.hasReservedDockForUnit(s)&&this.target.dockTrait.unreserveDockForUnit(s),this.target=a}let e=this.target.dockTrait.getFirstAvailableDockNumber(),t=!1;void 0===e&&(e=this.target.dockTrait.getFirstEmptyDockNumber(),void 0!==e&&(t=!this.target.dockTrait.hasReservedDockForUnit(s)));let i=this.findRefineryDockingTile(this.target);var n=this.rangeHelper.tileDistance(s,i);if(void 0===e||t||n>this.game.rules.general.harvesterTooFarDistance&&!this.explicitOrder){var o=this.findReachableQueueingTile(s);return o?(s.tile!==o&&this.children.push(s.rules.teleporter?new ch(this.game,i,o,()=>this.chronoMinerCanTeleport(s,i,this.target)):new _a(this.game,o,!1),new ya(()=>{s.moveTrait.lastMoveResult===Zr.Fail?r.status=Nn.LookingForRefinery:s.moveTrait.lastMoveResult===Zr.CloseEnough?this.children.push(new fa(5/60)):s.moveTrait.lastMoveResult===Zr.Success&&this.children.push(new fa(2/60))})),!1):!0}if(this.target.dockTrait.hasReservedDockForUnit(s)||this.target.dockTrait.reserveDockAt(s,e),void 0===this.reservedDockNumber&&(this.reservedDockNumber=this.target.dockTrait.getReservedDockForUnit(s)),s.tile!==i)return this.children.push(s.rules.teleporter?new ch(this.game,i,void 0,()=>this.chronoMinerCanTeleport(s,i,this.target)):new _a(this.game,i,!1,{closeEnoughTiles:0,strictCloseEnough:!0}),new ya(()=>{s.moveTrait.lastMoveResult===Zr.Fail&&(r.status=Nn.LookingForRefinery)})),!1;r.status=Nn.Docking}if(!this.isValidTargetRefinery(this.target,s))return r.status=Nn.MovingToRefinery,this.forceTarget=void 0,this.onTick(s);if(r.status===Nn.Docking){if(270!==s.direction)return this.children.push(new Sr(270)),!1;this.target.dockTrait.dockUnitAt(s,this.reservedDockNumber),this.reservedDockNumber=void 0,r.status=Nn.PreparingToUnload}if(r.status===Nn.PreparingToUnload)return this.preventOpportunityFire=!0,this.children.push(new fa(2/60)),r.status=Nn.Unloading,!1;if(r.status!==Nn.Unloading)return!1;var e=r.ore*this.game.rules.getTiberium(la.Ore).value+r.gems*this.game.rules.getTiberium(la.Gems).value,a=e,n=[...this.target.owner.buildings].filter(e=>e.rules.orePurifier&&(!e.poweredTrait||!this.target.owner.powerTrait?.isLowPower())).length,o=this.game.rules.general.purifierBonus;return a+=n*Math.floor(e*o),this.target.owner.credits+=a,this.target.owner.creditsGained+=a,r.ore=0,r.gems=0,1===s.unitOrderTrait.getTasks().length&&s.unitOrderTrait.addTask(new dh(this.game)),!0}isValidTargetRefinery(e,t){return e.isSpawned&&this.game.areFriendly(e,t)&&!e.warpedOutTrait.isActive()}findClosestReachableRefinery(i){let s=this.rangeHelper;var e=i.zone===Ss.Air,t=i.rules.speedType,r=i.isInfantry();let a=!e&&this.game.map.terrain.getPassableSpeed(i.tile,t,r,i.onBridge)?this.game.map.terrain.getIslandIdMap(t,r):void 0,n=[...i.owner.buildings].filter(e=>e.rules.refinery&&e.dockTrait&&!e.warpedOutTrait.isActive()&&(e=>i.rules.teleporter||a?.get(e,!1)===a?.get(i.tile,i.onBridge))(this.findRefineryDockingTile(e))).sort((e,t)=>s.distance2(i,e)-s.distance2(i,t));t=n[0],r=n.find(e=>0<e.dockTrait.getAvailableDockCount());return!r||t&&s.tileDistance(i,r.centerTile)-s.tileDistance(i,t.centerTile)>this.game.rules.general.harvesterTooFarDistance?t:r}findReachableQueueingTile(t){if(this.target.art.queueingCell){var e=new Os(this.target.tile.rx,this.target.tile.ry).add(this.target.art.queueingCell),e=this.game.map.tiles.getByMapCoords(e.x,e.y);if(e&&this.isValidQueueingTile(e,t))return e}return new Ws(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>this.isValidQueueingTile(e,t)).getNextTile()}isValidQueueingTile(e,t){var i=t.zone===Ss.Air,s=t.rules.speedType,r=t.isInfantry();let a=!i&&this.game.map.terrain.getPassableSpeed(t.tile,s,r,t.onBridge)?this.game.map.terrain.getIslandIdMap(s,r):void 0;return i||a?.get(e,!1)===a?.get(t.tile,t.onBridge)&&Math.abs(e.z-this.target.tile.z)<2&&!e.onBridgeLandType}findRefineryDockingTile(e){e={x:e.tile.rx+e.getFoundation().width-1,y:e.tile.ry+Math.floor(e.getFoundation().height/2)};return this.game.map.tiles.getByMapCoords(e.x,e.y)}chronoMinerCanTeleport(e,t,i){let s=this.rangeHelper;t=s.tileDistance(e,t);return!(!this.forceTarget&&t>this.game.rules.general.chronoHarvTooFarDistance)&&(!(t<=1)&&(!!this.isValidTargetRefinery(i,e)&&!(0===i.dockTrait.getAvailableDockCount()&&!i.dockTrait.hasReservedDockForUnit(e))))}}(En=En||{}).onPush=Symbol(),(r=Pn=Pn||{})[r.Move=0]="Move",r[r.ForceMove=1]="ForceMove",r[r.Attack=2]="Attack",r[r.ForceAttack=3]="ForceAttack",r[r.AttackMove=4]="AttackMove",r[r.Guard=5]="Guard",r[r.GuardArea=6]="GuardArea",r[r.Capture=7]="Capture",r[r.Occupy=8]="Occupy",r[r.Deploy=9]="Deploy",r[r.DeploySelected=10]="DeploySelected",r[r.Stop=11]="Stop",r[r.Cheer=12]="Cheer",r[r.Dock=13]="Dock",r[r.Gather=14]="Gather",r[r.Repair=15]="Repair",r[r.Scatter=16]="Scatter",r[r.EnterTransport=17]="EnterTransport",r[r.PlaceBomb=18]="PlaceBomb",(r=Nn=Nn||{})[r.Idle=0]="Idle",r[r.LookingForOreSite=1]="LookingForOreSite",r[r.MovingToOreSite=2]="MovingToOreSite",r[r.Harvesting=3]="Harvesting",r[r.LookingForRefinery=4]="LookingForRefinery",r[r.MovingToRefinery=5]="MovingToRefinery",r[r.Docking=6]="Docking",r[r.PreparingToUnload=7]="PreparingToUnload",r[r.Unloading=8]="Unloading";class ph{constructor(e){this.storage=e,this.ore=0,this.gems=0,this.status=Nn.Idle,this.lastGatherExplicit=!1,this.autoGatherOnNextIdle=!1,this.ticksSinceLastRefineryCheck=0,this.ticksSinceLastOreCheck=0}[Kr.onSpawn](e,t){e.owner.isCombatant()&&(t.afterTick(()=>{e.unitOrderTrait.addTask(new dh(t))}),e.attackTrait?.increasePassiveScanCooldown(1))}[Yr.onChange](e,t,i){(!t.isCombatant()&&e.owner.isCombatant()||i.alliances.areAllied(e.owner,t))&&i.afterTick(()=>{e.unitOrderTrait.addTask(new dh(i))})}[jr.onTick](e,t){this.status===Nn.LookingForRefinery?this.ticksSinceLastRefineryCheck++>5*Us.BASE_TICKS_PER_SECOND&&(this.ticksSinceLastRefineryCheck=0,e.unitOrderTrait.hasTasks()?this.ticksSinceLastRefineryCheck=-25*Us.BASE_TICKS_PER_SECOND:[...e.owner.buildings].some(e=>e.rules.refinery)||this.lastGatherExplicit?e.unitOrderTrait.addTask(new gh(t)):this.status=Nn.Idle):this.status===Nn.LookingForOreSite?this.ticksSinceLastOreCheck++>20*Us.BASE_TICKS_PER_SECOND&&(this.ticksSinceLastOreCheck=0,e.unitOrderTrait.hasTasks()||e.unitOrderTrait.addTask(new dh(t))):this.status===Nn.Idle&&this.autoGatherOnNextIdle&&e.unitOrderTrait.isIdle()&&e.tile.landType===ei.Tiberium&&(this.autoGatherOnNextIdle=!1,e.unitOrderTrait.addTask(new dh(t,e.tile,!0)))}[zr.onBeforeTeleport](e,t,i,s){!s&&e.owner.isCombatant()&&(this.status=Nn.Idle,this.lastOreSite=void 0,i&&e.rules.teleporter&&t.afterTick(()=>{e.unitOrderTrait.addTask(new(this.isFull()?gh:dh)(t))}))}[En.onPush](e,t){this.autoGatherOnNextIdle=[Pn.AttackMove,Pn.Move,Pn.ForceMove,Pn.Scatter].includes(t),[Nn.LookingForRefinery,Nn.LookingForOreSite].includes(this.status)&&(this.status=Nn.Idle)}isFull(){return this.ore+this.gems>=this.storage}isEmpty(){return!this.ore&&!this.gems}getHash(){return 100*this.ore+this.gems}debugGetState(){return{ore:this.ore,gems:this.gems}}}class mh{constructor(e){this.target=e,this.type=rs.LeaveTransport}}class fh{constructor(e){this.obj=e,this.units=[],this.loadQueue=[]}unitFitsInside(e){return e.rules.size<=this.obj.rules.sizeLimit&&e.rules.size<=this.getAvailableCapacity()}getOccupiedCapacity(){return this.units.reduce((e,t)=>e+t.rules.size,0)}getMaxCapacity(){return this.obj.rules.passengers}getAvailableCapacity(){return this.getMaxCapacity()-this.getOccupiedCapacity()}addToLoadQueue(e){return this.loadQueue.push(e),this.loadQueue.length-1}unitIsFirstInLoadQueue(e){return this.loadQueue[0]===e}removeFromLoadQueue(e){e=this.loadQueue.indexOf(e);-1!==e&&this.loadQueue.splice(e,1)}[jr.onTick](e,t){this.loadQueue=this.loadQueue.filter(e=>!e.isDestroyed&&!e.isCrashing)}[Vr.onDestroy](e,t,i,s){var r=!!e.armedTrait?.deathWeapon,a=i?.weapon?.warhead.rules.parasite;if(s||r||e.zone===Ss.Air||a)for(var n of this.units)r&&n.armedTrait&&(n.armedTrait.deathWeapon=void 0),n.position.tileElevation=e.position.tileElevation,n.zone=e.zone,n.onBridge=e.onBridge,n.position.tile=e.tile,n.deathType=e.deathType,t.destroyObject(n,i,!0);else this.spawnSurvivors(t);this.units=[]}spawnSurvivors(e){var t=this.obj;if(this.units.length){for(var i of this.units)0<e.map.terrain.getPassableSpeed(t.tile,i.rules.speedType,i.isInfantry(),t.onBridge)?(i.owner.addOwnedObject(i),i.position.tileElevation=t.onBridge?e.map.tileOccupation.getBridgeOnTile(t.tile).tileElevation:0,i.onBridge=t.onBridge,i.zone=e.map.getTileZone(t.tile,!t.onBridge),e.unlimboObject(i,t.tile),i.unitOrderTrait.addTask(new Oa(e))):(i.position.tileElevation=t.position.tileElevation,i.zone=t.zone,i.onBridge=t.onBridge,i.position.tile=t.tile,i.zone===Ss.Water&&(i.deathType=Hr.Sink),i.armedTrait?.deathWeapon&&(i.armedTrait.deathWeapon=void 0),e.destroyObject(i,{player:i.owner}));e.events.dispatch(new mh(t))}}getHash(){return G(this.units.map(e=>e.getHash()))}debugGetState(){return this.units.map(e=>e.debugGetState())}dispose(){this.obj=void 0}}class yh{[jr.onTick](e){var t,i;!!e.transportTrait.units.length!==this.lastHadGunner&&(this.lastHadGunner=!!e.transportTrait.units.length,i=t=e.transportTrait.units[0]?.rules.ifvMode??0,(t=e.rules.turretIndexesByIfvMode.get(t)??0)<e.rules.turretCount&&(e.turretNo=t,e.armedTrait?.selectSpecialWeapon(i,e.veteranLevel===ta.Elite)))}getUiNameForIfvMode(e,t){switch(e){case 0:return"tip:rocket";case 1:return"tip:repair";case 2:case 4:case 5:return"tip:machinegun";default:return t?"name:"+t.toLowerCase():void 0}}}(Dn=Dn||{}).onHeal=Symbol();class wh{constructor(e){this.gameObject=e,this.beingBoarded=!1}infest(e,t){this.beingBoarded=!1,this.parasite=e,this.parasiteWeapon=t,e.rules.organic?this.damageTickCooldown=kh+2:this.damageTickCooldown=0,this.lastExternalDamageInflicted=void 0,this.lastExternalDamageTick=void 0,t.warhead.rules.paralyzes&&this.gameObject.moveTrait.setDisabled(!0)}isInfested(){return!(!this.parasite||this.parasite.isDestroyed)||this.beingBoarded}isParalyzed(){return!!this.parasiteWeapon?.warhead.rules.paralyzes}uninfest(){this.parasite&&(this.parasiteWeapon.warhead.rules.paralyzes&&this.gameObject.moveTrait.setDisabled(!1),this.parasite=void 0,this.parasiteWeapon=void 0)}getParasite(){return this.parasite}[jr.onTick](s,r){if(this.parasite)if(this.parasite.isDestroyed)this.uninfest();else if(0<this.damageTickCooldown)this.damageTickCooldown--;else{let e=this.parasiteWeapon;this.damageTickCooldown=this.parasite.rules.organic?kh+2:e.getCooldownTicks();let t=e.rules.damage;this.parasite.veteranTrait&&(t*=this.parasite.veteranTrait.getVeteranDamageMultiplier());let i=e.warhead.computeDamage(t,s,r);this.canBeCulled(s,this.parasite,e,r)&&(i=s.healthTrait.getHitPoints()),e.warhead.inflictDamage(i,s,{player:this.parasite.owner,obj:this.parasite,weapon:e},r),s.isCrashing?(this.parasiteWeapon.expireCooldown(),this.evictOrDestroyParasite(s,r)):!s.isDestroyed&&s.isVehicle()&&s.zone!==Ss.Air&&e.warhead.rules.rocker&&s.applyRocking(90*(.5<=r.generateRandom()?1:-1),1)}}canBeCulled(e,t,i,s){if(!i.warhead.rules.culling)return!1;s=s.rules.audioVisual,s=t.veteranTrait?.isElite()?s.conditionYellow:s.conditionRed;return e.healthTrait.health<=100*s}[Dn.onHeal](e,t,i,s){var r;!this.parasite||this.parasite.isDestroyed||s===e||e.isAircraft()&&s?.rules.unitReload||(this.parasite.rules.organic?(r=this.parasite,this.evictOrDestroyParasite(e,t),this.stunParasite(r,t)):(this.parasite.deathType=Hr.None,t.destroyObject(this.parasite,s?{player:s.owner,obj:s}:void 0),this.uninfest()))}[ga.onDamage](e,t,i,s){s?.obj!==this.parasite&&(this.lastExternalDamageInflicted=i,this.lastExternalDamageTick=t.currentTick)}[ea.onAttack](i,s,r){if(this.parasite&&!this.parasite.isDestroyed&&s?.weapon?.warhead.rules.sonic){var a=this.parasite;this.evictOrDestroyParasite(i,r),this.stunParasite(a,r);let e=s.weapon.warhead;e.canDamage(a,a.tile,a.zone)&&(i=e.computeDamage(s.weapon.rules.damage,a,r),e.inflictDamage(i,a,s,r));let t=s.obj?.unitOrderTrait.getCurrentTask();t instanceof Io&&t.getWeapon().warhead.rules.sonic&&t.cancel()}}[Vr.onDestroy](e,t,i,s){this.parasite&&!this.parasite.isDestroyed&&(s||!this.parasite.invulnerableTrait.isActive()&&this.shouldSupressParasite(t,this.parasite,i)?(this.parasite.deathType=Hr.None,t.destroyObject(this.parasite,i,s),this.uninfest()):(this.parasiteWeapon.expireCooldown(),this.evictOrDestroyParasite(e,t)))}shouldSupressParasite(e,t,i){return i?.obj!==t||this.lastExternalDamageInflicted&&this.lastExternalDamageInflicted>t.rules.suppressionThreshold&&e.currentTick-this.lastExternalDamageTick<2*this.lastExternalDamageInflicted}[zr.onBeforeTeleport](e,t,i,s){i&&s&&this.parasite&&!this.parasite.isDestroyed&&(this.parasiteWeapon.expireCooldown(),s=this.parasite,this.evictOrDestroyParasite(e,t,!0),s.isDestroyed||this.stunParasite(s,t))}stunParasite(e,t){e.unitOrderTrait.addTaskToFront(new fa(10/60).setCancellable(!1)),e.isVehicle()&&e.submergibleTrait&&(e.submergibleTrait.emerge(e,t),e.cloakableTrait?.uncloak(t),e.submergibleTrait.setCooldown(10*Us.BASE_TICKS_PER_SECOND))}evictOrDestroyParasite(s,r,a=!1){if(this.parasite&&!this.parasite.isDestroyed){if(r.map.terrain.getPassableSpeed(s.tile,this.parasite.rules.speedType,this.parasite.isInfantry(),s.onBridge)||r.map.getObjectsOnTile(s.tile).find(e=>e.isBuilding())){let t=s.tile,i=s.onBridge;if(!a&&!s.isDestroyed||this.parasite.rules.organic){let e=new Ws(r.map.tiles,r.map.mapBounds,t,{width:1,height:1},1,1,e=>0<r.map.terrain.getPassableSpeed(e,this.parasite.rules.speedType,this.parasite.isInfantry(),i)&&!r.map.terrain.findObstacles({tile:e,onBridge:i},this.parasite).length);a=e.getNextTile();if(!a)return this.parasite.deathType=Hr.None,r.destroyObject(this.parasite,{player:s.owner,obj:s}),void this.uninfest();t=a}this.parasite.onBridge=i,this.parasite.position.subCell=this.parasite.isInfantry()?s.position.subCell:0,this.parasite.zone=r.map.getTileZone(t,!i),this.parasite.position.tileElevation=i?r.map.tileOccupation.getBridgeOnTile(t).tileElevation:0,this.parasite.resetGuardModeToIdle(),r.unlimboObject(this.parasite,t,!0)}else this.parasite.deathType=Hr.None,r.destroyObject(this.parasite,{player:s.owner,obj:s});this.uninfest()}}destroyParasite(e,t){this.parasite&&(this.parasite.deathType=Hr.None,t.destroyObject(this.parasite,e),this.uninfest())}dispose(){this.gameObject=void 0}}class Th{constructor(e){this.target=e,this.type=rs.ShipSubmergeChange}}class bh{constructor(){this.isActive=!1}isSubmerged(){return this.isActive}setCooldown(e){this.cooldownTicks=e}[jr.onTick](e,t){this.isActive||e.parasiteableTrait?.isInfested()||(e.attackTrait&&e.attackTrait.attackState!==bn.Idle&&!e.moveTrait.isMoving()?this.cooldownTicks=Math.max(this.cooldownTicks??0,5*Us.BASE_TICKS_PER_SECOND):this.cooldownTicks??(this.cooldownTicks=Math.floor(60*t.rules.general.cloakDelay*Us.BASE_TICKS_PER_SECOND)),0<this.cooldownTicks&&this.cooldownTicks--,this.cooldownTicks<=0&&(this.isActive=!0,t.events.dispatch(new Th(e))))}[ga.onDamage](e,t){this.emerge(e,t)}emerge(e,t){this.isActive&&(this.isActive=!1,this.cooldownTicks=void 0,t.events.dispatch(new Th(e)))}}class vh{constructor(){this.prevHoverBobLeptons=0,this.spawnTick=0}[Kr.onSpawn](e,t){this.setBaseElevation(e,t),this.spawnTick=t.currentTick}[$r.onTileChange](e,t,i,s){s&&(this.prevHoverBobLeptons=0,this.setBaseElevation(e,t))}setBaseElevation(e,t){e.position.tileElevation=(e.onBridge?t.map.tileOccupation.getBridgeOnTile(e.tile)?.tileElevation??0:0)+_s.worldToTileHeight(t.rules.general.hover.height)}[jr.onTick](e,t){var i=this.computeHoverBobLeptons(t.currentTick,t.rules.general.hover),t=i-this.prevHoverBobLeptons;this.prevHoverBobLeptons=i;i=_s.tileHeightToWorld(e.position.tileElevation);e.position.tileElevation=_s.worldToTileHeight(i+t)}computeHoverBobLeptons(e,t){e=(e-this.spawnTick)/Us.BASE_TICKS_PER_SECOND/(60*t.bob);return.1*t.height*Ki.sin(2*e*Math.PI)}}class Sh{constructor(){this.tilt={pitch:0,yaw:0}}[Kr.onSpawn](e){this.tilt=this.computeTilt(e.tile.rampType)}[$r.onTileChange](e){this.tilt=this.computeTilt(e.tile.rampType)}computeTilt(e){let t,i;return 0===e||17<=e?t=i=0:i=e<=4?(t=25,-90*e):(t=25,225-(e-1)%4*90),{pitch:t,yaw:i}}}const kh=34;class Oh extends Pa{get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,s,r){let a=new this(e,t,i);return a.isSinker=!t.underwater&&(t.weight>=s.general.shipSinkingWeight||!t.naval),a.moveTrait=new Aa(a,r),a.traits.add(a.moveTrait),t.crashable&&(a.crashableTrait=new Ma(a),a.traits.add(a.crashableTrait)),t.crewed&&(a.crewedTrait=new Fo,a.traits.add(a.crewedTrait)),t.harvester&&(a.harvesterTrait=new ph(t.storage),a.traits.add(a.harvesterTrait)),t.passengers&&(a.transportTrait=new fh(a),a.traits.add(a.transportTrait),t.gunner&&(a.gunnerTrait=new yh,a.traits.add(a.gunnerTrait))),t.turret&&(a.turretTrait=new co,a.traits.add(a.turretTrait)),t.consideredAircraft&&!t.landable||a.traits.add(new Eo),t.parasiteable&&(a.parasiteableTrait=new wh(a),a.traits.add(a.parasiteableTrait)),t.naval&&t.underwater&&(a.submergibleTrait=new bh,a.traits.add(a.submergibleTrait)),t.locomotor===ri.Hover&&a.traits.add(new vh),[ri.Vehicle,ri.Chrono].includes(t.locomotor)&&i.isVoxel&&(a.tilterTrait=new Sh,a.traits.add(a.tilterTrait)),a}constructor(e,t,i){super(Et.Vehicle,e,t,i),this.direction=0,this.spinVelocity=0,this.crateBonuses=new La,this.turretNo=0,this.onBridge=!1,this.isSinker=!1,this.isFiring=!1,this.zone=t.naval?Ss.Water:Ss.Ground}isUnit(){return!0}isVehicle(){return!0}getUiName(){if(this.gunnerTrait){var e=this.armedTrait.getSpecialWeaponIndex(),t=this.gunnerTrait.getUiNameForIfvMode(e,this.transportTrait?.units[0]?.name),e=`name:${this.name}`;return t?`{${t}} {${e}}`:e}return super.getUiName()}update(e){this.rocking&&(this.rocking.ticksLeft--,this.rocking.ticksLeft||(this.rocking=void 0)),super.update(e)}applyRocking(e,t){this.rules.consideredAircraft||(this.rocking={ticksLeft:this.rocking?.ticksLeft??kh,facing:e,factor:t})}}class _h{constructor(e){this.airportNames=e}findAvailableAirport(e){return[...e.owner.buildings].find(e=>e.dockTrait&&this.airportNames.includes(e.name)&&0<e.dockTrait.getAvailableDockCount())}}class Ih{setParent(e){this.parent=e}getParent(){return this.parent}[jr.onTick](s,r){if(this.parent&&s.attackTrait&&s.primaryWeapon){let e=this.parent.attackTrait?.currentTarget,t=s.unitOrderTrait.getCurrentTask(),i=new Bs(r.map.tileOccupation);var a=this.parent.armedTrait?.getWeapons().find(e=>e.rules.spawner);s.ammo&&!(e&&s.attackTrait.currentTarget?e.equals(s.attackTrait.currentTarget):e===s.attackTrait.currentTarget||!e&&this.parent.isUnit()&&(this.parent.unitOrderTrait.getCurrentTask()instanceof _a||this.parent.unitOrderTrait.getCurrentTask()instanceof Io))&&(!e||a&&i.isInWeaponRange(this.parent,e.obj??e.tile,a,r.rules))?e&&s.primaryWeapon.targeting.canTarget(e.obj,e.tile,r,!0,!1)?!t||t instanceof _a?(s.unitOrderTrait.cancelAllTasks(),s.unitOrderTrait.addTask(s.attackTrait.createAttackTask(r,e.obj,e.tile,s.primaryWeapon,{force:!0}))):s.attackTrait.attackState!==bn.Idle&&t.requestTargetUpdate(e):t?t instanceof _a||t.cancel():this.tryMoveToParent(s,this.parent,r):this.tryMoveToParent(s,this.parent,r)}}tryMoveToParent(t,i,s){if(t.tile!==i.tile){let e=t.unitOrderTrait.getCurrentTask();e?e instanceof _a&&e.updateTarget(i.tile,!!i.isUnit()&&i.onBridge):t.unitOrderTrait.addTask(new _a(s,i.tile,!!i.isUnit()&&i.onBridge,{closeEnoughTiles:0,strictCloseEnough:!0}))}}}class Ch{setWarhead(e){return this.warhead=e,this}setDamage(e){return this.damage=e,this}setLauncher(e){return this.launcher=e,this}[Vr.onDestroy](e,t){this.warhead&&this.damage&&this.launcher&&this.warhead.detonate(t,this.damage,e.tile,e.tileElevation,e.position.worldPosition,e.zone,na.None,t.createTarget(void 0,e.tile),{player:e.owner,obj:this.launcher,weapon:void 0})}dispose(){this.launcher=void 0}}class Ah extends Pa{get direction(){return this.yaw}set direction(e){this.yaw=e}get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,s,r){let a=new this(e,t,i);return a.rules.airportBound&&a.rules.dock.length&&(a.airportBoundTrait=new _h(a.rules.dock),a.traits.add(a.airportBoundTrait)),a.rules.missileSpawn||(a.crashableTrait=new Ma(a),a.traits.add(a.crashableTrait)),a.rules.spawned&&(a.rules.missileSpawn?(a.missileSpawnTrait=new Ch,a.traits.add(a.missileSpawnTrait)):(a.spawnLinkTrait=new Ih,a.traits.add(a.spawnLinkTrait))),a.moveTrait=new Aa(a,r),a.traits.add(a.moveTrait),t.dock.length&&a.traits.add(new Eo),t.landable&&e!==s.general.paradrop.paradropPlane||a.traits.add(new Va),t.parasiteable&&(a.parasiteableTrait=new wh(a),a.traits.add(a.parasiteableTrait)),a}constructor(e,t,i){super(Et.Aircraft,e,t,i),this.pitch=0,this.yaw=0,this.roll=0,this.onBridge=!1,this.zone=Ss.Ground,this.crateBonuses=new La}isUnit(){return!0}isAircraft(){return!0}}class Bh{constructor(e){this.gameObject=e,this.orders=[],this.queuedOrders=new Set,this.tasks=[],this.taskRunner=new ko}[jr.onTick](i,e){if(i.isSpawned){var s=this.hasTasks(),t=this.tasks.find(e=>!e.isCancelling());if(s&&this.taskRunner.tick(this.tasks,i),i.isSpawned){var r,a=this.orders.length;if(a&&(!s||!t)){let e,t=!1;for(;e=this.orders[0];){if(e.isValid()&&e.isAllowed()&&((r=e.process())&&(this.queuedOrders.has(e)&&(this.tasks.push(new Xs(5)),this.tasks.push(new ya(()=>{i.resetGuardModeToIdle()}))),this.tasks.push(...r),s||this.taskRunner.tick(this.tasks,i)),t=!0),this.orders.shift(),this.queuedOrders.delete(e),!i.isSpawned)return;if(this.waypointPath&&(this.currentWaypoint?(this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.currentWaypoint=this.currentWaypoint?.next):this.currentWaypoint=this.waypointPath.waypoints[0],this.currentWaypoint||this.cleanupWaypointPath()),t)break}}!a&&!s&&this.waypointPath&&this.currentWaypoint&&(this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.cleanupWaypointPath());let e=t;for(;e?.useChildTargetLines;){var n=e.children.find(e=>!e.isCancelling());if(!n)break;e=n}this.targetLinesTask!==e&&(this.targetLinesTask=e,this.targetLinesConfig=e?.getTargetLinesConfig(this.gameObject))}}}[Yr.onChange](){this.clearOrders(),this.cancelAllTasks()}[zr.onBeforeTeleport](e,t,i,s){i&&!s&&(this.clearOrders(),this.tasks.length=0)}addOrder(t,e=!1){!1!==t.onAdd(this.tasks,e)?(e||(this.clearOrders(),this.tasks=this.tasks.filter(e=>e.status!==js.NotStarted),this.tasks.forEach(e=>e.cancel())),this.orders.push(t),e&&this.queuedOrders.add(t),this.gameObject.traits.filter(En).forEach(e=>{e[En.onPush](this.gameObject,t.orderType)})):this.targetLinesTask=void 0}clearOrders(){this.orders.length=0,this.queuedOrders.clear(),this.currentWaypoint&&this.waypointPath&&this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.cleanupWaypointPath(),this.gameObject.resetGuardModeToIdle()}unmarkNextQueuedOrder(){this.orders.length&&this.queuedOrders.delete(this.orders[0])}hasTasks(){return!!this.tasks.length}isIdle(){return!this.orders.length&&!this.tasks.length}getCurrentTask(){return this.tasks[0]}cancelAllTasks(){this.tasks.forEach(e=>e.cancel())}addTask(e){this.tasks.push(e)}addTasks(...e){e.forEach(e=>this.addTask(e))}addTaskToFront(e){this.tasks.unshift(e)}addTaskNext(e){this.tasks.splice(1,0,e)}getTasks(){return[...this.tasks]}dispose(){this.clearOrders(),this.tasks.length=0,this.gameObject=void 0}cleanupWaypointPath(){this.waypointPath&&(this.waypointPath.units.splice(this.waypointPath.units.indexOf(this.gameObject),1),this.waypointPath.units.length||(this.waypointPath.waypoints.forEach(e=>e.next=void 0),this.waypointPath.waypoints.length=0),this.waypointPath=void 0),this.currentWaypoint=void 0}cleanupWaypoint(t,e){if(!e.units.find(e=>e!==this.gameObject&&(e.unitOrderTrait.currentWaypoint??e.unitOrderTrait.waypointPath?.waypoints[0])===t)&&!e.waypoints.find(e=>e.next===t)){var i=e.waypoints.indexOf(t);if(-1===i)throw new Error("Given waypoint not found in waypoint path");e.waypoints.splice(i,1)}}}const xh=[[0,0,0,0],[0,0,1,1],[1,0,0,1],[1,1,0,0],[0,1,1,0],[0,0,0,1],[1,0,0,0],[0,1,0,0],[0,0,1,0],[1,0,1,1],[1,1,0,1],[1,1,1,0],[0,1,1,1],[1,0,1,2],[2,1,0,1],[1,2,1,0],[0,1,2,1],[1,0,1,0],[0,1,0,1],[1,0,1,0],[0,1,0,1]];class Eh{get onPositionChange(){return this._onPositionChange.asEvent()}get worldPosition(){return this._worldPosition}get tile(){return this._tile}set tile(e){var t=!!this._tile&&e!==this._tile;(this._tile=e)&&(this.updateWorldPosition(e,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:t}))}get tileElevation(){return void 0===this._tileElevation?(void 0===this._computedTileElevation&&(this._computedTileElevation=this.computeTileElevationFromWorldPos()),this._computedTileElevation):this._tileElevation}set tileElevation(e){this._absoluteElevation=void 0,this._tileElevation=e,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}get subCell(){if(!this._tileOffset.x&&!this._tileOffset.y)return 0;var e=Math.sign(this._tileOffset.x/_s.LEPTONS_PER_TILE-.5),t=Math.sign(this._tileOffset.y/_s.LEPTONS_PER_TILE-.5);return e&&t?t+1+(e+1)/2+1:0}set subCell(e){this._tileOffset=this.computeSubCellOffset(e),this.desiredSubCell=e,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}constructor(e,t){this.tiles=e,this.tileOccupation=t,this._worldPosition=new as,this._tileOffset=new Os,this._centerOffset=new Os,this.desiredSubCell=0,this._tileElevation=0,this._onPositionChange=new wo}getTileOffset(){return this._tileOffset.clone()}setTileOffset(e){this._tileOffset.copy(e),this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}setCenterOffset(e){this._centerOffset.copy(e),this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}getMapPosition(){if(this._tile)return new Os(this._tile.rx*_s.LEPTONS_PER_TILE+this._tileOffset.x+this._centerOffset.x,this._tile.ry*_s.LEPTONS_PER_TILE+this._tileOffset.y+this._centerOffset.y)}getBridgeBelow(){return this._tile?.onBridgeLandType?this.tileOccupation.getBridgeOnTile(this._tile):void 0}moveToTileCell(e,t=0){if(!this._tile)throw new Error("Tile is not set");var i=e!==this._tile;this._tile=e,this._tileOffset=this.computeSubCellOffset(t),this.desiredSubCell=t,this.updateWorldPosition(e,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:i})}moveToTileCoords(e,t,i=!1){var s=Math.floor(e),r=Math.floor(t),a=!this._tile||this._tile.rx!==s||this._tile.ry!==r;if(a){let e=this.tiles.getByMapCoords(s,r);if(!e){if(!i)throw new RangeError(`Attempted move to a non-existent tile: [${s},${r}]`);e=this.tiles.getPlaceholderTile(s,r)}this._tile=e}this._tileOffset.set((e-s)*_s.LEPTONS_PER_TILE,(t-r)*_s.LEPTONS_PER_TILE),this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:a})}moveToLeptons(e,t=!1){this.moveToTileCoords(e.x/_s.LEPTONS_PER_TILE,e.y/_s.LEPTONS_PER_TILE,t)}moveByLeptons(e,t,i=!1){if(!this._tile)throw new Error("Tile is not set");this.moveToTileCoords(this._tile.rx+(this._tileOffset.x+e)/_s.LEPTONS_PER_TILE,this._tile.ry+(this._tileOffset.y+t)/_s.LEPTONS_PER_TILE,i)}moveByLeptons3(e,t=!1){var i=this._worldPosition.y;this.moveByLeptons(e.x,e.z,t),this.setAbsoluteElevationWorld(i+e.y)}setAbsoluteElevationWorld(e){this._absoluteElevation=e,this._tileElevation=void 0,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}computeSubCellOffset(e){let t={width:0,height:0};var i;e&&(i=(e-1)%2*2-1,s=2*Math.floor((e-1)/2)-1,t={width:i*_s.LEPTONS_PER_TILE/4,height:s*_s.LEPTONS_PER_TILE/4});var s=_s.LEPTONS_PER_TILE/2;return new Os(s+t.width,s+t.height)}interpolateRampHeight(e,t,i){var s=xh[i],r=s[1],i=s[0];return r*(1-e)*(1-t)+s[2]*e*(1-t)+i*(1-e)*t+s[3]*e*t}updateWorldPosition(t,i){var e=i.x+this._centerOffset.x,s=i.y+this._centerOffset.y,r=e/_s.LEPTONS_PER_TILE,i=s/_s.LEPTONS_PER_TILE;let a;if(void 0!==this._tileElevation){let e=0;0!==t.rampType&&(e=this.interpolateRampHeight(r,i,t.rampType)),a=_s.tileHeightToWorld(t.z+e+this._tileElevation)}else a=this._absoluteElevation;this._worldPosition.set(t.rx*_s.LEPTONS_PER_TILE+e,a,t.ry*_s.LEPTONS_PER_TILE+s),void 0===this._tileElevation&&(this._computedTileElevation=this.computeTileElevationFromWorldPos())}computeTileElevationFromWorldPos(){if(!this._tile)return 0;var e=(t=_s.worldToTileHeight(this._worldPosition.y),i=14,t&&(i=10**i,Math.round(t*i)/i)),t=(this._tileOffset.x+this._centerOffset.x)/_s.LEPTONS_PER_TILE,i=(this._tileOffset.y+this._centerOffset.y)/_s.LEPTONS_PER_TILE;let s=0;return 0!==this._tile.rampType&&(s=this.interpolateRampHeight(t,i,this._tile.rampType)),e-this._tile.z-s}clone(){let e=new Eh(this.tiles,this.tileOccupation);return e._worldPosition=this._worldPosition.clone(),e._tile=this._tile,e._tileOffset=this._tileOffset.clone(),e._centerOffset=this._centerOffset.clone(),e._tileElevation=this._tileElevation,e._absoluteElevation=this._absoluteElevation,e._computedTileElevation=this._computedTileElevation,e}}class Ph{constructor(e){this.tileOccupation=e}checkCollisions(e,t,i){var s,r=e.tile;let a,n,o;for(s of this.tileOccupation.getObjectsOnTile(r))s.isOverlay()&&s.isBridge()&&(a=s),s.isOverlay()&&s.wallTrait&&(o=s),s.isTechno()&&!s.isDestroyed&&(n=s);if(i.walls){if(e.tileElevation<=2&&r.landType===ei.Wall)return{type:na.Wall,target:o};if(i.units&&n?.tile===r&&(!n.isUnit()||n.zone===Ss.Ground)&&e.tileElevation<=1.1&&i.units(n.owner))return{type:na.Wall,target:n}}if(i.shore&&r.landType!==ei.Water)return{type:na.Shore};if(i.ground&&e.tileElevation<0)return{type:na.Ground};var h=e.tileElevation+r.z,l=t.tileElevation+t.tile.z;if(a?.isHighBridge()){var c=a.tile.z+a.tileElevation;if(c<l&&h<=c||l<c&&c-1<=h)return l<c?{type:na.UnderBridge,target:a}:{type:na.OnBridge,target:a}}else if(a?.isLowBridge()&&i.shore)return{type:na.UnderBridge,target:a};if(i.cliffs){t=r.z-t.tile.z;if(e.tileElevation<0&&4<=t)return{type:na.Cliff}}return{type:na.None}}computeDetonationZone(e,t,i){let s=this.tileOccupation.getBridgeOnTile(e);return i===na.None&&t>1.5+(s?.tileElevation??0)?Ss.Air:s&&1.5<t||e.terrainType!==Jt.Water||s?.isLowBridge()?Ss.Ground:Ss.Water}}(r=Mn=Mn||{})[r.Travel=0]="Travel",r[r.Impact=1]="Impact",r[r.Detonation=2]="Detonation";class Nh extends Ea{get fromObject(){return this._fromObject}set fromObject(e){(this._fromObject=e)&&e.veteranTrait&&!e.isDestroyed&&(this.veteranDamageMult=e.veteranTrait.getVeteranDamageMultiplier())}get rot(){return this.fromWeapon.rules.isSonic?Ai.iniRotToDegsPerTick(this.iniRot):this.rules.rot}get iniRot(){return this.fromWeapon.rules.isSonic?10:this.rules.iniRot}static factory(e,t,i,s){return new this(e,t,i,s)}constructor(e,t,i,s){super(Et.Projectile,e,t,i),this.tileOccupation=s,this.state=Mn.Travel,this.detonationTimer=0,this.collisionType=na.None,this.direction=0,this.zone=Ss.Air,this.isShrapnel=!1,this.isNuke=!1,this.baseDamageMultiplier=1,this.veteranDamageMult=1,this.snapToTarget=!1,this.targetLockLost=!1,this.limboTravelTicks=0,this.homingTravelDistance=0,this.homingTravelTicks=0,this.velocity=new as,this.sonicVisitedObjects=new Map,this.collisionHelper=new Ph(s)}onSpawn(a){var e;if(super.onSpawn(a),this.initialSelfPosition=this.position.worldPosition.clone(),!this.target.obj||this.fromWeapon.type===li.DeathWeapon||this.fromWeapon.rules.limboLaunch||!this.isHoming()&&this.fromWeapon.speed===Number.POSITIVE_INFINITY||this.rules.inaccurate||this.rules.arcing||this.rules.flakScatter||0<(e=this.computeBaseDamage(a))&&(e=this.fromWeapon.warhead.computeDamage(e,this.target.obj,a),this.target.obj.healthTrait?.projectDamage(e)),a.afterTick(()=>{let e=new Bs(this.tileOccupation);var t=e.distance2(this.target.getWorldCoords(),this)/_s.LEPTONS_PER_TILE;this.initialTileDistToTarget=t,this.maxSpeed=this.computeMaxSpeed(this.fromWeapon.speed,t,a.rules.audioVisual.gravity)}),this.isHoming()){if(1===this.iniRot&&(this.homingMoveDir=this.target.getWorldCoords().clone().sub(this.position.worldPosition)),this.fromObject?.isAircraft()&&this.rules.isAntiGround&&!this.rules.isAntiAir){let e=this.target.obj;!e?.isVehicle()||e.isDestroyed||e.veteranLevel!==ta.Elite||e.unitOrderTrait.hasTasks()||e.unitOrderTrait.addTask(new Oa(a))}}else if(this.rules.vertical){let e=this.position.clone();e.tileElevation=this.fromWeapon.warhead.rules.nukeMaker?_s.worldToTileHeight(this.fromWeapon.projectileRules.detonationAltitude):0,this.aimPoint=e.worldPosition.clone()}else{let r=this.target.getWorldCoords().clone();a.afterTick(()=>{let e=this.target.getWorldCoords().clone().sub(r);var t=e.length()>_s.LEPTONS_PER_TILE;let i=t?r:this.target.obj?.isUnit()&&this.target.obj.moveTrait.velocity.length()&&isFinite(this.maxSpeed)?this.computeAimPointVersusMovingTarget(this.target.obj,this.maxSpeed,this.position.worldPosition,a.map):this.target.getWorldCoords().clone();this.aimPoint=i,this.snapToTarget=!t&&isFinite(this.maxSpeed)&&!this.fromWeapon.warhead.rules.sonic,(this.rules.inaccurate||this.rules.flakScatter)&&(this.adjustAimForBallisticScatter(a,i),this.snapToTarget=!1),!t&&this.rules.arcing&&(this.rules.inaccurate?(this.overshootTiles=this.calculateInaccurateBallisticOvershoot(a),this.snapToTarget=!1):this.target.obj?.isVehicle()&&this.target.obj.moveTrait.isMoving()&&(this.overshootTiles=this.calculateBallisticOvershootVsMoving(a,this.target.obj),this.overshootTiles&&(this.snapToTarget=!1)));let s=i.clone().sub(this.position.worldPosition);s.length()<this.fromWeapon.speed&&this.update(a)})}}adjustAimForBallisticScatter(e,t){let i=e.rules.combatDamage.ballisticScatter,s;s=this.rules.flakScatter?(this.rules.inviso&&(i*=2),e.generateRandom()*i):i/2+e.generateRandom()*(i/2);let r=s*_s.LEPTONS_PER_TILE;this.rules.flakScatter&&(n=t.clone().sub(this.initialSelfPosition).length(),r*=n/(this.fromWeapon.range*_s.LEPTONS_PER_TILE));var a=nr(new Os(r,0),e.generateRandomInt(0,360)),n=_s.vecWorldToGround(t).add(a).multiplyScalar(1/_s.LEPTONS_PER_TILE).floor();e.map.tiles.getByMapCoords(n.x,n.y)&&t.add(new as(a.x,0,a.y))}calculateBallisticOvershootVsMoving(e,t){let i=this.target.getWorldCoords().clone().sub(this.initialSelfPosition);var s=lr(_s.vecWorldToGround(i),_s.vecWorldToGround(t.moveTrait.velocity)),t=(90<s?180-s:s)/90,s=i.length()/_s.LEPTONS_PER_TILE,t=t*s/5;return e.generateRandom()<=t?2*Math.min(1,s/5):0}calculateInaccurateBallisticOvershoot(e){return e.generateRandom()<=.5?2:0}update(o){if(void 0!==this.maxSpeed)if(super.update(o),this.state!==Mn.Impact){var r=this.velocity.clone(),h=this.position.clone();if(this.velocity.set(0,0,0),this.fromWeapon.rules.limboLaunch){if(!this.fromObject)throw new Error("Limbo launch projectile must be fired from a unit");if(this.fromObject.isDestroyed)return void o.destroyObject(this)}var l=this.updateSpeed(this.maxSpeed);this.speed=l;let n=this.target.getWorldCoords();if(this.lastTargetLockPosition&&(this.targetLockLost||n.clone().sub(this.lastTargetLockPosition).length()>=_s.LEPTONS_PER_TILE)?(n=this.lastTargetLockPosition,this.targetLockLost=!0):this.lastTargetLockPosition=n.clone(),this.isHoming()){if(this.target.obj?.isUnit()&&(this.target.obj.isDestroyed||this.target.obj.isCrashing||!this.target.obj.isSpawned)&&(this.fromWeapon.rules.limboLaunch||this.homingTravelDistance>=2*_s.LEPTONS_PER_TILE))return void this.detonate(o);if(this.homingMoveDir||(u=vr.toMapCoords(this.direction),this.homingMoveDir=new as(u.x,0,u.y),this.fromObject?.isAircraft()&&(this.homingMoveDir.y=-9999999,this.homingMoveDir.normalize())),this.fromWeapon.rules.limboLaunch){if(!this.targetLockLost){if(10<this.limboTravelTicks)return this.position.moveToLeptons(this.target.obj.position.getMapPosition()),this.position.tileElevation=this.target.obj.position.tileElevation,void this.detonate(o);this.limboTravelTicks++}}else if(!this.isInHomingRange(n,o))return void this.detonate(o);let e=new Bs(this.tileOccupation);var c=Math.floor(e.distance2(n,this)/_s.LEPTONS_PER_TILE),u=2<c&&1<this.iniRot;let t=n.clone().sub(this.position.worldPosition),i=0;this.homingTravelTicks<this.rules.courseLockDuration||(u?(mr(this.homingMoveDir,new as(t.x,this.homingMoveDir.y,t.z),this.rot),this.rules.level||(c=z(Math.floor(this.initialTileDistToTarget)-1,0,2)+z(c-2,0,3),d=this.tileOccupation.getBridgeOnTile(this.tile)?.tileElevation??0,(d=c-(this.position.tileElevation-d))&&(g=.25+6/this.iniRot*.1,i=_s.tileHeightToWorld(Math.sign(d)*Math.min(Math.abs(d),g))))):mr(this.homingMoveDir,t,this.rot)),this.direction=vr.fromMapCoords(new Os(this.homingMoveDir.x,this.homingMoveDir.z));var d=t.length(),g=Math.min(d,l);this.homingTravelDistance+=g,this.homingTravelTicks++;let s=!1,r=na.None,a;if(1<=g){let e=this.homingMoveDir.clone().setLength(g);i&&(e.y+=i),g===l&&this.velocity.copy(e);var p=e.clone().add(this.position.worldPosition);o.map.mapBounds.isWithinHardBounds(p)?this.position.moveByLeptons3(e):s=!0;var m=this.checkObstacles(h,o);r=m.type,a=m.target,(r||g<l)&&(s=!0)}else this.position.moveByLeptons3(t),s=!0;if(s){if(a&&r===na.Wall){let e=a.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}this.collisionType=r,this.detonate(o,r)}}else{let t=this.aimPoint.clone().sub(this.position.worldPosition);this.rules.vertical||(this.direction=vr.fromMapCoords(new Os(t.x,t.z))),this.rules.arcing&&(t.y=0);d=Math.min(t.length(),l);if(t.setLength(d),this.rules.arcing){let e=_s.vecWorldToGround(this.position.worldPosition.clone().sub(this.initialSelfPosition).add(t));var p=this.aimPoint.clone().sub(this.initialSelfPosition),a=e.length(),m=_s.vecWorldToGround(p).length(),g=p.y,p=o.rules.audioVisual.gravity;t.y=(g/m*l+p/2*m/l)*a/l-p*(a/l)*(a/l)/2+this.initialSelfPosition.y-this.position.worldPosition.y}let e=!1;a=t.clone().add(this.position.worldPosition);o.map.isWithinHardBounds(a)?this.position.moveByLeptons3(t):e=!0;let i=na.None,s;if(1<=d?(d!==l&&!this.overshootTiles||this.velocity.copy(t),h=this.checkObstacles(h,o),i=h.type,s=h.target,(i||d<l)&&(e=!0)):e=!0,e){if(i){if(s&&i===na.Wall){let e=s.isBuilding()?_s.tile3dToWorld(s.tile.rx+.5,s.tile.ry+.5,s.tile.z):s.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}}else if(this.overshootTiles){var f=_s.vecWorldToGround(r).setLength(this.overshootTiles*_s.LEPTONS_PER_TILE);if(nr(f,o.generateRandomInt(-45,45)),a=_s.vecGroundToWorld(f).add(this.position.worldPosition),!o.map.isWithinHardBounds(a))return void o.unspawnObject(this);this.position.moveByLeptons(f.x,f.y)}else if(this.snapToTarget&&!this.targetLockLost){if(!o.map.isWithinHardBounds(n))return void o.unspawnObject(this);this.position.moveByLeptons3(n.clone().sub(this.position.worldPosition))}this.collisionType=i,this.isNuke?(this.state=Mn.Impact,this.detonationTimer=2.5*Us.BASE_TICKS_PER_SECOND):this.detonate(o,i)}}let e=this.fromWeapon.warhead;if(e.rules.sonic){var t,i,f=11/30*_s.LEPTONS_PER_TILE,f=this.position.worldPosition.clone().add(this.velocity.clone().setLength(f)),f=_s.vecWorldToGround(f).multiplyScalar(1/_s.LEPTONS_PER_TILE).floor(),s=o.map.tiles.getByMapCoords(f.x,f.y);if(s&&s!==this.fromObject?.tile){var y,w=o.map.getTileZone(s);for(y of o.map.getGroundObjectsOnTile(s))if((!y.isUnit()||!y.onBridge)&&(!y.isTechno()||!y.rules.typeImmune||y.owner!==this.fromPlayer||y.name!==this.fromObject?.name)&&(!y.isAircraft()||!y.rules.spawned)&&e.canDamage(y,s,w)){let e=this.sonicVisitedObjects.get(y)??new Set;e.add(s),this.sonicVisitedObjects.set(y,e)}}for([t,i]of this.sonicVisitedObjects)for(var T of i)o.map.tileOccupation.isTileOccupiedBy(T,t)&&t.isSpawned&&(T=this.fromWeapon.rules.ambientDamage*this.veteranDamageMult*this.baseDamageMultiplier,T=e.computeDamage(T,t,o),e.inflictDamage(T,t,{player:this.fromPlayer,weapon:this.fromWeapon,obj:this.fromObject},o,t!==this.target.obj))}}else 0<this.detonationTimer?this.detonationTimer--:this.detonate(o,this.collisionType)}isHoming(){return!!this.rot&&!this.rules.arcing}isInHomingRange(t,i){let s=!0,r=this.target.obj;if(r?.isUnit()&&this.fromObject){let e=new Bs(this.tileOccupation);i=e.computeWeaponRangeVsTarget(this.fromObject,r,this.fromWeapon,i.rules).range;this.fromWeapon.rules.limboLaunch?s=e.isInRange3(this.initialSelfPosition,t,0,i+.5):(t=r.moveTrait.velocity.length())&&(this.fromObject.rules.movementZone===ai.Fly?5<this.speed/t&&(s=e.isInRange2(this.initialSelfPosition,this.position.worldPosition,0,i)):isFinite(this.fromWeapon.speed)&&3.5<this.fromWeapon.speed/r.rules.speed&&(s=e.isInRange3(this.initialSelfPosition,this.position.worldPosition,0,i)))}return s}updateSpeed(e){let t;return t=this.isHoming()||this.rules.vertical?void 0===this.speed?Math.min(e,this.rules.acceleration):Math.min(e,this.speed+this.rules.acceleration):e,t}computeMaxSpeed(e,t,i){let s=e;return this.rules.arcing&&(s*=(1+i/6)/2,t=Math.floor(t),s*=t<=8?1:1+t/8*.5),this.fromWeapon.warhead.rules.sonic&&(s=Math.ceil(t*_s.LEPTONS_PER_TILE/21)),s}checkObstacles(e,t){return this.fromWeapon.rules.limboLaunch?{type:na.None}:this.collisionHelper.checkCollisions(this.position,e,{cliffs:this.rules.subjectToCliffs,ground:this.isHoming(),shore:this.rules.level,walls:this.rules.subjectToWalls,units:!this.rules.inaccurate&&(e=>this.fromPlayer!==e&&!t.alliances.areAllied(this.fromPlayer,e))})}computeBaseDamage(e){var t=this.fromWeapon,i=t.warhead;let s=t.rules.damage;t.type===li.DeathWeapon&&i.rules.ivanBomb&&(s=e.rules.combatDamage.ivanDamage);let r=s*this.baseDamageMultiplier;return t.type===li.DeathWeapon&&this.fromObject&&(r*=this.fromObject.rules.deathWeaponDamageModifier),r*=this.veteranDamageMult,r}detonate(n,e=na.None){var i=this.fromWeapon;let s=i.warhead;var t,r=this.zone=this.collisionHelper.computeDetonationZone(this.tile,this.tileElevation,e);let o=this.tile;i.type===li.DeathWeapon&&s.rules.ivanBomb&&(s=new Ja(n.rules.getWarhead(n.rules.combatDamage.ivanWarhead)));let a=this.computeBaseDamage(n);n.destroyObject(this),this.state=Mn.Detonation;let h=this.target.obj,l=!1;if(s.rules.parasite&&h?.isUnit()&&o===h.tile&&s.canDamage(h,o,r))if(h.isInfantry())a=Number.POSITIVE_INFINITY;else if(h.parasiteableTrait&&this.fromObject?.isUnit()){if(!(this.fromWeapon instanceof rn))throw new Error("Projectile with parasite warhead must have a weapon reference");h.parasiteableTrait.infest(this.fromObject,this.fromWeapon),l=!0}let c=!0;if(l&&(c=!1),s.rules.sonic&&(c=!1),s.rules.ivanBomb&&(c=!1,!h?.isTechno()||!h.tntChargeTrait||h.tntChargeTrait.hasCharge()||h.isDestroyed||h.warpedOutTrait.isInvulnerable()||(t=n.rules.combatDamage.ivanTimedDelay,h.tntChargeTrait.setCharge(t,n.currentTick,{player:this.fromPlayer,obj:this.fromObject}))),s.rules.bombDisarm&&(c=!1,h?.isTechno()&&h.tntChargeTrait?.hasCharge()&&!h.isDestroyed&&h.tntChargeTrait.removeCharge()),s.rules.mindControl&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&h?.isTechno()&&h.mindControllableTrait&&!h.mindControllableTrait?.isActive()&&!n.areFriendly(h,this.fromObject)&&s.canDamage(h,o,r)&&!h.invulnerableTrait.isActive()&&this.fromObject.mindControllerTrait.control(h,n)),s.rules.temporal&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&h?.isTechno()&&s.canDamage(h,o,r)&&!h.invulnerableTrait.isActive()&&(s.inflictDamage(0,h,{player:this.fromPlayer,weapon:i,obj:this.fromObject},n),this.fromObject.temporalTrait.updateTarget(h,i,n))),s.rules.makesDisguise&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&(this.fromObject.isInfantry()||this.fromObject.isVehicle())&&h?.isUnit()&&h.type===this.fromObject.type&&this.fromObject.disguiseTrait?.disguiseAs(h,this.fromObject,n)),s.rules.electricAssault&&(this.fromObject?.isUnit()&&!this.fromObject.isDestroyed&&h?.isBuilding()&&!h.isDestroyed&&h.overpoweredTrait&&h.owner===this.fromPlayer&&h.overpoweredTrait.chargeFrom(this.fromObject),c=!1),c&&s.detonate(n,a,o,this.tileElevation,this.position.worldPosition,r,e,this.target,{player:this.fromPlayer,weapon:i,obj:this.fromObject},this.isShrapnel?ca.Shrapnel:ca.None,this.impactAnim),s.rules.nukeMaker){let e;e=this.fromObject?(u=rn.factory(rn.NUKE_PAYLOAD_NAME,li.Primary,this.fromObject,n.rules),n.createProjectile(u.projectileRules.name,this.fromObject,u,this.target,!1)):n.createLooseProjectile(rn.NUKE_PAYLOAD_NAME,this.fromPlayer,this.target),e.isNuke=!0,e.impactAnim="NUKEBALL";var u=this.target.tile;e.position.moveToTileCoords(u.rx+.5,u.ry+.5),e.position.tileElevation=this.position.tileElevation,n.spawnObject(e,u)}if(this.rules.shrapnelCount&&this.rules.shrapnelWeapon&&((this.target.obj?!this.target.obj.isBuilding():n.map.getGroundObjectsOnTile(this.target.tile).some(e=>e.isTerrain())&&!i.projectileRules.isAntiAir)||this.isShrapnel)){let t=n.rules.getWeapon(this.rules.shrapnelWeapon);var d,g=n.rules.getProjectile(t.projectile);let i=this.rules.shrapnelCount,s=new Bs(n.map.tileOccupation),e=new Ws(n.map.tiles,n.map.mapBounds,o,{width:1,height:1},1,t.range,e=>s.isInTileRange(o,e,t.minimumRange,t.range)),r=new Set;for(;0<Math.floor(i);){var p,m=e.getNextTile();if(!m)break;for(p of n.map.tileOccupation.getObjectsOnTileByLayer(m,g.isAntiAir?Sn.Air:Sn.Ground).filter(e=>n.isValidTarget(e)&&(e.isTerrain()||e.isTechno()&&e.owner!==this.fromPlayer&&!n.alliances.areAllied(e.owner,this.fromPlayer)&&!(e.isInfantry()&&e.stance===Fs.Paradrop))))if(!r.has(p)&&(r.add(p),i=Math.max(0,i-1-(p.isTechno()?.5:0)),Math.floor(i)<=0))break}for(d of r){var f=n.createTarget(d.isTerrain()?void 0:d,d.tile);this.createShrapnel(n,f,t.name)}i=Math.floor(i);let a=new va(n.map.tiles,n.map.mapBounds,o,t.range,n,e=>s.isInTileRange(o,e,t.minimumRange,t.range));for(let e=0;e<i;e++){var y=a.getNextTile();if(!y)break;y=n.createTarget(void 0,y);this.createShrapnel(n,y,t.name)}}if(i.rules.limboLaunch&&!l&&this.fromObject?.isUnit()){let r=this.fromObject;s.rules.parasite&&(this.target.obj.isVehicle()||this.target.obj?.isAircraft())&&this.target.obj.parasiteableTrait&&(this.target.obj.parasiteableTrait.beingBoarded=!1);let t,a;i=r.rules.movementZone===ai.Fly;if(i)t=o,a=!1;else{let i=this.target.obj.isUnit()&&this.target.obj.tile.onBridgeLandType&&!this.target.obj.onBridge?void 0:n.map.tileOccupation.getBridgeOnTile(o),s=new Zs(n.map),e=new Ws(n.map.tiles,n.map.mapBounds,o,{width:1,height:1},0,1,e=>{var t=n.map.tileOccupation.getBridgeOnTile(e);return 0<n.map.terrain.getPassableSpeed(e,r.rules.speedType,r.isInfantry(),!!t)&&s.isEligibleTile(e,t,i,o)&&(e===o||!n.map.terrain.findObstacles({tile:e,onBridge:i},r).length)});t=e.getNextTile(),a=!!t?.onBridgeLandType}t?(!i&&this.target.obj.isUnit()&&(r.onBridge=a,r.position.tileElevation=a?n.map.tileOccupation.getBridgeOnTile(t)?.tileElevation??0:0),n.unlimboObject(r,t),r.isInfantry()&&(r.position.subCell=this.target.obj.position.subCell),r.direction=this.direction):r.owner.removeOwnedObject(r)}}createShrapnel(e,t,i){let s=e.createLooseProjectile(i,this.fromPlayer,t);s.isShrapnel=!0,s.veteranDamageMult=this.veteranDamageMult,s.position.moveToLeptons(this.position.getMapPosition()),s.position.tileElevation=this.position.tileElevation,e.spawnObject(s,s.position.tile)}computeAimPointVersusMovingTarget(t,i,e,s){let r=t.position.worldPosition,a=r.clone();var n=i,i=t.moveTrait.velocity.length();if(n<3*i)return r.clone();let o=Er.computeInterceptPoint(e,n,r,t.moveTrait.velocity);if(o.length()){let e=o.clone().sub(r);n=e.length(),i=i,n=i?Math.ceil(n/i):0;if(o=r.clone().add(e.setLength(n*i)),s.isWithinHardBounds(o))if(t.zone!==Ss.Air){o.multiplyScalar(1/_s.LEPTONS_PER_TILE);let e=t.position.clone();e.moveToTileCoords(o.x,o.z),a=e.worldPosition}else a=o;else a=r}return a.clone()}}(r=Rn=Rn||{})[r.None=0]="None",r[r.PreparingToFire=1]="PreparingToFire",r[r.FiringUp=2]="FiringUp",r[r.Firing=3]="Firing";class Dh{constructor(e){this.gameObject=e,this.deployed=!1,this.deployFireDelay=0,this.deployFireState=Rn.None,this.fireUpDelay=0,this.deployFireCount=0}isDeployed(){return this.deployed}setDeployed(t){var e=this.deployed;if((this.deployed=t)!==e){let e=this.gameObject;e.isInfantry()&&(e.stance=t?Fs.Deployed:Fs.None),t?(this.deployFireState=Rn.PreparingToFire,t=this.gameObject.armedTrait?.getDeployFireWeapon(),this.deployWeapon=t?.rules.areaFire?t:void 0,this.deployFireDelay=15+((t===e.primaryWeapon?e.secondaryWeapon:e.primaryWeapon)?.getCooldownTicks()??0),this.deployFireCount=0,this.undeployDelay=this.gameObject.rules.undeployDelay||void 0):(this.deployFireState===Rn.FiringUp&&(e.isFiring=!1),this.deployFireState=Rn.None,this.deployWeapon=void 0)}}toggleDeployed(){this.setDeployed(!this.isDeployed())}[jr.onTick](e,t){if(void 0!==this.undeployDelay&&(0<this.undeployDelay&&this.undeployDelay--,this.undeployDelay<=0&&[Rn.None,Rn.PreparingToFire].includes(this.deployFireState)))return this.undeployDelay=void 0,void this.setDeployed(!1);if(this.deployWeapon&&this.deployFireState!==Rn.None){if(this.deployFireState===Rn.PreparingToFire){if(0<this.deployFireDelay--||0===e.ammo)return;if(0<this.computeDeployFireCooldown(this.deployWeapon,t))return;this.fireUpDelay=Math.max(1,e.art.fireUp),this.deployFireState=Rn.FiringUp}if(this.deployFireState===Rn.FiringUp){if(e.isFiring=!0,0<this.fireUpDelay--)return;this.deployFireState=Rn.Firing}var i;this.deployFireState===Rn.Firing&&(e.isFiring=!1,i=e.onBridge?t.map.tileOccupation.getBridgeOnTile(e.tile):void 0,this.deployWeapon.fire(t.createTarget(i,e.tile),t),this.deployFireCount++,(this.deployWeapon===e.primaryWeapon?e.secondaryWeapon:e.primaryWeapon)?.resetCooldown(),this.deployWeapon.rules.fireOnce?(this.deployFireState=Rn.None,this.deployWeapon=void 0):this.deployFireState=Rn.PreparingToFire)}}computeDeployFireCooldown(t,i){if(t.rules.radLevel&&t.rules.areaFire){var s=this.gameObject.tile,s=i.mapRadiationTrait.getRadSiteLevel(s);if(!s)return 0;i=i.rules.radiation;let e=Math.max(0,s*i.radDurationMultiple-i.radLevelDelay);return 1===this.deployFireCount&&(i=i.radDurationMultiple*t.rules.radLevel,e=Math.max(0,e-Math.floor(.25*i))),e}return t.getCooldownTicks()}getHash(){return this.deployed?1:0}debugGetState(){return{deployed:this.deployed}}dispose(){this.gameObject=void 0}}(Ln=Ln||{}).onChange=Symbol();class Mh{constructor(e,t,i,s,r){this.target=e,this.attacker=t,this.damageHitPoints=i,this.currentHealth=s,this.prevHealth=r,this.type=rs.InflictDamage}}(Fn=Fn||{}).onChange=Symbol(),(r=jn=jn||{})[r.Green=0]="Green",r[r.Yellow=1]="Yellow",r[r.Red=2]="Red";class Rh{constructor(e,t,i){this.target=e,this.currentHealth=t,this.prevHealth=i,this.type=rs.HealthChange}}class Lh{get health(){return this._computedHealth}set health(e){this.setHitPoints(0<e?Math.max(1,Math.floor(e*this.maxHitPoints/100)):0),this.projectedHitPoints=this.hitPoints}get level(){return this.health>100*this.conditionYellow?jn.Green:this.health>100*this.conditionRed?jn.Yellow:jn.Red}constructor(e,t,i,s){this.maxHitPoints=e,this.gameObject=t,this.conditionYellow=i,this.conditionRed=s,this.setHitPoints(e),this.projectedHitPoints=this.hitPoints}setHitPoints(e){if(e!==Math.floor(e))throw new Error(`Value ${e} is not an integer`);this.hitPoints=z(e,0,this.maxHitPoints),this._computedHealth=this.hitPoints/this.maxHitPoints*100}getHitPoints(){return this.hitPoints}getProjectedHitPoints(){return this.projectedHitPoints}inflictDamage(t,i,s){var e=this.hitPoints,r=this.health;this.applyHitPoints(e-t,s),e!==this.hitPoints&&0<t&&(this.gameObject.traits.filter(ga).forEach(e=>{e[ga.onDamage](this.gameObject,s,t,i)}),s.events.dispatch(new Mh(this.gameObject,i,t,this.health,r)))}healBy(e,i,s){if(e<0)throw new Error(`Can't heal by negative value ${e}`);if(this.hitPoints<this.maxHitPoints){var r=this.hitPoints;this.applyHitPoints(this.hitPoints+e,s),this.projectedHitPoints=this.hitPoints;let t=this.hitPoints-r;this.gameObject.traits.filter(Dn).forEach(e=>{e[Dn.onHeal]?.(this.gameObject,s,t,i)})}}healToFull(i,s){if(this.hitPoints<this.maxHitPoints){var e=this.hitPoints;this.applyHitPoints(this.maxHitPoints,s),this.projectedHitPoints=this.hitPoints;let t=this.hitPoints-e;this.gameObject.traits.filter(Dn).forEach(e=>{e[Dn.onHeal]?.(this.gameObject,s,t,i)})}}applyHitPoints(e,t){let i=this.health;this.setHitPoints(e),i!==this.health&&(t.traits.filter(Ln).forEach(e=>{e[Ln.onChange](this.gameObject,t,i)}),this.gameObject.traits.filter(Fn).forEach(e=>{e[Fn.onChange](this.gameObject,t,i)}),t.events.dispatch(new Rh(this.gameObject,this.health,i)))}projectDamage(e){if(e<0)throw new Error("Projected damage must be positive");this.projectedHitPoints=Math.max(-30,this.projectedHitPoints-e)}[jr.onTick](e,t){t.currentTick%4==0&&(this.projectedHitPoints=Math.min(this.projectedHitPoints+1,this.hitPoints))}getHash(){return this.hitPoints}debugGetState(){return{hitPoints:this.hitPoints}}dispose(){this.gameObject=void 0}}class Fh{constructor(e){this.bridges=e,this.needsImageUpdate=!1,this.dominoHandled=!1}[ga.onDamage](){this.needsImageUpdate=!0}[jr.onTick](e){this.needsImageUpdate&&(this.needsImageUpdate=!1,this.bridges.handlePieceHealthChange(this.bridges.getPieceAtTile(e.tile)))}[Vr.onDestroy](r,a,n){var e=this.bridges.getPieceAtTile(r.tile);this.dominoHandled||this.bridges.findDominoPieces(e).filter(e=>!e.obj.isDestroyed).forEach(e=>{e.obj.traits.get(Fh).dominoHandled=!0,a.destroyObject(e.obj,n)});let t=a.map.tileOccupation.calculateTilesForGameObject(r.tile,r);t.forEach(e=>{let i=$i(e.terrainType),s=a.rules.getLandRules(i);a.map.getGroundObjectsOnTile(e).forEach(e=>{if(e.isUnit()&&(e.onBridge||e.moveTrait.reservedPathNodes.some(e=>e.onBridge===r))&&!e.isDestroyed)if(r.isLowBridge()&&0<s.getSpeedModifier(e.rules.speedType)||e.isInfantry()&&e.stance===Fs.Paradrop){e.onBridge&&(e.onBridge=!1,e.zone=Is(i));for(var t of e.moveTrait.reservedPathNodes)t.onBridge===r&&(t.onBridge=void 0);e.moveTrait.currentWaypoint?.onBridge===r&&(e.moveTrait.currentWaypoint.onBridge=void 0)}else e.isInfantry()&&(e.infDeathType=ii.None),a.destroyObject(e,n,!0)})})}}(r=Un=Un||{})[r.Idle=0]="Idle",r[r.Spawning=1]="Spawning";class jh{constructor(e){this.rules=e,this.ticksSinceLastSpawn=0,this.cooldownTicks=Math.floor(1/this.rules.animationProbability),this.status=Un.Idle}[jr.onTick](e,t){this.status=Un.Idle,this.ticksSinceLastSpawn++>this.cooldownTicks&&(this.ticksSinceLastSpawn=0,this.status=Un.Spawning,this.spawnTiberium(e.tile,t))}spawnTiberium(s,r){for(let i=1;i<=2;i++){let e=new Ws(r.map.tiles,r.map.mapBounds,s,{width:1,height:1},i,i,e=>Qa.canBePlacedOn(e,r.map));var a=e.getNextTile();if(a){var n=pn.calculateOverlayId(ha.Ore,a);if(void 0===n)throw new Error("Expected an overlayId");let e=r.createObject(Et.Overlay,r.rules.getOverlayName(n));return e.overlayId=n,e.value=3,void r.spawnObject(e,a)}e=new Ws(r.map.tiles,r.map.mapBounds,s,{width:1,height:1},i,i,e=>e.landType===ei.Tiberium);let t;for(;!t;){var o=e.getNextTile();if(!o)break;t=r.map.getObjectsOnTile(o).find(e=>e.isOverlay()&&e.isTiberium()&&e.traits.get(Qa).getBailCount()+1<=Qa.maxBails)}if(t)return void t.traits.get(Qa).spawnBails(1)}}}class Uh{constructor(e=!1){this.freeRepair=e,this.disabled=!0,this.cooldownTicks=0,this.healLeftover=0}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}[jr.onTick](t,i){if(!this.isDisabled())if(100===t.healthTrait.health&&this.setDisabled(!0),this.cooldownTicks<=0){var s=i.rules.general.repair,r=t.isInfantry()?s.iRepairRate:t.isBuilding()?s.repairRate:s.uRepairRate;this.cooldownTicks+=Us.BASE_TICKS_PER_SECOND*r*60;var a=t.isInfantry()?s.iRepairStep:s.repairStep,r=this.freeRepair?0:s.repairPercent;let e;r?(s=r*t.purchaseValue/t.healthTrait.maxHitPoints,(r=Math.min(t.owner.credits,Math.max(1,Math.floor(s*a))))?(e=s?r/s:a,t.owner.credits-=r):(e=0,this.setDisabled(!0))):e=a,e&&(e+=this.healLeftover,e=Math.min(t.healthTrait.maxHitPoints-t.healthTrait.getHitPoints(),e),e&&(a=Math.floor(e),this.healLeftover=e-a,a&&t.healthTrait.healBy(a,t,i)))}else this.cooldownTicks--}[Yr.onChange](){this.setDisabled(!0)}}(Wn=Wn||{}).onDestroy=Symbol();class Wh{constructor(e){this.target=e,this.type=rs.UnitPromote}}class zh{constructor(){this.cooldownTicks=0}[jr.onTick](e,t){100!==e.healthTrait.health&&(this.cooldownTicks<=0?(this.cooldownTicks+=Us.BASE_TICKS_PER_SECOND*t.rules.general.repair.repairRate*60,e.healthTrait.healBy(1,e,t)):this.cooldownTicks--)}}class Vh{constructor(e,t){this.gameObject=e,this.rules=t,this.specialWeaponIndex=0;t=e.veteranLevel===ta.Elite;e.rules.weaponCount?(this.selectSpecialWeapon(0,t),this.guardWeaponRangeOverride=this.primaryWeapon?.range):this.selectStandardWeapons(t)}selectStandardWeapons(e=!1){var t=this.gameObject,i=e&&t.rules.elitePrimary||t.rules.primary;i?(r=e?t.art.elitePrimaryFireFlh:t.art.primaryFireFlh,this.primaryWeapon=rn.factory(i,li.Primary,t,this.rules,r)):this.primaryWeapon=void 0;var s,r=e&&t.rules.eliteSecondary||t.rules.secondary;r?(s=e?t.art.eliteSecondaryFireFlh:t.art.secondaryFireFlh,this.secondaryWeapon=rn.factory(r,li.Secondary,t,this.rules,s)):this.secondaryWeapon=void 0,(t.explodes||t.crashableTrait)&&(s=t.rules.deathWeapon||!!t.crashableTrait&&this.secondaryWeapon?.rules.name||this.primaryWeapon?.rules.name||this.rules.combatDamage.deathWeapon,this.deathWeapon=rn.factory(s,li.DeathWeapon,t,this.rules))}selectSpecialWeapon(e,t=!1){let i=this.gameObject;var s=i.rules.weaponCount;if(s<1)throw new Error(`Object "${i.name}" doesn't support special weapons`);if(s-1<e)throw new RangeError(`Weapon index ${e} out of bounds (max ${s}) for object ${i.name}`);s=t&&i.rules.getEliteWeaponAtIndex(e)||i.rules.getWeaponAtIndex(e);if(!s)throw new Error(`Missing weapon at index ${e} for object "${i.name}"`);t=i.art.getSpecialWeaponFlh(e);this.primaryWeapon=rn.factory(s,li.Primary,i,this.rules,t),this.secondaryWeapon=void 0,this.specialWeaponIndex=e,this.deathWeapon=this.primaryWeapon.rules.suicide?rn.factory(i.rules.deathWeapon||this.primaryWeapon.name,li.DeathWeapon,i,this.rules):void 0}toggleEliteWeapons(e){this.gameObject.rules.weaponCount?this.selectSpecialWeapon(this.specialWeaponIndex,e):this.selectStandardWeapons(e)}getSpecialWeaponIndex(){return this.specialWeaponIndex}computeGuardScanRange(t){var e=this.guardWeaponRangeOverride??[this.primaryWeapon,this.secondaryWeapon].filter(e=>e===t||e?.rules.neverUse).reduce((e,t)=>Math.max(e,t.range),0),e=Math.max(e,this.gameObject.rules.guardRange);return Math.min(15,2*e-1)}getDeployFireWeapon(){if(this.gameObject.rules.deployFire)return this.gameObject.rules.deployFireWeapon===li.Primary?this.primaryWeapon:this.secondaryWeapon}isEquippedWithWeapon(e){return[this.primaryWeapon,this.secondaryWeapon].includes(e)}getWeapons(){return[this.primaryWeapon,this.secondaryWeapon].filter(Wa)}[jr.onTick](){this.primaryWeapon&&this.primaryWeapon.tick(),this.secondaryWeapon&&this.secondaryWeapon.tick()}[Vr.onDestroy](t,e,i){!this.deathWeapon||i?.weapon?.warhead.rules.temporal||t.crashableTrait&&!t.isCrashing||i?.obj?.isVehicle()&&i.weapon?.rules.suicide&&i.obj.transportTrait?.units.find(e=>e===t)||this.deathWeapon.fire(e.createTarget(t,t.tile),e)}dispose(){this.gameObject=void 0,this.primaryWeapon=void 0,this.secondaryWeapon=void 0,this.deathWeapon=void 0}}class Hh{}class Gh{constructor(e,t){this.gameObject=e,this.veteranRules=t,this.veteranLevel=ta.None,this.xp=0,this.promotionThresh=e.rules.cost*t.veteranRatio+1}[Wn.onDestroy](e,t,i,s){e.isDestroyed&&!e.isCrashing||t.isTechno()&&(t.rules.dontScore||t.rules.insignificant||(i&&(i.warhead.rules.temporal||i.warhead.rules.parasite&&e.rules.organic)||!s.areFriendly(e,t))&&(this.veteranLevel>=this.veteranRules.veteranCap||this.gainXP(t.rules.cost*(t.veteranLevel+1))&&this.handlePromotion(e,s)))}setRelativeXP(e){this.gainXP(Math.floor(e*this.promotionThresh))}gainXP(e){if(this.xp+=e,this.xp>=this.promotionThresh){var t=Math.min(this.veteranLevel+Math.floor(this.xp/this.promotionThresh),this.veteranRules.veteranCap),e=t-this.veteranLevel;if(e)return this.xp-=e*this.promotionThresh,this.setVeteranLevel(t),!0}return!1}promote(e,t){e=Math.min(this.veteranLevel+e,this.veteranRules.veteranCap);e-this.veteranLevel&&(this.setVeteranLevel(e),this.handlePromotion(this.gameObject,t))}isMaxLevel(){return this.veteranLevel===this.veteranRules.veteranCap}isElite(){return this.veteranLevel===ta.Elite}setVeteranLevel(e){this.veteranLevel=e,this.veteranLevel===ta.Elite&&this.gameObject.armedTrait?.toggleEliteWeapons(!0)}handlePromotion(e,t){this.hasVeteranAbility(ci.SELF_HEAL)&&(e.traits.find(zh)||t.addObjectTrait(e,new zh)),this.hasVeteranAbility(ci.CLOAK)&&(e.cloakableTrait||(e.cloakableTrait=new gn(e,t.rules.general.cloakDelay),t.addObjectTrait(e,e.cloakableTrait))),this.hasVeteranAbility(ci.EXPLODES)&&(e.explodes||(e.explodes=!0,e.armedTrait||(e.armedTrait=new Vh(e,t.rules),t.addObjectTrait(e,e.armedTrait)))),this.hasVeteranAbility(ci.RADAR_INVISIBLE)&&(e.radarInvisible||(e.radarInvisible=!0)),this.hasVeteranAbility(ci.SENSORS)&&(e.sensorsTrait||(e.sensorsTrait=new Hh,t.addObjectTrait(e,e.sensorsTrait))),e.isInfantry()&&this.hasVeteranAbility(ci.FEARLESS)&&e.suppressionTrait?.disable(),this.hasVeteranAbility(ci.C4)&&(e.c4||(e.c4=!0)),this.hasVeteranAbility(ci.GUARD_AREA)&&(e.defaultToGuardArea||(e.defaultToGuardArea=!0,e.unitOrderTrait.isIdle()&&e.resetGuardModeToIdle())),this.hasVeteranAbility(ci.CRUSHER)&&(e.crusher||(e.crusher=!0)),t.events.dispatch(new Wh(e))}getVeteranSightMultiplier(){return this.getVeteranAbilityMultiplier(ci.SIGHT)}getVeteranSpeedMultiplier(){return this.getVeteranAbilityMultiplier(ci.FASTER)}getVeteranArmorMultiplier(){return this.getVeteranAbilityMultiplier(ci.STRONGER)}getVeteranDamageMultiplier(){return this.getVeteranAbilityMultiplier(ci.FIREPOWER)}getVeteranRofMultiplier(){return this.getVeteranAbilityMultiplier(ci.ROF)}hasVeteranAbility(e){return this.veteranLevel===ta.Veteran&&this.gameObject.rules.veteranAbilities.has(e)||this.veteranLevel>=ta.Elite&&this.gameObject.rules.eliteAbilities.has(e)}getVeteranAbilityMultiplier(e){let t=1;return(this.veteranLevel===ta.Veteran&&this.gameObject.rules.veteranAbilities.has(e)||this.veteranLevel>=ta.Elite&&this.gameObject.rules.eliteAbilities.has(e))&&(t=this.getVeteranRulesMultiplier(e)),t}getVeteranRulesMultiplier(e){switch(e){case ci.FASTER:return this.veteranRules.veteranSpeed;case ci.STRONGER:return this.veteranRules.veteranArmor;case ci.FIREPOWER:return this.veteranRules.veteranCombat;case ci.ROF:return this.veteranRules.veteranROF;case ci.SIGHT:return this.veteranRules.veteranSight;default:throw new Error(`Unhandled VeteranAbility ${e}`)}}dispose(){this.gameObject=void 0}}class $h{constructor(e,t=e){this.maxAmmo=e,this.ammo=t}get ammo(){return this._ammo}set ammo(e){this._ammo=z(e,0,this.maxAmmo)}isFull(){return this.ammo===this.maxAmmo}}class qh{constructor(e){this.target=e,this.type=rs.ObjectDisguiseChange}}class Xh{constructor(){this.isActive=!1,this.cooldownTicks=0}isDisguised(){return this.isActive}getDisguise(){return this.isActive?this.disguisedAs:void 0}hasTerrainDisguise(){return this.getDisguise()?.rules.type===Et.Terrain}disguiseAs(e,t,i){this.disguisedAs={rules:e.rules,owner:e.owner},this.isActive=!0,i.events.dispatch(new qh(t))}revealDisguise(e,t){this.cooldownTicks=t.rules.general.infantryBlinkDisguiseTime,this.isActive=!1,t.events.dispatch(new qh(e))}[Kr.onSpawn](e,t){var i;!this.disguisedAs&&e.rules.permaDisguise&&e.isInfantry()&&e.owner.country&&((i=this.getDefaultInfantryDisguise(e.owner.country.side,t.rules.general))&&(i=t.rules.getObject(i,Et.Infantry),this.disguisedAs={rules:i,owner:e.owner},this.isActive=!0))}getDefaultInfantryDisguise(e,t){switch(e){case Qt.GDI:return t.alliedDisguise;case Qt.Nod:return t.sovietDisguise;default:return}}[jr.onTick](e,t){e.rules.permaDisguise||(e.attackTrait?.attackState===bn.JustFired||e.moveTrait.moveState!==Xr.Idle?this.revealDisguise(e,t):0<this.cooldownTicks?this.cooldownTicks--:!this.isActive&&e.rules.disguiseWhenStill&&(this.isActive=!0,this.disguisedAs={rules:this.selectRandomMirageDisguise(t),owner:void 0},t.events.dispatch(new qh(e))))}[ga.onDamage](e,t){this.revealDisguise(e,t)}selectRandomMirageDisguise(e){var t=e.rules.general.defaultMirageDisguises;if(!t.length)throw new Error("No default mirage disguises are defined");t=t[e.generateRandomInt(0,t.length-1)];return e.rules.getObject(t,Et.Terrain)}}class Zh{constructor(){this.timer=new Xo}isActive(){return this.timer.isActive()}setActiveFor(e,t){this.timer.setActiveFor(e,t)}[jr.onTick](e,t){this.timer.tick(t.currentTick)}}class Qh{constructor(e){this.gameObject=e,this.ticksWhenWarpedOut=!0,this.remainingTicks=0,this.invulnerable=!1}isActive(){return 0<this.remainingTicks}setActive(e,t,i){this.remainingTicks=e?Number.POSITIVE_INFINITY:0,this.invulnerable=t,this.notifyChange(e,i)}setTimed(e,t,i){this.remainingTicks=e,this.invulnerable=t,this.notifyChange(!0,i)}debugSetActive(e){this.remainingTicks=e?Number.POSITIVE_INFINITY:0}notifyChange(t,i){i.traits.filter(Ns).forEach(e=>{e[Ns.onChange](this.gameObject,i,t)}),this.gameObject.traits.filter(kn).forEach(e=>{e[kn.onChange](this.gameObject,i,t)})}expire(e){this.remainingTicks=0,this.notifyChange(!1,e)}isInvulnerable(){return this.isActive()&&this.invulnerable}[jr.onTick](e,t){0<this.remainingTicks&&(this.remainingTicks--,this.remainingTicks<=0&&this.notifyChange(!1,t))}dispose(){this.gameObject=void 0}}class Yh{constructor(){this.timer=new Xo}hasCharge(){return this.timer.isActive()}setCharge(e,t,i){this.hasCharge()||(this.timer.setActiveFor(e,t),this.attackerInfo=i)}getChargeOwner(){return this.attackerInfo?.player}removeCharge(){this.timer.reset()}getTicksLeft(){return this.timer.getTicksLeft()}getInitialTicks(){return this.timer.getInitialTicks()}[jr.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.isBuilding()&&e.cabHutTrait&&e.cabHutTrait.demolishBridge(t,this.attackerInfo),this.detonateIvanWarhead(t,e))}[Vr.onDestroy](e,t,i){!this.timer.isActive()||i?.weapon?.warhead.rules.ivanBomb||[Hr.None,Hr.Temporal,Hr.Sink].includes(e.deathType)||(this.timer.reset(),this.detonateIvanWarhead(t,e))}detonateIvanWarhead(e,t){var i=e.rules.combatDamage.ivanDamage;let s=new Ja(e.rules.getWarhead(e.rules.combatDamage.ivanWarhead));var r=t.tile,a=t.tileElevation,n=t.isUnit()?t.zone:e.map.getTileZone(r),o=!!t.isUnit()&&t.onBridge;s.detonate(e,i,r,a,t.isBuilding()?_s.tile3dToWorld(r.rx+.5,r.ry+.5,r.z+a):t.position.worldPosition,n,o?na.OnBridge:na.None,e.createTarget(t,r),{...this.attackerInfo,weapon:void 0},ca.TntCharge)}}class Kh{constructor(e){this.gameObject=e}getOriginalOwner(){return this.prevOwner}isActive(){return!!this.controller}getController(){return this.controller}controlBy(e,t){if(this.controller)throw new Error(`Object "${this.gameObject?.name}" is already mind controlled by "${e.name}"`);this.controller=e,this.prevOwner=this.gameObject.owner,t.changeObjectOwner(this.gameObject,e.owner)}restore(e){this.prevOwner&&(e.changeObjectOwner(this.gameObject,this.prevOwner),this.prevOwner=void 0,this.controller=void 0)}[Jr.onUnspawn](e,t){this.controller&&(this.controller.mindControllerTrait.cleanTarget(e),!e.isDestroyed&&e.limboData&&this.restore(t))}dispose(){this.gameObject=void 0}}class Jh{constructor(e,t=1){this.gameObject=e,this.maxCapacity=t,this.targets=[]}isActive(){return 0<this.targets.length}isAtCapacity(){return this.targets.length===this.maxCapacity}getTargets(){return this.targets}control(e,t){if(!this.gameObject)throw new Error("Trait already disposed");if(!e.mindControllableTrait)throw new Error(`Target "${e.name}" cannot be mind controlled`);if(e.isDisposed)throw new Error(`Target "${e.name}" is disposed`);for(e.mindControllableTrait.controlBy(this.gameObject,t),this.targets.push(e);this.targets.length>this.maxCapacity;){let e=this.targets.shift();e.mindControllableTrait.restore(t)}}cleanTarget(e){e=this.targets.indexOf(e);-1!==e&&this.targets.splice(e,1)}[Jr.onUnspawn](e,t){for(var i of this.targets)i.mindControllableTrait.restore(t);this.targets.length=0}dispose(){this.gameObject=void 0}}class el{constructor(e){this.gameObject=e,this.ticksWhenWarpedOut=!0,this.attackers=new Set}[jr.onTick](e,t){if(e.attackTrait&&(e.attackTrait.currentTarget&&!e.warpedOutTrait.isActive()||this.releaseCurrentTarget(t)),void 0!==this.eraseTicks)for(var i of this.attackers){var s=i.temporalTrait.currentWeapon;if(!s)throw new Error(`Attacker "${i.name}" is no longer targeting "${e.name}"`);var r=s.rules.damage;if(this.eraseTicks-=r,this.eraseTicks<=0){e.deathType=Hr.Temporal,t.destroyObject(e,{player:i.owner,obj:i,weapon:s},!0),this.eraseTicks=void 0;break}}}getTarget(){return this.currentTarget}updateTarget(t,e,i){if(this.currentTarget!==t){this.releaseCurrentTarget(i),this.currentTarget=t,this.currentWeapon=e;e=t.temporalTrait.attackers.size;if(t.temporalTrait.attackers.add(this.gameObject),!e){t.warpedOutTrait.setActive(!0,!0,i);let e=t.unitOrderTrait.getCurrentTask();(e&&e instanceof Io||e instanceof _a)&&e.cancel(),t.temporalTrait.eraseTicks=10*t.healthTrait.maxHitPoints}}}releaseCurrentTarget(t){if(this.currentTarget){if(!this.currentTarget.isDisposed){let e=this.currentTarget.temporalTrait.attackers;e.delete(this.gameObject),e.size||(this.currentTarget.warpedOutTrait.expire(t),this.currentTarget.temporalTrait.eraseTicks=void 0)}this.currentTarget=void 0,this.currentWeapon=void 0}}[Vr.onDestroy](e,t){this.releaseCurrentTarget(t)}dispose(){this.gameObject=void 0,this.attackers.clear()}}class tl{constructor(){this.spawns=[],this.storage=[],this.missileLaunches=[],this.nextRegenTicks=[]}get availableSpawns(){return this.storage.length}debugSetStorage(e,t){this.storage.length=t,this.storage.fill(e,0,t)}isLaunchingMissiles(){return 0<this.missileLaunches.length}[Kr.onSpawn](t,i){var s=i.rules.getObject(t.rules.spawns,Et.Aircraft);for(let e=0;e<t.rules.spawnsNumber;e++)this.pushNewSpawn(s,i,t)}[Jr.onUnspawn](e,t){this.destroySpawns(e,t)}[Vr.onDestroy](e,t,i,s){this.destroySpawns(e,t,i,s)}pushNewSpawn(e,t,i){let s=t.createUnitForPlayer(e,i.owner);s.limboData={selected:!1,controlGroup:void 0},e.missileSpawn&&(s.pitch=90*t.rules.general.getMissileRules(e.name).pitchInitial),this.spawns.push(s),this.storage.push(s)}destroySpawns(e,t,i,s){for(var r of this.spawns)r.isDestroyed||(r.isSpawned&&!r.rules.missileSpawn&&r.crashableTrait?r.crashableTrait.crash(i):(r.isSpawned||(r.armedTrait&&(r.armedTrait.deathWeapon=void 0),r.position.tileElevation=e.position.tileElevation,r.zone=e.isUnit()?e.zone:Ss.Ground,r.onBridge=!!e.isUnit()&&e.onBridge,r.position.tile=e.tile),t.destroyObject(r,i,s)));this.spawns.length=0,this.storage.length=0,this.missileLaunches.length=0}[jr.onTick](r,a){var t;if(this.spawns=this.spawns.filter(e=>!e.isDestroyed),this.missileLaunches=this.missileLaunches.filter(e=>!e.missile.isDestroyed),this.spawns.length<r.rules.spawnsNumber){var i=r.rules.spawnsNumber-this.spawns.length,s=a.rules.getObject(r.rules.spawns,Et.Aircraft);for(let e=0;e<i;e++)s.missileSpawn&&e&&void 0===this.nextRegenTicks[e]?this.nextRegenTicks[e]=this.nextRegenTicks[0]:((t=this.nextRegenTicks)[e]??(t[e]=r.rules.spawnRegenRate),0<this.nextRegenTicks[e]&&this.nextRegenTicks[e]--),this.nextRegenTicks[e]<=0&&this.pushNewSpawn(s,a,r);this.nextRegenTicks=this.nextRegenTicks.filter(e=>0<e)}if(this.storage.length){if(this.nextReloadTicks??(this.nextReloadTicks=r.rules.spawnReloadRate),0<this.nextReloadTicks&&this.nextReloadTicks--,this.nextReloadTicks<=0){for(var e of this.storage)e.ammoTrait&&e.ammoTrait.ammo<e.ammoTrait.maxAmmo&&e.ammoTrait.ammo++;this.nextReloadTicks=r.rules.spawnReloadRate}}else this.nextReloadTicks=void 0;for(let s of this.missileLaunches.slice()){var n=a.rules.general.getMissileRules(s.missile.name);if(s.pauseFrames??(s.pauseFrames=n.pauseFrames),0<s.pauseFrames&&s.pauseFrames--,s.pauseFrames<=0){var o=90*n.pitchFinal,n=90*(n.pitchFinal-n.pitchInitial)/n.tiltFrames;let i=s.missile;if(i.pitch<o)i.pitch=Math.min(o,i.pitch+n);else{i.unitOrderTrait.addTask(new za(new _a(a,s.targetTile,!!s.targetBridge),new ya(()=>{var e,t;i.isDestroyed||(a.unspawnObject(i),i.dispose(),t=_s.vecGroundToWorld(vr.toMapCoords(i.direction).multiplyScalar(1)),e=s.targetWorldPos.clone().add(t),t=a.map.getTileZone(s.targetTile),s.warhead.detonate(a,s.damage,s.targetTile,s.targetBridge?.tileElevation??0,e,t,s.targetBridge?na.OnBridge:na.None,s.target,{player:i.owner,obj:r,weapon:void 0}))})).setCancellable(!1));n=this.spawns.indexOf(i);if(-1===n)throw new Error("Missile not found in spawns list");this.spawns.splice(n,1),this.missileLaunches.splice(this.missileLaunches.indexOf(s),1)}}}}[Yr.onChange](e,t,i){for(var s of this.spawns)s.isDestroyed||i.changeObjectOwner(s,e.owner)}[kn.onChange](e,t,i){i&&this.removeMissileLaunches(t)}[zr.onBeforeTeleport](e,t,i,s){s||this.removeMissileLaunches(t)}removeMissileLaunches(e){if(this.missileLaunches.length){for(var t of this.missileLaunches){e.unspawnObject(t.missile),t.missile.dispose();t=this.spawns.indexOf(t.missile);if(-1===t)throw new Error("Missile not found in spawns list");this.spawns.splice(t,1)}this.missileLaunches.length=0}}prepareLaunch(s,r,a){if(this.storage.length){let i=this.storage[0];if(!i.ammo)return;if(this.storage.shift(),i.missileSpawnTrait){let e,t;var n=s.veteranTrait?.isElite(),o=a.rules;if(s.rules.spawns===o.general.v3Rocket.type)e=n?o.combatDamage.v3EliteWarhead:o.combatDamage.v3Warhead,t=n?o.general.v3Rocket.eliteDamage:o.general.v3Rocket.damage;else{if(s.rules.spawns!==o.general.dMisl.type)throw new Error(`Unhandled missile type "${s.rules.spawns}"`);e=n?o.combatDamage.dMislEliteWarhead:o.combatDamage.dMislWarhead,t=n?o.general.dMisl.eliteDamage:o.general.dMisl.damage}a=new Ja(a.rules.getWarhead(e));i.missileSpawnTrait.setDamage(t).setWarhead(a).setLauncher(s),this.missileLaunches.push({missile:i,targetTile:(r.obj?.isUnit()?r.obj:r).tile,targetBridge:r.getBridge(),targetWorldPos:r.getWorldCoords().clone(),target:r,warhead:a,damage:t,pauseFrames:void 0})}else{if(!i.spawnLinkTrait)throw new Error(`Aircraft "${i.name}" must have Spawned=yes to be launchable`);i.spawnLinkTrait.setParent(s)}return i}}storeAircraft(e,t){if(!this.spawns.includes(e))throw new Error(`Object "${e.name}#${e.id}" not found in list of linked spawns`);if(e.limboData)throw new Error(`Object "${e.name}#${e.id}" is already in limbo`);t.limboObject(e,{selected:!1,controlGroup:void 0}),this.storage.push(e)}}class il{[ia.onCrash](e,t){this.handleDestroy(e,t)}[Vr.onDestroy](e,t,i){i?.weapon?.warhead.rules.temporal||e.isCrashing||e.deathType!==Hr.Sink&&e.isSpawned&&this.handleDestroy(e,t)}handleDestroy(e,t){var i,s;(e.isVehicle()||e.isBuilding()||e.isOverlay())&&(i=e.isOverlay()?0:e.rules.minDebris,s=e.isOverlay()?t.rules.general.bridgeVoxelMax:e.rules.maxDebris,0<(s=t.generateRandomInt(i,s))&&this.spawnDebris(e,t,s))}spawnDebris(t,i,s){let r=t.position.getMapPosition();if(i.map.isWithinHardBounds(r)){let e=t.isOverlay()?[]:t.isVehicle()?t.rules.debrisTypes:t.rules.debrisAnims;e.length||(e=i.rules.audioVisual.metallicDebris),e=e.filter(e=>i.rules.hasObject(e,Et.VoxelAnim)||i.art.hasObject(e,Et.Animation)),new Array(s).fill(0).map(()=>e[i.generateRandomInt(0,e.length-1)]).map(e=>i.createObject(Et.Debris,e)).forEach(e=>{e.position.moveToLeptons(r),e.position.tileElevation=t.position.tileElevation,i.spawnObject(e,e.position.tile)})}}}class sl extends Ea{static factory(e,t,i,s){return new this(e,t,i,s)}constructor(e,t,i,s){super(Et.Debris,e,t,i),this.age=0,this.direction=0,this.rotationAxis=new as,this.angularVelocity=0,this.zone=Ss.Air,this.velocity=new as,this.collisionHelper=new Ph(s)}onSpawn(e){super.onSpawn(e),this.direction=e.generateRandomInt(0,359),this.xySpeed=H(0,this.rules.maxXYVel,e.generateRandom()),this.zSpeed=H(this.rules.minZVel,this.rules.maxZVel||1.5*this.rules.minZVel,e.generateRandom()),this.rotationAxis.set(e.generateRandom(),e.generateRandom(),e.generateRandom()).normalize(),this.angularVelocity=H(this.rules.minAngularVelocity,this.rules.maxAngularVelocity,e.generateRandom())}update(t){if(super.update(t),this.age++,this.rules.duration&&this.age>this.rules.duration)return this.velocity.set(0,0,0),void this.detonate(t);--this.zSpeed;var i=vr.toMapCoords(this.direction).setLength(this.xySpeed);let s=new as(i.x,this.zSpeed,i.y);var r=this.position.clone(),i=s.clone().add(this.position.worldPosition);if(t.map.isWithinHardBounds(i)){this.position.moveByLeptons3(s);let e=!1;var{type:i,target:r}=this.collisionHelper.checkCollisions(this.position,r,{cliffs:!0,ground:!0,shore:!1,walls:!0,units:!1});if(i&&(!([na.Ground,na.OnBridge].includes(i)&&0<this.rules.elasticity&&t.map.getTileZone(this.tile)!==Ss.Water)||Math.abs(this.zSpeed)<1?e=!0:(this.zSpeed=-this.zSpeed*this.rules.elasticity,this.velocity.y=-this.velocity.y*this.rules.elasticity,this.rotationAxis.negate())),e){if(this.velocity.set(0,0,0),r&&i===na.Wall){let e=r.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}this.detonate(t,i)}else this.velocity.copy(s)}else t.unspawnObject(this)}detonate(t,i=na.None){var e,s=this.rules.warhead?t.rules.getWarhead(this.rules.warhead):void 0,r=this.zone=this.collisionHelper.computeDetonationZone(this.tile,this.tileElevation,i);let a;r===Ss.Water?(e=t.rules.combatDamage.splashList,a=e[0]):(e=this.rules.expireAnim)&&t.rules.animationNames.has(e)&&(a=e),this.explodeAnim=a;let n=new Ya;if(a&&n.spawnSmudges(a,this.tile,t),t.destroyObject(this),s){let e=new Ja(s);e.detonate(t,this.rules.damage,this.tile,this.tileElevation,this.position.worldPosition,r,i,t.createTarget(void 0,this.tile),void 0,ca.None,void 0,this.rules.damageRadius||void 0,!0)}}}class rl{constructor(e,t,i,s){this.tiles=e,this.tileOccupation=t,this.bridges=i,this.nextObjectId=s}create(e,t,i,s){let r,a;e===Et.Debris?r=i.hasObject(t,Et.VoxelAnim)?(a=s.getObject(t,Et.VoxelAnim),i.getObject(t,Et.VoxelAnim)):(a=s.getAnimation(t),new ds(Et.Debris,s.getIni().getOrCreateSection(t))):a=e===Et.Projectile?(r=i.getProjectile(t),r.inviso?new ao(Et.Projectile,r,new h(t)):s.getProjectile(t)):(r=i.getObject(t,e),s.getObject(t,e));let n;switch(e){case Et.Building:n=nh.factory(t,r,i,a,this.tiles,this.bridges);break;case Et.Infantry:n=Fa.factory(t,r,a,this.tileOccupation);break;case Et.Vehicle:n=Oh.factory(t,r,a,i,this.tileOccupation);break;case Et.Aircraft:n=Ah.factory(t,r,a,i,this.tileOccupation);break;case Et.Terrain:n=oh.factory(t,r,a);break;case Et.Overlay:n=hh.factory(t,r,a);break;case Et.Smudge:n=lh.factory(t,r,a);break;case Et.Projectile:n=Nh.factory(t,r,a,this.tileOccupation);break;case Et.Debris:n=sl.factory(t,r,a,this.tileOccupation);break;default:throw new Error("Not implemented")}if(n.id=this.nextObjectId.value++,n.position=new Eh(this.tiles,this.tileOccupation),n.isUnit()?n.position.subCell=0:n.isBuilding()&&n.position.setCenterOffset(n.getFoundationCenterOffset()),n.isTechno()&&((n.rules.primary||n.rules.secondary||n.rules.weaponCount||n.rules.explodes)&&(n.armedTrait=new Vh(n,i),n.traits.add(n.armedTrait)),-1!==n.rules.ammo&&(o=n.rules.initialAmmo,n.ammoTrait=new $h(n.rules.ammo,-1!==o?o:void 0),n.traits.add(n.ammoTrait)),n.unitOrderTrait=new Bh(n),n.traits.addToFront(n.unitOrderTrait),(n.primaryWeapon||n.secondaryWeapon)&&(n.attackTrait=new _o(this.tiles,this.tileOccupation),n.traits.add(n.attackTrait)),(n.isInfantry()||n.isVehicle())&&n.rules.deployer&&(n.deployerTrait=new Dh(n),n.traits.add(n.deployerTrait)),(n.isInfantry()||n.isVehicle())&&n.rules.canDisguise&&(n.disguiseTrait=new Xh,n.traits.add(n.disguiseTrait)),n.rules.cloakable&&(n.cloakableTrait=new gn(n,i.general.cloakDelay),n.traits.add(n.cloakableTrait)),n.rules.sensors&&(n.sensorsTrait=new Hh,n.traits.add(n.sensorsTrait)),n.autoRepairTrait=new Uh(!n.isBuilding()),n.traits.add(n.autoRepairTrait),n.rules.trainable&&(n.veteranTrait=new Gh(n,i.general.veteran),n.traits.add(n.veteranTrait)),n.rules.selfHealing&&n.traits.add(new zh),n.invulnerableTrait=new Zh,n.traits.add(n.invulnerableTrait),n.warpedOutTrait=new Qh(n),n.traits.add(n.warpedOutTrait),n.temporalTrait=new el(n),n.traits.add(n.temporalTrait),n.rules.bombable&&(n.tntChargeTrait=new Yh,n.traits.add(n.tntChargeTrait)),n.rules.immuneToPsionics||n.isBuilding()||(n.mindControllableTrait=new Kh(n),n.traits.add(n.mindControllableTrait)),[n.primaryWeapon,n.secondaryWeapon].some(e=>e?.warhead.rules.mindControl)&&(n.mindControllerTrait=new Jh(n),n.traits.add(n.mindControllerTrait)),n.rules.spawns&&(n.airSpawnTrait=new tl,n.traits.add(n.airSpawnTrait)),n.rules.maxDebris&&n.traits.add(new il)),n.isTechno()||n.isOverlay()||n.isTerrain()){var o=n.isOverlay()&&$a.isBridge(i.getOverlayId(n.name));let e=n.rules.strength;!e&&n.isTerrain()&&(e=i.general.treeStrength),o&&(e=i.combatDamage.bridgeStrength),(e||n.isTechno())&&(n.healthTrait=new Lh(e,n,i.audioVisual.conditionYellow,i.audioVisual.conditionRed),n.traits.add(n.healthTrait)),n.isOverlay()&&o&&(n.bridgeTrait=new Fh(this.bridges),n.traits.add(n.bridgeTrait),$a.getOverlayBridgeType(i.getOverlayId(n.name))===ra.Concrete&&n.traits.add(new il))}return n.isOverlay()&&n.isOverlay()&&Za.getOverlayTibType(i.getOverlayId(n.name))!==ha.NotSpecial&&n.traits.add(new Qa(n)),n.isTerrain()&&n.rules.spawnsTiberium&&n.traits.add(new jh(n.rules)),n.cachedTraits.tick.push(...n.traits.filter(jr)),n}}class al{constructor(){this.allObjects=new Map,this._onObjectSpawned=new wo,this._onObjectRemoved=new wo}get onObjectSpawned(){return this._onObjectSpawned.asEvent()}get onObjectRemoved(){return this._onObjectRemoved.asEvent()}spawnObject(e){if(this.allObjects.has(e.id))throw new Error("Trying to add an already existing object");this.allObjects.set(e.id,e),this._onObjectSpawned.dispatch(this,e)}removeObject(e){if(!this.allObjects.has(e.id))throw new Error("Trying to remove non-existent object");this.allObjects.delete(e.id),this._onObjectRemoved.dispatch(this,e)}hasObjectId(e){return this.allObjects.has(e)}getObjectById(e){if(!this.allObjects.has(e))throw new Error(`Object with id ${e} doesn't exist`);return this.allObjects.get(e)}getAllObjects(){return[...this.allObjects.values()]}}class nl{constructor(e,t){this.id=e,this.data=t,this.neighbors=new Set}addLink(e){this.neighbors.add(e),e!==this&&e.neighbors.add(this)}removeLink(e){this.neighbors.delete(e),e.neighbors.delete(this)}deleteLinks(){for(var e of this.neighbors)e.neighbors.delete(this);this.neighbors.clear()}}class ol{constructor(){this.nodes=new Map}addNode(e,t){let i=this.getNode(e);return i?i.data=t:i=new nl(e,t),this.nodes.set(e,i),i}removeNode(e){let t=this.getNode(e);return!!t&&(t.deleteLinks(),this.nodes.delete(e),!0)}hasNode(e){return this.nodes.has(e)}getNode(e){return this.nodes.get(e)}getNodeCount(){return this.nodes.size}forEachNode(e){for(var t of this.nodes.values())e(t)}clear(){for(var e of this.nodes.values())e.deleteLinks();this.nodes.clear()}}class hl{constructor(e=[]){if(this.data=e,this.length=e.length,0<this.length)for(let e=this.length>>1;0<=e;e--)this.down(e);for(let e=0;e<this.length;++e)this.setNodeId(this.data[e],e)}compare(e,t){return e.fScore-t.fScore}setNodeId(e,t){e.heapIndex=t}push(e){this.data.push(e),this.setNodeId(e,this.length),this.length++,this.up(this.length-1)}pop(){if(0!==this.length){var e=this.data[0];return this.length--,0<this.length&&(this.data[0]=this.data[this.length],this.setNodeId(this.data[0],0),this.down(0)),this.data.pop(),e}}peek(){return this.data[0]}updateItem(e){this.down(e),this.up(e)}up(e){let t=this.data;for(var i=t[e];0<e;){var s=e-1>>1,r=t[s];if(0<=this.compare(i,r))break;t[e]=r,this.setNodeId(r,e),e=s}t[e]=i,this.setNodeId(i,e)}down(i){let s=this.data;for(var e=this.length>>1,r=s[i];i<e;){let e=1+(i<<1);var a=e+1;let t=s[e];if(a<this.length&&this.compare(s[a],t)<0&&(e=a,t=s[a]),0<=this.compare(t,r))break;s[i]=t,this.setNodeId(t,i),i=e}s[i]=r,this.setNodeId(r,i)}}class ll{constructor(e){this.node=e,this.closed=!1,this.open=0,this.distanceToSource=Number.POSITIVE_INFINITY,this.fScore=Number.POSITIVE_INFINITY,this.heapIndex=-1}}function cl(){return 0}function ul(){return 1}function dl(u,e={}){let d=e.bestEffort,g=e.maxExpandedNodes||Number.POSITIVE_INFINITY,p=e.heuristic??cl,m=e.distance??ul,f=e.excludedNodes,y=function(){let i=0,s=[];return{createNewState(e){let t=s[i];return t?(t.node=e,t.parent=void 0,t.closed=!1,t.open=0,t.distanceToSource=Number.POSITIVE_INFINITY,t.fScore=Number.POSITIVE_INFINITY,t.heapIndex=-1):(t=new ll(e),s[i]=t),i++,t},reset(){i=0}}}();return{find:function(e,t){let i=u.getNode(e);if(!i)throw new Error("fromId is not defined in this graph: "+e);let s=u.getNode(t);if(!s)throw new Error("toId is not defined in this graph: "+t);if(i===s)return[];y.reset();let r=new Map,a=new hl,n=y.createNewState(i);if(r.set(e,n),n.fScore=f?.(s.data)?Number.POSITIVE_INFINITY:p(i,s),!Number.isFinite(n.fScore)&&i.neighbors.has(s))return[];n.distanceToSource=0,a.push(n),n.open=1;let o,h=n,l=0;for(;0<a.length;){if(o=a.pop(),o.node===s)return gl(o);if(l++,l>g)break;o.closed=!0,o.node.neighbors.forEach(c)}return d?gl(h):[];function c(e){let t=r.get(e.id);t||(t=y.createNewState(e),r.set(e.id,t)),t.closed||(0===t.open&&(a.push(t),t.open=1),(e=f?.(e.data)?Number.POSITIVE_INFINITY:o.distanceToSource+m(o.node,e))>=t.distanceToSource||(t.parent=o,t.distanceToSource=e,f?.(s.data)?t.fScore=Number.POSITIVE_INFINITY:t.fScore=e+p(t.node,s,t),t.fScore-t.distanceToSource<h.fScore-h.distanceToSource&&(h=t),a.updateItem(t.heapIndex)))}}}}function gl(e){let t=[e.node],i=e.parent;for(;i;)t.push(i.node),i=i.parent;return t}function pl(e,t){var i=Math.abs(e.data.tile.rx-t.data.tile.rx),t=Math.abs(e.data.tile.ry-t.data.tile.ry);return i+t+(Math.SQRT2-2)*Math.min(i,t)}function ml(e,t,i){var s=Math.abs(e.data.tile.rx-t.data.tile.rx),t=Math.abs(e.data.tile.ry-t.data.tile.ry);let r=s+t+(Math.SQRT2-2)*Math.min(s,t);return i?.parent&&(t=(s=i.parent.node).data.tile.rx-e.data.tile.rx,e=s.data.tile.ry-e.data.tile.ry,i.dirX=t,i.dirY=e,t===i.parent.dirX&&e===i.parent.dirY||(r+=.2)),r}class fl{constructor(e,t,i,s,r){this.tiles=e,this.theaterType=t,this.mapBounds=i,this.tileOccupation=s,this.rules=r,this.passabilityGraphs=new Map,this.invalidatedTiles=new Map,this.handleTileOccupationUpdate=({tiles:e,object:s})=>{e=e.filter(e=>{let t=ti.Foot,i=!0;return s.isTerrain()&&s.rules.getOccupationBits(this.theaterType)!==is.All&&(t=ti.Wheel,i=!1),s.isOverlay()&&(s.isBridge()||s.isTiberium())||this.isBlockerObject(s,e,!1,t,i)||this.isBlockerObject(s,e,!0,t,i)||s.isBuilding()&&s.rules.leaveRubble});e.length&&this.invalidateTiles(e)},this.handleMapBoundsResize=()=>{this.passabilityGraphs.clear()},s.onChange.subscribe(this.handleTileOccupationUpdate),i.onLocalResize.subscribe(this.handleMapBoundsResize)}getGraphKey(e,t){return e+"_"+Number(t)}invalidateTiles(i){i.length&&[...this.passabilityGraphs.keys()].forEach(e=>{let t=this.invalidatedTiles.get(e);t?i.forEach(e=>t.add(e)):this.invalidatedTiles.set(e,new Set(i))})}computePath(r,a,e,t,i,s,{maxExpandedNodes:n=Number.POSITIVE_INFINITY,bestEffort:o=!0,excludeTiles:h,ignoredBlockers:l=[]}={}){let c=this.computePassabilityGraph(r,a);var u=l.map(e=>this.tileOccupation.calculateTilesForGameObject(e.tile,e)).reduce((e,t)=>e.concat(t),[]);u.length&&this.updatePassability(u,r,a,c,l);var d=this.getNodeId(e,t),g=!!c.hasNode(d);g||this.updatePassability([e],r,a,c,l,1);var p=this.getNodeId(i,s),m=!!c.hasNode(p);let f;var y=g&&!u.length;if(y){let i=this.getIslandIdMap(r,a),s=i.get(e,t);f=(e,t)=>i.get(e,t)===s}else f=(e,t)=>0<this.getPassableSpeed(e,r,a,t,l);if(!m||!f(i,s)){var w=y?15:5,w=o?new Ws(this.tiles,this.mapBounds,i,{width:1,height:1},1,w,e=>f(e,!1)&&Math.abs(e.z-i.z)<2&&!h?.({tile:e,onBridge:void 0})).getNextTile():void 0;if(w)i=w,s=!1;else{if(y)return u.length&&this.updatePassability(u,r,a,c),[];c.addNode(p,{tile:i,onBridge:void 0}),n=Math.min(n,500)}}let T=dl(c,{bestEffort:o,maxExpandedNodes:n,excludedNodes:h,distance:pl,heuristic:ml}),b=T.find(this.getNodeId(e,t),this.getNodeId(i,s)).map(e=>({tile:e.data.tile,onBridge:e.data.onBridge}));return(b.length<2||h&&b.length&&(!o&&b[0].tile!==i||b[b.length-1].tile!==e))&&(b=[]),g||(c.removeNode(d),this.updatePassability([e],r,a,c)),m||c.removeNode(p),u.length&&this.updatePassability(u,r,a,c),b}computeAllPassabilityGraphs(){Object.keys(ti).forEach(e=>{e=Number(e);isNaN(e)||e===ti.Winged||(this.computePassabilityGraph(e,!1),this.computePassabilityGraph(e,!0))})}computePassabilityGraph(t,i){var s=this.getGraphKey(t,i);let r=this.passabilityGraphs.get(s);if(r){let e=this.invalidatedTiles.get(s);e?.size&&(this.updatePassability([...e],t,i,r),e.clear(),this.computeIslandIds(r))}else r=new ol,this.passabilityGraphs.set(s,r),this.tiles.forEach(e=>{this.computePassability(e,t,i,r)}),this.computeIslandIds(r);return r}updatePassability(t,i,s,r,a=[],n){let o=new Set;t.forEach(e=>{[e,this.tiles.getNeighbourTile(e,oa.Right),this.tiles.getNeighbourTile(e,oa.BottomRight),this.tiles.getNeighbourTile(e,oa.Bottom),this.tiles.getNeighbourTile(e,oa.BottomLeft)].filter(Wa).forEach(e=>o.add(e))});let h=new Map;t.forEach(e=>{var t;for(t of[r.getNode(this.getNodeId(e,!1)),r.getNode(this.getNodeId(e,!0))])t&&(h.set(t.id,t.data.islandId),r.removeNode(t.id))}),o.forEach(e=>{this.computePassability(e,i,s,r,a,n&&t.includes(e)?n:void 0)}),h.forEach((e,t)=>{let i=r.getNode(t);i&&(i.data.islandId=e)})}computePassability(e,t,i,s,r=[],a){var n=[oa.Left,oa.TopLeft,oa.Top,oa.TopRight];if(a||this.getPassableSpeed(e,t,i,!1,r)){var o,h=this.getNodeId(e,!1);s.hasNode(h)||s.addNode(h,{tile:e,onBridge:void 0,forceLandSpeed:a});for(o of n)this.connectTiles(e,void 0,o,t,i,s,r)}var l=this.tileOccupation.getBridgeOnTile(e);if(l&&(a||this.getPassableSpeed(e,t,i,!0,r))){var c,h=this.getNodeId(e,!0);s.hasNode(h)||s.addNode(h,{tile:e,onBridge:l,forceLandSpeed:a});for(c of n)this.connectTiles(e,l,c,t,i,s,r)}}connectTiles(i,s,r,a,n,o,h=[]){var l=this.tiles.getNeighbourTile(i,r);if(l){let e=this.tileOccupation.getBridgeOnTile(l);r=s||e?0:1;if(Math.abs(i.z+(s?.tileElevation??0)-(l.z+(e?.tileElevation??0)))>r){if(!e?.isHighBridge()&&!s?.isHighBridge()||0!==Math.abs(i.z-l.z)||!o.hasNode(this.getNodeId(i,!1)))return;s=e=void 0}r=this.getNodeId(l,!!e);let t=o.getNode(r);this.getPassableSpeed(l,a,n,!!e,h,void 0,t?.data.forceLandSpeed)&&(t=t??o.addNode(r,{tile:l,onBridge:e}),s=this.getNodeId(i,!!s),o.getNode(s).addLink(t))}}getNodeId(e,t){return e.id+(t?"_bridge":"")}computeIslandIds(e){let t=1;e.forEachNode(e=>{e.data.islandId=void 0}),e.forEachNode(e=>{e.data.islandId||this.floodIslandId(e,t++)})}floodIslandId(e,t){let i=[e];for(;i.length;){let e=i.pop();e.data.islandId=t;for(var s of e.neighbors)s.data.islandId||i.push(s)}}getIslandIdMap(e,t){let i=this.computePassabilityGraph(e,t);return{get:(e,t)=>{t=this.getNodeId(e,t);return i.getNode(t)?.data.islandId}}}getPassableSpeed(e,t,i,s,r=[],a=!1,n){if(!this.mapBounds.isWithinBounds(e))return 0;let o=s?e.onBridgeLandType:e.landType;if(void 0===o)return 0;o===ei.Wall&&t===ti.Track&&(o=$i(e.terrainType));let h=this.rules.getLandRules(o);var l,n=n||h.getSpeedModifier(t);if(!n)return 0;if(!a)for(l of this.tileOccupation.getObjectsOnTile(e))if(this.isBlockerObject(l,e,s,t,i)&&!r.includes(l))return 0;return n}isBlockerObject(t,i,e,s,r){if(t.isTerrain()&&r&&t.rules.getOccupationBits(this.theaterType)!==is.All)return!1;if(t.isBuilding()){if(t.rules.invisibleInGame)return!1;if(t.isDestroyed&&t.rules.leaveRubble)return!1;if(t.rules.gate)return!1;var a=t.art.foundation;let e=t.rules.numberImpassableRows;return r?e=a.width:t.rules.weaponsFactory&&!e&&(e=a.width-1),Dr({x:t.tile.rx,y:t.tile.ry,width:(e||a.width)-1,height:a.height-1},{x:i.rx,y:i.ry})}return!(t.isAircraft()||t.isInfantry()||t.isVehicle()||t.isSmudge()||t.isOverlay()&&(e&&t.isBridge()||!e&&t.isHighBridge()||t.isTiberium()||t.rules.crate||t.isBridgePlaceholder())||[ti.Track,ti.Hover].includes(s)&&t.rules.crushable)}findObstacles(t,e){var i,s,r=e.rules.speedType,a=e.isInfantry();let n=[];for(i of this.tileOccupation.getGroundObjectsOnTile(t.tile))i!==e&&(((s=this.isBlockerObject(i,t.tile,!!t.onBridge,r,a))||i.isUnit()&&(i.tile===t.tile&&i.onBridge===!!t.onBridge||i.moveTrait.reservedPathNodes.find(e=>e.tile===t.tile&&!!e.onBridge==!!t.onBridge))||[ti.Track,ti.Hover].includes(r)&&i.rules.crushable||a&&i.isTerrain()||i.isBuilding()&&i.rules.gate)&&(s={obj:i,static:s},i.isInfantry()&&a?i.position.desiredSubCell===e.position.desiredSubCell&&n.push(s):i.isTerrain()&&a&&!i.rules.getOccupiedSubCells(this.theaterType).includes(e.position.desiredSubCell)||n.push(s)));return n}dispose(){this.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate),this.mapBounds.onLocalResize.unsubscribe(this.handleMapBoundsResize)}}class yl{constructor(){this.mapCutoffHeight=0,this.mapBuildableSize={x:0,y:0,width:0,height:0},this.localSize={x:0,y:0,width:0,height:0},this.fullSize={width:0,height:0},this.clampedFullSize={x:0,y:0,width:0,height:0},this.rawLocalSize={x:0,y:0,width:0,height:0},this._onLocalResize=new wo}get onLocalResize(){return this._onLocalResize.asEvent()}fromMapFile(e,t){this.fullSize={width:2*e.fullSize.width,height:2*e.fullSize.height},this.clampedFullSize={x:1,y:2,width:2*(e.fullSize.width-1)-1/_s.ISO_TILE_SIZE,height:2*(e.fullSize.height-1)+1-1/_s.ISO_TILE_SIZE},this.mapCutoffHeight=Math.max(9,t.getCutoffTileHeight());t=Math.max(2,e.localSize.x),e={x:t,y:e.localSize.y,width:Math.min(e.fullSize.width-2-t,e.localSize.width),height:e.localSize.height};return this.updateRawLocalSize(e),this}updateRawLocalSize(e){var t,i;this.rawLocalSize.width&&this.rawLocalSize.height&&!function(e,t){let i=new Pr.Box2(new Pr.Vector2(e.x,e.y),new Pr.Vector2(e.x+e.width,e.y+e.height));return t=new Pr.Box2(new Pr.Vector2(t.x,t.y),new Pr.Vector2(t.x+t.width,t.y+t.height)),i.containsBox(t)}(e,this.rawLocalSize)?console.warn("New map limits must be outside old limits. Skipping."):(t=e,i=this.rawLocalSize,t.x===i.x&&t.y===i.y&&t.width===i.width&&t.height===i.height||(this.localSize=this.computeLocalSize(e,this.fullSize.height/2,this.mapCutoffHeight),this.rawLocalSize={...e},this.mapBuildableSize={x:this.localSize.x,y:this.localSize.y+4,width:this.localSize.width-2,height:this.localSize.height-8},this._onLocalResize.dispatch(this)))}computeLocalSize(e,t,i){return{x:2*e.x,y:2*e.y-4,height:Math.min(2*(e.height+5)-1,2*t-2*(e.y-3)-i),width:2*e.width}}getLocalSize(){return this.localSize}getRawLocalSize(){return this.rawLocalSize}getFullSize(){return this.fullSize}getClampedFullSize(){return this.clampedFullSize}isWithinBounds(e){return Dr(this.mapBuildableSize,{x:e.dx,y:e.dy-e.z})}clampWithinBounds(e){let{x:t,y:i}=function(e,t){let i=new Pr.Box2(new Pr.Vector2(e.x,e.y),new Pr.Vector2(e.x+e.width,e.y+e.height));return i.clampPoint(new Pr.Vector2(t.x,t.y),new Pr.Vector2)}(this.mapBuildableSize,{x:e.dx,y:e.dy-e.z});return i+=t%2-i%2,i>this.mapBuildableSize.y+this.mapBuildableSize.height&&(i-=2),{dx:t,dy:i}}isWithinHardBounds(e){var t=e.x/_s.LEPTONS_PER_TILE,i=(e.z??e.y)/_s.LEPTONS_PER_TILE,e=t-i+this.fullSize.width/2-1,i=t+i-this.fullSize.width/2-1;return Dr(this.clampedFullSize,{x:++e,y:++i})}}class wl{constructor(e,t,i,s,r,a,n,o=()=>!0,h=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=r,this.dirX=a,this.dirY=n,this.predicate=o,this.checkBounds=h,this.finished=!1,this.distance=s}getNextTile(){if(!this.finished){let t;do{let e={x:this.startTile.rx,y:this.startTile.ry};e.x+=this.distance*Math.sign(this.dirX),e.y+=this.distance*Math.sign(this.dirY);var i=this.tiles.getByMapCoords(e.x,e.y);if(i&&(!this.checkBounds||this.mapBounds.isWithinBounds(i))&&this.predicate(i)&&(t=i),this.maxDistance&&this.distance>=this.maxDistance)return this.finished=!0,t}while(this.distance++,!t);return t}}}class Tl{constructor(e,t,i,s,r,a=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.areConnected=s,this.predicate=r,this.checkBounds=a,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){let e=[this.startTile],t=new Set;for(;e.length;){var i,s=e.pop();if(!t.has(s)){t.add(s),this.checkBounds&&!this.mapBounds.isWithinBounds(s)||!this.predicate(s)||(yield s);for(i of this.tiles.getAllNeighbourTiles(s))this.areConnected(i,s)&&e.push(i)}}}}(r=zn=zn||{})[r.None=0]="None",r[r.Start=1]="Start",r[r.End=2]="End";class bl{constructor(e,t,i,s,r){this.tileSets=e,this.tiles=t,this.tileOccupation=i,this.mapBounds=s,this.rules=r,this.pieces=new Set,this.piecesByTile=new Map,this.handleTileOccupationUpdate=({object:t,type:i})=>{if(t.isOverlay()&&t.isBridge()){var s=t.tile;let e=this.piecesByTile.get(s);if("added"===i){if(e)throw new Error(`A bridge piece already exists at tile (${s.rx},${s.ry})`);var r=this.findBridgeAdjacentTiles(t);e={obj:t,prev:void 0,next:void 0,headType:this.computeHead(t,r.prev,r.next)},this.piecesByTile.set(s,e),this.pieces.add(e),this.connectPiece(e,r.prev,r.next),this.updateOverlayData(e),e.prev&&this.updateOverlayData(e.prev),e.next&&this.updateOverlayData(e.next)}else{if(!e)throw new Error(`Bridge piece was alredy removed at tile (${s.rx},${s.ry})`);t=e.prev,r=e.next;this.disconnectPiece(e),this.piecesByTile.delete(s),this.pieces.delete(e),t&&this.updateOverlayData(t),r&&this.updateOverlayData(r)}}},i.onChange.subscribe(this.handleTileOccupationUpdate)}getPieceAtTile(e){return this.piecesByTile.get(e)}handlePieceHealthChange(e){this.updateOverlayData(e),e.prev&&this.updateOverlayData(e.prev),e.next&&this.updateOverlayData(e.next)}findDominoPieces(t){let i=[],s=!1,e=t.next;if(t.headType===zn.None||e)for(;e;){if(i.push(e),e.headType!==zn.None){s=!0;break}e=e.next}else s=!0;if(s){s=!1,i.length=0;let e=t.prev;if(t.headType===zn.None||e)for(;e;){if(i.push(e),e.headType!==zn.None){s=!0;break}e=e.prev}else s=!0;if(s)return[]}return i}findBridgeAdjacentTiles(e){var t=e.isXBridge(),t=new Os(Number(t),Number(!t));let i=new Os(e.tile.rx,e.tile.ry);e=i.clone().sub(t),e=this.tiles.getByMapCoords(e.x,e.y),t=i.clone().add(t);return{prev:e,next:this.tiles.getByMapCoords(t.x,t.y)}}connectPiece(e,t,i){t&&(e.prev=this.getPieceAtTile(t),e.prev&&(e.prev.next=e)),i&&(e.next=this.getPieceAtTile(i),e.next&&(e.next.prev=e))}disconnectPiece(e){e.next&&(e.next.prev=void 0,e.next=void 0),e.prev&&(e.prev.next=void 0,e.prev=void 0)}computeHead(e,t,i){var s=e.tile;if(e.isHighBridge()){s=s.z+e.tileElevation;return t?.z===s?zn.Start:i?.z===s?zn.End:zn.None}return $a.isLowBridgeHead(e.overlayId)?$a.isLowBridgeHeadStart(e.overlayId)?zn.Start:zn.End:zn.None}updateOverlayData(t){let i=t.obj,s=t.prev,r=t.next,a=!1;var n=i.isXBridge(),o=$a.getOverlayBridgeType(i.overlayId);if($a.isLowBridgeHead(i.overlayId)){let e=0;$a.isLowBridgeHeadStart(i.overlayId)?(e=n?20:22,r||e++):(e=n?18:24,s||e++),i.overlayId=(o===ra.Wood?$a.minLowBridgeWoodId:$a.minLowBridgeConcreteId)+e,i.value=e,a=!0}else{let e;var h,l=(i.healthTrait?.health??100)<=50;e=t.headType!==zn.None?t.headType===zn.Start?r?l?6:(r.obj.healthTrait?.health??100)<=50?5:0:n?8:7:s?l?6:(s.obj.healthTrait?.health??100)<=50?4:0:n?7:8:(n||(h=s,s=r,r=h),s||r?s?r?(t=(s.obj.healthTrait?.health??100)<=50,h=(r.obj.healthTrait?.health??100)<=50,l||t&&h?6:t?4:h?5:0):8:7:0),n||(e+=9),i.isHighBridge()?i.value=e:(i.overlayId=(o===ra.Wood?$a.minLowBridgeWoodId:$a.minLowBridgeConcreteId)+e,i.value=e,a=!0)}a&&(i.name=this.rules.getOverlayName(i.overlayId))}findClosestBridgeSpec(i){let e=new Ws(this.tiles,this.mapBounds,i,{width:1,height:1},1,3,e=>{if(e.z!==i.z)return!1;let t=this.tileOccupation.getBridgeOnTile(e);return!(!t?.isLowBridge()||this.getPieceAtTile(t.tile)?.headType===zn.None)||!!this.tileSets.isHighBridgeBoundaryTile(e.tileNum)},!1);var o=e.getNextTile();if(o){let s,t,r,a;var h=!this.tileOccupation.getBridgeOnTile(o);let e;if(h){var l=this.findHighBridgeBoundary(o);if(!l)return;s=l.tile,t=ra.Concrete,this.tileSets.getSetNum(o.tileNum)===this.tileSets.getGeneralValue("WoodBridgeSet")&&(t=ra.Wood),r=l.headType===O.TopLeft||l.headType===O.BottomRight,a=l.headType===O.TopLeft||l.headType===O.TopRight,e=l.headType}else{s=this.tileOccupation.getBridgeOnTile(o).tile;let e=this.getPieceAtTile(s);if(!e)throw new Error("Bridge head is not defined");var c=$a.getOverlayBridgeType(e.obj.overlayId);if(c===ra.NotBridge)throw new Error("Expected a bridge type");t=c,r=e.obj.isXBridge(),a=e.headType===zn.Start}var u=Number(r)*(a?1:-1),d=Number(!r)*(a?1:-1);let n;if(h){o=new wl(this.tiles,this.mapBounds,s,1,100,u,d,e=>e.z===s.z&&this.tileSets.isHighBridgeBoundaryTile(e.tileNum),!1).getNextTile(),c=this.tileSets.getSetNum(s.tileNum);if(!o||this.tileSets.getSetNum(o.tileNum)!==c)return;o=this.findHighBridgeBoundary(o);if(!o)return;if(e!==this.tileSets.getOppositeHighBridgeHeadType(o.headType))return;n=o.tile}else{let t,i=1;for(var g=s.rx,p=s.ry;!t;){var m=this.tiles.getByMapCoords(g+u*i,p+d*i);if(!m)return;let e=this.getPieceAtTile(m);if(e&&e.obj.isXBridge()!==r)return;e?.headType===(a?zn.End:zn.Start)&&(t=e),i++}n=t.obj.tile}return{start:a?s:n,end:a?n:s,type:t,isHigh:h}}}findHighBridgeBoundary(r){var a,e=this.tileSets.getTile(r.tileNum),n=this.tileSets.getHighBridgeHeadType(e.index);if(void 0!==n){let i=0,s=0;switch(n){case O.TopLeft:i=1,s=0;break;case O.BottomRight:i=-1,s=0;break;case O.TopRight:i=0,s=1;break;case O.BottomLeft:i=0,s=-1;break;case O.MiddleTlBr:i=1,s=0;break;case O.MiddleTrBl:i=0,s=1;break;default:throw new Error(`Unhandled head type "${n}"`)}let e=new Tl(this.tiles,this.mapBounds,r,e=>e.tileNum===r.tileNum,e=>e.terrainType===Jt.Pavement&&e.z>=r.z,!1),t=[];for(;a=e.getNextTile();)t.push(a);if(t.sort((e,t)=>100*(i?i*(t.rx-e.rx):s*(t.ry-e.ry))+(i?e.ry-t.ry:e.rx-t.rx)),t.length)return{tile:t[0],headType:n}}else console.warn(`Couldn't find a valid bridge type for index "${e.index}" @ ${r.rx},${r.ry}`)}canBeRepaired(i){let e=this.createBridgePieceTileFinder(i,e=>!(this.getPieceAtTile(e)||this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===i.start.z)),s=!1,r;for(var a=i.start.rx!==i.end.rx?oa.BottomLeft:oa.BottomRight;r=e.getNextTile();){s=!0;let e=this.tiles.getNeighbourTile(r,a),t=this.tiles.getNeighbourTile(e,a);if(i.isHigh){if([r,e,t].find(e=>this.tileOccupation.getGroundObjectsOnTile(e).some(e=>e.isBuilding()&&!e.rules.invisibleInGame)))return!1}else if([r,e,t].find(e=>this.tileOccupation.getGroundObjectsOnTile(e).some(e=>!(e.isUnit()||e.isSmudge()||e.isOverlay()&&e.isBridgePlaceholder()))))return!1}return s}getPieceTiles(e){var t=e.obj.tile,i=e.obj.isXBridge()?oa.BottomLeft:oa.BottomRight,e=this.tiles.getNeighbourTile(t,i);return[t,e,this.tiles.getNeighbourTile(e,i)]}findMapHighBridgeHeadTiles(){var e,t=this.tiles.getAllBridgeSetTiles();let i=new Set;for(e of t){var s=this.findHighBridgeBoundary(e);s&&i.add(s.tile)}return i}findBridgeSpecsForHeadTiles(e){let t=new Map;for(var i of e){i=this.findClosestBridgeSpec(i);i&&t.set(i.start.id+":"+i.end.id,i)}return[...t.values()]}findAllBridgeTiles(e){let t=[];var i,s=e.start.rx!==e.end.rx?oa.BottomLeft:oa.BottomRight;for(i of this.findNonBuildablePieceTiles(e)){var r=this.tiles.getNeighbourTile(i,s),a=this.tiles.getNeighbourTile(r,s);t.push(i,r,a)}return t}findBridgePieces(e){let t=this.createBridgePieceTileFinder(e,e=>!!this.getPieceAtTile(e)),i=[];for(var s;s=t.getNextTile();)i.push(this.getPieceAtTile(s));return i}findDestroyedPieceTiles(t){let e=this.createBridgePieceTileFinder(t,e=>!(this.getPieceAtTile(e)||this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===t.start.z)),i=[];for(var s;s=e.getNextTile();)i.push(s);return i}findNonBuildablePieceTiles(t){let e=this.createBridgePieceTileFinder(t,e=>!(this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===t.start.z)),i=[];for(var s;s=e.getNextTile();)i.push(s);return i}createBridgePieceTileFinder(e,t){var i=e.start.rx!==e.end.rx;return new wl(this.tiles,this.mapBounds,e.start,1,(i?e.end.rx-e.start.rx:e.end.ry-e.start.ry)-1,Number(i),Number(!i),t,!1)}dispose(){this.pieces.forEach(e=>{e.prev=void 0,e.next=void 0}),this.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate)}}const vl=new(__webpack_require__(949).Vector2);class Sl{constructor(e,t){this.box=e,this.config=t,this.parentMap=new Map,this.objects=[]}add(e,t=!0){var i=this.config.getKey(e);if(this.box.containsPoint(i)){if(!this.regions)return this.parentMap.get(e)?.remove(e),this.parentMap.set(e,this),this.objects.push({key:i,value:e}),t&&this.update(),!0;for(var s of this.regions)if(s.add(e,t))return!0}return!1}remove(t,e=!0){let i=this.parentMap.get(t);i&&(i===this?(this.parentMap.delete(t),this.objects.splice(this.objects.findIndex(e=>e.value===t),1),e&&this.parent?.update()):i.remove(t,e))}updateObject(t){let i=this.parentMap.get(t);if(i){var e=this.config.getKey(t);if(i.box.containsPoint(e))i.objects.find(e=>e.value===t).key=e;else{i.remove(t,!1);let e=i.parent;for(;e&&!e.add(t,!1);)e=e.parent}}}queryRange(e,t=[]){if(this.box.intersectsBox(e))if(this.regions)for(var i of this.regions)i.queryRange(e,t);else for(var s of this.objects)e.containsPoint(s.key)&&t.push(s.value);return t}update(){let e=0;if(this.regions){for(var t of this.regions)e+=t.update();e<=this.config.joinThreshold&&this.join()}else e=this.objects.length,e>=this.config.splitThreshold&&this.split()&&this.update();return e}split(){if(this.regions||this.config.maxDepth<=1)return!1;var t,e,i={getKey:this.config.getKey,joinThreshold:this.config.joinThreshold,splitThreshold:this.config.splitThreshold,maxDepth:this.config.maxDepth-1},s=this.generateRegions(),r=this.objects;this.objects=[],this.regions=[];for(t of s){let e=new Sl(t,i);e.parentMap=this.parentMap,this.regions.push(e),e.parent=this}for(e of r)this.parentMap.delete(e.value),this.add(e.value,!1);return!0}join(){if(!this.regions)return!1;for(var e of this.regions){e.join(),e.parent=void 0;for(var t of e.objects)this.objects.push(t),this.parentMap.set(t.value,this)}return!(this.regions=void 0)}generateRegions(){let i=[this.box.clone()];var s=this.box.getCenter(vl);let r=i[0],a=r.clone();r.max.x=s.x,a.min.x=s.x,i.push(a);for(let e=0,t=i.length;e<t;e++)r=i[e],a=r.clone(),r.max.y=s.y,a.min.y=s.y,i.push(a);return i}}class kl{constructor(e){this.tiles=e,this.tileOcclusion=[];let t=this.tileOcclusion;for(var i of e.getAll())t[i.rx]=t[i.rx]||[],t[i.rx][i.ry]=new Set}addOccluder(t){let e=this.calculateTilesForGameObject(t);e.forEach(e=>this.occludeTile(e,t))}removeOccluder(t){let e=this.calculateTilesForGameObject(t);e.forEach(e=>this.unoccludeTile(e,t))}calculateTilesForGameObject(e){var t=e.art.occupyHeight,i=Math.max(0,t-2);let s=[];var r=e.getFoundation();for(let t=1;t<=i;t++)for(let e=0;e<r.width;e++)s.push(new Os(e-t,-t));for(let t=1;t<=i;t++)for(let e=1;e<r.height;e++)s.push(new Os(-t,e-t));s.push(...e.art.addOccupy);for(let{x:t,y:i}of e.art.removeOccupy){var a=s.findIndex(e=>e.x===t&&e.y===i);-1!==a&&s.splice(a,1)}var n,o,h=e.tile;let l=[];for({x:n,y:o}of s){var c=this.tiles.getByMapCoords(h.rx+n,h.ry+o);c&&l.push(c)}return l}occludeTile(e,t){this.tileOcclusion[e.rx][e.ry].add(t),e.occluded=!0}unoccludeTile(e,t){let i=this.tileOcclusion[e.rx][e.ry];i.delete(t),e.occluded=0<i.size}isTileOccluded(e){return 0<this.tileOcclusion[e.rx][e.ry].size}}class Ol{static calculate(u,d){let g=new Map;u.forEach(e=>{var t=d.getSetNum(e.tileNum);g.set(e,t),d.isCLAT(t)&&(t=d.getLAT(t),g.set(e,t),e.tileNum=d.getTileNumFromSet(t))}),u.forEach(t=>{var i=g.get(t);if(d.isLAT(i)){let e=0;var s=u.getNeighbourTile(t,oa.TopRight),r=u.getNeighbourTile(t,oa.BottomRight),a=u.getNeighbourTile(t,oa.BottomLeft),n=u.getNeighbourTile(t,oa.TopLeft);s&&d.canConnectTiles(i,g.get(s))&&(e+=1),r&&d.canConnectTiles(i,g.get(r))&&(e+=2),a&&d.canConnectTiles(i,g.get(a))&&(e+=4),n&&d.canConnectTiles(i,g.get(n))&&(e+=8),0<e&&(n=d.getCLATSet(i),t.tileNum=d.getTileNumFromSet(n,e))}else if(i===d.getGeneralValue("RampBase")&&!(t.rampType<1||4<t.terrainType)){let e=-1;var o=u.getNeighbourTile(t,oa.TopRight),h=u.getNeighbourTile(t,oa.BottomRight),l=u.getNeighbourTile(t,oa.BottomLeft),c=u.getNeighbourTile(t,oa.TopLeft);switch(t.rampType){case 1:c&&0===c.rampType&&e++,h&&0===h.rampType&&(e+=2);break;case 2:o&&0===o.rampType&&e++,l&&0===l.rampType&&(e+=2);break;case 3:h&&0===h.rampType&&e++,c&&0===c.rampType&&(e+=2);break;case 4:l&&0===l.rampType&&e++,o&&0===o.rampType&&(e+=2)}-1!==e&&(t.tileNum=d.getTileNumFromSet(d.getGeneralValue("RampSmooth"),3*(t.rampType-1)+e))}})}}class _l{get startingLocations(){return this.mapFile.startingLocations}constructor(e,t,i,s){this.mapFile=e,this.tiles=new Xa(this.mapFile.tiles,t,i.general,s),this.mapBounds=(new yl).fromMapFile(this.mapFile,this.tiles),this.tileOccupation=new Do(this.tiles),this.tileOcclusion=new kl(this.tiles),this.terrain=new fl(this.tiles,this.mapFile.theaterType,this.mapBounds,this.tileOccupation,i),this.bridges=new bl(t,this.tiles,this.tileOccupation,this.mapBounds,i);let r=this.mapFile.tags;for(let t of this.mapFile.cellTags){let e=this.tiles.getByMapCoords(t.coords.x,t.coords.y);e&&(e.tag=r.find(e=>e.id===t.tagId))}s=this.tiles.getMapSize(),i=Math.max(s.width,s.height)/5;this.technosByTile=new Sl(new Yn(new Os(0,0),new Os(s.width,s.height)),{getKey:e=>{e=e.isBuilding()?e.centerTile:e.tile;return new Os(e.rx,e.ry)},maxDepth:this.computeQuadDepth(i),splitThreshold:10,joinThreshold:5}),this.mapFile.theaterType!==I.Snow&&Ol.calculate(this.tiles,t)}computeQuadDepth(e){if(e<=1)return 1;let t=0;for(;1<=e/2;)e/=2,t++;return t+(1<e?1:0)}getLighting(){return this.mapFile.lighting}getIonLighting(){return this.mapFile.ionLighting}getTheaterType(){return this.mapFile.theaterType}getTags(){return this.mapFile.tags}getTriggers(){return this.mapFile.triggers}getCellTags(){return this.mapFile.cellTags}getVariables(){return this.mapFile.variables}getWaypoint(t){return this.mapFile.waypoints.find(e=>e.number===t)}getTileAtWaypoint(e){e=this.getWaypoint(e);if(e){e=this.tiles.getByMapCoords(e.rx,e.ry);if(e)return e}}isWithinBounds(e){return this.mapBounds.isWithinBounds(e)}clampWithinBounds(e){var t=this.mapBounds.clampWithinBounds(e);let i=this.tiles.getByDisplayCoords(t.dx,t.dy);if(i&&this.mapBounds.isWithinBounds(i)){let e=i,t=i.z;for(;0<=t&&e&&this.mapBounds.isWithinBounds(e);)i=e,e=this.tiles.getByDisplayCoords(e.dx,e.dy+2),t-=2}else{let e=0;for(;!i||!this.mapBounds.isWithinBounds(i);){if(30<e)throw new Error("Exceeded max elevation while trying to clamp tile to map bounds");i=this.tiles.getByDisplayCoords(t.dx,t.dy+e),e+=2}}return i}isWithinHardBounds(e){return this.mapBounds.isWithinHardBounds(e)}getInitialMapObjects(){return{terrains:this.mapFile.terrains,overlays:this.mapFile.overlays,smudges:this.mapFile.smudges,technos:[...this.mapFile.structures,...this.mapFile.infantries,...this.mapFile.vehicles,...this.mapFile.aircrafts]}}getObjectsOnTile(e){return this.tileOccupation.getObjectsOnTile(e)}getGroundObjectsOnTile(e){return this.tileOccupation.getGroundObjectsOnTile(e)}getTileZone(e,t=!1){return this.tileOccupation.getTileZone(e,t)}dispose(){this.terrain.dispose(),this.bridges.dispose()}}class Il{constructor(e,t){this.first=e,this.second=t}has(e){return this.first===e||this.second===e}equals(e){return this.first===e.first&&this.second===e.second||this.first===e.second&&this.second===e.first}}(r=Vn=Vn||{})[r.Requested=0]="Requested",r[r.Formed=1]="Formed";class Cl{constructor(e){this.playerList=e,this.alliances=[]}findByPlayers(e,t){let i=new Il(e,t);return this.alliances.find(e=>e.players.equals(i))}filterByPlayer(t){return this.alliances.filter(e=>e.players.first===t||e.players.second===t)}request(e,t){if(!this.canRequestAlliance(t))throw new Error(`Player ${t.name} is not a human combatant.`);if(this.canFormAlliance(e,t)){if(this.findByPlayers(e,t))throw new Error("Can't request alliance because an alliance is already pending or formed between "+`${e.name} and ${t.name}.`);return this.setAlliance(e,t,Vn.Requested)}}cancelRequest(e,t){var i=this.findByPlayers(e,t);if(!i||i.status!==Vn.Requested)throw new Error(`There is no pending alliance request for player ${t.name} from player ${e.name}`);if(i.players.first!==e)throw new Error(`Can't cancel request initiated by the other player (${t.name})`);this.alliances.splice(this.alliances.indexOf(i),1)}acceptRequest(t,i){if(this.canFormAlliance(t,i)){let e=this.findByPlayers(t,i);if(!e||e.status!==Vn.Requested)throw new Error(`There is no pending alliance request for player ${i.name} from player ${t.name}`);if(e.players.first!==t)throw new Error(`Can't accept own alliance request for player ${i.name}`);e.status=Vn.Formed}}setAlliance(e,t,i){if(!this.canFormAlliance(e,t))throw new Error(`Can't form alliance between players "${e.name}" and "${t.name}"`);var s;if(s=this.findByPlayers(e,t))throw new Error(`An alliance already exists between players ${e.name} and ${t.name}`);return s={players:new Il(e,t),status:i},this.alliances.push(s),s}breakAlliance(e,t){var i=this.findByPlayers(e,t);if(!i||i.status!==Vn.Formed)throw new Error(`There is no alliance between player ${e.name} and player ${t.name}`);this.alliances.splice(this.alliances.indexOf(i),1)}areAllied(e,t){t=this.findByPlayers(e,t);return!!t&&t.status===Vn.Formed}getAllies(t){return this.filterByPlayer(t).filter(e=>e.status===Vn.Formed).map(e=>e.players.first===t?e.players.second:e.players.first)}haveSharedIntel(e,t){return e.isObserver||t.isObserver||e===t||this.areAllied(e,t)}canRequestAlliance(e){return e.isCombatant()&&!e.isAi}canFormAlliance(t,i){let e=this.getHostilePlayers();if(0===e.filter(e=>e.has(t)&&!e.has(i)).length)return!1;if(0===e.filter(e=>e.has(i)&&!e.has(t)).length)return!1;let s=new Il(t,i);return!!e.filter(e=>!e.equals(s)).length}getHostilePlayers(){var i,s=this.playerList.getCombatants();let r=[];for(let t=0;t<s.length;t++)for(let e=t+1;e<s.length;e++)this.getAllies(s[t]).includes(s[e])||(i=new Il(s[t],s[e]),r.push(i));return r}getHash(){return G(this.alliances.map(e=>[this.playerList.getPlayerNumber(e.players.first),this.playerList.getPlayerNumber(e.players.second),e.status]).flat())}debugGetState(){return this.alliances.map(e=>({first:e.players.first,second:e.players.second,status:e.status}))}}class Al{constructor(){this.players=[]}addPlayer(e){this.players.push(e)}getPlayerAt(e){if(e>=this.players.length)throw new RangeError(`Player #${e} out of bounds`);return this.players[e]}getPlayerByName(t){var e=this.players.find(e=>e.name===t);if(!e)throw new Error(`Player with name "${t}" not found`);return e}getPlayerNumber(e){var t=this.players.indexOf(e);if(-1===t)throw new Error(`Player ${e.name} not found`);return t}getCombatants(){return this.players.filter(e=>e.isCombatant())}getNonNeutral(){return this.players.filter(e=>!e.isNeutral)}getCivilian(){return this.players.find(e=>e.country?.side===Qt.Civilian)}getAll(){return this.players}}(r=Hn=Hn||{})[r.None=0]="None",r[r.Hover=1]="Hover",r[r.Selected=2]="Selected",r[r.SelectedHover=3]="SelectedHover";class Bl{constructor(e){this.selectionLevel=Hn.None,e.isBuilding()&&e.rules.wall?this.maxSelectionLevel=Hn.None:this.maxSelectionLevel=e.rules.selectable?Hn.Selected|Hn.Hover:Hn.Hover}getSelectionLevel(){return this.selectionLevel}setSelectionLevel(e){this.selectionLevel=Math.min(this.maxSelectionLevel,e)}setHover(e){this.setSelectionLevel(e?this.selectionLevel|Hn.Hover:this.selectionLevel&~Hn.Hover)}setSelected(e){this.setSelectionLevel(e?this.selectionLevel|Hn.Selected:this.selectionLevel&~Hn.Selected)}isHovered(){return this.selectionLevel>>Hn.Hover&1}isSelected(){return this.selectionLevel>=Hn.Selected}getControlGroupNumber(){return this.controlGroupNumber}setControlGroupNumber(e){this.controlGroupNumber=e}}class xl{constructor(){this.selectedUnits=new Set,this.selectionModelsByUnit=new Map,this.groups=new Map,this.hashNeedsUpdate=!0}getOrCreateSelectionModel(e){let t=this.selectionModelsByUnit.get(e);return t||(t=new Bl(e),this.selectionModelsByUnit.set(e,t)),t}deselectAll(){this.selectedUnits.forEach(e=>this.selectionModelsByUnit.get(e)?.setSelected(!1)),this.selectedUnits.clear(),this.hashNeedsUpdate=!0}addToSelection(e){this.selectedUnits.add(e),this.getOrCreateSelectionModel(e).setSelected(!0),this.hashNeedsUpdate=!0}removeFromSelection(e){e.forEach(e=>{this.selectedUnits.delete(e),this.getOrCreateSelectionModel(e).setSelected(!1)}),this.hashNeedsUpdate=!0}getSelectedUnits(){return[...this.selectedUnits].filter(e=>!e.isDestroyed&&!e.isCrashing&&!e.isDisposed&&e.isSpawned)}isSelected(e){return this.selectedUnits.has(e)}cleanupUnit(e){this.selectionModelsByUnit.delete(e),this.selectedUnits.delete(e),this.removeUnitsFromGroup([e]),this.hashNeedsUpdate=!0}updateHash(){this.hash=G([...this.selectedUnits].map(e=>e.id))}getHash(){return this.hashNeedsUpdate&&(this.updateHash(),this.hashNeedsUpdate=!1),this.hash}createGroup(e){this.addUnitsToGroup(e,this.getSelectedUnits())}addUnitsToGroup(e,t,i=!0){this.removeUnitsFromGroup(t);let s=this.groups.get(e);s||(s=new Set,this.groups.set(e,s)),i&&([...s.values()].forEach(e=>this.selectionModelsByUnit.get(e)?.setControlGroupNumber(void 0)),s.clear());for(var r of t)s.add(r),this.getOrCreateSelectionModel(r).setControlGroupNumber(e)}addGroupToSelection(e){if(this.groups.has(e))for(var t of[...this.groups.get(e)])this.addToSelection(t)}selectGroup(e){this.deselectAll(),this.addGroupToSelection(e)}getGroupUnits(e){return[...this.groups.get(e)??[]]}removeUnitsFromGroup(e){for(var t of this.groups.values())for(var i of e)t.delete(i),this.selectionModelsByUnit.get(i)?.setControlGroupNumber(void 0)}}class El{constructor(e){this._onChange=new wo,this.value=e}get value(){return this._value}set value(e){var t=e!==this._value;this._value=e,t&&this._onChange.dispatch(this,e)}get onChange(){return this._onChange.asEvent()}}class Pl{get credits(){return this._credits}set credits(e){if(e<0)throw new RangeError("Can't set credits to a negative value");this._credits=e}constructor(e,t=void 0,i,s=new W(255,0,0)){this.name=e,this.country=t,this.startLocation=i,this.color=s,this.isAi=!1,this.defeated=!1,this.resigned=!1,this.dropped=!1,this.objectsByType=new Map,this.objectsById=new Map,this.traits=new xa,this._credits=0,this.score=0,this.limitedUnitsBuiltByName=new Map,this.unitsBuiltByType=new Map,this.unitsKilledByType=new Map,this.unitsLostByType=new Map,this.buildingsCaptured=0,this.cratesPickedUp=0,this.creditsGained=0,this.cheerCooldownTicks=0,this.isObserver=!t,this.isNeutral=!!t&&!t.isPlayable()}getOrCreateObjectsForType(e){let t=this.objectsByType.get(e);return t||(t=new Set,this.objectsByType.set(e,t)),t}addOwnedObject(e){let t=this.getOrCreateObjectsForType(e.type);t.add(e),(e.owner=this).objectsById.set(e.id,e)}removeOwnedObject(e){let t=this.objectsByType.get(e.type);if(!t||!t.has(e))throw new Error(`GameObject ${e.name} does not belong to player ${this.name}`);t.delete(e),this.objectsById.delete(e.id)}getOwnedObjectById(e){return this.objectsById.get(e)}getOwnedObjectsByType(e,t=!1){let i=[];return i=[...this.objectsByType.get(e)||new Set],t||(i=i.filter(e=>!e.limboData)),i}getOwnedObjects(e=!1){let t=[];return[...this.objectsByType.values()].forEach(e=>{e.forEach(e=>t.push(e))}),e||(t=t.filter(e=>!e.limboData)),t}removeAllOwnedObjects(){this.objectsByType.forEach(e=>e.clear()),this.objectsById.clear()}get buildings(){return this.getOrCreateObjectsForType(Et.Building)}addUnitsBuilt(e,t){this.unitsBuiltByType.set(e.type,(this.unitsBuiltByType.get(e.type)??0)+t),e.buildLimit<0&&this.limitedUnitsBuiltByName.set(e.name,(this.limitedUnitsBuiltByName.get(e.name)??0)+t)}getUnitsBuilt(e){return void 0!==e?this.unitsBuiltByType.get(e)??0:[...this.unitsBuiltByType.values()].reduce((e,t)=>e+t,0)}getLimitedUnitsBuilt(e){return this.limitedUnitsBuiltByName.get(e)??0}addUnitsKilled(e,t){this.unitsKilledByType.set(e,(this.unitsKilledByType.get(e)??0)+t)}getUnitsKilled(e){return void 0!==e?this.unitsKilledByType.get(e)??0:[...this.unitsKilledByType.values()].reduce((e,t)=>e+t,0)}addUnitsLost(e,t){this.unitsLostByType.set(e,(this.unitsLostByType.get(e)??0)+t)}getUnitsLost(e){return void 0!==e?this.unitsLostByType.get(e)??0:[...this.unitsLostByType.values()].reduce((e,t)=>e+t,0)}isCombatant(){return!this.isNeutral&&!this.isObserver&&!this.defeated}canProduceVeteran(e){if(!this.production||!this.country)throw new Error("Non-combatants can't produce units");var t=this.production.getQueueTypeForObject(e),t=this.production.getFactoryTypeForQueueType(t);return this.production.hasVeteranType(t)||this.country.hasVeteranUnit(e.type,e.name)}getHash(){return G([this.credits,...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{name:this.name,credits:this.credits,traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.traits.dispose(),this.production?.dispose()}}class Nl{constructor(){this.disabled=!0,this.activeEvents=[]}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}}const Dl=(new Map).set("POWER",Kt.Power).set("FACTORY",Kt.Factory).set("BARRACKS",Kt.Barracks).set("RADAR",Kt.Radar).set("TECH",Kt.Tech).set("PROC",Kt.Proc);class Ml{static factory(e,t,i,s){let r=new Ml(e,t.mpDialogSettings.techLevel,i,t,s);t=t.general.maximumQueuedObjects+1;return r.addQueue(wn.Structures,new To(wn.Structures,1,1)),r.addQueue(wn.Armory,new To(wn.Armory,1,1)),r.addQueue(wn.Infantry,new To(wn.Infantry,t,t)),r.addQueue(wn.Vehicles,new To(wn.Vehicles,t,t)),r.addQueue(wn.Ships,new To(wn.Ships,t,t)),r.addQueue(wn.Aircrafts,new To(wn.Aircrafts,0,t)),r}constructor(e,t,i,s,r){this.player=e,this.maxTechLevel=t,this.gameOpts=i,this.rules=s,this.allAvailableObjects=r,this.buildSpeedModifier=1,this.queues=new Map,this._onQueueUpdate=new wo,this.primaryFactories=new Map,this.factoryCounts=new Map,this.veteranTypes=new Set,this.stolenTech=new Set}get onQueueUpdate(){return this._onQueueUpdate.asEvent()}addQueue(e,t){this.queues.set(e,t),t.onUpdate.subscribe(()=>this._onQueueUpdate.dispatch(this,t))}getQueue(e){var t=this.queues.get(e);if(!t)throw new Error(`No queue found with type ${wn[e]}`);return t}getAllQueues(){return[...this.queues.values()]}getQueueTypeForObject(e){if(e.type===Et.Building)return e.buildCat===es.Combat?wn.Armory:wn.Structures;if(e.type===Et.Infantry)return wn.Infantry;if(e.type===Et.Vehicle)return e.naval?wn.Ships:wn.Vehicles;if(e.type===Et.Aircraft)return wn.Aircrafts;throw new Error(`Unsupported object type ${Et[e.type]}`)}getQueueForObject(e){return this.getQueue(this.getQueueTypeForObject(e))}getQueueTypeForFactory(e){if(e===ts.InfantryType)return wn.Infantry;if(e===ts.UnitType)return wn.Vehicles;if(e===ts.AircraftType)return wn.Aircrafts;if(e===ts.NavalUnitType)return wn.Ships;throw new Error(`Unsupported factory type ${ts[e]}`)}getFactoryTypeForQueueType(e){if(e===wn.Structures||e===wn.Armory)return ts.BuildingType;if(e===wn.Infantry)return ts.InfantryType;if(e===wn.Vehicles)return ts.UnitType;if(e===wn.Aircrafts)return ts.AircraftType;if(e===wn.Ships)return ts.NavalUnitType;throw new Error(`Unsupported queue type ${wn[e]}`)}getQueueForFactory(e){return this.getQueue(this.getQueueTypeForFactory(e))}isAvailableForProduction(e){return-1!==e.techLevel&&e.techLevel<=this.maxTechLevel&&!(0===e.buildLimit&&!this.player.isAi)&&!(e.superWeapon&&this.rules.getSuperWeapon(e.superWeapon).disableableFromShell&&!this.gameOpts.superWeapons)&&this.hasFactoryFor(e)&&this.meetsPrerequisites(e)}getAvailableObjects(){return this.allAvailableObjects.filter(e=>this.isAvailableForProduction(e))}hasFactoryFor(i){if(i.owner.length){let t=this.getFactoryTypeFor(i);return!![...this.player.buildings].find(e=>e.factoryTrait?.type===t&&(t!==ts.UnitType||e.rules.naval===i.naval)&&!!e.rules.owner.find(e=>i.owner.includes(e)))}return!0}meetsStolenTech(e){return e.requiresStolenAlliedTech?this.stolenTech.has(Qt.GDI):!e.requiresStolenSovietTech||this.stolenTech.has(Qt.Nod)}getFactoryTypeFor(e){return e.type===Et.Building?ts.BuildingType:e.type===Et.Infantry?ts.InfantryType:e.type===Et.Aircraft?ts.AircraftType:e.naval?ts.NavalUnitType:ts.UnitType}meetsPrerequisites(e){let t=[...this.player.buildings].map(e=>e.name);for(var i of e.prerequisiteOverride)if(i=i.toUpperCase(),t.includes(i))return!0;if(!e.isAvailableTo(this.player.country))return!1;var s;for(s of e.prerequisite)if(s=s.toUpperCase(),Dl.has(s)){var r=Dl.get(s);if(void 0===r)throw new Error(`Unknown prereqName ${s}`);var a,n=this.rules.general.prereqCategories.get(r);if(void 0===n)throw new Error(`Missing prerequisite category ${r} in rules`);let e=!1;for(a of n)if(-1!==t.indexOf(a)){e=!0;break}if(!e)return!1}else if(-1===t.indexOf(s))return!1;return!!this.meetsStolenTech(e)}getPrimaryFactory(e){return this.primaryFactories.get(e)}setPrimaryFactory(e){e.rules.factory&&this.primaryFactories.set(e.rules.factory,e)}isPrimaryFactory(e){return this.getPrimaryFactory(e.rules.factory)===e}incrementFactoryCount(e){this.factoryCounts.set(e,(this.factoryCounts.get(e)??0)+1)}decrementFactoryCount(e){if(!this.factoryCounts.get(e))throw new Error(`Can't decrement factory count ${ts[e]}. Already 0`);this.factoryCounts.set(e,this.factoryCounts.get(e)-1)}getFactoryCount(e){return this.factoryCounts.get(e)??0}crownPrimaryFactoryHeir(t){var e=[...this.player.buildings].find(e=>e.rules.factory===t);e?this.primaryFactories.set(t,e):this.primaryFactories.delete(t)}hasAnyFactory(){return 0<this.primaryFactories.size}addVeteranType(e){this.veteranTypes.add(e)}hasVeteranType(e){return this.veteranTypes.has(e)}addStolenTech(e){this.stolenTech.add(e)}dispose(){this.queues.clear(),this.player=void 0}}class Rl{constructor(){this.superWeapons=new Map}getAll(){return[...this.superWeapons.values()]}add(e){this.superWeapons.set(e.name,e)}has(e){return this.superWeapons.has(e)}get(e){return this.superWeapons.get(e)}remove(e){this.superWeapons.delete(e)}}class Ll{constructor(){this.objects=new Set}add(e){this.objects.add(e)}delete(e){this.objects.delete(e)}has(e){return this.objects.has(e)}dispose(){this.objects.clear()}}class Fl{constructor(e,t,i){this.rules=e,this.gameOpts=t,this.allAvailableObjects=i}createCombatant(e,t,i,s,r,a){let n=new Pl(e,t,i,s);return n.isAi=r,n.aiDifficulty=a,n.powerTrait=new fo(n),n.traits.add(n.powerTrait),n.radarTrait=new Nl,n.traits.add(n.radarTrait),n.superWeaponsTrait=new Rl,n.traits.add(n.superWeaponsTrait),n.production=Ml.factory(n,this.rules,this.gameOpts,this.allAvailableObjects),n.sharedDetectDisguiseTrait=new Ll,n}createObserver(e,t){let i=new Pl(e,void 0,void 0,t.colors.get("LightGrey"));return i.radarTrait=new Nl,i.traits.add(i.radarTrait),i.radarTrait.setDisabled(!1),i}createNeutral(e,t){var i=[...e.countryRules.values()].find(e=>e.side===Qt.Civilian);if(!i)throw new Error("Missing neutral country. No country found in rules with Civilian side");i=new oo(i);let s=new Pl(t,i,void 0,e.colors.get("LightGrey"));return s.powerTrait=new fo(s),s.traits.add(s.powerTrait),s}}(Gn=Gn||{}).onSpawn=Symbol(),($n=$n||{}).onUnspawn=Symbol(),(qn=qn||{}).onChange=Symbol();class jl{[Gn.onSpawn](e,t){e.isTechno()&&e.rules.power&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"add",t)}[$n.onUnspawn](e,t){e.isTechno()&&e.rules.power&&!e.warpedOutTrait.isActive()&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"remove",t)}[Ln.onChange](e,t){e.isTechno()&&e.rules.power&&!e.warpedOutTrait.isActive()&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"update",t)}[qn.onChange](e,t,i){e.rules.power&&!e.warpedOutTrait.isActive()&&(this.isCapturablePower(e,t)||t.powerTrait?.updateFrom(e,"remove",i),this.isCapturablePower(e,e.owner)||e.owner.powerTrait?.updateFrom(e,"add",i))}[Ns.onChange](e,t,i){e.rules.power&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,i?"remove":"add",t)}[Ps.onTick](e){for(var t of e.getCombatants())t.powerTrait.updateBlackout(e)}isCapturablePower(e,t){return 0<e.rules.power&&t.isNeutral&&e.rules.needsEngineer}}class Ul{constructor(e){this.target=e,this.type=rs.ObjectSell}}class Wl{constructor(e,t){this.game=e,this.generalRules=t}sell(t){if(!t.isBuilding()||!t.rules.unsellable){let e=this.computeRefundValue(t);e&&(t.rules.wall&&(e=0),t.traits.filter(vn).forEach(e=>{e[vn.onSell](t,this.game)}),t.isBuilding()?this.game.getConstructionWorker(t.owner).unplace(t,()=>this.afterObjectUnspawned(t,e)):(this.game.unspawnObject(t),this.afterObjectUnspawned(t,e)))}}afterObjectUnspawned(e,t){e.owner.credits+=t,this.game.events.dispatch(new Ul(e)),e.dispose()}computeRefundValue(e){let t=0;return 0<e.rules.soylent?t=e.rules.soylent:e.rules.cost&&(t=e.purchaseValue,e.owner.isAi||(t=Math.floor(t*this.generalRules.refundPercent))),t}computePurchaseValue(e,t){return e.cost}dispose(){this.game=void 0}}class zl{constructor(e,t){this.target=e,this.radarEnabled=t,this.type=rs.RadarOnOff}}class Vl{constructor(e,t,i){this.target=e,this.radarEventType=t,this.tile=i,this.type=rs.RadarEvent}}class Hl{constructor(){this.activeLightningStrikes=new Map}[Gn.onSpawn](e,t){e.isBuilding()&&e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[$n.onUnspawn](e,t){e.isBuilding()&&e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[Rs.onPowerLow](e,t){this.updateRadarForPlayer(e,t)}[Rs.onPowerRestore](e,t){this.updateRadarForPlayer(e,t)}[Rs.onPowerChange](){}[qn.onChange](e,t,i){e.rules.radar&&(this.updateRadarForPlayer(t,i),this.updateRadarForPlayer(e.owner,i))}[Ns.onChange](e,t){e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[Ls.onActivate](e,t,i){if(e===ss.LightningStorm){this.activeLightningStrikes.set(t,(this.activeLightningStrikes.get(t)??0)+1);for(var s of i.getCombatants())s===t||i.alliances.areAllied(s,t)||this.updateRadarForPlayer(s,i)}}[da.onDeactivate](e,t,i){if(e===ss.LightningStorm){e=(this.activeLightningStrikes.get(t)??0)-1;if(0<e?this.activeLightningStrikes.set(t,e):this.activeLightningStrikes.delete(t),e<=0)for(var s of i.getCombatants())this.updateRadarForPlayer(s,i)}}updateRadarForPlayer(i,s){var e,t;i.radarTrait&&(e=i.radarTrait?.isDisabled(),t=![...i.buildings].find(e=>e.rules.radar&&!e.warpedOutTrait.isActive())||i.powerTrait.level===yn.Low||[...this.activeLightningStrikes.entries()].some(([e,t])=>t&&e!==i&&!s.alliances.areAllied(e,i)),i.radarTrait.setDisabled(t),e!==t&&s.events.dispatch(new zl(i,!t)))}[aa.onAttack](e,t,i){e.isTechno()&&(!e.isBuilding()||e.rules.canBeOccupied||e.rules.needsEngineer?e.isVehicle()&&e.harvesterTrait&&this.addEventForPlayer(Yt.HarvesterUnderAttack,e.owner,e.tile,i):this.addEventForPlayer(Yt.BaseUnderAttack,e.owner,e.tile,i))}addEventForPlayer(s,e,r,a){let n=e.radarTrait;if(n){let t=a.rules.general.radar;n.activeEvents=n.activeEvents.filter(e=>a.currentTick-e.startTick<t.getEventDuration(e.type));let i=new Bs(a.map.tileOccupation);!!n.activeEvents.find(e=>e.type===s&&i.isInTileRange(r,e.tile,0,t.getEventSuppresionDistance(e.type)))||(n.activeEvents.push({startTick:a.currentTick,tile:r,type:s}),a.events.dispatch(new Vl(e,s,r)))}}}class Gl{constructor(e){this.target=e,this.type=rs.InsufficientFunds}}class $l{constructor(e,t){this.rules=e,this.speedCheat=t,this.availableObjectRules=new Set;t=60*e.general.buildSpeed*Us.BASE_TICKS_PER_SECOND;this.baseBuildSpeed=1/(t/1e3),[...e.buildingRules.values(),...e.infantryRules.values(),...e.vehicleRules.values(),...e.aircraftRules.values()].forEach(e=>{e.owner.length&&this.availableObjectRules.add(e)})}[Ps.onTick](e){for(var t of e.getCombatants())for(var i of t.production.getAllQueues())this.tickQueue(i,t,e)}[Gn.onSpawn](e,t){var i;e.isBuilding()&&e.owner.production?(i=e.rules.factory)&&(e.owner.production.getPrimaryFactory(i)||e.owner.production.setPrimaryFactory(e),e.owner.production.incrementFactoryCount(i),i===ts.AircraftType&&this.updateAircraftQueueMaxSize(e.owner,t)):e.isAircraft()&&e.owner.production&&this.rules.general.padAircraft.includes(e.name)&&this.updateAircraftQueueMaxSize(e.owner,t)}[$n.onUnspawn](e,t){var i;e.isBuilding()&&e.owner.production?(this.ensurePrerequisites(e.owner),(i=e.rules.factory)&&(e.owner.production.getPrimaryFactory(i)===e&&e.owner.production.crownPrimaryFactoryHeir(i),e.owner.production.decrementFactoryCount(i),i===ts.AircraftType&&this.updateAircraftQueueMaxSize(e.owner,t))):e.isAircraft()&&e.owner.production&&this.rules.general.padAircraft.includes(e.name)&&this.updateAircraftQueueMaxSize(e.owner,t)}[qn.onChange](e,t,i){var s;e.isBuilding()?(this.ensurePrerequisites(t),(s=e.rules.factory)&&(t.production?.getPrimaryFactory(s)===e&&t.production.crownPrimaryFactoryHeir(s),e.owner.production&&!e.owner.production.getPrimaryFactory(s)&&e.owner.production.setPrimaryFactory(e),t.production?.decrementFactoryCount(s),e.owner.production?.incrementFactoryCount(s),s===ts.AircraftType&&(this.updateAircraftQueueMaxSize(e.owner,i),this.updateAircraftQueueMaxSize(t,i)))):e.isAircraft()&&this.rules.general.padAircraft.includes(e.name)&&(this.updateAircraftQueueMaxSize(e.owner,i),this.updateAircraftQueueMaxSize(t,i))}[Rs.onPowerLow](e){e.production&&(e.production.buildSpeedModifier=this.computeLowPowerBuildSpeedModifier(e.powerTrait.power,e.powerTrait.drain))}[Rs.onPowerRestore](e){e.production&&(e.production.buildSpeedModifier=1)}[Rs.onPowerChange](e){e.powerTrait?.level===yn.Low&&e.production&&(e.production.buildSpeedModifier=this.computeLowPowerBuildSpeedModifier(e.powerTrait.power,e.powerTrait.drain))}computeLowPowerBuildSpeedModifier(e,t){e=1-Math.min(1,e/t),t=this.rules.general;return z(1-.3*t.lowPowerPenaltyModifier*e/.15,t.minLowPowerProductionSpeed,t.maxLowPowerProductionSpeed)}updateAircraftQueueMaxSize(i,s){i.production&&s.afterTick(()=>{var e=[...i.buildings].filter(e=>e.helipadTrait).reduce((e,t)=>e+t.dockTrait.numberOfDocks,0),t=i.getOwnedObjectsByType(Et.Aircraft,!0).filter(e=>s.rules.general.padAircraft.includes(e.name)).length;i.production.getQueueForFactory(ts.AircraftType).maxSize=Math.max(0,e-t)})}tickQueue(i,s,r){if(i.status===Tn.Active){let e=!1,t=i.getFirst();var a,n=s.production.getFactoryTypeForQueueType(i.type),o=s.production.getFactoryCount(n),h=s.production.buildSpeedModifier,n=1/Ki.pow(this.rules.general.multipleFactory,o-1),o=t.rules.wall?1/this.rules.general.wallBuildSpeedCoefficient:1,n=this.baseBuildSpeed*h*n*o,o=t.creditsEach,n=o&&!this.speedCheat.value?(l=o/n*t.rules.buildTimeMultiplier,c=54,Math.floor(l/c)*c):54,n=Math.max(54,n),l=s.credits,c=t.creditsEach-t.creditsSpent,c=Math.min(s.credits,o/n+t.creditsSpentLeftover,c);0<c?(a=Math.floor(c),t.creditsSpentLeftover=c-a,a&&(t.creditsSpent+=a,t.progress=t.creditsSpent/t.creditsEach,s.credits-=a,e=!0)):t.creditsEach||(a=t.progress*n,t.progress=Math.min(1,(1+a)/n),e=!0),e&&1===t.progress&&(i.status=Tn.Ready),0<l&&!s.credits&&r.events.dispatch(new Gl(s)),e&&i.notifyUpdated()}}ensurePrerequisites(e){if(e.production)for(var t of e.production.getAllQueues()){var i;for(i of t.getAll().map(e=>({rules:e.rules,quantity:e.quantity,creditsSpent:e.creditsSpent})))e.production.isAvailableForProduction(i.rules)||(t.pop(i.rules,i.quantity),e.credits+=i.creditsSpent)}}getAvailableObjects(){return[...this.availableObjectRules]}}(Xn=Xn||{}).onChange=Symbol();class ql{constructor(e,t){this.map=e,this.alliances=t,this.shroudByPlayer=new Map,this.revealedToAll=new Set,this.gapGenerators=new Set,this.handleTileOccupationUpdate=({object:e,type:t})=>{if("removed"!==t&&e.isTechno()){var i,t=e.owner;for(i of[t,...this.alliances.getAllies(t)])this.shroudByPlayer.get(i)?.revealFrom(e)}}}getPlayerShroud(e){return this.shroudByPlayer.get(e)}init(t){t.map.tileOccupation.onChange.subscribe(this.handleTileOccupationUpdate);let i=(new eh).fromTiles(this.map.tiles);for(var s of t.getCombatants()){let e=i.clone();this.shroudByPlayer.set(s,e),this.revealObjects(e,s,t),e.update()}}[qr.onElevationChange](e,t,i){if(Math.floor(e.tileElevation)!==Math.floor(i)){var s,i=e.owner;for(s of[i,...this.alliances.getAllies(i)])this.shroudByPlayer.get(s)?.revealFrom(e)}}[Ps.onTick](e){for(var[t,i]of this.shroudByPlayer)t.defeated&&!t.isObserver?this.shroudByPlayer.delete(t):i.update()}[qn.onChange](e,t,i){if(e.isBuilding()&&e.rules.spySat&&(this.revealMap(e.owner,i),t.getOwnedObjectsByType(Et.Building).find(e=>e.rules.spySat)||this.resetShroud(t,i)),e.isSpawned)for(var s of[e.owner,...i.alliances.getAllies(e.owner)])this.shroudByPlayer.get(s)?.revealFrom(e)}[Xn.onChange](t,e,i){if(e){let e=this.getPlayerShroud(t.players.first);var s,r,t=i.alliances.getAllies(t.players.first).map(e=>this.getPlayerShroud(e)).filter(Wa);for(s of t)e.merge(s);e.invalidateFull();for(r of t)r.copy(e),r.invalidateFull()}}[Gn.onSpawn](e,t){if(e.isBuilding()){if(e.rules.spySat&&this.revealMap(e.owner,t),e.rules.revealToAll){this.revealedToAll.add(e);for(var i of t.getCombatants())i===e.owner||t.alliances.areAllied(e.owner,i)||(this.shroudByPlayer.get(i)?.revealObject(e),t.traits.get(Hl).addEventForPlayer(Yt.EnemyObjectSensed,i,e.centerTile,t))}e.gapGeneratorTrait&&this.gapGenerators.add(e)}}[$n.onUnspawn](e,t){e.isBuilding()&&(e.rules.spySat&&(e.owner.getOwnedObjectsByType(Et.Building).find(e=>e.rules.spySat)||this.resetShroud(e.owner,t)),e.rules.revealToAll&&this.revealedToAll.delete(e),e.gapGeneratorTrait&&this.gapGenerators.delete(e))}[Rs.onPowerLow](e,t){this.updateGaps(t,e)}[Rs.onPowerRestore](e,t){this.updateGaps(t,e)}[Rs.onPowerChange](e,t){}revealMap(e,t){this.shroudByPlayer.get(e)?.revealAll(),this.markOwnGapTiles(t,e),this.updateGaps(t)}resetShroud(e,t){let i=this.shroudByPlayer.get(e);i&&(i.reset(),this.markOwnGapTiles(t,e),this.revealObjects(i,e,t))}revealObjects(t,e,i){var s;for(s of[...e.getOwnedObjects(),...i.alliances.getAllies(e).map(e=>e.getOwnedObjects()).flat()])t.revealFrom(s);this.revealedToAll.forEach(e=>t.revealObject(e))}updateGaps(e,t){for(var i of this.gapGenerators)t&&i.owner!==t||i.gapGeneratorTrait.update(i,e)}markOwnGapTiles(e,t){for(var i of this.gapGenerators)i.owner!==t&&!e.alliances.areAllied(i.owner,t)||this.getPlayerShroud(t)?.toggleFlagsAround(i.tile,i.gapGeneratorTrait.radiusTiles,Bn.Darken,!0)}dispose(){this.map.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate)}}class Xl extends $s{constructor(e){super(),this.game=e}onTick(e){return!(e.buildStatus!==xn.BuildDown&&(e.setBuildStatus(xn.BuildDown,this.game),!e.rules.wall))||(this.children.push(new fa(this.game.rules.general.buildupTime)),!1)}}class Zl{constructor(){this.disposables=new Set}add(...e){e.map(e=>this.disposables.add("function"==typeof e?{dispose:e}:e))}remove(...e){e.map(e=>this.disposables.delete(e))}dispose(){this.disposables.forEach(e=>{"function"==typeof e?e():e.dispose?e.dispose():e.destroy()}),this.disposables.clear()}}class Ql{constructor(e,t,i,s,r){this.player=e,this.rules=t,this.art=i,this.map=s,this.game=r,this.adjacencyMaps=new Map,this.disposables=new Zl;let a=({object:e})=>{e.isBuilding()&&this.adjacencyMaps.clear()};this.map.tileOccupation.onChange.subscribe(a),this.disposables.add(()=>this.map.tileOccupation.onChange.unsubscribe(a)),this.disposables.add(this.game.events.subscribe(rs.AllianceChange,()=>this.adjacencyMaps.clear()),this.game.events.subscribe(rs.ObjectOwnerChange,e=>{e.target.isBuilding()&&this.adjacencyMaps.clear()}),this.game.events.subscribe(rs.ObjectDestroy,e=>{e.target.isBuilding()&&e.target.rules.leaveRubble&&this.adjacencyMaps.clear()}))}getAdjacentRect(e,t,i){return{x:e.rx-i,y:e.ry-i,width:t.width+2*i,height:t.height+2*i}}getAdjacencyMap(e){var t;let i=[];for(t of[...this.player.buildings,...this.game.gameOpts.buildOffAlly?this.game.alliances.getAllies(this.player).map(e=>[...e.buildings].filter(e=>e.rules.eligibileForAllyBuilding)).flat():[]])t.rules.baseNormal&&i.push(this.getAdjacentRect(t.tile,t.art.foundation,e));return i}meetsAdjacency(e,t){let i=this.adjacencyMaps.get(t);i||(i=this.getAdjacencyMap(t),this.adjacencyMaps.set(t,i));for(var s of i)if(r=e,s=s,r.x<=s.x+s.width&&s.x<=r.x+r.width&&r.y<=s.y+s.height&&s.y<=r.y+r.height)return!0;var r;return!1}getPlacementPreview(e,t,i={}){var{normalizedTile:s=!1,ignoreObjects:r,ignoreAdjacent:i=!1}=i,a=this.rules.getBuilding(e),e=this.art.getObject(e,Et.Building);let n=[];var o=e.foundation,h=s?t:this.normalizePlacementTileCoords(e,t);let l=!0;t={x:h.rx,y:h.ry,width:o.width,height:o.height};a.constructionYard||i||this.meetsAdjacency(t,a.adjacent)||(l=!1);for(let t=0;t<o.width;t++)for(let e=0;e<o.height;e++){var c={x:h.rx+t,y:h.ry+e},u=this.map.tiles.getByMapCoords(c.x,c.y);u&&n.push({rx:c.x,ry:c.y,buildable:l&&this.isTileBuildable(u,a,r)})}if(a.wall&&n[0].buildable){let e=this.getWallConnectingTiles(h,a);e.forEach(e=>{n.push({rx:e.rx,ry:e.ry,buildable:!0})})}return n}canPlaceAt(e,t,i={}){var{normalizedTile:s=!1,ignoreObjects:r,ignoreAdjacent:i=!1}=i,a=this.rules.getBuilding(e),e=this.art.getObject(e,Et.Building),n=e.foundation,o=s?t:this.normalizePlacementTileCoords(e,t),t={x:o.rx,y:o.ry,width:n.width,height:n.height};if(!a.constructionYard&&!i&&!this.meetsAdjacency(t,a.adjacent))return!1;for(let t=0;t<n.width;t++)for(let e=0;e<n.height;e++){var h={x:o.rx+t,y:o.ry+e},h=this.map.tiles.getByMapCoords(h.x,h.y);if(!h||!this.isTileBuildable(h,a,r))return!1}return!0}placeAt(e,t,i=!1){let s=[],r=this.rules.getBuilding(e),a=i?t:this.normalizePlacementTile(e,t);if(r.wall){let t=[[a,r]],e=this.getWallConnectingTiles(a,r);e.forEach(e=>{e!==a&&t.push([e,r])});for(var n of t)s.push(this.executePlacement(n[0],n[1]))}else{var o,t=this.executePlacement(a,r);s.push(t);for(o of this.map.tileOccupation.calculateTilesForGameObject(a,t)){var h=this.map.getObjectsOnTile(o).find(e=>e.isSmudge());h&&this.game.unspawnObject(h)}}return s}normalizePlacementTileCoords(e,t){e=e.foundationCenter;return{rx:t.rx-e.x,ry:t.ry-e.y}}normalizePlacementTile(e,t){e=this.art.getObject(e,Et.Building),e=this.normalizePlacementTileCoords(e,t),t=this.map.tiles.getByMapCoords(e.rx,e.ry);if(!t)throw new Error(`Can't build outside map (${e.rx}, ${e.ry})`);return t}unplace(e,t){e.unitOrderTrait.cancelAllTasks(),e.unitOrderTrait.addTasks(new za(new Xl(this.game),new ya(()=>{this.game.unspawnObject(e),t()})).setCancellable(!1)),e.unitOrderTrait[jr.onTick](e,this.game)}executePlacement(e,t){let i=this.game.createObject(Et.Building,t.name);return this.game.changeObjectOwner(i,this.player),i.purchaseValue=this.game.sellTrait.computePurchaseValue(t,this.player),this.game.spawnObject(i,e),i}getWallConnectingTiles(i,s){var r,a=s.guardRange+1;let n=[];for(r of[[0,1],[0,-1],[1,0],[-1,0]]){let t=[];for(let e=0;e<a;++e){var o={x:i.rx+r[0]*e,y:i.ry+r[1]*e},o=this.map.tiles.getByMapCoords(o.x,o.y);if(!o)break;if(this.map.getObjectsOnTile(o).find(e=>e.isBuilding()&&e.name===s.name&&e.owner===this.player)){n=n.concat(t);break}if(!this.isTileBuildable(o,s))break;t.push(o)}}return n}isTileBuildable(e,t,i){return!!this.map.isWithinBounds(e)&&(!this.game.mapShroudTrait.getPlayerShroud(this.player)?.isShrouded(e)&&(!this.map.getGroundObjectsOnTile(e).some(e=>!(i?.includes(e)||e.isBuilding()&&e.rules.invisibleInGame||e.isSmudge()))&&(t.waterBound?0<this.rules.getLandRules(e.landType).getSpeedModifier(ti.Float):0===e.rampType&&this.rules.getLandRules(e.landType).buildable)))}dispose(){this.disposables.dispose()}}class Yl{static generate(e,t,i,s){var r,a=i.reduce((e,t)=>e+t.cost,0)/i.length*e;let n=[],o=a,h=(i=i.filter(e=>e.isAvailableTo(s)&&e.hasOwner(s))).filter(e=>t.includes(e.name));for(r of h){if(o<=0)break;var l=2/3/h.length,l=Math.ceil(l*a/r.cost);o-=l*r.cost,n.push({name:r.name,type:Et.Vehicle,count:l})}var c,i=i.filter(e=>!h.includes(e)),u=o/i.length;for(c of i){if(o<=0)break;var d=Math.ceil(u/c.cost);o-=d*c.cost,n.push({name:c.name,type:Et.Infantry,count:d})}return n}}class Kl{constructor(){this.dispatcher=new wo,this.dispatchersByType=new Map}dispatch(e){this.dispatcher.dispatch(void 0,e),this.dispatchersByType.get(e.type)?.dispatch(void 0,e)}subscribe(e,t){let i=void 0,s;return s="function"==typeof e?e:(i=e,t),void 0===i?(this.dispatcher.subscribe(s),()=>this.unsubscribe(s)):this.subscribeType(i,s)}unsubscribe(e,t){let i=void 0,s;s="function"==typeof e?e:(i=e,t),void 0===i?this.dispatcher.unsubscribe(s):this.unsubscribeType(i,s)}subscribeType(e,t){let i=this.dispatchersByType.get(e);return i||(i=new wo,this.dispatchersByType.set(e,i)),i.subscribe(t),()=>this.unsubscribeType(e,t)}unsubscribeType(e,t){this.dispatchersByType.get(e)?.unsubscribe(t)}}class Jl{constructor(e,t,i){this.target=e,this.attackerInfo=t,this.incidental=i,this.type=rs.ObjectDestroy}}class ec{constructor(e){this.target=e,this.type=rs.PlayerDefeated}}(Zn=Zn||{}).onDestroy=Symbol();class tc{constructor(e,t){this.target=e,this.prevOwner=t,this.type=rs.ObjectOwnerChange}}class ic{constructor(e){this.gameObject=e,this.type=rs.ObjectUnspawn}}class sc{constructor(e){this.gameObject=e,this.type=rs.ObjectSpawn}}(r=Qn=Qn||{})[r.Requested=0]="Requested",r[r.Formed=1]="Formed",r[r.Broken=2]="Broken";class rc{constructor(e,t,i){this.alliance=e,this.changeType=t,this.from=i,this.type=rs.AllianceChange}}var ac,nc,oc,hc,lc,cc,uc,dc,gc,pc,mc,r=__webpack_require__(948),fc=__webpack_require__.n(r);class yc{static factory(e,t){t=Number.isNaN(Number(e))?oe.calculateCrc(R(e)):Number(e+""+t);return new yc(t)}constructor(e){this.prng=new(fc())(e)}generateRandomInt(e,t){var i=this.prng.random();return this.lastRandom=i,Math.round(i*(t-e))+e}generateRandom(){var e=this.prng.random();return this.lastRandom=e}getLastRandom(){return this.lastRandom}}class wc{constructor(e,t){this.action=e,this.trigger=t}getDebugName(){return`${this.action.triggerId}[${this.action.index}] (${this.trigger.name}).`}}class Tc extends wc{constructor(e,t,i){super(e,t),this.oneTimeOnly=i,this.superWeaponIdx=Number(e.params[1])}execute(i){var s=[...i.rules.superWeaponRules.values()].find(e=>e.index===this.superWeaponIdx);if(s){let t=i.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);if(t&&t.superWeaponsTrait&&!t.superWeaponsTrait.has(s.name)){let e=i.createSuperWeapon(s.name,t,this.oneTimeOnly);e.isGift=!0,t.superWeaponsTrait.add(e)}}else console.warn(`No superweapon found with index "${this.superWeaponIdx}". `+`Skipping action ${this.getDebugName()}.`)}}class bc extends wc{constructor(e,t,i){super(e,t),this.damage=i}execute(t){var e=Number(this.action.params[1]),i=t.map.getTileAtWaypoint(e);if(i){var s=t.rules.getWarhead(Ja.HE_WARHEAD_NAME);let e=new Ja(s);var r=t.map.tileOccupation.getBridgeOnTile(i),a=r?.tileElevation??0,s=t.map.getTileZone(i);e.detonate(t,this.damage,i,a,_s.tile3dToWorld(i.rx+.5,i.ry+.5,i.z+a),s,r?na.OnBridge:na.None,t.createTarget(r,i),void 0)}else console.warn(`No valid location found for waypoint ${e}. `+`Skipping action ${this.getDebugName()}.`)}}class vc extends wc{execute(s){let t=s.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);if(t){let i=Number(this.action.params[1]),e;if(i>=vc.locationHouseIdBegin&&i<vc.locationHouseIdBegin+s.map.startingLocations.length){let t=i-vc.locationHouseIdBegin;e=s.getAllPlayers().find(e=>e.startLocation===t)}else e=s.getAllPlayers().find(e=>e.country?.id===i);if(e)for(var r of t.getOwnedObjects(!0))s.changeObjectOwner(r,e)}}}vc.locationHouseIdBegin=4475;class Sc extends wc{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e,t){let i;if(this.houseId>=Sc.locationHouseIdBegin&&this.houseId<Sc.locationHouseIdBegin+e.map.startingLocations.length){let t=this.houseId-Sc.locationHouseIdBegin;i=e.getAllPlayers().find(e=>e.startLocation===t)}else i=e.getAllPlayers().find(e=>e.country?.id===this.houseId);if(i)for(var s of t)s instanceof Ea&&s.isSpawned&&e.changeObjectOwner(s,i)}}Sc.locationHouseIdBegin=4475;class kc extends $s{constructor(){super(),this.executed=!1,this.cancellable=!1}onTick(e){return this.executed?(e.stance=Fs.None,!0):!e.isInfantry()||!e.art.sequences.has(mn.Cheer)||(e.stance!==Fs.None&&e.stance!==Fs.Guard||(e.stance=Fs.Cheer,this.children.push(new fa(1/60).setCancellable(!1)),!(this.executed=!0)))}}class Oc extends wc{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e){let t=e.getAllPlayers().filter(e=>e.country&&!e.defeated);if(-1!==this.houseId&&(t=t.filter(e=>e.country?.id===this.houseId)),t.length)for(var i of t[0].getOwnedObjectsByType(Et.Infantry))i.unitOrderTrait.isIdle()&&i.unitOrderTrait.addTask(new kc)}}const _c=new Map([[0,e=>{e=e.rules.powerups.powerups.find(e=>e.type===Es.Money);return e?{...e,data:"5000"}:void 0}],[1,Es.Unit],[2,Es.HealBase],[3,Es.Cloak],[4,Es.Explosion],[5,Es.Napalm],[6,Es.Money],[7,Es.Darkness],[8,Es.Reveal],[9,Es.Armor],[10,Es.Speed],[11,Es.Firepower],[12,Es.ICBM],[13,void 0],[14,Es.Veteran],[15,void 0],[16,Es.Gas],[17,Es.Tiberium],[18,void 0]]);class Ic extends wc{execute(e){var t=Number(this.action.params[1]),i=this.action.params[6],s=e.map.getTileAtWaypoint(i);if(s)if(_c.has(t)){const r=_c.get(t);t="function"==typeof r?r(e):e.rules.powerups.powerups.find(e=>e.type===r);t&&e.crateGeneratorTrait.spawnCrateAt(s,t,e)}else e.crateGeneratorTrait.spawnRandomCrateAt(s,e);else console.warn(`No valid location found for waypoint ${i}. `+`Skipping action ${this.getDebugName()}.`)}}class Cc extends wc{execute(e){var t=Number(this.action.params[1])-1;if(Object.values(Yt).includes(t)){var i=this.action.params[6],s=e.map.getTileAtWaypoint(i);if(s)for(var r of e.getCombatants())e.traits.get(Hl).addEventForPlayer(t,r,s,e);else console.warn(`No valid location found for waypoint ${i}. `+`Skipping action ${this.getDebugName()}.`)}else console.warn(`Unknown radar event type "${1+t}". Skipping action ${this.getDebugName()}.`)}}class Ac extends wc{execute(e,t){for(var i of t)i instanceof Ea&&i.isSpawned&&e.destroyObject(i)}}class Bc extends wc{execute(e){var t=this.action.params[1];e.triggers.destroyTag(t)}}class xc extends wc{execute(e){var t=this.action.params[1];e.triggers.destroyTrigger(t)}}class Ec extends wc{execute(s){var r=Number(this.action.params[1]),e=this.action.params[6],a=s.map.getTileAtWaypoint(e);if(a){let t;try{t=s.rules.getWeaponByInternalId(r)}catch(e){if(e instanceof RangeError)return void console.warn(`Weapon with internal ID "${r}" not found. `+`Skipping action ${this.getDebugName()}.`);throw e}let e;try{e=s.rules.getWarhead(t.warhead)}catch(e){return void console.warn(`Warhead "${t.warhead}" not found. `+`Skipping action ${this.getDebugName()}.`)}let i=new Ja(e);var n=s.map.tileOccupation.getBridgeOnTile(a),o=n?.tileElevation??0,r=s.map.getTileZone(a);i.detonate(s,t.damage,a,o,_s.tile3dToWorld(a.rx+.5,a.ry+.5,a.z+o),r,n?na.OnBridge:na.None,s.createTarget(n,a),void 0)}else console.warn(`No valid location found for waypoint ${e}. `+`Skipping action ${this.getDebugName()}.`)}}class Pc extends wc{execute(e,t){for(var i of t)i instanceof Ea&&i.isBuilding()&&i.garrisonTrait&&!i.isDestroyed&&i.garrisonTrait.evacuate(e)}}class Nc extends wc{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e){var t=e.getAllPlayers().find(e=>e.country?.id===this.houseId);if(t)for(var i of t.buildings)e.sellTrait.sell(i)}}class Dc extends wc{execute(e){e.end()}}class Mc extends wc{execute(e){var t=this.action.params[1];e.triggers.forceTrigger(t,e)}}class Rc extends wc{constructor(e,t,i){super(e,t),this.value=i,this.variableIdx=Number(e.params[1])}execute(e){e.triggers.toggleGlobalVariable(this.variableIdx,this.value)}}class Lc extends wc{execute(e){var t,i,s=this.action.params[6],r=e.map.getTileAtWaypoint(s);r?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===ss.IronCurtain))&&e.traits.get(un).activateEffect(i,t,e,r,void 0,!0):console.warn(`No valid location found for waypoint ${s}. `+`Skipping action ${this.getDebugName()}.`)}}class Fc extends wc{execute(e){var t,i,s=this.action.params[6],r=e.map.getTileAtWaypoint(s);r?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===ss.LightningStorm))&&e.traits.get(un).activateEffect(i,t,e,r,void 0,!0):console.warn(`No valid location found for waypoint ${s}. `+`Skipping action ${this.getDebugName()}.`)}}class jc extends wc{constructor(e,t,i){super(e,t),this.value=i,this.variableIdx=Number(e.params[1])}execute(e){e.triggers.toggleLocalVariable(this.variableIdx,this.value)}}class Uc extends wc{execute(){}}class Wc extends wc{execute(e){var t,i,s=this.action.params[6],r=e.map.getTileAtWaypoint(s);r?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===ss.MultiMissile))&&e.traits.get(un).activateEffect(i,t,e,r,void 0,!0):console.warn(`No valid location found for waypoint ${s}. `+`Skipping action ${this.getDebugName()}.`)}}class zc{constructor(e,t){this.name=e,this.tile=t,this.type=rs.TriggerAnim}}class Vc extends wc{execute(e){var t,i=this.action,s=Number(i.params[1]),r=e.rules.getAnimationName(s);void 0!==r?(t=i.params[6],(i=e.map.getTileAtWaypoint(t))?e.events.dispatch(new zc(r,i)):console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)):console.warn(`No animation found for index "${s}". Skipping action ${this.getDebugName()}`)}}class Hc{constructor(e,t){this.soundId=e,this.tile=t,this.type=rs.TriggerSoundFx}}class Gc extends wc{execute(e){var t=this.action,i=t.params[1],s=t.params[6],t=e.map.getTileAtWaypoint(s);t?e.events.dispatch(new Hc(i,t)):console.warn(`No valid location found for waypoint ${s}. `+`Skipping action ${this.getDebugName()}.`)}}class $c extends wc{execute(e){e.events.dispatch(new Hc(this.action.params[1]))}}class qc{constructor(e){this.soundId=e,this.type=rs.TriggerEva}}class Xc extends wc{execute(e){e.events.dispatch(new qc(this.action.params[1]))}}class Zc extends wc{execute(e){for(var t of e.getCombatants())e.mapShroudTrait.resetShroud(t,e)}}class Qc extends wc{execute(e){var[t,i,s,r]=this.action.params.slice(2,6).map(Number);e.map.mapBounds.updateRawLocalSize({x:t,y:i,width:s,height:r})}}class Yc extends wc{execute(e){var t=Number(this.action.params[1]),i=e.map.getTileAtWaypoint(t);if(i)for(var s of e.getCombatants())e.mapShroudTrait.getPlayerShroud(s)?.revealAround(i,e.rules.general.revealTriggerRadius);else console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class Kc extends wc{execute(e){for(var t of e.getCombatants())e.mapShroudTrait.revealMap(t,e)}}class Jc extends wc{execute(e,t){for(var i of t)i instanceof Ea&&i.isBuilding()&&!i.isDestroyed&&e.sellTrait.sell(i)}}class eu extends wc{execute(e){var t=Number(this.action.params[1])/100;e.mapLightingTrait.setTargetAmbientIntensity(t)}}function tu(e){let t=new DataView(new ArrayBuffer(4));return t.setInt32(0,e),t.getFloat32(0)}class iu extends wc{execute(e){var t=tu(Number(this.action.params[1]));e.mapLightingTrait.setAmbientChangeRate(t)}}class su extends wc{execute(e){var t=tu(Number(this.action.params[1]));e.mapLightingTrait.setAmbientChangeStep(t)}}class ru{constructor(e){this.tile=e,this.type=rs.TriggerStopSoundFx}}class au extends wc{execute(e){var t=this.action.params[6],i=e.map.getTileAtWaypoint(t);i?e.events.dispatch(new ru(i)):console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class nu{constructor(e){this.label=e,this.type=rs.TriggerText}}class ou extends wc{execute(e){e.events.dispatch(new nu(this.action.params[1]))}}class hu extends wc{execute(e){e.countdownTimer.addSeconds(Number(this.action.params[1]))}}class lu extends wc{execute(e){e.countdownTimer.setSeconds(Number(this.action.params[1]))}}class cu extends wc{execute(e){e.countdownTimer.addSeconds(-Number(this.action.params[1]))}}class uu extends wc{execute(e){e.countdownTimer.start()}}class du extends wc{execute(e){e.countdownTimer.stop()}}class gu extends wc{execute(e){e.countdownTimer.text=this.action.params[1]}}class pu extends wc{constructor(e,t,i){super(e,t),this.triggerEnable=i}execute(e){var t=this.action.params[1];e.triggers.setTriggerEnabled(t,this.triggerEnable)}}class mu extends wc{constructor(e,t,i){super(e,t),this.turnOn=i}execute(e,t){for(var i of t)i instanceof Ea&&i.isBuilding()&&i.poweredTrait?.setTurnedOn(this.turnOn)}}class fu extends wc{execute(e){var t=Number(this.action.params[1]),i=e.map.getTileAtWaypoint(t);if(i)for(var s of e.getCombatants())e.mapShroudTrait.getPlayerShroud(s)?.unrevealAround(i,e.rules.general.revealTriggerRadius);else console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class yu{create(e,t){switch(e.type){case Zt.NoAction:return new Uc(e,t);case Zt.FireSale:return new Nc(e,t);case Zt.TextTrigger:return new ou(e,t);case Zt.DestroyTrigger:return new xc(e,t);case Zt.ChangeHouse:return new Sc(e,t);case Zt.RevealMap:return new Kc(e,t);case Zt.RevealAroundWaypoint:return new Yc(e,t);case Zt.PlaySoundFx:return new $c(e,t);case Zt.PlaySpeech:return new Xc(e,t);case Zt.ForceTrigger:return new Mc(e,t);case Zt.TimerStart:return new uu(e,t);case Zt.TimerStop:return new du(e,t);case Zt.TimerExtend:return new hu(e,t);case Zt.TimerShorten:return new cu(e,t);case Zt.TimerSet:return new lu(e,t);case Zt.GlobalSet:return new Rc(e,t,!0);case Zt.GlobalClear:return new Rc(e,t,!1);case Zt.DestroyObject:return new Ac(e,t);case Zt.AddOneTimeSuperWeapon:return new Tc(e,t,!0);case Zt.AddRepeatingSuperWeapon:return new Tc(e,t,!1);case Zt.AllChangeHouse:return new vc(e,t);case Zt.ResizePlayerView:return new Qc(e,t);case Zt.PlayAnimAt:return new Vc(e,t);case Zt.DetonateWarhead:return new Ec(e,t);case Zt.ReshroudMap:return new Zc(e,t);case Zt.EnableTrigger:return new pu(e,t,!0);case Zt.DisableTrigger:return new pu(e,t,!1);case Zt.CreateRadarEvent:return new Cc(e,t);case Zt.LocalSet:return new jc(e,t,!0);case Zt.LocalClear:return new jc(e,t,!1);case Zt.SellBuilding:return new Jc(e,t);case Zt.TurnOffBuilding:return new mu(e,t,!1);case Zt.TurnOnBuilding:return new mu(e,t,!0);case Zt.ApplyOneHundredDamage:return new bc(e,t,100);case Zt.ForceEnd:return new Dc(e,t);case Zt.DestroyTag:return new Bc(e,t);case Zt.SetAmbientStep:return new su(e,t);case Zt.SetAmbientRate:return new iu(e,t);case Zt.SetAmbientLight:return new eu(e,t);case Zt.NukeStrike:return new Wc(e,t);case Zt.PlaySoundFxAt:return new Gc(e,t);case Zt.UnrevealAroundWaypoint:return new fu(e,t);case Zt.LightningStrike:return new Fc(e,t);case Zt.TimerText:return new gu(e,t);case Zt.CreateCrate:return new Ic(e,t);case Zt.IronCurtainAt:return new Lc(e,t);case Zt.EvictOccupiers:return new Pc(e,t);case Zt.Cheer:return new Oc(e,t);case Zt.StopSoundsAt:return new au(e,t);default:throw new Error(`Unhandled action type "${Zt[e.type]}"`)}}}class wu{constructor(e,t){this.event=e,this.trigger=t,this.blocking=!1,this.targets=[]}init(e){e=e.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);e&&(this.player=e)}setTargets(e){this.targets=e}reset(){}getDebugName(){return`${this.event.triggerId}[${this.event.eventIndex}] (${this.trigger.name}).`}}class Tu extends wu{constructor(e,t,i){super(e,t),this.type=i,this.threshold=Number(e.params[1])/100}check(e){var t=this.previousAmbient,e=e.mapLightingTrait.getAmbient().ambient;return this.previousAmbient=e,void 0!==t&&t!==e&&("above"===this.type?e>=this.threshold&&t<this.threshold:e<=this.threshold&&t>this.threshold)}}class bu extends wu{check(e){return!0}}class vu extends wu{check(s,e){return e.filter(e=>{if(e.type!==rs.ObjectAttacked)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;var i=e.attacker?.player;return(!i||!s.alliances.areAllied(i,t.owner)&&i!==t.owner)&&!e.incidental}).map(e=>e.target)}}class Su extends wu{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==rs.ObjectAttacked)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;e=e.attacker?.player;return e&&(-1===this.houseId||e?.country?.id===this.houseId)}).map(e=>e.target)}}class ku extends wu{constructor(e,t,i=!1){super(e,t),this.negate=i,this.objectIndex=Number(e.params[1])}check(){if(!this.player)return!1;for(var e of this.player.buildings)if(e.rules.index===this.objectIndex)return!this.negate;return this.negate}}class Ou extends wu{constructor(e,t,i){super(e,t),this.objectType=i,this.objectIndex=Number(e.params[1])}check(e,t){return t.some(e=>e.type===rs.ObjectSpawn&&e.gameObject.type===this.objectType&&e.gameObject.rules.index===this.objectIndex)}}class _u extends wu{constructor(e,t){super(e,t)}init(e){super.init(e);var t=Number(this.event.params[1]);this.waypointTile=e.map.getTileAtWaypoint(t),this.waypointTile||console.warn(`No valid location found for waypoint ${t}. `+`Skipping event ${this.getDebugName()}.`)}check(t,e){if(!this.waypointTile||!this.player)return!1;for(var i of e)if(i.type===rs.EnterTile&&i.source.owner===this.player){let e=new Bs(t.map.tileOccupation);if(e.tileDistance(i.target,this.waypointTile)<2)return!0}return!1}}class Iu extends wu{constructor(e,t){super(e,t),this.threshold=Number(e.params[1])}check(e,t){return!!this.player&&this.player.credits<this.threshold}}class Cu extends wu{constructor(e,t){super(e,t),this.threshold=Number(e.params[1])}check(e,t){return!!this.player&&this.player.credits>this.threshold}}class Au extends wu{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(t=>t.type===rs.EnterTile&&t.source.zone!==Ss.Air&&this.targets.some(e=>e.ry===t.target.ry)&&(-1===this.houseId||t.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class Bu extends wu{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(t=>t.type===rs.EnterTile&&t.source.zone!==Ss.Air&&this.targets.some(e=>e.rx===t.target.rx)&&(-1===this.houseId||t.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class xu extends wu{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;return!(!t.isBuilding()||t.owner.country?.id!==this.houseId)&&!t.owner.buildings.size})&&(this.allDestroyed=!0)}}class Eu extends wu{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;return!(!t.isTechno()||t.owner.country?.id!==this.houseId)&&!t.owner.getOwnedObjects(!0).length})&&(this.allDestroyed=!0)}}class Pu extends wu{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;return!(!t.isUnit()||t.owner.country?.id!==this.houseId)&&!this.hasUnitsLeft(t.owner)})&&(this.allDestroyed=!0)}hasUnitsLeft(e){var t;for(t of[Et.Aircraft,Et.Vehicle,Et.Infantry])if(e.getOwnedObjectsByType(t,!0).length)return!0;return!1}}class Nu extends wu{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;return!(!t.isUnit()||t.owner.country?.id!==this.houseId)&&!this.hasLandUnitsLeft(t.owner)})&&(this.allDestroyed=!0)}hasLandUnitsLeft(e){var t;for(t of[Et.Vehicle,Et.Infantry])if(e.getOwnedObjectsByType(t,!0).filter(e=>!e.rules.naval).length)return!0;return!1}}class Du extends wu{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;return!(!t.isVehicle()||t.owner.country?.id!==this.houseId)&&!t.owner.getOwnedObjectsByType(Et.Vehicle,!0).filter(e=>e.rules.naval).length})&&(this.allDestroyed=!0)}}class Mu extends wu{check(s,e){return e.filter(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;if(!t.isOverlay()||!t.isBridge())return!1;e=t.bridgeTrait?.bridgeSpec;if(!e)return!1;let i=s.map.bridges.findAllBridgeTiles(e);return i.find(e=>this.targets.includes(e))}).map(e=>e.target.tile)}}class Ru extends wu{constructor(e,t){super(e,t),this.count=0,this.threshold=Number(e.params[1])}check(e,t){if(!this.player)return!1;if(this.count>=this.threshold)return!0;for(var i of t)if(i.type===rs.ObjectDestroy){let e=i.target;e.isBuilding()&&e.owner.country?.id===this.houseId&&this.count++}return this.count>=this.threshold}}class Lu extends wu{check(s,e){return e.filter(e=>{if(e.type!==rs.ObjectDestroy)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;var i=e.attackerInfo?.player;return(!i||!s.alliances.areAllied(i,t.owner)&&i!==t.owner)&&!e.incidental}).map(e=>e.target)}}class Fu extends wu{check(e,t){return t.filter(e=>{if(e.type!==rs.ObjectDestroy&&e.type!==rs.ObjectOwnerChange)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))}).map(e=>e.target)}}class ju extends wu{constructor(){super(...arguments),this.eventsFilter=[rs.ObjectDestroy,rs.ObjectOwnerChange,rs.BuildingInfiltration]}check(e,t){return t.filter(e=>{if(!this.eventsFilter.includes(e.type))return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))}).map(e=>e.target)}}class Uu extends wu{constructor(e,t){super(e,t),this.count=0,this.threshold=Number(e.params[1])}check(e,t){if(!this.player)return!1;if(this.count>=this.threshold)return!0;for(var i of t)if(i.type===rs.ObjectDestroy){let e=i.target;e.isUnit()&&e.owner.country?.id===this.houseId&&this.count++}return this.count>=this.threshold}}class Wu extends wu{constructor(e,t){super(e,t),this.timerTicks=Number(this.event.params[1])*Us.BASE_TICKS_PER_SECOND}check(e){return e.currentTick>this.timerTicks}}class zu extends wu{constructor(e,t){super(e,t),this.elapsedTicks=0,this.timerTicks=Number(this.event.params[1])*Us.BASE_TICKS_PER_SECOND}check(e){return this.elapsedTicks++>this.timerTicks}reset(){this.elapsedTicks=0}}class Vu extends wu{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(e=>(e.type===rs.EnterObject||e.type===rs.EnterTile)&&this.targets.includes(e.target)&&(e.type!==rs.EnterTile||e.source.zone!==Ss.Air)&&(-1===this.houseId||e.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class Hu extends wu{constructor(e,t,i){super(e,t),this.value=i,this.blocking=!0,this.variableIdx=Number(e.params[1])}check(e){return e.triggers.getGlobalVariable(this.variableIdx)===this.value}}class Gu extends wu{constructor(e,t,i){super(e,t),this.threshold=i}check(e,t){return t.filter(e=>{if(e.type!==rs.HealthChange)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))&&(e.currentHealth<this.threshold&&e.prevHealth>this.threshold)}).map(e=>e.target)}}class $u extends wu{constructor(e,t,i){super(e,t),this.threshold=i}check(e,t){return t.filter(e=>{if(e.type!==rs.InflictDamage)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))&&(e.currentHealth<this.threshold&&e.prevHealth>this.threshold)}).map(e=>e.target)}}class qu extends wu{constructor(e,t,i){super(e,t),this.value=i,this.blocking=!0,this.variableIdx=Number(e.params[1])}check(e){return e.triggers.getLocalVariable(this.variableIdx)===this.value}}class Xu extends wu{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}init(e){super.init(e),this.targetPlayer=e.getAllPlayers().find(e=>e.country?.id===this.houseId)}check(){return!!this.targetPlayer?.powerTrait?.isLowPower()}}class Zu extends wu{check(e){return!1}}class Qu extends wu{check(){if(!this.player)return!1;for(var e of this.player.buildings)if(e.factoryTrait)return!1;return!0}}class Yu extends wu{check(e,t){return t.some(e=>e.type===rs.CratePickup)}}class Ku extends wu{check(e,t){return t.filter(e=>e.type===rs.CratePickup&&this.targets.includes(e.source)).map(e=>e.source)}}class Ju extends wu{constructor(){super(...arguments),this.elapsedTicks=0}check(e){return this.timerTicks??(this.timerTicks=Math.floor(e.generateRandomInt(50,150)/100*Number(this.event.params[1]))*Us.BASE_TICKS_PER_SECOND),this.elapsedTicks++>this.timerTicks}reset(){this.timerTicks=void 0,this.elapsedTicks=0}}class ed extends wu{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(e=>e.type===rs.BuildingInfiltration&&this.targets.includes(e.target)&&(-1===this.houseId||e.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class td extends wu{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==rs.BuildingInfiltration)return!1;var t=e.target;return!!this.targets.includes(t)&&(-1===this.houseId||e.source.disguiseTrait?.getDisguise()?.owner?.country?.id===this.houseId)}).map(e=>e.target)}}class id extends wu{constructor(e,t){super(e,t),this.infantryIdx=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==rs.BuildingInfiltration)return!1;var t=e.target;return!!this.targets.includes(t)&&e.source.disguiseTrait?.getDisguise()?.rules.index===this.infantryIdx}).map(e=>e.target)}}class sd extends wu{check(e,t){return t.some(e=>e.type===rs.TimerExpire)}}class rd{create(e,t){switch(e.type){case Xt.NoEvent:return new Zu(e,t);case Xt.EnteredBy:return new Vu(e,t);case Xt.SpiedBy:return new ed(e,t);case Xt.AttackedByAny:return new vu(e,t);case Xt.DestroyedByAny:return new Lu(e,t);case Xt.AnyEvent:return new bu(e,t);case Xt.DestroyedAllUnits:return new Pu(e,t);case Xt.DestroyedAllBuildings:return new xu(e,t);case Xt.DestroyedAll:return new Eu(e,t);case Xt.CreditsExceed:return new Cu(e,t);case Xt.ElapsedTime:return new zu(e,t);case Xt.MissionTimerExpired:return new sd(e,t);case Xt.DestroyedBuildings:return new Ru(e,t);case Xt.DestroyedUnits:return new Uu(e,t);case Xt.NoFactoriesLeft:return new Qu(e,t);case Xt.BuildBuilding:return new Ou(e,t,Et.Building);case Xt.BuildUnit:return new Ou(e,t,Et.Vehicle);case Xt.BuildInfantry:return new Ou(e,t,Et.Infantry);case Xt.BuildAircraft:return new Ou(e,t,Et.Aircraft);case Xt.CrossesHorizontalLine:return new Au(e,t);case Xt.CrossesVerticalLine:return new Bu(e,t);case Xt.GlobalIsSet:return new Hu(e,t,!0);case Xt.GlobalIsCleared:return new Hu(e,t,!1);case Xt.DestroyedOrCaptured:return new Fu(e,t);case Xt.LowPower:return new Xu(e,t);case Xt.DestroyedBridge:return new Mu(e,t);case Xt.BuildingExists:return new ku(e,t);case Xt.ComesNearWaypoint:return new _u(e,t);case Xt.LocalIsSet:return new qu(e,t,!0);case Xt.LocalIsCleared:return new qu(e,t,!1);case Xt.FirstDamagedCombat:return new $u(e,t,100);case Xt.HalfHealthCombat:return new $u(e,t,50);case Xt.QuarterHealthCombat:return new $u(e,t,25);case Xt.FirstDamagedAny:return new Gu(e,t,100);case Xt.HalfHealthAny:return new Gu(e,t,50);case Xt.QuarterHealthAny:return new Gu(e,t,25);case Xt.AttackedByHouse:return new Su(e,t);case Xt.AmbientLightBelow:return new Tu(e,t,"below");case Xt.AmbientLightAbove:return new Tu(e,t,"above");case Xt.ElapsedScenarioTime:return new Wu(e,t);case Xt.DestroyedOrCapturedOrInfiltrated:return new ju(e,t);case Xt.PickupCrate:return new Ku(e,t);case Xt.PickupCrateAny:return new Yu(e,t);case Xt.RandomDelay:return new Ju(e,t);case Xt.CreditsBelow:return new Iu(e,t);case Xt.SpyEnteringAsHouse:return new td(e,t);case Xt.SpyEnteringAsInfantry:return new id(e,t);case Xt.DestroyedAllUnitsNaval:return new Du(e,t);case Xt.DestroyedAllUnitsLand:return new Nu(e,t);case Xt.BuildingNotExists:return new ku(e,t,!0);default:throw new Error(`Unhandled trigger event type "${Xt[e.type]}"`)}}}class ad{constructor(){this.disposables=new Zl,this.triggerInstances=new Map,this.targetsByTag=new Map,this.conditionFactory=new rd,this.executorFactory=new yu,this.pendingGameEvents=[],this.globalVariables=new Map,this.localVariables=new Map}init(i){var t,e,s,r,a=i.map.getInitialMapObjects()["technos"];for(let t of a)if(t.tag){let e=this.targetsByTag.get(t.tag);e||(e=[],this.targetsByTag.set(t.tag,e));var n=i.map.tiles.getByMapCoords(t.rx,t.ry);!n||(n=i.map.getObjectsOnTile(n).find(e=>e.name===t.name&&e.type===t.type))&&e.push(n)}for(t of i.map.getCellTags()){var o=i.map.tiles.getByMapCoords(t.coords.x,t.coords.y);if(o){let e=this.targetsByTag.get(t.tagId);e||(e=[],this.targetsByTag.set(t.tagId,e)),e.push(o)}else console.warn(`CellTag out of bounds at (${t.coords.x}, ${t.coords.y}). Skipping.`)}for([e,s]of i.map.getVariables())this.localVariables.set(e,s.clone());for(r of i.map.getTriggers())this.triggerInstances.set(r.id,this.createTriggerInstance(r,i));this.disposables.add(i.events.subscribe(e=>this.pendingGameEvents.push(e)))}createTriggerInstance(i,s){let r=this.targetsByTag.get(i.tag.id)??[];return{trigger:i,conditions:i.events.map(e=>{let t=this.conditionFactory.create(e,i);return t.setTargets(r),t.init(s),t}).sort((e,t)=>Number(t.blocking)-Number(e.blocking)),targets:r,remainingTargets:new Set(i.tag.repeatType===qt.OnceAll?r:[]),disabled:i.disabled,finished:!1}}update(i){var s,r=this.pendingGameEvents.splice(0,this.pendingGameEvents.length);for(s of this.triggerInstances.values())if(!s.finished&&!s.disabled){let e=!0,t=[];for(var a of s.conditions){var n=a.check(i,r);if("boolean"==typeof n?n||(e=!1):n.length?t.push(...n):e=!1,a.blocking&&!e)break}if(e){var o=s.trigger;s.conditions.forEach(e=>e.reset?.());let e=[];if(o.tag.repeatType===qt.OnceAll){for(var h of t)s.remainingTargets.delete(h);if(s.remainingTargets.size)continue;e=t.length?[t[t.length-1]]:[]}else e=s.targets;this.executeActions(o,e,i),o.tag.repeatType!==qt.Repeat&&(s.finished=!0)}}}executeActions(t,i,s){for(var r of t.actions){let e=this.executorFactory.create(r,t);e.execute(s,i)}}setTriggerEnabled(e,t){let i=this.triggerInstances.get(e);i&&(i.disabled=!t)}forceTrigger(e,t){e=this.triggerInstances.get(e);e&&this.executeActions(e.trigger,e.targets,t)}destroyTrigger(e){this.triggerInstances.delete(e)}destroyTag(e){let t=[];for(var[i,s]of this.triggerInstances)s.trigger.tag.id===e&&t.push(i);for(var r of t)this.destroyTrigger(r)}getGlobalVariable(e){return!!this.globalVariables.get(e)?.value}toggleGlobalVariable(e,t){let i=this.globalVariables.get(e);void 0===i?this.globalVariables.set(e,new Si("No name",t)):i.value=t}getLocalVariable(e){return!!this.localVariables.get(e)?.value}toggleLocalVariable(e,t){let i=this.localVariables.get(e);void 0===i?this.localVariables.set(e,new Si("No name",t)):i.value=t}dispose(){this.disposables.dispose()}}class nd{constructor(e){this.target=e,this.type=rs.TimerExpire}}class od{constructor(){this.ticks=0,this.running=!1}getSeconds(){return Math.floor(this.ticks/Us.BASE_TICKS_PER_SECOND)}setSeconds(e){this.ticks=Math.max(0,Math.floor(Us.BASE_TICKS_PER_SECOND*e))}addSeconds(e){this.ticks=Math.max(0,this.ticks+Math.floor(Us.BASE_TICKS_PER_SECOND*e))}start(){this.running=!0}stop(){this.running=!1}isRunning(){return this.running}update(e){this.running&&(0<this.ticks?this.ticks--:(this.running=!1,e.events.dispatch(new nd(this))))}}(ac=ac||{}).onAdd=Symbol(),(r=nc=nc||{})[r.NotStarted=0]="NotStarted",r[r.Started=1]="Started",r[r.Ended=2]="Ended";class hd{get onEnd(){return this._onEnd.asEvent()}constructor(e,t,i,s,r,a,n,o,h,l,c,u,d,g,p){this.updatableObjects=new Set,this.constructionWorkers=new Map,this.currentTick=0,this.currentTime=0,this.countdownTimer=new od,this._onEnd=new wo,this.afterTickCallbacks=[],this.events=new Kl,this.traits=new xa,this.debugText=new El(""),this.world=e,this.map=t,this.rules=i,this.art=s,this.ai=r,this.id=a,this.startTimestamp=n,this.prng=yc.factory(a,n),this.gameOpts=o,this.gameModeType=h,this.playerList=l,this.unitSelection=c,this.alliances=u,this.desiredSpeed=new El(Us.computeGameSpeed(o.gameSpeed)),this.speed=new El(this.desiredSpeed.value),this.nextObjectId=d,this.objectFactory=g,this.botManager=p,this.triggers=new ad}addPlayer(e){this.playerList.addPlayer(e),this.constructionWorkers.set(e,this.createConstructionWorker(e))}getPlayer(e){return this.playerList.getPlayerAt(e)}getPlayerByName(e){return this.playerList.getPlayerByName(e)}getAiPlayerName(e){let t;return t="number"==typeof e?e:this.gameOpts.aiPlayers.indexOf(e),`@@AI${t+1}@@`}getPlayerNumber(e){return this.playerList.getPlayerNumber(e)}getCombatants(){return this.playerList.getCombatants()}getCivilianPlayer(){return this.playerList.getCivilian()}getAllPlayers(){return this.playerList.getAll()}getNonNeutralPlayers(){return this.playerList.getNonNeutral()}areFriendly(e,t){return e.owner===t.owner||this.alliances.areAllied(e.owner,t.owner)}getWorld(){return this.world}createConstructionWorker(e){return new Ql(e,this.rules,this.art,this.map,this)}getConstructionWorker(e){var t=this.constructionWorkers.get(e);if(!t)throw new Error(`No construction worker found for player "${e.name}"`);return t}getUnitSelection(){return this.unitSelection}init(e){this.localPlayer=e,this.createMapObjects(),this.createPlayerInitialUnits(),this.map.terrain.computeAllPassabilityGraphs(),this.mapShroudTrait.init(this),this.crateGeneratorTrait.init(this),this.playerList.getAll().forEach(e=>e.credits=this.gameOpts.credits),this.rules.mpDialogSettings.alliesAllowed&&this.createInitialTeams()}start(){this.status=nc.Started,this.currentTick=0,this.currentTime=0,this.botManager.init(this),this.triggers.init(this)}createInitialTeams(){for(let t=0;t<this.gameOpts.maxSlots;t++){var i=[...this.gameOpts.humanPlayers,...this.gameOpts.aiPlayers].filter(e=>e?.teamId===t&&-3!==e.countryId).map(e=>xs(e)?e.name:this.getAiPlayerName(e));if(1<i.length)for(let t=0;t<i.length-1;t++)for(let e=t+1;e<i.length;e++){var s=this.getPlayerByName(i[t]),r=this.getPlayerByName(i[e]),r=this.alliances.setAlliance(s,r,Vn.Formed);this.onAllianceChange(r,s,!0)}}}createMapObjects(){var e=this.rules.general.harvesterUnit.every(e=>!V(this.rules.getObject(e,Et.Vehicle).techLevel,0,this.rules.mpDialogSettings.techLevel)),t=this.map.getInitialMapObjects();this.createInitialMapTerrains(t.terrains,e),this.createInitialMapOverlays(t.overlays,e),this.createInitialMapSmudges(t.smudges),this.createInitialMapTechnos(t.technos)}createInitialMapTerrains(e,t){for(var i of e){var s,r,a=i.name;this.validateMapObjectRulesAndArt(a,Et.Terrain)&&((s=this.map.tiles.getByMapCoords(i.rx,i.ry))?(r=this.rules.getObject(a,Et.Terrain),t&&r.spawnsTiberium||(a=this.createObject(Et.Terrain,a),this.spawnObject(a,s))):console.warn(`Invalid map object location (${i.rx},${i.ry})`,i))}}createInitialMapOverlays(e,s){let r=new Map,a=new Map;for(var n of e){var o=this.rules.getOverlayName(n.id);if(this.validateMapObjectRulesAndArt(o,Et.Overlay)){let e=this.createObject(Et.Overlay,o);e.overlayId=n.id,e.value=n.value;let t=n.rx,i=n.ry;e.isBridge()&&e.isHighBridge()&&(e.position.tileElevation=4,t+=e.isXBridge()?0:-1,i+=e.isXBridge()?-1:0);var h=this.map.tiles.getByMapCoords(t,i);if(h)if(e.rules.tiberium&&(o=Za.getOverlayTibType(n.id),void 0!==(o=pn.calculateOverlayId(o,h))&&o!==n.id&&(e.dispose(),e=this.createObject(Et.Overlay,this.rules.getOverlayName(o)),e.overlayId=o,e.value=n.value)),$a.isLowBridge(n.id))$a.isBridgePlaceholder(n.id)||(r.set(h,n.value),1===n.value?a.set(h,e):e.dispose());else{if(e.isTiberium()){if(![ha.Ore,ha.Gems,ha.Vinifera].includes(Za.getOverlayTibType(e.overlayId))){console.warn(`Found unsupported TS tiberium overlay ${e.overlayId} @${h.rx},${h.ry}. Skipping.`);continue}if(this.map.getObjectsOnTile(h).find(e=>e.isTerrain())){e.dispose();continue}}s&&e.isTiberium()?e.dispose():this.spawnObject(e,h)}else console.warn(`Invalid map object location (${t},${i})`,n),e.dispose()}}for(var[t,i]of a){var l=i.isXBridge(),c=this.map.tiles.getByMapCoords(t.rx+(l?0:-1),t.ry+(l?-1:0)),l=this.map.tiles.getByMapCoords(t.rx+(l?0:1),t.ry+(l?1:0));c&&l&&(0===r.get(c)||2===r.get(l))?(i.value=0,this.spawnObject(i,c)):(i.dispose(),console.warn(`Invalid bridge segment @${t.rx},${t.ry}. Skipping.`))}var u,d=[...a.keys()].filter(e=>this.map.bridges.getPieceAtTile(e)?.headType!==zn.None),e=this.map.bridges.findMapHighBridgeHeadTiles();let g=this.map.bridges.findBridgeSpecsForHeadTiles([...d,...e]);for(u of g)for(var p of this.map.bridges.findBridgePieces(u))p.obj.bridgeTrait.bridgeSpec=u;var m,e=g.map(e=>this.map.bridges.findAllBridgeTiles(e)).flat(),f=$a.bridgePlaceholderIds[0],y=this.rules.getOverlayName(f);for(m of e){let e=this.createObject(Et.Overlay,y);e.overlayId=f,this.spawnObject(e,m)}}createInitialMapSmudges(e){for(var t of e){var i=t.name,s=this.map.tiles.getByMapCoords(t.rx,t.ry);s?(i=this.createObject(Et.Smudge,i),this.spawnObject(i,s)):console.warn(`Invalid map object location (${t.rx},${t.ry})`,t)}}createInitialMapTechnos(e){let t=new Map(this.playerList.getAll().filter(e=>!!e.country).map(e=>[e.country.name,e])),s=this.map.getTags();for(let i of e){var r=i.name;if(this.validateMapObjectRulesAndArt(r,i.type)){var a=this.map.tiles.getByMapCoords(i.rx,i.ry);if(a){var n=t.get(i.owner);if(n){if(n.isNeutral){let t=this.createObject(i.type,r);i.tag&&(t.tag=s.find(e=>e.id===i.tag)),t.healthTrait.health=i.health/256*100;let e=!1;if(!t.healthTrait.health){if(!t.isBuilding()||!t.rules.leaveRubble){t.dispose();continue}e=!0}if(i.isInfantry()||i.isVehicle()||i.isAircraft()){t.direction=(-i.direction/256*360+360)%360,i.isInfantry()&&(t.position.subCell=i.subCell);let e=!1;i.onBridge&&(void 0===a.onBridgeLandType?console.warn(`Cannot place unit "${i.name}" on a bridge because `+`no bridge was found at ${a.rx}, ${a.ry}`):e=!0),t.onBridge=e,t.zone=Is(e?a.onBridgeLandType:a.landType),e&&(t.position.tileElevation+=this.map.tileOccupation.getBridgeOnTile(a)?.tileElevation??0),i.veterancy&&t.veteranTrait?.setRelativeXP(i.veterancy)}else t.poweredTrait?.setTurnedOn(i.poweredOn);this.changeObjectOwner(t,n),this.spawnObject(t,a),e&&this.destroyObject(t,void 0,!0)}}else console.warn(`Invalid owner "${i.owner}" for map object`,i)}else console.warn(`Invalid map object location (${i.rx},${i.ry})`,i)}}}validateMapObjectRulesAndArt(e,t){return this.rules.hasObject(e,t)?!!this.art.hasObject(e,t)||(console.warn(`Map object '${e}' has no art section. Skipping.`),!1):(console.warn(`Map object '${e}' has no rules section. Skipping.`),!1)}createPlayerInitialUnits(){let e=this.playerList.getCombatants().map(e=>e.country);var i=[...this.rules.infantryRules.values(),...this.rules.vehicleRules.values()].filter(t=>t.allowedToStartInMultiplayer&&!t.naval&&-1!==t.techLevel&&t.techLevel<=this.rules.mpDialogSettings.techLevel&&!this.rules.general.baseUnit.includes(t.name)&&e.some(e=>t.isAvailableTo(e)&&t.hasOwner(e)));for(let h of this.playerList.getCombatants()){var l=this.map.startingLocations[h.startLocation],c=this.map.tiles.getByMapCoords(l.x,l.y);let t=this.rules.general.baseUnit.find(e=>{let t=this.rules.getObject(e,Et.Vehicle);return t.isAvailableTo(h.country)&&t.hasOwner(h.country)});if(!t)throw new Error(`No suitable MCV found for player country ${h.country?.name}`);l=this.rules.getObject(t,Et.Vehicle),l=this.createUnitForPlayer(l,h);this.spawnObject(l,c);let e=Yl.generate(this.gameOpts.unitCount,[...this.rules.vehicleRules.keys()],i,h.country);this.gameModeType===St.Unholy&&e.push(...this.rules.general.baseUnit.filter(e=>e!==t).map(e=>({name:e,type:Et.Vehicle,count:1})));var u,d,g;let s=[],r=!1,a=new xo(this.map.tiles,this.map.mapBounds,c,4,4,e=>!this.map.getGroundObjectsOnTile(e).find(e=>!(e.isSmudge()||e.isOverlay()&&e.isTiberium()))&&0<this.map.terrain.getPassableSpeed(e,ti.Foot,!1,!1)),n=new Map,o=0;for({name:u,type:d,count:g}of e){let i=g;for(;0<i;){let t;if(r||(t=a.getNextTile(),t?s.push(t):r=!0),r&&s.length){var p=s[o];let e=n.get(p);e||(e=new xo(this.map.tiles,this.map.mapBounds,p,1,0,e=>!this.map.getGroundObjectsOnTile(e).find(e=>!(e.isSmudge()||e.isOverlay()&&e.isTiberium()))&&0<this.map.terrain.getPassableSpeed(e,ti.Foot,!1,!1)),n.set(p,e)),o=(o+1)%s.length,t=e.getNextTile()}if(t){var m,f=this.rules.getObject(u,d);if(d===Et.Vehicle){p=this.createUnitForPlayer(f,h);this.applyInitialVeteran(p,h),this.spawnObject(p,t),i--}else{if(d!==Et.Infantry)throw new Error("Should not reach this line");for(m of Fa.SUB_CELLS.slice(0,i)){let e=this.createUnitForPlayer(f,h);e.position.subCell=m,this.applyInitialVeteran(e,h),this.spawnObject(e,t),i--}}}else i--}}}}applyInitialVeteran(e,t){e.veteranTrait&&(this.rules.general.veteran.initialVeteran?e.veteranTrait.setVeteranLevel(ta.Elite):t.country.hasVeteranUnit(e.type,e.name)&&e.veteranTrait.setVeteranLevel(ta.Veteran))}createObject(e,t){return this.objectFactory.create(e,t,this.rules,this.art)}createUnitForPlayer(e,t){if(![Et.Aircraft,Et.Vehicle,Et.Infantry].includes(e.type))throw new Error(`Attempted to create an invalid unit type "${e.type}"`);let i=this.createObject(e.type,e.name);return this.changeObjectOwner(i,t),i.purchaseValue=this.sellTrait.computePurchaseValue(i.rules,t),i}createProjectile(e,t,i,s,r){let a=this.createObject(Et.Projectile,e);return a.fromWeapon=i,a.fromObject=t,a.fromPlayer=t.owner,a.target=s,a.isShrapnel=r,a}createLooseProjectile(e,t,i){var s=this.rules.getWeapon(e),r=s.projectile,a=this.rules.getProjectile(r),e=this.rules.getWarhead(s.warhead),e={minRange:0,projectileRules:a,range:Number.POSITIVE_INFINITY,rules:s,speed:rn.computeSpeed(s,a),type:li.Primary,warhead:new Ja(e)};let n=this.createObject(Et.Projectile,r);return n.fromWeapon=e,n.fromObject=void 0,n.fromPlayer=t,n.target=i,n}createSuperWeapon(e,t,i=!1){var s=this.rules.getSuperWeapon(e);return new Vs(e,s,t,i)}createTarget(e,t){return new Oo(e,t,this.map.tileOccupation)}isValidTarget(e){if(e){if(!e.isSpawned||e.isCrashing)return!1;if(!(e.rules.legalTarget||e.isBuilding()&&e.rules.hospital))return!1;if(e.isBuilding()&&e.rules.invisibleInGame)return!1}return!0}spawnObject(e,t){if(e.isTechno()&&e.limboData)throw new Error(`Object ${e.name}#${e.id} is in limbo. Use unlimboObject instead or clear limboData first`);this.doSpawnObject(e,t)}unspawnObject(e){e.isTechno()&&e.owner&&e.owner.removeOwnedObject(e),this.doUnspawnObject(e)}limboObject(e,t){e.limboData=t,this.doUnspawnObject(e)}unlimboObject(e,t,i=!1){var s=e.limboData;if(!s)throw new Error(`Object ${e.name}#${e.id} has no limboData attached`);e.limboData=void 0,this.doSpawnObject(e,t);let r=this.getUnitSelection();s.selected&&!i&&r.addToSelection(e),void 0!==s.controlGroup&&r.addUnitsToGroup(s.controlGroup,[e],!1)}doSpawnObject(t,e){var i,s;t.position.tile=e,t.isBuilding()&&(s=t.art.foundationCenter,i=e.rx+s.x,s=e.ry+s.y,t.centerTile=this.map.tiles.getByMapCoords(i,s)??this.map.tiles.getPlaceholderTile(i,s)),this.world.spawnObject(t),(t.cachedTraits.tick.length||t.isProjectile()||t.isDebris()||t.isTechno())&&this.updatableObjects.add(t),t.isTechno()&&this.map.technosByTile.add(t),t.isProjectile()||t.isDebris()||this.map.tileOccupation.occupyTileRange(e,t),t.art.canHideThings&&this.map.tileOcclusion.addOccluder(t),t.onSpawn(this),this.traits.filter(Gn).forEach(e=>{e[Gn.onSpawn](t,this)}),this.events.dispatch(new sc(t))}doUnspawnObject(t){var e=t.tile;t.isProjectile()||t.isDebris()||this.map.tileOccupation.unoccupyTileRange(e,t),t.art.canHideThings&&this.map.tileOcclusion.removeOccluder(t),t.isTechno()&&(this.unitSelection.cleanupUnit(t),this.map.technosByTile.remove(t)),this.world.removeObject(t),this.updatableObjects.delete(t),t.onUnspawn(this),this.traits.filter($n).forEach(e=>{e[$n.onUnspawn](t,this)}),this.events.dispatch(new ic(t))}destroyObject(t,i,e=!1,s=!1){if(t.isDestroyed)throw new Error(`Object with ID "${t.id}" is already destroyed`);if(t.isTechno()){let e=t.mindControllableTrait?.getOriginalOwner()??t.owner;!i||t.isBuilding()&&!e.isCombatant()||(i.player.addUnitsKilled(t.type,1),i.player===e||this.alliances.areAllied(i.player,e)||(i.player.score+=t.rules.points)),e.isNeutral||e.addUnitsLost(t.type,1)}if(t.isDestroyed=!0,t.healthTrait&&(t.healthTrait.health=0),t.onDestroy(this,i,e),this.traits.filter(Zn).forEach(e=>{e[Zn.onDestroy](t,this,i)}),i?.obj?.traits.filter(Wn).forEach(e=>{e[Wn.onDestroy](i.obj,t,i.weapon,this)}),this.events.dispatch(new Jl(t,i,s)),t.isBuilding()&&t.rules.leaveRubble&&t.deathType!==Hr.Temporal){t.owner.removeOwnedObject(t),this.unitSelection.cleanupUnit(t);s=this.map.tileOccupation.calculateTilesForGameObject(t.tile,t);this.map.terrain.invalidateTiles(s),t.art.canHideThings&&this.map.tileOcclusion.removeOccluder(t),this.updatableObjects.delete(t),t.onUnspawn(this),this.traits.filter($n).forEach(e=>{e[$n.onUnspawn](t,this)}),this.events.dispatch(new ic(t))}else if(t.isSpawned)this.unspawnObject(t);else if(t.isTechno()&&t.owner){if(!t.limboData)throw new Error(`Object with ID "${t.id}" should be in limbo but has no limboData`);t.owner.removeOwnedObject(t)}t.dispose()}getObjectById(e){return this.world.getObjectById(e)}changeObjectOwner(t,e){const i=t.owner;i&&i.removeOwnedObject(t),e.addOwnedObject(t),i&&i!==e&&(this.traits.filter(qn).forEach(e=>{e[qn.onChange](t,i,this)}),t.onOwnerChange(i,this),this.events.dispatch(new tc(t,i)),i===this.localPlayer&&t.owner!==this.localPlayer&&(this.unitSelection.removeFromSelection([t]),this.unitSelection.removeUnitsFromGroup([t])))}addObjectTrait(t,i){t.addTrait(i),this.traits.filter(ac).forEach(e=>{e[ac.onAdd](t,i,this)})}onAllianceChange(t,e,i){this.events.dispatch(new rc(t,i?Qn.Formed:Qn.Broken,e)),this.traits.filter(Xn).forEach(e=>{e[Xn.onChange](t,i,this)})}update(){if(this.status!==nc.NotStarted){this.botManager.update(this),this.status!==nc.Ended&&(void 0===this.lastGameEndCheck||1e3<=this.currentTime-this.lastGameEndCheck)&&(this.checkGameEndConditions(),this.lastGameEndCheck=this.currentTime);for(var e of[...this.updatableObjects])e.isSpawned&&e.update(this);if(this.playerList.getCombatants().forEach(e=>e.cheerCooldownTicks=Math.max(0,e.cheerCooldownTicks-1)),this.traits.filter(Ps).forEach(e=>{e[Ps.onTick](this)}),this.localPlayer&&!this.localPlayer.isObserver&&!this.localPlayer.defeated){var t=this.unitSelection.getSelectedUnits();if(1===t.length){let i=t[0];if(i.isTechno()&&i.owner!==this.localPlayer){let t=this.mapShroudTrait.getPlayerShroud(this.localPlayer);this.map.tileOccupation.calculateTilesForGameObject(i.tile,i).find(e=>!t.isShrouded(e,i.tileElevation))||(this.unitSelection.deselectAll(),this.unitSelection.cleanupUnit(i))}}}for(var i of this.afterTickCallbacks)i();this.afterTickCallbacks.length=0,this.triggers.update(this),this.countdownTimer.update(this),this.currentTick++,this.currentTime+=1e3/Us.BASE_TICKS_PER_SECOND}}afterTick(e){this.afterTickCallbacks.push(e)}checkGameEndConditions(){this.updateDefeatedPlayers(this.playerList.getCombatants()),(this.localPlayer?.defeated&&!this.localPlayer.isObserver||!this.alliances.getHostilePlayers().length&&1<this.gameOpts.humanPlayers.length+this.gameOpts.aiPlayers.filter(e=>!!e).length)&&this.end()}end(){this.status!==nc.Ended&&(this.status=nc.Ended,this._onEnd.dispatch(this,void 0))}updateDefeatedPlayers(e){let s=this.stalemateDetectTrait?.isStale()&&0===this.stalemateDetectTrait.getCountdownTicks(),r=this.gameOpts.shortGame;e.forEach(t=>{let i;if(s)i=!0;else{let e;e=r?(e=[...t.getOwnedObjectsByType(Et.Building,!0)].some(e=>!e.rules.insignificant),e||t.getOwnedObjects(!0).some(e=>this.rules.general.baseUnit.includes(e.name))):t.getOwnedObjects(!0).some(e=>!e.rules.insignificant&&!e.limboData?.inTransport),i=!e}var e;i&&(t.defeated=!0,(e=this.alliances.getHostilePlayers().some(e=>!e.first.isAi||!e.second.isAi))&&(t.isObserver=!0),this.removeAllPlayerAssets(t),this.events.dispatch(new ec(t)),e&&(this.mapShroudTrait.getPlayerShroud(t)?.revealAll(),e=t.radarTrait.isDisabled(),t.radarTrait.setDisabled(!1),e&&this.events.dispatch(new zl(t,!0))))})}removeAllPlayerAssets(e){e.getOwnedObjects().forEach(e=>{e.isDestroyed||(e.isBuilding()&&e.rules.returnable&&e.rules.needsEngineer&&!e.garrisonTrait?this.changeObjectOwner(e,this.getCivilianPlayer()):e.isBuilding()&&e.wallTrait||this.destroyObject(e,void 0,!0))}),e.getOwnedObjects(!0).forEach(e=>{e.isDestroyed||(e.limboData?.inTransport||e.isBuilding()&&e.wallTrait?this.changeObjectOwner(e,this.getCivilianPlayer()):this.destroyObject(e,void 0,!0))})}redistributeAllPlayerAssets(e){if(e.isObserver)return!1;if(!(this.rules.mpDialogSettings.mustAlly&&!this.rules.mpDialogSettings.allyChangeAllowed))return!1;let t=this.alliances.getAllies(e).filter(e=>!e.isAi&&!e.defeated);if(0<t.length){var i,s=[...t].sort((e,t)=>t.score-e.score)[0];for(i of e.getOwnedObjects(!0))this.changeObjectOwner(i,s);var r,a=Math.floor(e.credits/t.length),e=e.credits%t.length;for(r of t)r.credits+=a;return t[0].credits+=e,!0}return!1}generateRandomInt(e,t){return this.prng.generateRandomInt(e,t)}generateRandom(){return this.prng.generateRandom()}getHash(){return G([...new Uint8Array(new Float64Array([this.prng.getLastRandom()]).buffer),this.nextObjectId.value,...this.world.getAllObjects().map(e=>e.getHash()),...this.playerList.getAll().map(e=>e.getHash()),this.alliances.getHash(),...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{currentTick:this.currentTick,lastRandom:this.prng.getLastRandom(),nextObjectId:this.nextObjectId.value,objects:this.world.getAllObjects().map(e=>e.debugGetState()),players:this.playerList.getAll().map(e=>e.debugGetState()),alliances:this.alliances.debugGetState(),traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.world.getAllObjects().forEach(e=>e.dispose()),this.playerList.getAll().forEach(e=>e.dispose()),this.constructionWorkers.forEach(e=>e.dispose()),this.botManager.dispose(),this.triggers.dispose(),this.map.dispose(),this.traits.dispose()}}class ld{get onChange(){return this._onChange.asEvent()}constructor(e){this.map=e,this.radSites=new Map,this.radLevelByTile=new Map,this._onChange=new wo}getRadLevel(e){return this.radLevelByTile.get(e)}[Ps.onTick](e){var t;this.radLevelByTile.size&&(t=e.rules.radiation,void 0===this.nextDamage?this.nextDamage=Math.max(0,t.radApplicationDelay-1):this.nextDamage<=0?(this.applyDamage(e),this.nextDamage=Math.max(0,t.radApplicationDelay)):this.nextDamage--,void 0===this.nextDecay?this.nextDecay=Math.max(0,t.radLevelDelay-1):this.nextDecay<=0?(this.applyDecay(Math.ceil(t.radLevelDelay/t.radDurationMultiple)),this.radLevelByTile.size?this.nextDecay=Math.max(0,t.radLevelDelay):this.nextDecay=void 0):this.nextDecay--)}applyDamage(a){let n=a.rules.radiation,o=new Ja(a.rules.getWarhead(n.radSiteWarhead));this.radLevelByTile.forEach((e,t)=>{var i,s,r=Math.min(n.radLevelMax,e)*n.radLevelFactor;for(i of a.map.getGroundObjectsOnTile(t).filter(e=>e.isUnit()&&!(e.isInfantry()&&e.stance===Fs.Paradrop&&1<e.tileElevation)))o.canDamage(i,t,i.zone)&&(0<(s=o.computeDamage(r,i,a))&&o.inflictDamage(s,i,void 0,a,!0))})}applyDecay(s){var e=new Set(this.radLevelByTile.keys());this.radLevelByTile.clear(),this.radSites.forEach(({radLevel:e,radius:t},i)=>{e-=s;e<=0?this.radSites.delete(i):(this.radSites.set(i,{radLevel:e,radius:t}),this.setRadLevelAround(i,t,e))}),this._onChange.dispatch(this,e)}createRadSite(e,t,i){(t-=this.radSites.get(e)?.radLevel??0)<=0||(this.radSites.set(e,{radLevel:(this.radSites.get(e)?.radLevel??0)+t,radius:i}),(t=this.setRadLevelAround(e,i,t)).size&&this._onChange.dispatch(this,t))}setRadLevelAround(e,t,i){let s=new Bs(this.map.tileOccupation),r=new Ws(this.map.tiles,this.map.mapBounds,e,{width:1,height:1},0,t,e=>!!e,!1);var a;let n=new Set;for(;a=r.getNextTile();){var o=s.tileDistance(e,a);o<=t&&(o=Math.ceil(H(i,0*i,o/t)),this.radLevelByTile.set(a,Math.min(1e3,(this.radLevelByTile.get(a)??0)+o)),n.add(a))}return n}getRadSiteLevel(e){return this.radSites.get(e)?.radLevel}}class cd{constructor(){this.factories=new Map}registerFactory(e,t){this.factories.set(e,t)}create(e){let t=this.factories.get(e);if(!t)throw new Error(`No factory registered for action type ${e}`);return t.create()}}class ud{constructor(e){this.player=e,this.selectedUnits=new Set}update(e){var t,i=[...e].reverse().find(e=>e.owner!==this.player);i&&(e=[i]),this.selectedUnits.clear();for(t of e)t.rules.selectable&&this.selectedUnits.add(t)}getSelectedUnits(){return[...this.selectedUnits].map(e=>e.isDisposed&&e.replacedBy?e.replacedBy:e).filter(e=>!e.isDestroyed&&!e.isCrashing)}isSelected(e){return this.selectedUnits.has(e)}}class dd{constructor(){this.unitSelectionByPlayer=new Map}getOrCreateSelection(e){let t=this.unitSelectionByPlayer.get(e);return t||(t=new ud(e),this.unitSelectionByPlayer.set(e,t)),t}}(r=oc=oc||{})[r.NoAction=0]="NoAction",r[r.DropPlayer=1]="DropPlayer",r[r.ObserveGame=2]="ObserveGame",r[r.ResignGame=3]="ResignGame",r[r.DebugCommand=4]="DebugCommand",r[r.PlaceBuilding=5]="PlaceBuilding",r[r.SellObject=6]="SellObject",r[r.ToggleRepair=7]="ToggleRepair",r[r.SelectUnits=8]="SelectUnits",r[r.OrderUnits=9]="OrderUnits",r[r.UpdateQueue=10]="UpdateQueue",r[r.ToggleAlliance=11]="ToggleAlliance",r[r.ActivateSuperWeapon=12]="ActivateSuperWeapon",r[r.PingLocation=13]="PingLocation";class gd{constructor(e){this.actionType=e}unserialize(e){}serialize(){return new Uint8Array}print(){return""}}class pd extends gd{constructor(){super(oc.NoAction)}process(){}}class md{create(){return new pd}}class fd{constructor(e){this.target=e,this.type=rs.BuildingPlace}}class yd{constructor(e,t,i){this.name=e,this.player=t,this.tile=i,this.type=rs.BuildingFailedPlace}}(hc=hc||{}).onPlace=Symbol();class wd extends gd{constructor(e){super(oc.PlaceBuilding),this.game=e}unserialize(e){let t=new k(e);this.buildingRules=this.game.rules.getTechnoByInternalId(t.readUint32(),Et.Building),this.tile={x:t.readUint16(),y:t.readUint16()}}serialize(){let e=new k(8);return e.writeUint32(this.buildingRules.index),e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),e.toUint8Array()}print(){return`Place building ${this.buildingRules.name} at tile (${this.tile.x}, ${this.tile.y})`}process(){var e=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);if(e){var t=this.player;const i=this.tryPlaceBuilding(t,e);i?(this.game.traits.filter(hc).forEach(e=>{e[hc.onPlace](i,this.game)}),this.game.events.dispatch(new fd(i))):this.game.events.dispatch(new yd(this.buildingRules.name,t,e))}else console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}tryPlaceBuilding(s,r){var a=this.buildingRules;if(s.production){let i=s.production.getQueueForObject(a);if(i.status===Tn.Ready&&i.getFirst().rules===a){let t=this.game.getConstructionWorker(s);if(s.production.isAvailableForProduction(a)&&t.canPlaceAt(a.name,r,{normalizedTile:!0})){r=t.placeAt(a.name,r,!0);s.addUnitsBuilt(a,1),i.shift(a,1);let e=s.production.getPrimaryFactory(ts.BuildingType);return e&&(e.factoryTrait.status=_n.Delivering),r[0]}}}}}class Td{constructor(e){this.game=e}create(){return new wd(this.game)}}class bd extends gd{constructor(e){super(oc.SellObject),this.game=e}unserialize(e){this.objectId=new k(e).readUint32()}serialize(){return new k(4).writeUint32(this.objectId).toUint8Array()}print(){return`Sell object ${this.objectId}`}process(){var t=this.player;if(this.game.getWorld().hasObjectId(this.objectId)){let e=this.game.getObjectById(this.objectId);e.isTechno()&&t===e.owner&&e.isSpawned&&(e.isBuilding()?e.buildStatus===xn.Ready&&!e.warpedOutTrait.isActive():e.traits.find(Eo)?.dock?.rules.unitSell)&&this.game.sellTrait.sell(e)}}}class vd{constructor(e){this.game=e}create(){return new bd(this.game)}}const Sd=[Pn.Occupy,Pn.Dock,Pn.Attack,Pn.Capture,Pn.Repair,Pn.EnterTransport,Pn.PlaceBomb,Pn.Deploy,Pn.Gather];(r=lc=lc||{})[r.Default=0]="Default",r[r.Mini=1]="Mini",r[r.Scroll=2]="Scroll",r[r.NoScroll=10]="NoScroll",r[r.Select=18]="Select",r[r.Move=31]="Move",r[r.NoMove=41]="NoMove",r[r.MoveMini=42]="MoveMini",r[r.NoActionMini=52]="NoActionMini",r[r.AttackRange=53]="AttackRange",r[r.AttackNoRange=58]="AttackNoRange",r[r.AttackMini=63]="AttackMini",r[r.Guard=68]="Guard",r[r.GuardMini=73]="GuardMini",r[r.Unknown1=78]="Unknown1",r[r.Unknown2=88]="Unknown2",r[r.Occupy=89]="Occupy",r[r.NoOccupy=99]="NoOccupy",r[r.OccupyMini=100]="OccupyMini",r[r.Deploy=110]="Deploy",r[r.NoDeploy=119]="NoDeploy",r[r.Unknown3=120]="Unknown3",r[r.Sell=129]="Sell",r[r.SellMini=139]="SellMini",r[r.NoSell=149]="NoSell",r[r.RepairMove=150]="RepairMove",r[r.SideRepair=170]="SideRepair",r[r.NoRepair=190]="NoRepair",r[r.Unknown4=191]="Unknown4",r[r.Unknown5=199]="Unknown5",r[r.Dynamite=204]="Dynamite",r[r.Unknown6=209]="Unknown6",r[r.Unknown7=214]="Unknown7",r[r.Unknown8=219]="Unknown8",r[r.Unknown9=224]="Unknown9",r[r.Unknown10=229]="Unknown10",r[r.Unknown11=234]="Unknown11",r[r.Unknwon12=239]="Unknwon12",r[r.Unknown13=249]="Unknown13",r[r.Para=259]="Para",r[r.Unknown14=269]="Unknown14",r[r.Storm=279]="Storm",r[r.EngineerDamage=299]="EngineerDamage",r[r.C4=309]="C4",r[r.Nuke=319]="Nuke",r[r.Unknown16=329]="Unknown16",r[r.Power=339]="Power",r[r.Unknown17=345]="Unknown17",r[r.Iron=346]="Iron",r[r.Unknown18=351]="Unknown18",r[r.Unknown19=356]="Unknown19",r[r.Chrono=357]="Chrono",r[r.DefuseBomb=369]="DefuseBomb",r[r.NoAction=384]="NoAction",r[r.Pan=385]="Pan",r[r.Unknown21=394]="Unknown21",r[r.AttackMove=404]="AttackMove",r[r.Unknown23=413]="Unknown23",r[r.Unknown24=422]="Unknown24",r[r.Unknown25=431]="Unknown25",r[r.Unknown26=432]="Unknown26",r[r.Unknown27=433]="Unknown27",r[r.Unknown28=434]="Unknown28",r[r.Beacon=435]="Beacon",(r=cc=cc||{})[r.None=0]="None",r[r.Move=1]="Move",r[r.Attack=2]="Attack",r[r.Enter=3]="Enter",r[r.Capture=4]="Capture",r[r.SpecialAttack=5]="SpecialAttack";class kd{constructor(e){this.orderType=e,this.targetOptional=!0,this.minimapAllowed=!0,this.singleSelectionRequired=!1,this.terminal=!1,this.feedbackType=cc.None}getPointerType(e,t){return e?lc.Mini:lc.Default}set(e,t){return this.sourceObject=e,this.target=t,this}isValid(){return!0}isAllowed(){return!0}onAdd(e,t){return!0}}class Od{constructor(e,t){this.from=e,this.to=t,this.type=rs.ObjectMorph}}class _d extends $s{constructor(e){super(),this.game=e}onStart(e){if(!this.morphInto)throw new Error("morphInto not set");e.isBuilding()&&e.buildStatus!==xn.BuildDown&&this.morphInto.type!==Et.Building&&this.children.push(new Xl(this.game)),e.isVehicle()&&this.morphInto.type===Et.Building&&this.children.push(new Sr(180))}onTick(t){if(!this.morphInto)throw new Error("morphInto not set");let e=this.game.getUnitSelection();var i=e.isSelected(t),s=e.getOrCreateSelectionModel(t).getControlGroupNumber(),r=this.morphInto;let a;if(r.type===Et.Building){if(t.isVehicle()&&t.parasiteableTrait?.isInfested()&&!t.parasiteableTrait.beingBoarded)return!0;var n=t.tile;let e=this.game.getConstructionWorker(t.owner);if(!e.canPlaceAt(this.morphInto.name,n,{ignoreAdjacent:!0,ignoreObjects:[t]}))return!0;this.game.unspawnObject(t),t.dispose(),[a]=e.placeAt(this.morphInto.name,n),a.healthTrait.health=t.healthTrait.health}else{let e=t.unitOrderTrait.getTasks().filter(e=>e instanceof _a);this.game.unspawnObject(t),t.dispose(),a=this.game.createUnitForPlayer(this.morphInto,t.owner),a.direction=180,a.healthTrait.health=t.healthTrait.health;n=t.art.foundationCenter;this.game.spawnObject(a,this.game.map.tiles.getByMapCoords(t.tile.rx+n.x,t.tile.ry+n.y)),e.forEach(e=>a.unitOrderTrait.addTask(e))}return a.purchaseValue=t.purchaseValue,t.replacedBy=a,i&&e.addToSelection(a),void 0!==s&&e.addUnitsToGroup(s,[a],!1),this.game.events.dispatch(new Od(t,a)),!0}}class Id extends _d{onStart(e){var t=e.rules.undeploysInto;if(!t)throw new Error(`Object type "${e.name}" doesn't undeploy into anything`);this.morphInto=this.game.rules.getObject(t,Et.Vehicle),super.onStart(e)}}class Cd{constructor(e){this.target=e,this.type=rs.RallyPointChange}}class Ad extends $s{constructor(e,t){super(),this.game=e,this.target=t,this.preventOpportunityFire=!1,this.useChildTargetLines=!0,this.attackPerformed=!1}onStart(e){this.children.push(new _a(this.game,this.target.centerTile,!1,{closeEnoughTiles:1,pathFinderIgnoredBlockers:[this.target],stopOnBlocker:this.target}))}onTick(e){if(this.attackPerformed||this.isCancelling()||!e.attackTrait||e.attackTrait.isDisabled())return!0;if(e.moveTrait.lastMoveResult!==Zr.CloseEnough)return!0;var t=e.attackTrait.selectWeaponVersus(e,this.target,this.game,!0);return!t||(this.children.push(e.attackTrait.createAttackTask(this.game,this.target,this.target.tile,t,{force:!0})),!(this.attackPerformed=!0))}}class Bd extends _a{constructor(e,t){super(e,t.tile,t.onBridge,{forceMove:!0,pathFinderIgnoredBlockers:[t]}),this.target=t,this.tilesSinceTargetUpdate=0}onTick(t){if(!(this.isCancelling()||t.moveTrait.moveState!==Xr.ReachedNextWaypoint||this.target.tile===this.targetTile&&this.target.onBridge===this.toBridge&&this.target.moveTrait.isIdle())){let e=!1;var i;(t.tile===this.targetTile&&this.target.tile!==this.targetTile||10<this.tilesSinceTargetUpdate++)&&(e=!0),e&&(this.tilesSinceTargetUpdate=0,(i=this.target.moveTrait.currentWaypoint)?this.updateTarget(i.tile,!!i.onBridge):this.updateTarget(this.target.tile,this.target.onBridge))}return super.onTick(t)}forceCancel(e){return super.forceCancel(e)}getTargetLinesConfig(e){return{target:this.target,pathNodes:[]}}}class xd extends kd{constructor(e,t,i,s=!1){super(s?Pn.ForceMove:Pn.Move),this.game=e,this.map=t,this.unitSelection=i,this.forceMove=s,this.targetOptional=!1,this.feedbackType=cc.Move}getPointerType(e){let t=this.isAllowed();var i,s,r,a,n;return!t||this.forceMove||this.sourceObject.isBuilding()||this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)||(i=!!this.target.getBridge(),s=this.sourceObject.rules.speedType,r=this.sourceObject.isInfantry(),a=this.sourceObject.rules.movementZone===ai.Fly,n=this.map.getObjectsOnTile(this.target.tile).some(e=>(e.isInfantry()||e.isVehicle())&&e.disguiseTrait?.hasTerrainDisguise()),t=a?this.sourceObject.rules.airportBound||this.target.tile.landType===ei.Cliff||0<this.map.terrain.getPassableSpeed(this.target.tile,ti.Amphibious,!1,i)&&!n:0<this.map.terrain.getPassableSpeed(this.target.tile,s,r,i)&&!n&&!(this.target.obj?.isTechno()&&!this.game.areFriendly(this.target.obj,this.sourceObject))),e?t?lc.MoveMini:lc.NoActionMini:t?lc.Move:lc.NoMove}isValid(){return!(this.sourceObject.isBuilding()&&(!this.sourceObject.rules.undeploysInto||this.sourceObject.rules.constructionYard&&!this.game.gameOpts.mcvRepacks)&&!this.sourceObject.rallyTrait?.getRallyPoint())&&(this.forceMove||!this.target.obj||(this.target.obj.isOverlay()||this.target.obj.isBuilding())&&this.target.obj.rules.wall||this.target.obj.isTechno()&&this.target.obj.owner===this.sourceObject.owner&&this.unitSelection.isSelected(this.target.obj)||(this.target.obj.isInfantry()||this.target.obj.isVehicle())&&!!this.target.obj.disguiseTrait?.hasTerrainDisguise()||this.target.obj.isTechno()&&!this.game.areFriendly(this.target.obj,this.sourceObject))}isAllowed(){return(!this.sourceObject.isUnit()||!this.sourceObject.moveTrait.isDisabled())&&(this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)?this.sourceObject.rules.moveToShroud:!(!this.forceMove&&this.target.obj?.isTechno()&&this.target.obj.owner===this.sourceObject.owner&&this.unitSelection.isSelected(this.target.obj)))}process(){const e=this.sourceObject;if(!e.isBuilding()||!e.rallyTrait?.getRallyPoint()){var t=this.game.rules.general.closeEnough;return e.isBuilding()&&e.rules.undeploysInto?[new Id(this.game),new _a(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:t,forceMove:this.forceMove})]:e.isUnit()?this.isEnemyBuildingBlock()?[new Ad(this.game,this.target.obj)]:this.isFollowMove()?[new Bd(this.game,this.target.obj)]:[new _a(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:t,forceMove:this.forceMove})]:void 0}}isEnemyBuildingBlock(){return this.forceMove&&this.sourceObject.isVehicle()&&!this.sourceObject.rules.consideredAircraft&&this.target.obj?.isBuilding()&&!this.game.areFriendly(this.sourceObject,this.target.obj)}isFollowMove(){return this.forceMove&&this.target.obj?.isInfantry()&&this.sourceObject.isVehicle()&&!this.sourceObject.rules.consideredAircraft&&!this.target.obj.moveTrait.isIdle()}onAdd(t,e){var i=this.sourceObject.isBuilding()&&this.sourceObject.rules.undeploysInto;if(i&&this.sourceObject.buildStatus===xn.BuildUp)return this.sourceObject.unitOrderTrait.getTasks().find(e=>e instanceof Ko)?.setCancellable(!0),!0;if(!i&&this.sourceObject.isBuilding()&&this.sourceObject.rallyTrait?.getRallyPoint())return this.sourceObject.rallyTrait.changeRallyPoint(this.target.tile,this.sourceObject,this.game),this.game.events.dispatch(new Cd(this.sourceObject)),!1;if(!this.isEnemyBuildingBlock()&&!this.isFollowMove()&&!e&&this.isValid()&&this.isAllowed()){this.sourceObject.attackTrait?.cancelOpportunityFire();let e=t.find(e=>e.constructor===_a&&!e.isCancelling());if(e)return e.setForceMove(this.forceMove),e.updateTarget(this.target.tile,!!this.target.getBridge()),e.children.length&&e.children[0]instanceof Io&&e.children[0].cancel(),t.splice(t.indexOf(e)+1),this.sourceObject.unitOrderTrait.clearOrders(),!1;if(this.sourceObject.isUnit()&&this.sourceObject.rules.movementZone===ai.Fly){let e=t.find(e=>[Io,Ao,Co].includes(e.constructor)&&!e.isCancelling());e&&e.forceCancel(this.sourceObject)&&t.splice(t.indexOf(e))}}return!0}}class Ed extends _d{onStart(e){var t=e.rules.deploysInto;if(!t)throw new Error(`Object type "${e.name}" doesn't deploy into anything`);this.morphInto=this.game.rules.getObject(t,Et.Building),super.onStart(e)}onTick(e){return!!this.isCancelling()||super.onTick(e)}}class Pd{constructor(e,t){this.unit=e,this.deployType=t,this.type=rs.UnitDeployUndeploy}}class Nd{constructor(e){this.target=e,this.type=rs.PrimaryFactoryChange}}(r=uc=uc||{})[r.None=0]="None",r[r.OnlyPassengers=1]="OnlyPassengers",r[r.All=2]="All";class Dd extends $s{constructor(e,t){super(),this.game=e,this.soft=t,this.evacState=uc.None,this.evacTries=0,this.turnPerformed=!1,this.preventLanding=!1}forceEvac(){this.evacState=uc.All}onStart(e){if(!e.transportTrait)throw new Error(`Object "${e.name}" is not a valid transport`);var t=e.transportTrait;0<t.units.length&&(this.evacState=this.evacState!==uc.OnlyPassengers&&1!==t.units.length||!e.rules.gunner?uc.OnlyPassengers:uc.All)}onTick(e){if(this.isCancelling()||this.evacState===uc.None)return!0;if(e.zone===Ss.Air)return this.children.push(new ya(()=>e.zone!==Ss.Air)),!1;let t=e.transportTrait.units;if(!t.length||e.rules.gunner&&1===t.length&&this.evacState!==uc.All)return!0;var i=t[t.length-1],s=this.findValidEvacTarget(e,i);if(s&&!this.turnPerformed){this.turnPerformed=!0;var r=(s.dir+180)%360;if(e.direction!==r)return this.children.push(new Sr(r)),!1}return this.evacuateUnit(i,e,s)?(t.pop(),this.children.push(new fa(1/60)),!1):!(++this.evacTries<=3)||(this.children.push(new fa(.05)),!1)}evacuateUnit(e,t,i){if(!i)return!this.soft&&(e.position.tile=t.tile,e.position.tileElevation=t.tileElevation,e.onBridge=t.onBridge,e.zone=t.zone,this.game.destroyObject(e,{player:e.owner}),!0);var{spawnNode:s,moveNode:i}=i;return e.position.tileElevation=s.onBridge?.tileElevation??0,e.onBridge=!!s.onBridge,e.zone=this.game.map.getTileZone(s.tile,!s.onBridge),this.game.unlimboObject(e,s.tile),e.unitOrderTrait.unmarkNextQueuedOrder(),i?e.unitOrderTrait.addTask(new _a(this.game,i.tile,!!i.onBridge)):e.unitOrderTrait.addTask(new Oa(this.game)),this.game.events.dispatch(new mh(t)),!0}findValidEvacTarget(a,n){let o=this.game.map,h=new Zs(o);var l,c,u,d,g,t=a.onBridge?o.tileOccupation.getBridgeOnTile(a.tile):void 0,i=(a.direction+180)%360;let p;for(let e=0;e<=180;e+=45)for(l of e&&e<180?[i+e,i-e]:[i]){var m=vr.toMapCoords(l);let i=a.tile,s=t,r;for(let t=1;t<=2;t++){if(2===t){if(!r)break;i=r.tile,s=r.onBridge}var f,y=a.tile.rx+Math.sign(m.x)*t,w=a.tile.ry+Math.sign(m.y)*t,T=o.tiles.getByMapCoords(y,w);if(!T||!o.mapBounds.isWithinBounds(T))break;let e=[o.tileOccupation.getBridgeOnTile(T)];e[0]&&e.push(void 0);for(f of e)if(c=T,u=f,d=s,g=i,0<o.terrain.getPassableSpeed(c,n.rules.speedType,n.isInfantry(),!!u)&&h.isEligibleTile(c,u,d,g)&&!o.terrain.findObstacles({tile:c,onBridge:u},n).length){if(1!==t)return{spawnNode:r,moveNode:{tile:T,onBridge:f},dir:l};r={tile:T,onBridge:f},p={spawnNode:r,moveNode:void 0,dir:l}}}}if(p)return p}}class Md extends kd{constructor(e,t){super(t?Pn.Deploy:Pn.DeploySelected),this.game=e,this.targeted=t,this.minimapAllowed=!1,this.getPointerType=()=>this.isAllowed()?lc.Deploy:lc.NoDeploy,this.targetOptional=!t,this.singleSelectionRequired=t}isValid(){if(this.targeted&&(!this.target.obj||this.target.obj!==this.sourceObject))return!1;let e=this.sourceObject;return!!(e.isInfantry()&&e.deployerTrait&&![Fs.Cheer].includes(e.stance)||e.isVehicle()&&e.deployerTrait||e.isVehicle()&&e.rules.deploysInto||e.isVehicle()&&e.transportTrait||e.isBuilding()&&e.rules.factory&&!e.owner.production?.isPrimaryFactory(e)||e.isBuilding()&&e.garrisonTrait?.units.length)}isAllowed(){let t=this.sourceObject;if(t.isVehicle()&&t.transportTrait)return!!(t.transportTrait.units.length&&0<this.game.map.terrain.getPassableSpeed(t.tile,ti.Foot,!1,t.onBridge));if((t.isInfantry()||t.isVehicle())&&t.deployerTrait)return!0;if(t.isVehicle()&&t.rules.deploysInto){if(t.parasiteableTrait?.isInfested()&&!t.parasiteableTrait.beingBoarded)return!1;let e=this.game.getConstructionWorker(t.owner);if(t.moveTrait.currentWaypoint?.onBridge)return!1;var i=t.moveTrait.currentWaypoint?.tile??t.tile;return e.canPlaceAt(t.rules.deploysInto,i,{ignoreObjects:[t],ignoreAdjacent:!0})}if(t.isBuilding()&&t.rules.factory)return!0;if(t.isBuilding()&&t.garrisonTrait?.units.length)return!0;throw new Error("Shouldn't reach this point. Missed a case.")}process(){const e=this.sourceObject;return e.isVehicle()&&e.transportTrait?[new Dd(this.game,!0)]:e.isBuilding()&&e.rules.factory?void 0:e.isVehicle()&&e.rules.deploysInto?[new Ed(this.game)]:(e.isInfantry()||e.isVehicle())&&e.deployerTrait?[new ya(()=>{e.deployerTrait.toggleDeployed(),this.game.events.dispatch(new Pd(e,e.deployerTrait.isDeployed()?"undeploy":"deploy"))})]:e.isBuilding()&&e.garrisonTrait?.units.length?[new ya(()=>{e.garrisonTrait.evacuate(this.game,!0)})]:void 0}onAdd(t,e){let i=this.sourceObject;if(i.isBuilding()&&i.rules.factory)return i.owner.production.setPrimaryFactory(i),this.game.events.dispatch(new Nd(i)),!1;if(i.isVehicle()&&i.transportTrait&&!e&&this.isValid()&&this.isAllowed()){let e=t.find(e=>e.constructor===Dd&&!e.isCancelling());if(e)return e.forceEvac(),!1}return!0}}class Rd{constructor(e){this.player=e,this.type=rs.Cheer}}class Ld{constructor(e){this.target=e,this.type=rs.DeployNotAllowed}}class Fd extends gd{constructor(e,t,i,s){super(oc.OrderUnits),this.game=e,this.map=t,this.orderActionContext=i,this.orderFactory=s,this.queue=!1,this.isInvalid=!1}unserialize(t){let i=new k(t);this.orderType=i.readUint8();var s=i.readUint8();if(0!==s){var r=i.readUint16(),t=i.readUint16();this.queue=2<s&&Boolean(i.readUint8());let e;if(3<s){s=i.readUint32();if(!this.game.getWorld().hasObjectId(s))return void(this.isInvalid=!0);e=this.game.getObjectById(s)}else e=void 0;t=this.map.tiles.getByMapCoords(r,t);t?this.target=this.game.createTarget(e,t):this.isInvalid=!0}}serialize(){let e=new k(11);e.dynamicSize=!1,e.writeUint8(this.orderType);let t=0;e.writeUint8(t),this.target&&(e.writeUint16(this.target.tile.rx),e.writeUint16(this.target.tile.ry),t+=2,i=(this.target.obj||this.target.getBridge())?.id,!this.queue&&void 0===i||(e.writeUint8(Number(this.queue)),t+=1),void 0!==i&&(e.writeUint32(i),t+=1));var i=e.position;return 0<t&&(e.seek(1),e.writeUint8(t)),new Uint8Array(e.buffer,e.byteOffset,i)}print(){return this.isInvalid?"":`${Pn[this.orderType]} order `+(this.target?`[obj: ${(this.target.obj||this.target.getBridge())?.name||"<none>"}, `+`tile: ${this.target.tile.rx},${this.target.tile.ry}]`+(this.queue?"(queue)":""):"")}process(){if(!this.isInvalid){let n=this.player;const c=this.game.mapShroudTrait.getPlayerShroud(n);if(c){const u=this.target?.obj;if(u){let e=this.game.map.tileOccupation.calculateTilesForGameObject(u.tile,u);if(!e.find(e=>!c.isShrouded(e,u.tileElevation)))return}let e=this.validateOrders(n).slice(0,128),a=[],t=[],s=[],i=[],r=[];if(e.forEach(e=>{(e instanceof xd?t:e.orderType===Pn.Scatter?s:e.orderType===Pn.DeploySelected?i:e.orderType===Pn.Cheer?r:a).push(e)}),t.length&&this.target){var o=t[0].isEnemyBuildingBlock(),h=t[0].isFollowMove();if(o||h)t.forEach(e=>a.push(e));else{let s=this.target.getBridge();var l=t[0].forceMove,h=t.map(e=>e.sourceObject);let r=new Zs(this.map).findPositions(h,this.target.tile,s,l);t.forEach(e=>{var t=r.get(e.sourceObject),i=!s||s.isHighBridge()?this.map.tileOccupation.getBridgeOnTile(t):s,t=this.game.createTarget(i,t);e.target=t,a.push(e)})}}if(s.length){l=s.map(e=>e.sourceObject).filter(e=>e.isInfantry()||e.isVehicle());let i=new ka(this.game).findPositions(l);s.forEach(e=>{var t=i.get(e.sourceObject);t&&(t=this.game.createTarget(t.onBridge,t.tile),e.target=t,a.push(e))})}if(i.length){let t=[];i.forEach(e=>{((e.sourceObject.isInfantry()||e.sourceObject.isVehicle())&&e.sourceObject.deployerTrait?t:a).push(e)});let e=t.filter(e=>!e.sourceObject.deployerTrait.isDeployed());e.length?e.forEach(e=>a.push(e)):t.forEach(e=>a.push(e))}r.length&&(n.cheerCooldownTicks||(n.cheerCooldownTicks=this.game.rules.general.maximumCheerRate,a.push(...r),this.game.events.dispatch(new Rd(n)))),a.forEach(e=>e.sourceObject.unitOrderTrait.addOrder(e,this.queue)),this.updateWaypointPaths(a)}}}validateOrders(e){let i=this.orderActionContext.getOrCreateSelection(e);var s,r=i.getSelectedUnits();let t=this.orderFactory.create(this.orderType,i);t.target=this.target;let a=[];for(s of r)if(!(s.owner!==e||s.rules.spawned||s.isDestroyed||s.isCrashing||s.isDisposed||s.warpedOutTrait.isActive()||(t.sourceObject=s,t instanceof Md&&t.isValid()&&!t.isAllowed()&&this.game.events.dispatch(new Ld(s)),t.singleSelectionRequired&&1<r.length)))if(t.isValid()&&t.isAllowed()){let e=this.orderFactory.create(this.orderType,i);e.set(s,this.target),a.push(e)}else{let t=!1;for(var n of Sd){let e=this.orderFactory.create(n,i);if(e.set(s,this.target),!(e.singleSelectionRequired&&1<r.length)&&(e.targetOptional===!this.target&&e.isValid()&&e.isAllowed())){a.push(e),t=!0;break}}if(!t&&this.target&&this.orderType!==Pn.Deploy){let e=this.orderFactory.create(Pn.Move,i);e.set(s,this.target),e.isValid()&&e.isAllowed()&&a.push(e)}}return a}updateWaypointPaths(i){if(this.queue&&this.target){let e=i.map(e=>e.sourceObject);var t=[...new Set(e.map(e=>e.unitOrderTrait.waypointPath).filter(Wa))];if(t.length<=1){i={orderType:this.orderType,target:this.target,terminal:i.some(e=>e.terminal),next:void 0};if(0===t.length){let t={units:e,waypoints:[i]};e.forEach(e=>{e.unitOrderTrait.waypointPath=t})}else{let e=t[0];e.waypoints[e.waypoints.length-1].next=i,e.waypoints.push(i)}}}}}class jd extends gd{get unitIds(){return this._unitIds}set unitIds(e){this._unitIds=e.slice(0,128)}constructor(e,t){super(oc.SelectUnits),this.orderActionContext=t}unserialize(t){let i=new k(t);this.unitIds=new Array(t.byteLength/4);for(let e=0;e<t.byteLength/4;e++)this.unitIds[e]=i.readUint32()}serialize(){let e=new k(4*this.unitIds.length);e.dynamicSize=!1;for(var t of this.unitIds)e.writeUint32(t);return e.toUint8Array()}print(){return`Select unit(s) [${this.unitIds.join(",")}]`}process(){let e=this.player,t=[];for(var i of this.unitIds){i=e.getOwnedObjectById(i);i&&t.push(i)}this.orderActionContext.getOrCreateSelection(e).update(t)}}class Ud{constructor(e,t){this.game=e,this.orderActionContext=t}create(){return new jd(this.game,this.orderActionContext)}}class Wd{constructor(e){this.target=e,this.type=rs.BuildingGarrison}}class zd extends _a{constructor(e,t,i){super(e,i??t.tile,!1,{ignoredBlockers:[t]}),this.target=t,this.cancellable=!1}canStopAtTile(e,t,i){return!this.game.map.tileOccupation.isTileOccupiedBy(t,this.target)&&super.canStopAtTile(e,t,i)}}class Vd extends _a{static chooseTargetFoundationTile(t,i){if(t.isBuilding()){let e=t.centerTile;return i.map.mapBounds.isWithinBounds(e)||(e=i.map.tileOccupation.calculateTilesForGameObject(t.tile,t).find(e=>i.map.mapBounds.isWithinBounds(e))??t.tile),e}return t.tile}constructor(e,t){super(e,Vd.chooseTargetFoundationTile(t,e),!1,{ignoredBlockers:[t],closeEnoughTiles:0}),this.target=t}hasReachedDestination(e){return super.hasReachedDestination(e)||this.canStopAtTile(e,e.tile,e.onBridge)}canStopAtTile(e,t,i){t=this.game.map.tileOccupation.isTileOccupiedBy(t,this.target);return(!this.isCancelling()||!t)&&!(!this.isCancelling()&&!t)}isCloseEnoughToDest(e,t,i){return this.game.map.tileOccupation.isTileOccupiedBy(t,this.target)}}class Hd{constructor(e,t){this.target=e,this.source=t,this.type=rs.EnterObject}}class Gd extends $s{constructor(e,t){super(),this.game=e,this.target=t,this.aborted=!1,this.movePerformed=!1,this.preventOpportunityFire=!1}onTick(e){return!!(this.isCancelling()&&!this.movePerformed||this.aborted||e.moveTrait.isDisabled())||(this.movePerformed&&this.children.length?(e.tile===this.lastOutsideTile||this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)||(this.lastOutsideTile=e.tile),!1):this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)?!this.isAllowed(e)||this.isCancelling()?(this.children.push(new zd(this.game,this.target,this.lastOutsideTile)),!(this.aborted=!0)):(this.game.events.dispatch(new Hd(this.target,e)),!1!==this.onEnter(e)||(this.children.push(new zd(this.game,this.target,this.lastOutsideTile)),!(this.aborted=!0))):!!this.movePerformed||(this.children.push(new Vd(this.game,this.target).setBlocking(!1)),this.movePerformed=!0,!(this.preventOpportunityFire=!0)))}getTargetLinesConfig(e){return{target:this.target,pathNodes:[]}}}class $d extends Gd{isAllowed(e){return!this.target.isDestroyed&&!!this.target.garrisonTrait?.canBeOccupied()&&this.target.garrisonTrait.units.length<this.target.garrisonTrait.maxOccupants&&!(this.target.garrisonTrait.units.length&&this.target.garrisonTrait.units[0].owner!==e.owner)&&!e.mindControllableTrait?.isActive()}onEnter(e){this.game.limboObject(e,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(e).getControlGroupNumber()});let t=this.target.garrisonTrait;t.units.length||(e.owner.buildingsCaptured++,this.game.changeObjectOwner(this.target,e.owner),this.game.events.dispatch(new Wd(this.target))),t.units.push(e)}}class qd{constructor(e){this.target=e,this.type=rs.UnitRecycle}}class Xd extends Gd{isAllowed(e){return e.rules.movementZone!==ai.Fly&&e.rules.locomotor!==ri.Chrono&&!e.rules.engineer&&0<this.game.sellTrait.computeRefundValue(e)&&(e.isInfantry()&&this.target.rules.cloning||this.target.rules.grinding)&&!this.target.isDestroyed&&this.target.buildStatus===xn.Ready&&e.owner===this.target.owner}onEnter(e){this.game.sellTrait.sell(e),this.game.events.dispatch(new qd(e))}}class Zd{constructor(e,t){this.target=e,this.source=t,this.type=rs.BuildingInfiltration}}class Qd extends Gd{isAllowed(e){return e.rules.infiltrate&&this.target.rules.spyable&&!this.target.isDestroyed&&!this.game.areFriendly(e,this.target)}onEnter(e){this.game.unspawnObject(e),e.agentTrait?.infiltrate(e,this.target,this.game),this.game.events.dispatch(new Zd(this.target,e))}}(r=dc=dc||{})[r.MoveToQueueingTile=0]="MoveToQueueingTile",r[r.WaitForTurn=1]="WaitForTurn",r[r.MoveToTarget=2]="MoveToTarget",r[r.EnterTarget=3]="EnterTarget",r[r.ClearTarget=4]="ClearTarget";class Yd extends $s{constructor(e,t){super(),this.game=e,this.target=t,this.movePerformed=!1}isAllowed(e){return e.rules.movementZone!==ai.Fly&&e.healthTrait.health<100&&this.target.hospitalTrait&&!this.target.isDestroyed&&!this.target.warpedOutTrait.isActive()&&this.game.areFriendly(e,this.target)&&(!this.target.ammoTrait||0<this.target.ammoTrait.ammo)}onStart(e){if(!this.target.hospitalTrait)throw new Error(`Target ${this.target.name} is not a valid hospital`);0<this.target.hospitalTrait.addToHealQueue(e)?this.state=dc.MoveToQueueingTile:this.state=dc.MoveToTarget}onEnd(e){!this.target.isDestroyed&&e.isSpawned&&this.target.hospitalTrait.removeFromHealQueue(e)}onTick(i){if(this.isCancelling()&&this.state!==dc.EnterTarget||this.state===dc.ClearTarget||i.moveTrait.isDisabled())return!0;if(this.state===dc.MoveToQueueingTile){let t=new Zs(this.game.map);var e=new Ws(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>0<this.game.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&t.isEligibleTile(e,void 0,void 0,this.target.tile)).getNextTile();return!e||(this.children.push(new _a(this.game,e,!1,{closeEnoughTiles:5})),this.children.push(new ya(()=>{[Zr.Success,Zr.CloseEnough].includes(i.moveTrait.lastMoveResult)||this.cancel()})),this.state=dc.WaitForTurn,this.queueingTile=e,!1)}if(this.state===dc.WaitForTurn){if(!this.target.hospitalTrait.unitIsFirstInHealQueue(i))return!1;this.queueingTile=void 0,this.state=dc.MoveToTarget}if(this.state===dc.MoveToTarget){if(this.movePerformed&&this.children.length)return i.tile===this.lastOutsideTile||this.game.map.tileOccupation.isTileOccupiedBy(i.tile,this.target)||(this.lastOutsideTile=i.tile),!1;if(!this.isAllowed(i))return!0;if(!this.game.map.tileOccupation.isTileOccupiedBy(i.tile,this.target))return!!this.movePerformed||(this.children.push(new Vd(this.game,this.target).setBlocking(!1)),!(this.movePerformed=!0));this.state=dc.EnterTarget}return this.state===dc.EnterTarget&&(!this.isAllowed(i)||this.isCancelling()?(this.children.push(new zd(this.game,this.target,this.lastOutsideTile)),this.state=dc.ClearTarget,!1):(this.game.limboObject(i,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(i).getControlGroupNumber()}),this.target.hospitalTrait.startHealing(i),this.game.events.dispatch(new Hd(this.target,i)),!0))}getTargetLinesConfig(e){return{target:this.queueingTile?void 0:this.target,pathNodes:this.queueingTile?[{tile:this.queueingTile,onBridge:void 0}]:[]}}}class Kd extends kd{constructor(e){super(Pn.Occupy),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=cc.Capture}getPointerType(e){return e?this.isAllowed()?lc.OccupyMini:lc.NoActionMini:this.isAllowed()?lc.Occupy:lc.NoOccupy}isValid(){return!!(this.target.obj?.isSpawned&&this.target.obj?.isBuilding()&&this.sourceObject.isUnit())&&(!!this.isUnitRecycle(this.sourceObject,this.target.obj)||!!this.sourceObject.isInfantry()&&(this.target.obj.isBuilding()&&this.target.obj.hospitalTrait?this.game.areFriendly(this.sourceObject,this.target.obj)&&this.sourceObject.isInfantry():this.target.obj.garrisonTrait?this.target.obj.garrisonTrait.canBeOccupied()&&this.sourceObject.rules.occupier&&!(this.target.obj.garrisonTrait.units.length&&this.target.obj.garrisonTrait.units[0].owner!==this.sourceObject.owner)&&!this.sourceObject.mindControllableTrait?.isActive()&&!this.sourceObject.mindControllerTrait?.isActive():!(!this.target.obj.rules.spyable||!this.sourceObject.rules.infiltrate||this.game.areFriendly(this.sourceObject,this.target.obj))))}isUnitRecycle(e,t){return e.owner===t.owner&&(e.isInfantry()&&t.rules.cloning||t.rules.grinding)&&!e.rules.engineer}isAllowed(){var e=this.target.obj,t=this.sourceObject;return this.isUnitRecycle(t,e)?t.rules.movementZone!==ai.Fly&&t.rules.locomotor!==ri.Chrono&&0<this.game.sellTrait.computeRefundValue(t):e.hospitalTrait?t.healthTrait.health<100&&t.rules.movementZone!==ai.Fly:!e.garrisonTrait||e.garrisonTrait.units.length<e.rules.maxNumberOccupants}process(){var e=this.target.obj,t=this.sourceObject;return this.isUnitRecycle(t,e)?[new Xd(this.game,e)]:e.hospitalTrait?[new Yd(this.game,e)]:e.garrisonTrait?[new $d(this.game,e)]:[new Qd(this.game,e)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof $d||e instanceof Qd);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new Bs(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class Jd extends Gd{isAllowed(e){return!this.target.isDestroyed&&!this.target.invulnerableTrait.isActive()}onEnter(e){var t=Math.floor(60*this.game.rules.combatDamage.c4Delay*Us.BASE_TICKS_PER_SECOND);return this.target.c4ChargeTrait.setCharge(t,{player:e.owner,obj:e}),this.game.events.dispatch(new Hd(this.target,e)),!1}getTargetLinesConfig(e){return{target:this.target,pathNodes:[],isAttack:!0}}}class eg extends kd{constructor(e,{forceAttack:t,noIvanBomb:i}={}){super(t?Pn.ForceAttack:Pn.Attack),this.game=e,this.isC4=!1,this.forceAttack=!!t,this.ivanBombAllowed=!i||!!t,this.targetOptional=!1,this.feedbackType=cc.None,this.rangeHelper=new Bs(this.game.map.tileOccupation),this.losHelper=new vo(this.game.map.tiles,e.map.tileOccupation)}getPointerType(e,t){if(!this.isAllowed())return e?lc.NoActionMini:lc.NoAction;if(this.isC4)return lc.C4;var i=this.sourceObject.attackTrait?.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);if(i?.rules.sabotageCursor)return lc.C4;if(this.ivanBombAllowed&&this.sourceObject.rules.ivan&&i?.warhead.rules.ivanBomb)return lc.Dynamite;if(i?.warhead.rules.bombDisarm)return lc.DefuseBomb;if(i&&i.rules.damage<0)return lc.RepairMove;t=t.every(e=>{if(!e.attackTrait)return!0;var t=e.attackTrait.selectWeaponVersus(e,this.target,this.game,this.forceAttack);return!t||this.rangeHelper.isInWeaponRange(e,this.target.obj||this.target.tile,t,this.game.rules)&&this.losHelper.hasLineOfSight(e,this.target.obj||this.target.tile,t)});return e?lc.AttackMini:t?lc.AttackRange:lc.AttackNoRange}isValid(){if(!this.sourceObject.attackTrait)return!1;if(this.forceAttack&&this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.isBuilding())return!1;let e=this.target.obj;var t=this.game.map.getGroundObjectsOnTile(this.target.tile).find(e=>e.isTerrain());if(this.terminal=!e&&!t,this.sourceObject.c4&&e?.isBuilding()&&e.c4ChargeTrait&&(this.forceAttack||!this.game.areFriendly(e,this.sourceObject)||e.cabHutTrait))return this.isC4=!0,this.feedbackType=cc.SpecialAttack,!0;if(this.isC4=!1,this.feedbackType=cc.Attack,!this.game.isValidTarget(e))return!1;if(!e&&t?.rules.immune)return!1;if(!(e||this.target.tile!==this.sourceObject.tile||this.sourceObject.isUnit()&&this.sourceObject.zone===Ss.Air))return!1;if(e===this.sourceObject)return!1;t=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);return!!t&&(!(!this.ivanBombAllowed&&t.warhead.rules.ivanBomb)&&(!(e?.isBuilding()&&e.cabHutTrait&&!t.warhead.rules.ivanBomb&&!t.warhead.rules.bombDisarm)&&(!!(this.sourceObject.isUnit()&&this.sourceObject.moveTrait&&!this.sourceObject.moveTrait.isDisabled()||this.rangeHelper.isInWeaponRange(this.sourceObject,e||this.target.tile,t,this.game.rules))&&(!(this.sourceObject.airSpawnTrait&&t.rules.spawner&&!this.game.map.isWithinBounds(this.target.tile))&&(!!this.forceAttack||(!e?.isBuilding()||!e.hospitalTrait)&&(!(!e||!e.healthTrait)&&(!e.isDestroyed&&!e.isCrashing&&(!(!e.isOverlay()||!(t.warhead.rules.wall||t.warhead.rules.wood&&e.rules.armor===ni.Wood))||e.isTechno()))))))))}isAllowed(){return!this.sourceObject.attackTrait.isDisabled()}process(){if(this.isC4)return[new Jd(this.game,this.target.obj)];var e=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);return[new Io(this.game,this.target,e,{force:this.forceAttack})]}onAdd(t,e){let i=this.sourceObject;if(!e&&i.isUnit()&&this.isValid()&&this.isAllowed())if(i.rules.movementZone===ai.Fly){let e=t.find(e=>(e.constructor===_a||e.constructor===Io)&&!e.isCancelling());e&&(i.moveTrait.currentWaypoint?.tile===this.target.tile||i.isAircraft()||e.constructor===Io)&&e.forceCancel(i)&&t.splice(t.indexOf(e))}else{t.length&&i.isUnit()&&(i.rules.locomotor===ri.Vehicle||i.rules.locomotor===ri.Ship)&&(i.moveTrait.speedPenalty=.5);let e=t.find(e=>e.constructor===Io&&!e.isCancelling());if(e?.getWeapon().warhead.rules.temporal)return e.setForceAttack(this.forceAttack),e.requestTargetUpdate(this.target),!1}return!0}}class tg extends kd{constructor(e){super(Pn.Stop),this.game=e,this.getPointerType=()=>lc.NoAction}isValid(){return this.sourceObject.isTechno()}isAllowed(){return!0}process(){return[new ya(e=>{!e.isUnit()||e.rules.locomotor!==ri.Vehicle&&e.rules.locomotor!==ri.Ship||(e.moveTrait.speedPenalty=0)})]}onAdd(e,t){let i=this.sourceObject;return t||!e.length||!i.isUnit()||i.rules.locomotor!==ri.Vehicle&&i.rules.locomotor!==ri.Ship||(i.moveTrait.speedPenalty=.5),i.isBuilding()&&i.rallyTrait?.getRallyPoint()&&(i.unitRepairTrait?.resetRallyPoint(i,this.game),i.factoryTrait?.resetRallyPoint(i,this.game)),!0}}class ig extends kd{constructor(){super(Pn.Cheer),this.getPointerType=()=>lc.NoAction}isValid(){return this.sourceObject.isInfantry()&&[Fs.None,Fs.Guard].includes(this.sourceObject.stance)}isAllowed(){return!0}process(){return[new kc]}}class sg extends kd{constructor(e){super(Pn.Dock),this.game=e,this.targetOptional=!1,this.feedbackType=cc.Move}getPointerType(e){return e?this.isAllowed()?lc.OccupyMini:lc.NoActionMini:this.isAllowed()?lc.Occupy:lc.NoOccupy}isValid(){if(!this.target.obj?.isBuilding()||this.target.obj.isDestroyed||!this.target.obj.dockTrait||this.target.obj.buildStatus!==xn.Ready||!this.sourceObject.isUnit()||this.target.obj.warpedOutTrait.isActive())return!1;var e=!(this.target.obj.rules.refinery||this.target.obj.unitRepairTrait);return this.game.areFriendly(this.target.obj,this.sourceObject)&&this.target.obj.dockTrait.isValidUnitForDock(this.sourceObject)&&!this.target.obj.dockTrait.isDocked(this.sourceObject)&&!(this.target.obj.unitRepairTrait&&!this.sourceObject.rules.dock.includes(this.target.obj.name)&&100===this.sourceObject.healthTrait.health)&&(!e||(0<(this.target.obj.dockTrait.getAvailableDockCount()??0)||this.target.obj.dockTrait.hasReservedDockForUnit(this.sourceObject)))}isAllowed(){return!0}process(){var e=this.target.obj;return e.rules.refinery&&this.sourceObject.isVehicle()&&this.sourceObject.harvesterTrait?[new gh(this.game,e,!0,!0)]:e.unitRepairTrait||this.sourceObject.rules.dock.includes(e.name)?[new wa(this.game,e)]:[]}}class rg extends kd{constructor(e){super(Pn.Gather),this.game=e,this.targetOptional=!1,this.feedbackType=cc.Move}getPointerType(e){return e?lc.AttackMini:lc.AttackNoRange}isValid(){return!(!this.sourceObject.isVehicle()||!this.sourceObject.harvesterTrait||this.sourceObject.moveTrait.isDisabled()||this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation))&&this.target.isOre}isAllowed(){return!0}process(){return[new dh(this.game,this.target.tile,!0)]}}class ag extends eg{constructor(e,t){super(e),this.map=t,this.orderType=Pn.AttackMove,this.targetOptional=!1,this.feedbackType=cc.Move}getPointerType(t,i){if(this.isTargetted()){let e=super.getPointerType(t,i);return e!==lc.AttackRange&&e!==lc.AttackNoRange||(e=lc.AttackMove),e}let e=this.isAllowed();var s,r,a;return e&&(s=!!this.target.getBridge(),r=this.sourceObject.rules.speedType,a=this.sourceObject.isInfantry(),i=this.sourceObject.rules.movementZone===ai.Fly,e=i||0<this.map.terrain.getPassableSpeed(this.target.tile,r,a,s)||!!this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)),t?e?lc.AttackMini:lc.NoActionMini:e?lc.AttackMove:lc.NoMove}isValid(){var e=this.sourceObject.isUnit()&&!!this.sourceObject.attackTrait&&!this.sourceObject.rules.preventAttackMove&&!(this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.rules.moveToShroud)&&(!this.isTargetted()||super.isValid());return this.feedbackType=cc.Move,e}isAllowed(){return!(!this.isTargetted()&&this.sourceObject.moveTrait.isDisabled())&&super.isAllowed()}process(){if(this.isTargetted()){if(this.isC4)return[new Jd(this.game,this.target.obj)];var e=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game);return[new Co(this.game,this.target,e)]}return[new Ao(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:this.game.rules.general.closeEnough})]}isTargetted(){return this.target.obj?.isTechno()}onAdd(t,e){let i=this.sourceObject;if(!e&&i.isUnit()&&this.isValid()&&this.isAllowed())if(i.rules.movementZone===ai.Fly){let e=t.find(e=>[_a,Io,Ao,Co].includes(e.constructor)&&!e.isCancelling());if(e)if(this.isTargetted())(i.moveTrait.currentWaypoint?.tile===this.target.tile||i.isAircraft()||e.constructor!==_a)&&e.forceCancel(i)&&t.splice(t.indexOf(e));else{if(e.constructor===Ao)return e.updateTarget(this.target.tile,!!this.target.getBridge()),t.splice(t.indexOf(e)+1),i.unitOrderTrait.clearOrders(),!1;e.forceCancel(i)&&t.splice(t.indexOf(e))}}else this.isTargetted()&&t.length&&i.isUnit()&&(i.rules.locomotor===ri.Vehicle||i.rules.locomotor===ri.Ship)&&(i.moveTrait.speedPenalty=.5);return!0}}class ng{constructor(e,t){this.target=e,this.source=t,this.type=rs.BuildingRepairFull}}class og{constructor(e,t){this.source=e,this.tile=t,this.type=rs.BridgeRepair}}class hg extends Gd{isAllowed(e){return this.target.cabHutTrait?this.target.cabHutTrait.canRepairBridge():e.rules.engineer&&!this.target.isDestroyed&&this.target.rules.repairable&&this.target.healthTrait.health<100&&(!this.target.owner.isCombatant()&&!!this.target.garrisonTrait||this.game.areFriendly(e,this.target))}onEnter(e){this.game.unspawnObject(e),this.target.cabHutTrait?(this.target.cabHutTrait.repairBridge(this.game,e.owner),this.game.events.dispatch(new og(e.owner,this.target.centerTile))):(this.target.healthTrait.healToFull(e,this.game),this.game.events.dispatch(new ng(this.target,e.owner)))}}class lg extends kd{constructor(e){super(Pn.Repair),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=cc.Capture}getPointerType(e){return e?this.isAllowed()?lc.OccupyMini:lc.NoActionMini:this.isAllowed()?lc.RepairMove:lc.NoRepair}isValid(){return!!this.target.obj?.isBuilding()&&!this.target.obj.isDestroyed&&this.sourceObject.isInfantry()&&this.sourceObject.rules.engineer&&(!this.target.obj.owner.isCombatant()&&(!!this.target.obj.garrisonTrait||!!this.target.obj.cabHutTrait)||this.game.areFriendly(this.target.obj,this.sourceObject))}isAllowed(){let e=this.target.obj;return e.cabHutTrait?e.cabHutTrait.canRepairBridge():!!(e.rules.repairable&&e.healthTrait.health<100)}process(){var e=this.target.obj;return[new hg(this.game,e)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof hg);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new Bs(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class cg extends kd{constructor(e,t){super(t?Pn.GuardArea:Pn.Guard),this.game=e,this.targeted=t,this.getPointerType=e=>e?this.isAllowed()?lc.GuardMini:lc.NoActionMini:this.isAllowed()?lc.Guard:lc.NoMove,this.terminal=!0,this.targetOptional=!t,this.minimapAllowed=t,this.feedbackType=t?cc.Move:cc.None}isValid(){return this.sourceObject.isUnit()&&(!!this.targetOptional||!this.sourceObject.moveTrait.isDisabled())&&!(this.target&&this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.rules.moveToShroud)}isAllowed(){return!0}process(){let t=this.targeted?this.target.tile:void 0;const e=this.sourceObject;let i=[];return t&&i.push(new _a(this.game,t,!!this.target.getBridge(),{closeEnoughTiles:this.game.rules.general.closeEnough})),e.isVehicle()&&e.harvesterTrait?i.push(new ya(()=>e.harvesterTrait.lastOreSite=void 0),new dh(this.game,void 0,!0)):i.push(new ya(e=>{t&&![Zr.Success,Zr.CloseEnough].includes(this.sourceObject.moveTrait?.lastMoveResult)||(this.sourceObject.guardMode=!0)})),i}}class ug extends kd{constructor(e){super(Pn.Scatter),this.game=e,this.getPointerType=()=>lc.NoAction}isValid(){return(this.sourceObject.isInfantry()||this.sourceObject.isVehicle())&&this.sourceObject.rules.movementZone!==ai.Fly&&!this.sourceObject.moveTrait.isDisabled()}isAllowed(){return!0}process(){if(!this.target)throw new Error("Target should be set for executing a scatter order. See OrderUnitsAction.");return[new Oa(this.game,{tile:this.target.tile,toBridge:!!this.target.getBridge()})]}}class dg{constructor(e){this.target=e,this.type=rs.EnterTransport}}(r=gc=gc||{})[r.MoveToQueueingTile=0]="MoveToQueueingTile",r[r.WaitForTurn=1]="WaitForTurn",r[r.MoveToTransport=2]="MoveToTransport",r[r.EnterTransport=3]="EnterTransport",r[r.ClearTransport=4]="ClearTransport";class gg extends $s{constructor(e,t){super(),this.game=e,this.target=t,this.movePerformed=!1,this.preventOpportunityFire=!1}isAllowed(e){return!this.target.isDestroyed&&!this.target.isCrashing&&this.game.areFriendly(this.target,e)&&e.zone!==Ss.Air&&this.target.zone!==Ss.Air&&this.target.transportTrait.unitFitsInside(e)&&this.target.moveTrait.moveState===Xr.Idle&&!this.target.warpedOutTrait.isActive()&&!e.mindControllableTrait?.isActive()&&!e.mindControllerTrait?.isActive()}onStart(e){if(!this.target.transportTrait)throw new Error(`Unit ${this.target.name} is not a valid transport`);this.initialTargetTile=this.target.tile,0<this.target.transportTrait.addToLoadQueue(e)?this.state=gc.MoveToQueueingTile:this.state=gc.MoveToTransport}onEnd(e){this.target.isDestroyed||this.target.transportTrait?.removeFromLoadQueue(e)}onTick(n){if(this.isCancelling()&&this.state!==gc.EnterTransport||this.state===gc.ClearTransport||n.moveTrait.isDisabled())return!0;if(this.target.tile!==this.initialTargetTile||this.target.moveTrait.moveState!==Xr.Idle)return!0;if(this.state===gc.MoveToQueueingTile){let s=new Zs(this.game.map),r=this.target.onBridge?this.game.map.tileOccupation.getBridgeOnTile(this.target.tile):void 0,a;var e=new Ws(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>{let t=[this.game.map.tileOccupation.getBridgeOnTile(e)];t[0]&&t.push(void 0);for(var i of t)if(0<this.game.map.terrain.getPassableSpeed(e,n.rules.speedType,n.isInfantry(),!!i)&&s.isEligibleTile(e,i,r,this.target.tile))return a=i,!0;return!1}).getNextTile();return!e||(this.children.push(new _a(this.game,e,!!a,{closeEnoughTiles:5})),this.children.push(new ya(()=>{[Zr.Success,Zr.CloseEnough].includes(n.moveTrait.lastMoveResult)||this.cancel()})),this.queueingNode={tile:e,onBridge:a},this.state=gc.WaitForTurn,!1)}if(this.state===gc.WaitForTurn){if(!this.target.transportTrait.unitIsFirstInLoadQueue(n))return!1;this.queueingNode=void 0,this.state=gc.MoveToTransport}if(this.state===gc.MoveToTransport){if(!this.isAllowed(n))return!0;if(!this.game.map.tileOccupation.isTileOccupiedBy(n.tile,this.target))return!!this.movePerformed||(this.children.push(new Vd(this.game,this.target)),this.movePerformed=!0,!(this.preventOpportunityFire=!0));this.state=gc.EnterTransport}return this.state===gc.EnterTransport&&(!this.isAllowed(n)||this.isCancelling()?(this.children.push(new zd(this.game,this.target)),this.state=gc.ClearTransport,!1):(this.game.limboObject(n,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(n).getControlGroupNumber(),inTransport:!0}),this.game.events.dispatch(new dg(this.target)),this.game.events.dispatch(new Hd(this.target,n)),this.target.transportTrait.units.push(n),!0))}getTargetLinesConfig(e){return{target:this.queueingNode?void 0:this.target,pathNodes:this.queueingNode?[this.queueingNode]:[]}}}class pg extends kd{constructor(e){super(Pn.EnterTransport),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=cc.Enter}getPointerType(e){return e?this.isAllowed()?lc.OccupyMini:lc.NoActionMini:this.isAllowed()?lc.Occupy:lc.NoOccupy}isValid(){return!(!this.target.obj?.isVehicle()||!this.target.obj.transportTrait||this.target.obj.isDestroyed||this.target.obj===this.sourceObject||!this.game.areFriendly(this.target.obj,this.sourceObject)||!this.sourceObject.isVehicle()&&!this.sourceObject.isInfantry())}isAllowed(){let e=this.target.obj,t=this.sourceObject;return t.zone!==Ss.Air&&e.zone!==Ss.Air&&e.transportTrait.unitFitsInside(t)&&e.moveTrait.moveState===Xr.Idle&&!e.warpedOutTrait.isActive()&&!t.mindControllableTrait?.isActive()&&!t.mindControllerTrait?.isActive()}process(){let e=this.sourceObject,t=this.target.obj;return this.game.map.terrain.getPassableSpeed(t.tile,e.rules.speedType,e.isInfantry(),e.onBridge)?[new gg(this.game,t)]:[new ya(()=>{t.unitOrderTrait.addTask(new _a(this.game,e.tile,e.onBridge)),t.unitOrderTrait.addTask(new ya(()=>{this.game.map.terrain.getPassableSpeed(t.tile,e.rules.speedType,e.isInfantry(),e.onBridge)&&e.unitOrderTrait.addTask(new gg(this.game,t))}))})]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof gg);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new Bs(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class mg{constructor(e){this.target=e,this.type=rs.BuildingCapture}}class fg extends Gd{isAllowed(e){return e.rules.engineer&&this.target.rules.capturable&&!this.target.isDestroyed&&this.target.buildStatus!==xn.BuildDown&&!this.game.areFriendly(e,this.target)}onEnter(t){if(this.game.unspawnObject(t),this.game.gameOpts.multiEngineer){var i=this.game.rules.general;if((!this.target.rules.needsEngineer||!i.engineerAlwaysCaptureTech)&&this.target.healthTrait.health>100*i.engineerCaptureLevel){var s=Math.floor(i.engineerDamage*this.target.healthTrait.maxHitPoints),i=Math.floor((1-Math.floor(1/i.engineerDamage)*i.engineerDamage)*this.target.healthTrait.maxHitPoints);if(0<(s=Math.min(s,this.target.healthTrait.getHitPoints()-i))){i=this.game.rules.combatDamage.c4Warhead;let e=new Ja(this.game.rules.getWarhead(i));return void e.detonate(this.game,s,this.target.tile,0,this.target.position.worldPosition,Ss.Ground,na.None,this.game.createTarget(this.target,this.target.tile),{player:t.owner,obj:t,weapon:void 0},ca.None,void 0,0)}}}t.owner.buildingsCaptured++,this.game.changeObjectOwner(this.target,t.owner),this.game.events.dispatch(new mg(this.target))}}class yg extends kd{constructor(e){super(Pn.Capture),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=cc.Capture}getPointerType(e){if(!this.isAllowed())return e?lc.NoActionMini:lc.NoOccupy;if(e)return lc.OccupyMini;if(this.game.gameOpts.multiEngineer){var t=this.game.rules.general,e=this.target.obj;if((!e.rules.needsEngineer||!t.engineerAlwaysCaptureTech)&&e.healthTrait.health>100*t.engineerCaptureLevel)return lc.EngineerDamage}return lc.Occupy}isValid(){return!(this.target.obj?.isDestroyed||!this.target.obj?.isBuilding()||!this.sourceObject.isInfantry())&&(this.target.obj.rules.capturable&&this.sourceObject.rules.engineer&&!this.game.areFriendly(this.sourceObject,this.target.obj))}isAllowed(){return!0}process(){return[new fg(this.game,this.target.obj)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof fg);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new Bs(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class wg{constructor(e,t){this.game=e,this.map=t}create(e,t){switch(e){case Pn.Deploy:return new Md(this.game,!0);case Pn.DeploySelected:return new Md(this.game,!1);case Pn.ForceMove:return new xd(this.game,this.map,t,!0);case Pn.Move:return new xd(this.game,this.map,t);case Pn.ForceAttack:return new eg(this.game,{forceAttack:!0});case Pn.Attack:return new eg(this.game,{noIvanBomb:!0});case Pn.PlaceBomb:return new eg(this.game);case Pn.AttackMove:return new ag(this.game,this.map);case Pn.Capture:return new yg(this.game);case Pn.Occupy:return new Kd(this.game);case Pn.Stop:return new tg(this.game);case Pn.Cheer:return new ig;case Pn.Dock:return new sg(this.game);case Pn.Gather:return new rg(this.game);case Pn.Repair:return new lg(this.game);case Pn.Guard:return new cg(this.game,!1);case Pn.GuardArea:return new cg(this.game,!0);case Pn.Scatter:return new ug(this.game);case Pn.EnterTransport:return new pg(this.game);default:throw new Error(`Unhandled order type ${Pn[e]}`)}}}class Tg{constructor(e,t,i){this.game=e,this.map=t,this.orderActionContext=i}create(){return new Fd(this.game,this.map,this.orderActionContext,new wg(this.game,this.map))}}(r=pc=pc||{})[r.Add=0]="Add",r[r.Cancel=1]="Cancel",r[r.Pause=2]="Pause",r[r.Resume=3]="Resume";class bg extends gd{constructor(e){super(oc.UpdateQueue),this.game=e}unserialize(e){let t=new k(e);var i;this.queueType=t.readUint8(),this.updateType=t.readUint8(),this.updateType!==pc.Add&&this.updateType!==pc.Cancel||(i=t.readUint32(),e=t.readUint8(),this.item=this.game.rules.getTechnoByInternalId(i,e),this.quantity=t.readUint16())}serialize(){let e=new k(9);if(e.dynamicSize=!1,e.writeUint8(this.queueType),e.writeUint8(this.updateType),this.updateType===pc.Add||this.updateType===pc.Cancel){if(void 0===this.quantity)throw new Error("Missing quantity");if(65535<this.quantity)throw new Error("Maximum quantity exceeded");e.writeUint32(this.item.index),e.writeUint8(this.item.type),e.writeUint16(this.quantity)}return new Uint8Array(e.buffer,e.byteOffset,e.position)}print(){return this.updateType===pc.Resume?`Resume queue ${wn[this.queueType]}`:this.updateType===pc.Add?`Add to queue ${this.item.name} x ${this.quantity}`:this.updateType===pc.Pause?`Put queue ${wn[this.queueType]} on hold.`:this.updateType===pc.Cancel?`Cancel ${this.item.name} x ${this.quantity}`:`Unhandled queue update type ${this.updateType}`}process(){let i=this.player,s=this.item,r=i.production.getQueue(this.queueType);if(this.updateType===pc.Resume)r.status===Tn.OnHold&&(r.status=Tn.Active);else if(this.updateType===pc.Add){let e=r.find(s);if(r.status===Tn.Active||r.status===Tn.Idle||r.status===Tn.OnHold&&e[0]!==r.getFirst()||r.status===Tn.Ready&&s.type!==Et.Building){let t;var a=e.reduce((e,t)=>e+t.quantity,0);if(Number.isFinite(s.buildLimit)){let e;e=0<=s.buildLimit?i.getOwnedObjectsByType(s.type,!0).filter(e=>e.name===s.name).length:i.getLimitedUnitsBuilt(s.name),t=Math.max(0,Math.abs(s.buildLimit)-(e+a))}else t=Number.POSITIVE_INFINITY;t&&i.production.isAvailableForProduction(s)&&(n=Math.min(r.maxSize-r.currentSize,r.maxItemQuantity-a,t),0<(o=Math.min(this.quantity,n))&&r.push(s,o,s.cost))}}else if(this.updateType===pc.Cancel){if([Tn.Ready,Tn.OnHold,Tn.Active].includes(r.status)){let e=r.find(s);var n,o;e.length&&(n=e.reduce((e,t)=>e+t.quantity,0),0<(o=Math.min(n,this.quantity))&&(r.pop(s,o),o===n&&(i.credits+=e[0].creditsSpent)))}}else this.updateType===pc.Pause&&r.status===Tn.Active&&(r.status=Tn.OnHold)}}class vg{constructor(e){this.game=e}create(){return new bg(this.game)}}class Sg{constructor(e,t){this.target=e,this.assetsRedistributed=t,this.type=rs.PlayerDropped}}class kg extends gd{constructor(e,t){super(oc.DropPlayer),this.game=e,this.localPlayerName=t}process(){if(this.localPlayerName!==this.player.name){let e=this.player;var t;e.defeated||(t=this.game.redistributeAllPlayerAssets(e),this.game.removeAllPlayerAssets(e),e.dropped=!0,this.game.events.dispatch(new Sg(e,t)))}}}class Og{constructor(e,t){this.game=e,this.localPlayerName=t}create(){return new kg(this.game,this.localPlayerName)}}class _g{constructor(e){this.target=e,this.type=rs.BuildingRepairStart}}class Ig extends gd{constructor(e){super(oc.ToggleRepair),this.game=e}unserialize(e){this.buildingId=new k(e).readUint32()}serialize(){return new k(4).writeUint32(this.buildingId).toUint8Array()}print(){return`Toggle repair ${this.buildingId}`}process(){var e=this.player;if(this.game.getWorld().hasObjectId(this.buildingId)){let t=this.game.getObjectById(this.buildingId);if(t.isBuilding()&&e===t.owner&&!t.isDestroyed&&t.rules.repairable&&t.rules.clickRepairable&&100!==t.healthTrait.health){let e=t.traits.get(Uh);e.setDisabled(!e.isDisabled()),e.isDisabled()||this.game.events.dispatch(new _g(t))}}}}class Cg{constructor(e){this.game=e}create(){return new Ig(this.game)}}class Ag extends gd{constructor(e){super(oc.ToggleAlliance),this.game=e}unserialize(e){this.toPlayer=this.game.getPlayer(e[0]),this.toggle=Boolean(e[1])}serialize(){return new Uint8Array([this.game.getPlayerNumber(this.toPlayer),this.toggle?1:0])}print(){return`Toggle alliance ${this.toggle?"on":"off"} with ${this.toPlayer.name}`}process(){var e=this.game.rules.mpDialogSettings;if(e.alliesAllowed&&e.allyChangeAllowed){var a,n=this.player,t=this.toPlayer,e=this.toggle;let i=n,s=t,r=this.game.alliances;if(!n.defeated&&r.canRequestAlliance(s)){let t=r.findByPlayers(i,s);t?t.status===Vn.Formed?e||(r.breakAlliance(i,s),this.game.onAllianceChange(t,i,!1)):t.status===Vn.Requested&&(t.players.first===s?e&&r.canFormAlliance(i,s)&&(r.acceptRequest(s,i),this.game.onAllianceChange(t,i,!0),1!==(n=this.game.getCombatants().filter(e=>e!==i&&!r.areAllied(i,e))).length||(a=r.findByPlayers(n[0],i))&&r.cancelRequest(a.players.first,a.players.second),1!==(a=this.game.getCombatants().filter(e=>e!==s&&!r.areAllied(s,e))).length||(a=r.findByPlayers(a[0],s))&&r.cancelRequest(a.players.first,a.players.second)):e||(r.cancelRequest(i,s),this.game.events.dispatch(new rc(t,Qn.Broken,i)),this.game.traits.filter(Xn).forEach(e=>{e[Xn.onChange](t,!1,this.game)}))):e&&r.canFormAlliance(i,s)&&((e=r.request(i,s))&&this.game.events.dispatch(new rc(e,Qn.Requested,i)))}}}}class Bg{constructor(e){this.game=e}create(){return new Ag(this.game)}}class xg extends gd{constructor(e){super(oc.ActivateSuperWeapon),this.game=e}unserialize(e){let t=new k(e);this.superWeaponType=t.readUint8();e=t.readUint8();this.tile={x:t.readUint16(),y:t.readUint16()},this.tile2=2<e?{x:t.readUint16(),y:t.readUint16()}:void 0}serialize(){let e=new k(6+(this.tile2?4:0));return e.dynamicSize=!1,e.writeUint8(this.superWeaponType),e.writeUint8(this.tile2?4:2),e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),this.tile2&&(e.writeUint16(this.tile2.x),e.writeUint16(this.tile2.y)),e.toUint8Array()}print(){return`Activate SuperW ${ss[this.superWeaponType]} at tile (${this.tile.x}, ${this.tile.y})`+(this.tile2?`, (${this.tile2.x}, ${this.tile2.y})`:"")}process(){var e,t=this.player,i=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);i?(e=this.tile2?this.game.map.tiles.getByMapCoords(this.tile2.x,this.tile2.y):void 0,this.game.traits.get(un).activateSuperWeapon(this.superWeaponType,t,this.game,i,e)):console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}}class Eg{constructor(e){this.game=e}create(){return new xg(this.game)}}class Pg{constructor(e,t){this.tile=e,this.player=t,this.type=rs.PingLocation}}class Ng extends gd{constructor(e){super(oc.PingLocation),this.game=e}unserialize(e){let t=new k(e);this.tile={x:t.readUint16(),y:t.readUint16()}}serialize(){let e=new k(4);return e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),e.toUint8Array()}print(){return`Ping location at tile (${this.tile.x}, ${this.tile.y})`}process(){var e=this.player,t=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);if(t){this.game.events.dispatch(new Pg(t,e));for(var i of[e,...this.game.alliances.getAllies(e)])this.game.events.dispatch(new Vl(i,Yt.GenericNonCombat,t))}else console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}}class Dg{constructor(e){this.game=e}create(){return new Ng(this.game)}}class Mg{constructor(e,t){this.target=e,this.assetsRedistributed=t,this.type=rs.PlayerResigned}}class Rg extends gd{constructor(e){super(oc.ObserveGame),this.game=e}process(){let e=this.player;var t;this.game.removeAllPlayerAssets(e),!e.isCombatant()||e.defeated||e.isObserver||(e.resigned=!0,e.defeated=!0,e.isObserver=!0,this.game.events.dispatch(new Mg(e)),this.game.events.dispatch(new ec(e)),this.game.mapShroudTrait.getPlayerShroud(e)?.revealAll(),t=e.radarTrait.isDisabled(),e.radarTrait.setDisabled(!1),t&&this.game.events.dispatch(new zl(e,!0)))}}class Lg{constructor(e){this.game=e}create(){return new Rg(this.game)}}class Fg extends gd{constructor(e,t){super(oc.ResignGame),this.game=e,this.localPlayerName=t}process(){if(this.localPlayerName!==this.player.name){let e=this.player;var t=this.game.redistributeAllPlayerAssets(e);this.game.removeAllPlayerAssets(e),e.isCombatant()&&(e.resigned=!0,this.game.events.dispatch(new Mg(e,t)))}}}class jg{constructor(e,t){this.game=e,this.localPlayerName=t}create(){return new Fg(this.game,this.localPlayerName)}}(r=mc=mc||{})[r.SetGlobalDebugText=0]="SetGlobalDebugText",r[r.SetUnitDebugText=1]="SetUnitDebugText";class Ug{constructor(e,t){this.type=e,this.params=t}}class Wg extends gd{constructor(e){super(oc.DebugCommand),this.game=e}unserialize(e){let t=new k(e);e=t.readUint8();e===mc.SetUnitDebugText?this.command=new Ug(e,{unitId:t.readUint32(),label:t.readCString()||void 0}):e===mc.SetGlobalDebugText?this.command=new Ug(e,{text:t.readCString()}):console.warn(`Debug command ${e} not implemented`)}serialize(){let e=new k;if(e.writeUint8(this.command.type),this.command.type===mc.SetUnitDebugText){var t=this.command.params;e.writeUint32(t.unitId),e.writeCString(t.label||"")}else{if(this.command.type!==mc.SetGlobalDebugText)throw new Error(`Debug command ${this.command.type} not implemented`);t=this.command.params;e.writeCString(t.text)}return e.toUint8Array()}process(){if(this.command.type===mc.SetUnitDebugText){var{unitId:t,label:i}=this.command.params;if(this.game.getWorld().hasObjectId(t)){let e=this.game.getObjectById(t);e.isTechno()&&(e.debugLabel=i)}}else this.command.type===mc.SetGlobalDebugText?(i=this.command.params["text"],this.game.debugText.value=i):console.warn(`Debug command ${this.command.type} not implemented`)}}class zg{constructor(e){this.game=e}create(){return new Wg(this.game)}}class Vg{register(e,t,i){var s=new dd;e.registerFactory(oc.NoAction,new md),e.registerFactory(oc.PlaceBuilding,new Td(t)),e.registerFactory(oc.SellObject,new vd(t)),e.registerFactory(oc.ToggleRepair,new Cg(t)),e.registerFactory(oc.SelectUnits,new Ud(t,s)),e.registerFactory(oc.OrderUnits,new Tg(t,t.map,s)),e.registerFactory(oc.UpdateQueue,new vg(t)),e.registerFactory(oc.ToggleAlliance,new Bg(t)),e.registerFactory(oc.ActivateSuperWeapon,new Eg(t)),e.registerFactory(oc.PingLocation,new Dg(t)),e.registerFactory(oc.DropPlayer,new Og(t,i)),e.registerFactory(oc.ObserveGame,new Lg(t)),e.registerFactory(oc.ResignGame,new jg(t,i)),e.registerFactory(oc.DebugCommand,new zg(t))}}class Hg{constructor(){this.detectors=new Set}[Gn.onSpawn](e,t){this.isGlobalDetector(e)&&(this.detectors.add(e),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&this.detect(e,t)}[$n.onUnspawn](e,t){e.isTechno()&&(this.isGlobalDetector(e)&&(this.detectors.delete(e),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&this.undetect(e,t))}[qn.onChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,i),this.isDisguisable(e)&&(this.undetect(e,i),this.detect(e,i))}[Gr.onTileChange](e,t,i){this.isGlobalDetector(e)&&(this.updateAroundDetector(e,t,i),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&(this.undetect(e,t),this.detect(e,t))}[Rs.onPowerLow](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait&&!e.poweredTrait.isPoweredOn());this.updateAroundDetectors(i,e)}[Rs.onPowerRestore](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait);this.updateAroundDetectors(i,e)}[Rs.onPowerChange](e,t){}updateAroundDetectors(e,t){let i=new Set;for(var s of e)for(var r of this.findTechnosAroundDetector(s,t,s.tile))i.add(r);for(var a of i)this.isDisguisable(a)&&(this.undetect(a,t),this.detect(a,t))}updateAroundDetector(e,t,i=e.tile){var s;for(s of this.findTechnosAroundDetector(e,t,i))this.isDisguisable(s)&&(this.undetect(s,t),this.detect(s,t))}findTechnosAroundDetector(e,t,i){var s=e.getFoundation(),s=Math.max(s.width,s.height),e=e.rules.detectDisguiseRange+s,s=new Os(i.rx,i.ry).addScalar(-e),e=new Os(i.rx,i.ry).addScalar(e);return t.map.technosByTile.queryRange(new Yn(s,e))}detect(e,t){let i=new Set,s=new Bs(t.map.tileOccupation);for(var r of this.detectors)if(!t.areFriendly(r,e)){var a=r.owner,n=r.rules.detectDisguiseRange;if(!i.has(a))if(!(r.isBuilding()&&r.poweredTrait&&!r.poweredTrait.isPoweredOn())&&s.tileDistance(e,r.tile)<=n)for(var o of[a,...t.alliances.getAllies(a)])i.add(o)}for(var h of i)h.sharedDetectDisguiseTrait?.add(e)}undetect(e,t){for(var i of t.getCombatants())i.sharedDetectDisguiseTrait?.delete(e)}isGlobalDetector(e){return!(!e.isTechno()||!e.rules.detectDisguiseRange)}isDisguisable(e){return!(!e.isInfantry()&&!e.isVehicle()||!e.disguiseTrait)}}class Gg{constructor(){this.detectors=new Set}[Gn.onSpawn](e,t){this.isGlobalDetector(e)&&(this.detectors.add(e),this.updateAroundDetector(e,t)),this.isCloakable(e)&&this.detect(e,t)}[$n.onUnspawn](e,t){e.isTechno()&&this.isGlobalDetector(e)&&this.detectors.delete(e)}[qn.onChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,i),this.isCloakable(e)&&this.detect(e,i)}[Gr.onTileChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,t),this.isCloakable(e)&&this.detect(e,t)}[ac.onAdd](e,t,i){e.isTechno()&&(t instanceof gn?this.isCloakable(e)&&this.detect(e,i):t instanceof Hh&&this.isGlobalDetector(e)&&this.updateAroundDetector(e,i))}[Rs.onPowerLow](e,t){}[Rs.onPowerRestore](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait);this.updateAroundDetectors(i,e)}[Rs.onPowerChange](e,t){}[Ps.onTick](e){for(var t of e.getCombatants()){var i;for(i of t.getOwnedObjects())i.cloakableTrait&&!i.cloakableTrait.isCloaked()&&this.detect(i,e)}}updateAroundDetectors(e,t){let i=new Set;for(var s of e)for(var r of this.findTechnosAroundDetector(s,t))i.add(r);for(var a of i)this.isCloakable(a)&&this.detect(a,t)}updateAroundDetector(e,t){var i;for(i of this.findTechnosAroundDetector(e,t))this.isCloakable(i)&&this.detect(i,t)}findTechnosAroundDetector(e,t){var i=e.getFoundation(),s=Math.max(i.width,i.height),i=e.rules.sensorsSight+s,s=new Os(e.tile.rx,e.tile.ry).addScalar(-i),i=new Os(e.tile.rx,e.tile.ry).addScalar(i);return t.map.technosByTile.queryRange(new Yn(s,i))}detect(e,t){let i=new Bs(t.map.tileOccupation);for(var s of this.detectors)if(!t.areFriendly(s,e)){var r=s.rules.sensorsSight;if(!(s.isBuilding()&&s.poweredTrait&&!s.poweredTrait.isPoweredOn())&&i.tileDistance(e,s.tile)<=r){r=e.cloakableTrait?.isCloaked();if(e.cloakableTrait.uncloak(t),r)for(var a of[s.owner,...t.alliances.getAllies(s.owner)])t.traits.get(Hl).addEventForPlayer(Yt.GenericNonCombat,a,e.tile,t);break}}}isGlobalDetector(e){return!(!e.isTechno()||!e.sensorsTrait&&!e.rules.sensorArray||!e.rules.sensorsSight)}isCloakable(e){return e.isTechno()&&!!e.cloakableTrait}}class $g{constructor(){this.type=rs.StalemateDetect}}class qg{constructor(){this.stale=!1,this.allPlayersCredits=new Map,this.resetCountdown()}isStale(){return this.stale}getCountdownTicks(){return this.countdownTicks}resetCountdown(){this.countdownTicks=Math.floor(60*qg.graceMinutes*Us.BASE_TICKS_PER_SECOND)}clearStale(){this.stale=!1,this.resetCountdown()}[Ps.onTick](e){0<this.countdownTicks?this.countdownTicks--:this.stale||(this.stale=!0,this.resetCountdown(),e.events.dispatch(new $g));for(var t of e.getCombatants()){var i=this.allPlayersCredits.get(t);i!==t.credits&&(this.allPlayersCredits.set(t,t.credits),t.credits>(i??0)&&t.production.hasAnyFactory()&&this.clearStale())}}[On.onProduce](){this.clearStale()}[hc.onPlace](e){e.wallTrait||this.clearStale()}[Zn.onDestroy](e,t,i){!e.isBuilding()||e.owner.isNeutral||e.wallTrait||e.rules.insignificant||e.owner.defeated&&this.stale||i?.obj&&t.areFriendly(e,i.obj)||this.clearStale()}[qn.onChange](e,t,i){e.isBuilding()&&!t.isNeutral&&(i.alliances.areAllied(e.owner,t)||this.clearStale())}}qg.graceMinutes=10;class Xg{static factory(e,t){return new this(yc.factory(e,t))}constructor(e){this.prng=e}generateColors(e){let t=[...e.humanPlayers,...e.aiPlayers].filter(Wa),i=t.map(e=>e.colorId).filter(e=>-2!==e);e=to.length;let s=new Array(e).fill(0).map((e,t)=>t).filter(e=>!i.includes(e)),r=new Map;return t.forEach(e=>{if(-3!==e.countryId&&-2===e.colorId){if(s.length<1)throw new Error("Out of available colors to choose from");var t=this.prng.generateRandomInt(0,s.length-1);r.set(e,s[t]),s.splice(t,1)}}),r}generateCountries(e,t){let i=t.getMultiplayerCountries().length,s=[...e.humanPlayers,...e.aiPlayers].filter(Wa),r=new Map;return s.forEach(e=>{-2===e.countryId&&r.set(e,this.prng.generateRandomInt(0,i-1))}),r}generateStartLocations(i,s){let e=[...i.humanPlayers,...i.aiPlayers].filter(Wa),t=e.filter(e=>-2!==e.startPos).map(e=>e.startPos),r=[...s.keys()].filter(e=>!t.includes(e)),a=[];for(;r.length;){var n=r.length?this.prng.generateRandomInt(0,r.length-1):0;a.push(...r.splice(n,1))}if(a.unshift(...t),3<=a.length)for(var o of[1,2])if(!(t.length-1>=o)){let e=a.map(e=>s[e]),t=this.findFarthestPointFrom(e.slice(0,o),e.slice(o));var h=e.findIndex(e=>e.x===t.x&&e.y===t.y);a.splice(o,0,...a.splice(h,1))}if(4<=a.length)if(t.length-1<3){let e=a.map(e=>s[e]),t=this.findFarthestPointFrom(e.slice(2,3),e.slice(3));i=e.findIndex(e=>e.x===t.x&&e.y===t.y);a.splice(3,0,...a.splice(i,1))}a.splice(0,t.length);let l=new Map,c=-1;return e.forEach(e=>{if(-3!==e.countryId&&-2===e.startPos){if(c>=a.length-1)throw new RangeError("Map has fewer starting locations than players");l.set(e,a[++c])}}),l}findFarthestPointFrom(e,t){let s=e.map(e=>new Os(e.x,e.y)),r,a=0;if(!t.length)throw new Error("Search array must have at least one element");for(var n of t){let i=new Os(n.x,n.y);var o=s.reduce((e,t)=>e+i.distanceTo(t),0);o>=a&&(r=n,a=o)}return r}}class Zg{get onChange(){return this._onChange.asEvent()}constructor(e,t){this.mapLighting=new bi,this._onChange=new wo,this.ambientChangeRate=e.ambientChangeRate,this.ambientChangeStep=e.ambientChangeStep,t&&this.mapLighting.copy(t)}setAmbientChangeRate(e){this.ambientChangeRate=e}setAmbientChangeStep(e){this.ambientChangeStep=e}setTargetAmbientIntensity(e){this.targetAmbient=e}getAmbient(){return this.mapLighting}[Ps.onTick](){var e;void 0!==this.targetAmbient&&(this.ambientUpdateTicks??(this.ambientUpdateTicks=Math.floor(60*Us.BASE_TICKS_PER_SECOND*this.ambientChangeRate)),this.ambientUpdateTicks<=0?(this.ambientUpdateTicks=void 0,e=this.mapLighting.ambient,(e=this.targetAmbient-e)?(e=Math.sign(e)*Math.min(this.ambientChangeStep,Math.abs(e)),this.mapLighting.ambient+=e,this._onChange.dispatch(this,this.mapLighting)):this.targetAmbient=void 0):this.ambientUpdateTicks--)}}class Qg{constructor(e){this.ini=e}getIni(){return this.ini}}var Yg,Kg,Jg=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)},ep=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i};class tp{constructor(e,t){this.name=e,this.country=t,Yg.set(this,!1)}setGameApi(e){this.gameApi=e}setActionsApi(e){this.actionsApi=e}setProductionApi(e){this.productionApi=e}setLogger(e){this.logger=e,this.logger.setDebugLevel(Jg(this,Yg,"f"))}setDebugMode(e){return ep(this,Yg,e,"f"),this.logger?.setDebugLevel(e),this}getDebugMode(){return Jg(this,Yg,"f")}onGameStart(e){}onGameTick(e){}onGameEvent(e,t){}}Yg=new WeakMap,(r=Kg=Kg||{})[r.Initial=0]="Initial",r[r.Deployed=1]="Deployed",r[r.Attacking=2]="Attacking",r[r.Defeated=3]="Defeated";class ip extends tp{constructor(){super(...arguments),this.botState=Kg.Initial}onGameStart(t){var e=t.getTickRate();this.tickRatio=Math.ceil(e/5),this.enemyPlayers=t.getPlayers().filter(e=>e!==this.name&&!t.areAlliedPlayers(this.name,e))}onGameTick(e){if(e.getCurrentTick()%this.tickRatio==0)switch(this.botState){case Kg.Initial:{const i=e.getGeneralRules().baseUnit;if(e.getVisibleUnits(this.name,"self",e=>e.constructionYard).length){this.botState=Kg.Deployed;break}var t=e.getVisibleUnits(this.name,"self",e=>i.includes(e.name));t.length&&this.actionsApi.orderUnits([t[0]],Pn.DeploySelected);break}case Kg.Deployed:break;case Kg.Attacking:e.getVisibleUnits(this.name,"self",e=>e.isSelectableCombatant).length||(this.botState=Kg.Defeated,this.actionsApi.quitGame())}}}class sp{constructor(e){this.botsLib=e}create(e){if(!e.isAi)throw new Error(`Player "${e.name}" is not an AI`);switch(e.aiDifficulty){case ks.Easy:return new ip(e.name,e.country.name);case ks.Medium:if(this.botsLib.SupalosaBot)return new this.botsLib.SupalosaBot(e.name,e.country.name);default:throw new Error(`Unsupported AI difficulty "${e.aiDifficulty}"`)}}}class rp{constructor(){this.actions=[]}push(...e){this.actions.push(...e)}getLast(){return this.actions[this.actions.length-1]}dequeueAll(){var e=[...this.actions];return this.actions.length=0,e}dequeueLast(){return this.actions.pop()}clear(){this.actions.length=0}}var ap=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},np=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class op{constructor(e,t,i,s,r){pp.add(this),lp.set(this,void 0),cp.set(this,void 0),up.set(this,void 0),dp.set(this,void 0),gp.set(this,void 0),ap(this,lp,t,"f"),ap(this,cp,i,"f"),ap(this,up,e,"f"),ap(this,dp,s,"f"),ap(this,gp,r,"f")}placeBuilding(t,i,s){np(this,pp,"m",mp).call(this,oc.PlaceBuilding,e=>{e.buildingRules=np(this,up,"f").rules.getBuilding(t),e.tile={x:i,y:s}})}sellObject(t){np(this,pp,"m",mp).call(this,oc.SellObject,e=>{e.objectId=t})}sellBuilding(e){this.sellObject(e)}toggleRepairWrench(t){np(this,pp,"m",mp).call(this,oc.ToggleRepair,e=>{e.buildingId=t})}toggleAlliance(t,i){np(this,pp,"m",mp).call(this,oc.ToggleAlliance,e=>{e.toPlayer=np(this,up,"f").getPlayerByName(t),e.toggle=i})}pauseProduction(t){np(this,pp,"m",mp).call(this,oc.UpdateQueue,e=>{e.queueType=t,e.updateType=pc.Pause})}resumeProduction(t){np(this,pp,"m",mp).call(this,oc.UpdateQueue,e=>{e.queueType=t,e.updateType=pc.Resume})}queueForProduction(t,e,i,s){let r=np(this,up,"f").rules.getObject(e,i);np(this,pp,"m",mp).call(this,oc.UpdateQueue,e=>{e.queueType=t,e.updateType=pc.Add,e.item=r,e.quantity=s})}unqueueFromProduction(t,e,i,s){let r=np(this,up,"f").rules.getObject(e,i);np(this,pp,"m",mp).call(this,oc.UpdateQueue,e=>{e.queueType=t,e.updateType=pc.Cancel,e.item=r,e.quantity=s})}activateSuperWeapon(t,i,s){np(this,pp,"m",mp).call(this,oc.ActivateSuperWeapon,e=>{e.superWeaponType=t,e.tile={x:i.rx,y:i.ry},e.tile2=s?{x:s.rx,y:s.ry}:void 0})}orderUnits(t,i,s,r,a){np(this,pp,"m",mp).call(this,oc.SelectUnits,e=>{e.unitIds=t});let n;if(s){let e,t;if(r){e=void 0;var o=np(this,up,"f").map.tiles.getByMapCoords(s,r);if(!o)throw new Error(`No tile found at rx,ry=${s},${r}`);t=o,a&&(e=np(this,up,"f").map.tileOccupation.getBridgeOnTile(o))}else{if(!np(this,up,"f").getWorld().hasObjectId(s))return;e=np(this,up,"f").getObjectById(s),t=e.tile}n=np(this,up,"f").createTarget(e,t)}np(this,pp,"m",mp).call(this,oc.OrderUnits,e=>{e.orderType=i,e.target=n})}sayAll(e){np(this,gp,"f")?.sayAll(np(this,dp,"f").name,e)}setGlobalDebugText(t){np(this,dp,"f").getDebugMode()&&np(this,pp,"m",mp).call(this,oc.DebugCommand,e=>{e.command=new Ug(mc.SetGlobalDebugText,{text:t||""})})}setUnitDebugText(t,i){np(this,dp,"f").getDebugMode()&&np(this,pp,"m",mp).call(this,oc.DebugCommand,e=>{e.command=new Ug(mc.SetUnitDebugText,{unitId:t,label:i})})}quitGame(){np(this,pp,"m",mp).call(this,oc.ResignGame)}}var hp,lp=new WeakMap,cp=new WeakMap,up=new WeakMap,dp=new WeakMap,gp=new WeakMap,pp=new WeakSet,mp=function(e,t){let i=np(this,lp,"f").create(e);i.player=np(this,up,"f").getPlayerByName(np(this,dp,"f").name),t?.(i),np(this,cp,"f").push(i)},fp=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},yp=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};(r=hp=hp||{})[r.ObjectOwnerChange=0]="ObjectOwnerChange",r[r.ObjectSpawn=1]="ObjectSpawn",r[r.ObjectUnspawn=2]="ObjectUnspawn",r[r.ObjectDestroy=3]="ObjectDestroy";class wp{constructor(e){vp.add(this),Tp.set(this,void 0),bp.set(this,[]),fp(this,Tp,e,"f")}subscribe(e,t){let i=void 0,s;s="function"==typeof e?e:(i=e,t);t=yp(this,Tp,"f").subscribe(e=>{e=yp(this,vp,"m",Sp).call(this,e);!e||void 0!==i&&i!==e.type||s(e)});return yp(this,bp,"f").push(t),t}dispose(){for(var e of yp(this,bp,"f"))e();yp(this,bp,"f").length=0}}var Tp=new WeakMap,bp=new WeakMap,vp=new WeakSet,Sp=function(t){switch(t.type){case rs.ObjectOwnerChange:return{type:hp.ObjectOwnerChange,prevOwnerName:t.prevOwner.name,newOwnerName:t.target.owner.name,target:t.target.id};case rs.ObjectSpawn:return{type:hp.ObjectSpawn,target:t.gameObject.id};case rs.ObjectUnspawn:return{type:hp.ObjectUnspawn,target:t.gameObject.id};case rs.ObjectDestroy:{let e=t;return e.target.isProjectile()?void 0:{type:hp.ObjectDestroy,target:e.target.id,attackerInfo:e.attackerInfo?{playerName:e.attackerInfo.player.name,objId:e.attackerInfo.obj?.id,weaponName:e.attackerInfo.weapon?.rules.name}:void 0}}default:return}},kp=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},Op=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class _p{constructor(e){Ap.add(this),Ip.set(this,void 0),Cp.set(this,void 0),kp(this,Ip,e,"f"),kp(this,Cp,e.map,"f")}getRealMapSize(){return Op(this,Cp,"f").tiles.getMapSize()}getStartingLocations(){return Op(this,Cp,"f").startingLocations.map(e=>new Os(e.x,e.y))}getTheaterType(){return Op(this,Cp,"f").getTheaterType()}getTile(e,t){t=Op(this,Cp,"f").tiles.getByMapCoords(e,t);if(t&&Op(this,Cp,"f").mapBounds.isWithinBounds(t))return t}getTilesInRect(e,t){let i=t?Op(this,Cp,"f").tiles.getInRectangle(e,t):Op(this,Cp,"f").tiles.getInRectangle(e);return i.filter(e=>Op(this,Cp,"f").mapBounds.isWithinBounds(e))}getObjectsOnTile(e){return Op(this,Cp,"f").getObjectsOnTile(e).map(e=>e.id)}hasBridgeOnTile(e){return!!e.onBridgeLandType}hasHighBridgeOnTile(e){return!!Op(this,Cp,"f").tileOccupation.getBridgeOnTile(e)?.isHighBridge()}isPassableTile(e,t,i,s){return s=s??t===ti.Foot,0<Op(this,Cp,"f").terrain.getPassableSpeed(e,t,s,i)}findPath(e,...t){const[i,s,r,a]=t="boolean"!=typeof t[0]?[e===ti.Foot,...t]:t;let n=Op(this,Ip,"f").map.terrain.computePath(e,i,s.tile,s.onBridge,r.tile,r.onBridge,{bestEffort:a?.bestEffort,excludeTiles:a?.excludeNodes?e=>a.excludeNodes({tile:e.tile,onBridge:!!e.onBridge}):void 0,maxExpandedNodes:a?.maxExpandedNodes});return n.map(e=>({tile:e.tile,onBridge:!!e.onBridge}))}isVisibleTile(e,t,i=0){var s=Op(this,Ip,"f").getPlayerByName(t);if(!s)throw new Error(`Player "${t}" doesn't exist`);return!Op(this,Ip,"f").mapShroudTrait.getPlayerShroud(s)?.isShrouded(e,i)}getTileResourceData(e){e=Op(this,Cp,"f").getObjectsOnTile(e).find(e=>e.isOverlay()&&e.isTiberium()||e.isTerrain()&&e.rules.spawnsTiberium);return e?Op(this,Ap,"m",Bp).call(this,e):void 0}getAllTilesResourceData(){var e;let t=[];for(e of Op(this,Ip,"f").getWorld().getAllObjects()){var i=Op(this,Ap,"m",Bp).call(this,e);i&&t.push(i)}return t}}var Ip=new WeakMap,Cp=new WeakMap,Ap=new WeakSet,Bp=function(t){let i;if(t.isOverlay()&&t.isTiberium()){let e=t.traits.get(Qa);var s=e.getTiberiumType(),r=e.getBailCount();i={tile:t.tile,ore:s===la.Ore?r:0,gems:s===la.Gems?r:0,spawnsOre:!1}}else t.isTerrain()&&t.rules.spawnsTiberium&&(i={tile:t.tile,ore:0,gems:0,spawnsOre:!0});return i},xp=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)},Ep=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i};class Pp{get allObjectRules(){return xp(this,Np,"f").allObjectRules}get buildingRules(){return xp(this,Np,"f").buildingRules}get infantryRules(){return xp(this,Np,"f").infantryRules}get vehicleRules(){return xp(this,Np,"f").vehicleRules}get aircraftRules(){return xp(this,Np,"f").aircraftRules}get terrainRules(){return xp(this,Np,"f").terrainRules}get overlayRules(){return xp(this,Np,"f").overlayRules}get countryRules(){return xp(this,Np,"f").countryRules}get general(){return xp(this,Np,"f").general}get ai(){return xp(this,Np,"f").ai}get crateRules(){return xp(this,Np,"f").crateRules}get combatDamage(){return xp(this,Np,"f").combatDamage}get radiation(){return xp(this,Np,"f").radiation}constructor(e){Np.set(this,void 0),Ep(this,Np,e,"f")}hasObject(e,t){return xp(this,Np,"f").hasObject(e,t)}getObject(e,t){return xp(this,Np,"f").getObject(e,t)}getBuilding(e){return xp(this,Np,"f").getBuilding(e)}getWeapon(e){return xp(this,Np,"f").getWeapon(e)}getWarhead(e){return xp(this,Np,"f").getWarhead(e)}getProjectile(e){return xp(this,Np,"f").getProjectile(e)}getOverlayName(e){return xp(this,Np,"f").getOverlayName(e)}getOverlayId(e){return xp(this,Np,"f").getOverlayId(e)}getOverlay(e){return xp(this,Np,"f").getOverlay(e)}getCountry(e){return xp(this,Np,"f").getCountry(e)}getMultiplayerCountries(){return xp(this,Np,"f").getMultiplayerCountries()}getIni(){return xp(this,Np,"f").getIni()}}var Np=new WeakMap,Dp=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},Mp=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class Rp{constructor(e,t){jp.add(this),Lp.set(this,void 0),Fp.set(this,void 0),Dp(this,Lp,e,"f"),Dp(this,Fp,t,"f"),this.mapApi=new _p(e),this.rulesApi=new Pp(e.rules)}isPlayerDefeated(e){return Mp(this,Lp,"f").getPlayerByName(e).defeated}areAlliedPlayers(e,t){var i=Mp(this,Lp,"f").getPlayerByName(e);if(!i)throw new Error(`Player "${e}" doesn't exist`);e=Mp(this,Lp,"f").getPlayerByName(t);if(!e)throw new Error(`Player "${t}" doesn't exist`);return Mp(this,Lp,"f").alliances.areAllied(i,e)}canPlaceBuilding(e,t,i){var s=Mp(this,Lp,"f").getPlayerByName(e);if(!s)throw new Error(`Player "${e}" doesn't exist`);return Mp(this,Lp,"f").getConstructionWorker(s).canPlaceAt(t,i,{normalizedTile:!0})}getBuildingPlacementData(e){e=Mp(this,Lp,"f").art.getObject(e,Et.Building);return{foundation:e.foundation,foundationCenter:e.foundationCenter}}getPlayers(){return Mp(this,Lp,"f").getNonNeutralPlayers().map(e=>e.name)}getPlayerData(e){let t=Mp(this,Lp,"f").getPlayerByName(e);if(!t)throw new Error(`Player "${e}" doesn't exist`);return{name:t.name,country:t.country,startLocation:this.mapApi.getStartingLocations()[t.startLocation??0],isObserver:t.isObserver,isAi:t.isAi,isCombatant:t.isCombatant(),credits:t.credits,power:{total:t.powerTrait?.power??0,drain:t.powerTrait?.drain??0,isLowPower:t.powerTrait?.level===yn.Low},radarDisabled:!!t.radarTrait?.isDisabled()}}getAllTerrainObjects(){return Mp(this,Lp,"f").getWorld().getAllObjects().filter(e=>e.isTerrain()).map(e=>e.id)}getAllUnits(t=()=>!0){return Mp(this,Lp,"f").getWorld().getAllObjects().filter(e=>e.isTechno()&&t(e.rules)).map(e=>e.id)}getNeutralUnits(t=()=>!0){return Mp(this,Lp,"f").getCivilianPlayer().getOwnedObjects().filter(e=>t(e.rules)).map(e=>e.id)}getUnitsInArea(e){return Mp(this,Lp,"f").map.technosByTile.queryRange(e).map(e=>e.id)}getVisibleUnits(e,s,t=()=>!0){const r=Mp(this,Lp,"f").getPlayerByName(e);if(!r)throw new Error(`Player "${e}" doesn't exist`);if("self"===s)return r.getOwnedObjects().filter(e=>t(e.rules)).map(e=>e.id);let a;if("allied"===s)a=e=>e.owner===r||Mp(this,Lp,"f").alliances.areAllied(e.owner,r);else{if("hostile"!==s&&"enemy"!==s)throw new Error(`Unexpected type ${s}`);{let i=Mp(this,Lp,"f").mapShroudTrait.getPlayerShroud(r);a=t=>Mp(this,Lp,"f").map.tileOccupation.calculateTilesForGameObject(t.tile,t).some(e=>!i?.isShrouded(e,t.tileElevation))&&t.owner!==r&&!Mp(this,Lp,"f").alliances.areAllied(t.owner,r)&&("enemy"!==s||t.owner.isCombatant())}}return Mp(this,Lp,"f").getWorld().getAllObjects().filter(e=>e.isTechno()&&!e.isDestroyed&&a(e)&&t(e.rules)).map(e=>e.id)}getGameObjectData(t){if(Mp(this,Lp,"f").getWorld().hasObjectId(t)){let e=Mp(this,Lp,"f").getObjectById(t);return{id:e.id,type:e.type,name:e.name,rules:e.rules,tile:e.tile,tileElevation:e.tileElevation,worldPosition:e.position.worldPosition.clone(),foundation:e.getFoundation(),hitPoints:e.healthTrait?.getHitPoints(),maxHitPoints:e.healthTrait?.maxHitPoints,owner:e.isTechno()?e.owner.name:void 0}}}getUnitData(t){var i=this.getGameObjectData(t);if(i){let e=Mp(this,Lp,"f").getObjectById(t);if(!e.isTechno())throw new Error(`Game object with id ${t} is not a Techno type`);return{...i,owner:e.owner.name,sight:e.sight,veteranLevel:e.veteranLevel,guardMode:e.guardMode,purchaseValue:e.purchaseValue,primaryWeapon:e.primaryWeapon?Mp(this,jp,"m",Up).call(this,e.primaryWeapon):void 0,secondaryWeapon:e.secondaryWeapon?Mp(this,jp,"m",Up).call(this,e.secondaryWeapon):void 0,deathWeapon:e.armedTrait?.deathWeapon?Mp(this,jp,"m",Up).call(this,e.armedTrait.deathWeapon):void 0,attackState:e.attackTrait?.attackState,direction:e.direction,onBridge:e.isInfantry()||e.isVehicle()?e.onBridge:void 0,zone:e.isUnit()?e.zone:void 0,buildStatus:e.isBuilding()?e.buildStatus:void 0,factory:e.isBuilding()&&e.factoryTrait?{deliveringUnit:e.factoryTrait.deliveringUnit?.id,status:e.factoryTrait.status}:void 0,rallyPoint:e.isBuilding()?e.rallyTrait?.getRallyPoint():void 0,isPoweredOn:e.isBuilding()&&e.poweredTrait?.isPoweredOn(),hasWrenchRepair:e.isBuilding()&&!e.autoRepairTrait.isDisabled(),turretFacing:e.isBuilding()||e.isVehicle()?e.turretTrait?.facing:void 0,turretNo:e.isVehicle()?e.turretNo:void 0,garrisonUnitCount:e.isBuilding()?e.garrisonTrait?.units.length:void 0,garrisonUnitsMax:e.isBuilding()?e.garrisonTrait?.maxOccupants:void 0,passengerSlotCount:e.isVehicle()?e.transportTrait?.getOccupiedCapacity():void 0,passengerSlotMax:e.isVehicle()?e.transportTrait?.getMaxCapacity():void 0,isIdle:!e.unitOrderTrait.hasTasks(),canMove:e.isUnit()?!e.moveTrait.isDisabled():void 0,velocity:e.isUnit()?e.moveTrait.velocity.clone():void 0,stance:e.isInfantry()?e.stance:void 0,harvestedOre:e.isVehicle()?e.harvesterTrait?.ore:void 0,harvestedGems:e.isVehicle()?e.harvesterTrait?.gems:void 0,ammo:e.isAircraft()?e.ammo:void 0,isWarpedOut:e.warpedOutTrait.isActive(),mindControlledBy:e.mindControllableTrait?.getController()?.id,tntTimer:e.tntChargeTrait?.getTicksLeft()}}}getAllSuperWeaponData(){return Mp(this,Lp,"f").getCombatants().map(t=>t.superWeaponsTrait.getAll().map(e=>({playerName:t.name,type:e.rules.type,status:e.status,timerSeconds:e.getTimerSeconds()}))).flat()}getGeneralRules(){return Mp(this,Lp,"f").rules.general}getRulesIni(){return Mp(this,Lp,"f").rules.getIni()}getArtIni(){return Mp(this,Lp,"f").art.getIni()}getAiIni(){return Mp(this,Lp,"f").ai.getIni()}generateRandomInt(e,t){if(Mp(this,Fp,"f"))return Mp(this,Lp,"f").generateRandomInt(e,t);var i=this.generateRandom();return Math.round(i*(t-e))+e}generateRandom(){return Mp(this,Fp,"f")?Mp(this,Lp,"f").generateRandom():Math.random()}getTickRate(){return Mp(this,Lp,"f").speed.value*Us.BASE_TICKS_PER_SECOND}getBaseTickRate(){return Us.BASE_TICKS_PER_SECOND}getCurrentTick(){return Mp(this,Lp,"f").currentTick}getCurrentTime(){return Mp(this,Lp,"f").currentTime/1e3}}var Lp=new WeakMap,Fp=new WeakMap,jp=new WeakSet,Up=function(e){return{type:e.type,rules:e.rules,projectileRules:e.projectileRules,warheadRules:e.warhead.rules,minRange:e.minRange,maxRange:e.range,speed:e.speed,cooldownTicks:e.getCooldownTicks()}},Wp=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},zp=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class Vp{constructor(e,t){Zp.add(this),qp.set(this,void 0),Xp.set(this,void 0),Wp(this,qp,e,"f"),Wp(this,Xp,t,"f")}setDebugLevel(e){zp(this,qp,"f").setLevel(e?Tr.DEBUG:Tr.WARN)}debug(...e){zp(this,qp,"f").debug(zp(this,Zp,"m",Qp).call(this),...e)}info(...e){zp(this,qp,"f").info(zp(this,Zp,"m",Qp).call(this),...e)}log(...e){zp(this,qp,"f").log(zp(this,Zp,"m",Qp).call(this),...e)}warn(...e){zp(this,qp,"f").warn(zp(this,Zp,"m",Qp).call(this),...e)}error(...e){zp(this,qp,"f").error(zp(this,Zp,"m",Qp).call(this),...e)}time(e){zp(this,qp,"f").time(e)}timeEnd(e){zp(this,qp,"f").timeEnd(e)}}var Hp,Gp,$p,qp=new WeakMap,Xp=new WeakMap,Zp=new WeakSet,Qp=function(){return"["+function(e,t=!1){var i=Math.floor(e/3600);e-=3600*i;var s=Math.floor(e/60),e=e-=60*s;return[...i||!t?[i]:[],N(s,"00"),N(e,"00")].join(":")}(Math.floor(zp(this,Xp,"f").getCurrentTime()))+"]"},Yp=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},Kp=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class Jp{constructor(e){Hp.set(this,void 0),Yp(this,Hp,e,"f")}isAvailableForProduction(e){return Kp(this,Hp,"f").isAvailableForProduction(e)}getAvailableObjects(t){let e=Kp(this,Hp,"f").getAvailableObjects();return void 0!==t&&(e=e.filter(e=>this.getQueueTypeForObject(e)===t)),e}getQueueTypeForObject(e){return Kp(this,Hp,"f").getQueueTypeForObject(e)}getQueueData(e){let t=Kp(this,Hp,"f").getQueue(e);return{size:t.currentSize,maxSize:t.maxSize,status:t.status,type:t.type,items:t.getAll().map(e=>({rules:e.rules,quantity:e.quantity}))}}}Hp=new WeakMap;class em{constructor(e,t,i,s,r,a){this.game=e,this.inputActions=t,this.replayRecorder=i,this.actionSerializer=s,this.actionFactory=r,this.actionLogger=a,this.errorState=!1}init(){this.gameTurnMillis=1e3/(this.game.speed.value*Us.BASE_TICKS_PER_SECOND)}setErrorState(){this.errorState=!0}getErrorState(){return this.errorState}getTurnMillis(){return this.gameTurnMillis}doGameTurn(){if(!this.errorState){if(this.game.status!==nc.Ended){var t,e=this.inputActions.dequeueAll();const s=new Map;for(t of e){var i=this.actionSerializer.getActionPayload(t);let e=s.get(t.player);e||(e=[],s.set(t.player,e)),e.push(i)}this.replayRecorder.recordActions(this.game.currentTick,new Map([...s].map(([e,t])=>[this.game.getPlayerNumber(e),t]))),s.forEach((t,i)=>{if(!t.length){let e=new pd;e.player=i,t.push(this.actionSerializer.getActionPayload(e))}}),this.processActions(s)}this.game.update()}}processActions(e){[...e].forEach(([i,e])=>e.forEach(e=>{let t=this.actionFactory.create(e.id);t.player=i,t.unserialize(e.params),t.process();e=t.print();e&&this.actionLogger?.debug(`(${i.name})@${this.game.currentTick}: ${e}`)}))}dispose(){}}(r=Gp=Gp||{})[r.Closed=0]="Closed",r[r.Open=1]="Open",r[r.OpenObserver=2]="OpenObserver",r[r.Player=3]="Player",r[r.Ai=4]="Ai";class tm{encode(e){let s=[],r=0;return e.split("").forEach((e,t)=>{var i=e.charCodeAt(0)<<2*t-7*r,e=127&i,t=i>>7&127,i=i>>14&127;i&&r++,s.push(e,t),i&&s.push(i)}),s.push(0,0),2<=e.length&&s.push(0),s=s.map(e=>128^e),s.map(e=>String.fromCharCode(e)).join("")}decode(e){let i=e.split("").map(e=>e.charCodeAt(0));for(i=i.map(e=>128^e);0===i[i.length-1];)i.pop();let s=[],r=0,a=0;for(;i.length;){var n=s.length,o=i.shift(),h=i.shift();let e=0,t=!1;(-1!==[1,2,3].indexOf(i[0])||n>r+3)&&(e=i.shift(),r=n,t=!0);n=(e<<14|h<<7|o)>>2*n-7*a;s.push(127&n),t&&a++}return s.map(e=>String.fromCharCode(e)).join("")}}class im{encode(e){return e.match(/^[a-z0-9-_]+\.[a-z]{3}$/i)?e:P.encode(j(e))}decode(e){return e.match(/\.[a-z]{3}$/i)?e:U(P.decode(e))}}class sm{serializeOptions(e,t=!1){let i=e.gameMode,s=t?(new tm).encode(e.mapTitle):P.encode(j(e.mapTitle)),r=(new im).encode(e.mapName);t=["0","0",6-e.gameSpeed,e.credits,e.unitCount,Number(e.shortGame),Number(e.superWeapons),Number(e.buildOffAlly),Number(e.mcvRepacks),Number(e.cratesAppear),i,Number(e.hostTeams??!1),s,e.maxSlots,Number(e.mapOfficial),e.mapSizeBytes,r,e.mapDigest,Number(e.destroyableBridges),Number(e.multiEngineer),Number(e.noDogEngiKills),...e.unknown?[e.unknown]:[]].join(",");return`${t}:${e.humanPlayers.map(e=>`${e.name},${e.countryId},${e.colorId},${e.startPos},${e.teamId},0,0,0`).join(",")}:@:${this.serializeAiOpts(e.aiPlayers)},`}serializeAiOpts(e){return e.map(e=>e?`${e.difficulty},${e.countryId},${e.colorId},${e.startPos},${e.teamId}`:"0,-1,-1,-1,-1").join(",")}serializePingData(e){return e.length+","+e.map(e=>`${e.playerName},${e.ping}`).join(",")}serializeSlotData(e){return e.map(e=>{if(e.type===Gp.Closed)return"@Closed@";if(e.type===Gp.Open)return"@Open@";if(e.type===Gp.OpenObserver)return"@OpenObserver@";if(e.type===Gp.Ai){if(e.difficulty===ks.Easy)return"@EasyAI@";if(e.difficulty===ks.Medium)return"@MediumAI@";if(e.difficulty===ks.Brutal)return"@HardAI@"}else if(e.type===Gp.Player)return e.name;throw new Error(`Unexpected slot info with type ${Gp[e.type]}`)}).join(",")+","}serializeLoadInfo(e){return e.map(e=>[e.name,e.status,e.loadPercent,e.ping,e.lagAllowanceMillis].join(",")).join(",")}serializePlayerActions(e){let t=new k;t.writeUint8(e.length);for(var{id:i,params:s}of e)if(t.writeUint8(i),t.writeUint16(s.byteLength),0<s.byteLength){if(s.byteLength>sm.MAX_ACTION_PAYLOAD_SIZE-t.position)throw console.error(`Action #${i} payload exceeds max data size`,s),new RangeError("Maximum payload data size exceeded");t.writeUint8Array(s)}return t.toUint8Array()}serializeAllPlayerActions(e,t){e.writeUint8(t.size);for(var[i,s]of t){e.writeUint8(i);var r=this.serializePlayerActions(s);if(e.writeUint16(r.byteLength),0<r.byteLength){if(r.byteLength>sm.MAX_ACTION_PAYLOAD_SIZE)throw console.error(`Player #${i} actions payload exceeds max data size`,s),new RangeError("Maximum payload data size exceeded");e.writeUint8Array(r)}}}serializeMapData(e){return R(e)}}sm.MAX_ACTION_PAYLOAD_SIZE=65536;class rm{parseOptions(e){let t={},[i,s,,r]=e.split(":"),a=i.split(",");a.shift(),a.shift(),t.gameSpeed=6-Number(a.shift()),t.credits=Number(a.shift()),t.unitCount=Number(a.shift()),t.shortGame=Boolean(Number(a.shift())),t.superWeapons=Boolean(Number(a.shift())),t.buildOffAlly=Boolean(Number(a.shift())),t.mcvRepacks=Boolean(Number(a.shift())),t.cratesAppear=Boolean(Number(a.shift())),t.gameMode=Number(a.shift()),t.hostTeams=Boolean(Number(a.shift()));e=a.shift();return t.mapTitle=P.isBase64(e)?U(P.decode(e)):(new tm).decode(e),t.maxSlots=Number(a.shift()),t.mapOfficial=Boolean(Number(a.shift())),t.mapSizeBytes=Number(a.shift()),t.mapName=(new im).decode(a.shift()),t.mapDigest=a.shift(),t.destroyableBridges=Boolean(Number(a.shift()??"1")),t.multiEngineer=Boolean(Number(a.shift()??"0")),t.noDogEngiKills=Boolean(Number(a.shift()??"0")),t.unknown=a.length?a.join(","):void 0,t.humanPlayers=this.parsePlayerOpts(s),t.aiPlayers=this.parseAiOpts(r?.slice(0,-1)),t}parsePlayerOpts(e){var i=e.split(",");if(i.length%8!=0)throw new Error(`Couldn't parse gameopt: unexpected players data length ${i.length}`);let s=[];for(let e=0,t=Math.floor(i.length/8);e<t;++e){var r={name:i[8*e],countryId:Number(i[8*e+1]),colorId:Number(i[8*e+2]),startPos:Number(i[8*e+3]),teamId:Number(i[8*e+4])};s.push(r)}return s}parseAiOpts(e){let i=[];if(e){var s=e.split(",");if(s.length%5!=0)throw new Error(`Couldn't parse gameopt: unexpected ai data length ${s.length}`);for(let e=0,t=Math.floor(s.length/5);e<t;++e){var r={difficulty:Number(s[5*e]),countryId:Number(s[5*e+1]),colorId:Number(s[5*e+2]),startPos:Number(s[5*e+3]),teamId:Number(s[5*e+4])};i.push(-1!==r.countryId?r:void 0)}}return i}parseTopic(e){var t=e.split(",");if(!(t.length<6)){var i=t[0],s=Number(t[1]),r=i[2],a=t[2],n=t[3],e=t[4],i=(new im).decode(t[5]);return{description:t[6]?U(P.decode(t[6])):"",modHash:s,modName:t[7]?U(P.decode(t[7])):void 0,aiPlayers:Number(a),maxPlayers:Number(r),observers:Number(n),observable:Boolean(Number(e)),mapName:i}}}parsePingData(e){var i=e.split(",").slice(1);if(i.length%2)throw new Error(`Couldn't parse gameopt: unexpected ping data length ${i.length}`);let s=[];for(let e=0,t=Math.floor(i.length/2);e<t;++e)s.push({playerName:i[2*e],ping:Number(i[2*e+1])});return s}parseSlotData(e){var i;let s=[];for(i of e.slice(1,-1).split(",")){let t={};if("@Closed@"===i)t.type=Gp.Closed;else if("@Open@"===i)t.type=Gp.Open;else if("@OpenObserver@"===i)t.type=Gp.OpenObserver;else if(-1!==["@EasyAI@","@MediumAI@","@HardAI@"].indexOf(i)){t.type=Gp.Ai;let e;if("@EasyAI@"===i)e=ks.Easy;else if("@MediumAI@"===i)e=ks.Medium;else{if("@HardAI@"!==i)throw new Error(`Couldn't parse gameopt: unknown slot type ${i}`);e=ks.Brutal}t.difficulty=e}else t.type=Gp.Player,t.name=i;s.push(t)}return s}parsePlayerActions(e){let t=new k(e);var i=t.readUint8();let s=[];for(let e=0;e<i;++e){var r=t.readUint8(),a=t.readUint16(),a=0<a?t.readUint8Array(a):new Uint8Array;s.push({id:r,params:a})}return s}parseAllPlayerActions(t){var i=t.readUint8();let s=new Map;for(let e=0;e<i;++e){var r=t.readUint8(),a=t.readUint16(),a=0<a?t.readUint8Array(a):new Uint8Array,a=this.parsePlayerActions(a);s.set(r,a)}return s}parseMapData(e){return F(e)}}class am{constructor(e,t){this.type=e,this.tickNo=t}}(r=$p=$p||{})[r.TurnActions=0]="TurnActions",r[r.ChatMessage=1]="ChatMessage",r[r.Taunt=2]="Taunt";class nm extends am{constructor(e){super($p.ChatMessage,e)}serialize(){return this.payload.playerId+":"+P.encode(j(this.payload.message))}unserialize(e){var[t,e]=e.split(":"),t=Number(t),e=U(P.decode(e));this.payload={playerId:t,message:e}}}class om extends am{constructor(e){super($p.Taunt,e)}serialize(){return this.payload.playerId+":"+this.payload.tauntNo}unserialize(e){var[t,e]=e.split(":"),t=Number(t),e=Number(e);this.payload={playerId:t,tauntNo:e}}}class hm extends am{constructor(e,t,i){super($p.TurnActions,i),this.gameOptsParser=e,this.gameOptsSerializer=t}serialize(){let e=new k;return this.gameOptsSerializer.serializeAllPlayerActions(e,new Map(this.payload)),t=e.toUint8Array(),P.encode(F(t));var t}unserialize(e){e=new k(L(e)),e=this.gameOptsParser.parseAllPlayerActions(e);this.payload=[...e]}}class lm{constructor(e,t){this.gameOptsParser=e,this.gameOptsSerializer=t}create(e,t){switch(e){case $p.TurnActions:return new hm(this.gameOptsParser,this.gameOptsSerializer,t);case $p.ChatMessage:return new nm(t);case $p.Taunt:return new om(t);default:throw new Error(`Unsupported replay event type "${e}" at game tick "${t}"`)}}}const cm=[5,6];class um{constructor(){this.name="",this.events=[]}static sanitizeFileName(e,t="_"){return e.replace(/[/?<>\\:*|"]/g,t).replace(/[\x00-\x1f\x7f\x80-\x9f]/g,t).slice(0,this.maxNameLength)}init(e,t,i,s,r){this.gameId=e,this.gameTimestamp=t,this.gameOpts=i,this.engineVersion=s,this.modHash=r,this.name=um.sanitizeFileName(this.gameOpts.mapTitle+" "+(new Date).toISOString().replace(/(\.|,)\d+Z$/,"Z")),this.timestamp=Date.now()}writeEvent(...e){this.events.push(...e)}finish(e){this.endTick=e}getEvents(){return this.events}*flush(){if(!this.gameOpts)throw new Error("Game options must be set first");if(!this.engineVersion)throw new Error("Engine version is not set");if(void 0===this.modHash)throw new Error("Mod hash is not set");let e=new sm,t=this.getHeaderTag()+"\n";for(t+=`ENGINE ${this.engineVersion} ${this.modHash}\n`,t+=[this.gameId,this.gameTimestamp,e.serializeOptions(this.gameOpts)].join(" ")+"\n",yield t,t="";void 0===this.endTick||this.events.length;){for(var i of this.events)t+=i.tickNo+"="+i.type+"|"+i.serialize()+"\n";this.events.length=0,yield t,t=""}t+=this.getEndTag()+" "+this.endTick+"\n",this.debugInfo&&(t+=P.encode(j(this.debugInfo))+"\n"),yield t}serialize(){if(void 0===this.endTick)throw new Error("Replay is not finished");let e="";var t,i=this.events.slice();for(t of this.flush())e+=t;return this.events=i,e}async parseHeader(e){let t=0,i,s,r,a,n,o;var h;for await(h of"string"==typeof e?e.split("\n"):async function*(e){const t=new TextDecoder("utf-8");let i=e.stream().getReader(),{value:s,done:r}=await i.read();s=s?t.decode(s,{stream:!0}):"";let a=/\r\n|\n|\r/gm,n=0;for(;;){var o=a.exec(s);if(o)yield s.substring(n,o.index),n=a.lastIndex;else{if(r)break;o=s.substr(n);({value:s,done:r}=await i.read()),s=o+(s?t.decode(s,{stream:!0}):""),n=a.lastIndex=0}}n<s.length&&(yield s.substr(n))}(e)){if(0===t)i=this.readReplayVersion(h);else if(1===t){if(!h.match(um.engineLineRegex))throw new Error("Missing or invalid game engine version line");var l=h.split(" ");s=l[1],r=Number(i<4?"0":l[2])}else{if(2!==t)break;if(!h.match(/^([a-zA-Z0-9-]+) \d+ .*$/))throw new Error("Missing or invalid game id/time/opts line");var[c,u,l]=h.split(" ");a=c,n=Number(u),o=i<6?P.decode(l):l}t++}if(t<3)throw new Error("Bad replay header");return{replayVersion:i,engineVersion:s,modHash:r,gameId:a,gameTimestamp:n,gameOptsSerialized:o}}unserialize(e,t){let i=e.split("\n");var s=this.readReplayVersion(i.shift()||"");if(!cm.includes(s))throw new Error(`Unsupported replay version ${s}`);let r=new rm,a=i.shift();if(!a||!a.match(um.engineLineRegex))throw new Error("Missing or invalid game engine version line");var[,n,o]=a.split(" ");let h=i.shift();if(!h)throw new Error("Missing game id/time/opts line");e=h.match(/^([a-zA-Z0-9-]+) (\d+) (.*)$/);if(!e)throw new Error("Invalid game id/time/opts line");let[,l,c,u]=e;s<6&&(u=P.decode(u));s=r.parseOptions(u);this.init(l,Number(c),s,n,Number(o)),this.name=t.name,this.timestamp=t.timestamp;let d,g=!1;for(;d=i.shift();){if(d.startsWith(this.getEndTag())){g=!0;break}var p=d.match(/^(\d+)=(\d+)\|(.+)$/);if(!p)throw new Error(`Invalid event line "${d}"`);var[,m,f,p]=p,m=Number(m),f=Number(f);let e=new lm(r,new sm).create(f,m);e.unserialize(p),this.writeEvent(e)}if(!g)throw new Error("Incomplete replay data");t=d.match(new RegExp(`^${this.getEndTag()} (\\d+)$`));if(!t)throw new Error("Invalid end tag");this.endTick=Number(t[1]),1<=i.length&&(this.debugInfo=U(P.decode(i[0])))}getHeaderTag(){return"RA2TSREPL_v6"}readReplayVersion(e){e=e.match(/^RA2TSREPL_v(\d+)$/);if(!e||e.length<2)throw new Error("Unknown replay format");return Number(e[1])}getEndTag(){return"END"}}um.extension=".rpl",um.maxNameLength=128,um.engineLineRegex=/^ENGINE \d+\.\d+( \d+)?$/;class dm{constructor(e,t,i,s){this.replay=e,this.playerId=t,this.humanPlayers=i,this.actionSerializer=s}recordActions(t,i){if(Array.isArray(i)){let e=new hm(new rm,new sm,t);e.payload=[[this.playerId,i.map(e=>this.actionSerializer.getActionPayload(e))]],this.replay.writeEvent(e)}else if(this.hasActualActions(i)){let e=new hm(new rm,new sm,t);e.payload=[...i].map(([e,t])=>[e,t]),this.replay.writeEvent(e)}}recordChatMessage(e,t,i){let s=new nm(e);s.payload={playerId:this.humanPlayers.findIndex(e=>e.name===t),message:i},this.replay.writeEvent(s)}recordTaunt(e,t,i){let s=new om(e);s.payload={playerId:this.humanPlayers.findIndex(e=>e.name===t),tauntNo:i},this.replay.writeEvent(s)}hasActualActions(e){return!![...e.values()].find(e=>e.find(e=>e.id!==oc.NoAction))}}class gm{getActionPayload(e){return{id:e.actionType,params:e.serialize()}}}class pm extends Error{constructor(e){super(),this.cancellationToken=e}}const mm=Symbol(),fm=Symbol();mm;fm;async function ym(t){return new Promise(e=>{setTimeout(()=>e(),t)})}class wm{constructor(e,t){this.options=e,this.logger=t,this.timeout=5,this._onMessage=new wo,this._onError=new wo,this._onClose=new wo,this.messageBuffer=""}get onMessage(){return this._onMessage.asEvent()}get onError(){return this._onError.asEvent()}get onClose(){return this._onClose.asEvent()}async connect(s,r){let e=r?.timeoutSeconds?setTimeout(()=>this.close(),1e3*r.timeoutSeconds):void 0;return r?.cancelToken?.register(()=>{e&&(clearTimeout(e),this.close())}),new Promise((e,t)=>{this.socket=new WebSocket(s),"binary"===this.options.mode&&(this.socket.binaryType="blob");let i=e=>{this.socket.removeEventListener("error",i),r?.cancelToken?.isCancelled()?t(new pm(r.cancelToken)):t(new wm.ConnectError(`Connection to "${s}" failed`))};this.socket.addEventListener("open",()=>{this.socket.removeEventListener("error",i),this.socket.addEventListener("error",e=>this.handleError(e)),this.handleOpen(),e()}),this.socket.addEventListener("error",i),this.socket.addEventListener("close",e=>this.handleClose(e)),this.socket.addEventListener("message",e=>{globalThis.Blob&&e.data instanceof Blob?this.parseData(e.data).then(e=>{this.handleMessage(e)}).catch(e=>{console.error("Failed to decode socket message.",e)}):this.handleMessage(e.data)})}).finally(()=>{e&&clearTimeout(e)})}handleOpen(){this.logger.info("Connection open to "+this.socket.url)}handleError(e){this.logger.error("Connection error",e),this._onError.dispatch(this,e)}handleClose(e){this.logger.info(`Connection closed (${this.socket.url})`,e),this._onClose.dispatch(this,e)}handleMessage(e){if("string"!=typeof e){if(e[0]===this.options.binaryRplPrefix)return void this._onMessage.dispatch(this,e.slice(1));e=F(e)}this.logger.enabledFor(Tr.DEBUG)&&this.logger.debug("Got message:","string"==typeof e?this.options.logFilter?.(e)??e:e),e=this.messageBuffer+e,this.messageBuffer="";let t=e.split(/\r?\n/);e=t.pop();e.length&&(this.messageBuffer=e),t.filter(e=>!!e).forEach(e=>this._onMessage.dispatch(this,e))}parseData(s){return new Promise((e,t)=>{let i=new FileReader;i.onload=()=>e(new Uint8Array(i.result)),i.onerror=()=>t(new Error("Failed to parse data")),i.readAsArrayBuffer(s)})}async sendCommand(e,h){if(h.replyStartCode&&!h.replyEndCode)throw new Error("Invalid argument. Expected a reply end code, but got only a start code.");let l=[];return await this.sendRawCommand(e,(e,r,a,n)=>{let o=(e,t)=>{if("number"==typeof e)return t.code===e;let[i,s]=e;return t.code===i&&s(t)};if("string"!=typeof e){if(e[0]===this.options.binaryRplPrefix)return!1;e=F(e)}return h.replyRawText?(a(e.split(/\r?\n/).map(e=>({raw:e,time:r}))),!0):e.split(/\r?\n/).filter(e=>!!e).some(e=>(e=>{if(h.replyMatch){if(h.replyMatch.exec(e))return a([{raw:e,time:r}]),!0;if(!h.replyCodes)return!1}if(!h.replyEndCode&&!h.replyCodes)return a([{raw:e,time:r}]),!0;var[,t,...i]=e.split(" "),t=parseInt(t,10);let s={raw:e,code:t,params:i,time:r};if(h.replyEndCode)return h.replyCodes&&h.replyCodes.some(e=>o(e,s))?(a([s]),!0):(h.replyHeartbeatCodes&&-1!==h.replyHeartbeatCodes.indexOf(t)&&n(h.heartbeatTimeout),(t===h.replyStartCode||h.replyBodyCodes&&-1!==h.replyBodyCodes.indexOf(t)||t===h.replyEndCode)&&l.push(s),t===h.replyEndCode&&(a(l),!0));if(void 0===h.replyCodes)throw new Error("List of replyCodes must be specified when not using start/end codes");return!!h.replyCodes.some(e=>o(e,s))&&(a([s]),!0)})(e))},h.timeout)}async sendBinCommand(e,r){const a=this.options.binaryRplPrefix;if(!a)throw new Error("Must configure binary message reply prefix to send binary commands");const t=this.options.binaryReqPrefix;if(!t)throw new Error("Must configure binary message request prefix to send binary commands");if(e[0]!==t)throw new Error(`Binary command must start with the magic prefix 0x${t.toString(16)}`);return await this.sendRawCommand(e,(e,t,i)=>{if("string"==typeof e||e[0]!==a)return!1;var s=e[1];return-1!==r.replyCodes.indexOf(s)&&(i({code:s,data:e.slice(2),time:t}),!0)},r.timeout)}sendRawCommand(d,g,p){return new Promise((t,i)=>{let s=!1,r,a=e=>{clearTimeout(r),void 0!==e&&Number.isFinite(e)&&(r=setTimeout(h,1e3*(e??p??this.timeout)))},n=e=>{clearTimeout(r),t(e)},o=e=>{this.socket.removeEventListener("message",u),this.socket.removeEventListener("close",l),clearTimeout(r),r=void 0,i(e)},h=()=>{var e="string"==typeof d?this.options.logFilter?.(d)??d:`0x${d[1].toString(16)}`;o(new wm.NoReplyError(`Timeout reached for command ${e}`))},l=async()=>{for(;s;)await ym(10);c||o(new wm.SocketError("Connection was closed prematurely"))},c=!1,u=e=>{if(!c){let t=Date.now();globalThis.Blob&&e.data instanceof Blob?(s=!0,this.parseData(e.data).then(e=>{s=!1,c||g(e,t,n,a)&&(c=!0,this.socket.removeEventListener("message",u),this.socket.removeEventListener("close",l))}).catch(e=>{s=!1,console.error("Failed to decode socket message.",e)})):g(e.data,t,n,a)&&(c=!0,this.socket.removeEventListener("message",u),this.socket.removeEventListener("close",l))}};if(this.socket&&this.socket.readyState===WebSocket.OPEN){r=setTimeout(h,1e3*(p??this.timeout)),this.socket.addEventListener("message",u),this.socket.addEventListener("close",l);try{this.sendMessage(d)}catch(e){o(e)}}else o(new wm.SocketError("Send command failed. Socket is not open."+(this.socket?` (readyState = ${this.socket.readyState})`:"")))})}sendMessage(e){if(!this.socket||this.socket.readyState!==WebSocket.OPEN)throw new wm.SocketError(`Socket is not open${this.socket?` (readyState = ${this.socket.readyState})`:""}`);this.logger.enabledFor(Tr.DEBUG)&&this.logger.debug("Sent message:","string"==typeof e?this.options.logFilter?.(e)??e:e),"string"==typeof e&&(e+="\r\n");let t;t="binary"===this.options.mode&&"string"==typeof e?R(e):e,this.socket.send(t)}async ping(e){var t=Date.now();return(await this.sendCommand(`ping :${t}`,{replyMatch:new RegExp(`^:[^ ]+ PONG [^ :]+ :${t}`,"i"),timeout:e}))[0].time-t}close(){this.socket&&this.socket.close()}isOpen(){return this.socket&&this.socket.readyState===WebSocket.OPEN}}!function(e){class t extends Error{constructor(e){super(e)}}e.NoReplyError=t;class i extends Error{constructor(e){super(e)}}e.SocketError=i;class s extends Error{constructor(e){super(e)}}e.ConnectError=s}(wm=wm||{});class Tm extends Error{constructor(e,t){super(e),this.code=t}}(r=(r=Tm=Tm||{}).Code||(r.Code={}))[r.Unknown=0]="Unknown",r[r.OutdatedClient=1]="OutdatedClient",r[r.BadLogin=2]="BadLogin",r[r.TooManyLoginAttempts=3]="TooManyLoginAttempts",r[r.AlreadyLoggedIn=4]="AlreadyLoggedIn",r[r.InstanceNonExistent=5]="InstanceNonExistent",r[r.InstanceAlreadyExists=6]="InstanceAlreadyExists",r[r.InstanceNotAllowed=7]="InstanceNotAllowed",r[r.InstanceAlreadyStarted=8]="InstanceAlreadyStarted",r[r.InstanceVersMismatch=9]="InstanceVersMismatch",r[r.CreatedTooManyInstances=10]="CreatedTooManyInstances";const bm="#all";var vm;(r=vm=vm||{})[r.Channel=0]="Channel",r[r.Page=1]="Page",r[r.Whisper=2]="Whisper";const Sm=new Map([[103,Tm.Code.BadLogin],[104,Tm.Code.TooManyLoginAttempts],[101,Tm.Code.AlreadyLoggedIn],[201,Tm.Code.InstanceAlreadyExists],[202,Tm.Code.CreatedTooManyInstances],[401,Tm.Code.InstanceNonExistent],[402,Tm.Code.InstanceNotAllowed],[403,Tm.Code.InstanceAlreadyStarted],[406,Tm.Code.InstanceVersMismatch]]);class km{get onLagStateChange(){return this._onLagStateChange.asEvent()}get onActionsSent(){return this._onActionsSent.asEvent()}get onActionsProcessed(){return this._onActionsProcessed.asEvent()}get onActionsReceived(){return this._onActionsReceived.asEvent()}constructor(e,t,i,s,r,a,n,o,h,l,c,u,d){this.game=e,this.gservCon=t,this.gameoptParser=i,this.gameoptSerializer=s,this.actionSerializer=r,this.actionFactory=a,this.inputActions=n,this.onDesync=o,this.actionLogger=h,this.netLogger=l,this.debugLogger=c,this.replayRecorder=u,this.debugGameState=d,this.debugGameStateHistory=[],this.queuedRateChanges=[],this.errorState=!1,this.passiveMode=!1,this.receivedActions=new Map,this.receivedNetworkTurn=0,this.lagState=!1,this._onLagStateChange=new wo,this._onActionsSent=new wo,this._onActionsProcessed=new wo,this._onActionsReceived=new wo,this.receiveActions=e=>{let t=new k(e);var i=t.readUint32(),e=this.gameoptParser.parseAllPlayerActions(t);this.receivedNetworkTurn=i,this.receivedActions.set(i,e),this._onActionsReceived.dispatch(void 0,i)},this.handleGameDesync=()=>{this.setErrorState(),this.onDesync()}}init(){this.gameTurnMillis=1e3/(this.game.desiredSpeed.value*Us.BASE_TICKS_PER_SECOND),this.currentNetworkTurn=0,this.currentSubTurn=0,this.gservCon.onGameActions.subscribe(this.receiveActions),this.gservCon.onGameDesync.subscribe(this.handleGameDesync),this.debug(`Init: gameTurnMillis = ${this.gameTurnMillis}`)}canAdvanceNetworkTurn(){return this.currentNetworkTurn<2||this.receivedActions.has(this.currentNetworkTurn-2)}setErrorState(){this.errorState=!0}getErrorState(){return this.errorState}setRate(e){if(this.debug(`Recv rate: ${e.rate} (turn ${e.turnNo})`),0===this.currentSubTurn&&0===this.currentNetworkTurn&&0===e.turnNo)this.updateRate(e.rate);else{if(e.turnNo<this.currentNetworkTurn-2)throw new Error("Rate change has turn number more than two turns in the past.");this.queuedRateChanges.push(e)}}updateRate(e){var t;this.networkTurnMillis=(t=this.gameTurnMillis,Math.max(1,Math.ceil(e/t))*t),this.hashCheckTurnInterval=Math.ceil(km.PREFERRED_HASH_CHECK_MILLIS/this.networkTurnMillis),this.netLogger?.debug(`Rate set to ${e} (${this.networkTurnMillis}ms) @ ${this.currentNetworkTurn}`)}setPassiveMode(e){this.debug(`Send passive: ${e}`),this.passiveMode=e,this.gservCon.sendPlayerActive(!e)}getTurnMillis(){return this.gameTurnMillis}doGameTurn(e){if(!this.errorState){if(!this.networkTurnMillis)throw new Error("Network turn rate should be set by now.");if(this.game.status!==nc.Ended){if(0===this.currentSubTurn){var t=this.queuedRateChanges[0];if(t&&t.turnNo+2===this.currentNetworkTurn&&(this.debug(`Process rate ${t.rate} (turn ${t.turnNo})`),this.updateRate(t.rate),this.queuedRateChanges.shift()),!this.canAdvanceNetworkTurn())return this.handleCommsLag(!0,e),this.debug(`Lag state: ${this.lagState}`),!1;this.debug("Advance turn"),this.commsLagStartTime&&0<e-this.commsLagStartTime&&this.netLogger?.debug(`Waited ${Math.round(e-this.commsLagStartTime)}ms `+"for other clients to catch up."),this.handleCommsLag(!1,e),!this.passiveMode&&this.currentNetworkTurn>=this.receivedNetworkTurn&&this.sendActions(),2<=this.currentNetworkTurn&&(i=this.receivedActions.get(this.currentNetworkTurn-2),this.replayRecorder.recordActions(this.game.currentTick,i),this.processActions(i),this.receivedActions.delete(this.currentNetworkTurn-2),this._onActionsProcessed.dispatch(void 0,this.currentNetworkTurn-2)),this.game.update(),this.passiveMode||this.currentNetworkTurn%this.hashCheckTurnInterval!=0||this.gservCon.sendGameStateHash(this.currentNetworkTurn,this.game.getHash()),this.networkTurnMillis>this.gameTurnMillis?this.currentSubTurn++:this.currentNetworkTurn++}else this.debug("Update"),this.game.update(),this.currentSubTurn++,this.currentSubTurn>=this.networkTurnMillis/this.gameTurnMillis&&(this.currentSubTurn=0,this.currentNetworkTurn++);var i;this.debugGameState&&(i=this.networkTurnMillis/this.gameTurnMillis*this.hashCheckTurnInterval,this.debugGameStateHistory.length>i&&this.debugGameStateHistory.shift(),this.debugGameStateHistory.push(this.game.debugGetState()))}else this.game.update()}}handleCommsLag(e,t){e?(this.commsLagStartTime||(this.commsLagStartTime=t),1e3<t-this.commsLagStartTime&&this.updateLagState(!0)):(this.commsLagStartTime=void 0,this.updateLagState(!1))}updateLagState(e){e!==this.lagState&&(this.lagState=e,this._onLagStateChange.dispatch(void 0,e))}sendActions(){let e=this.inputActions.dequeueAll();e.length||e.push(new pd);var t=this.gameoptSerializer.serializePlayerActions(e.map(e=>this.actionSerializer.getActionPayload(e)));this.debug(`Send actions: ${t}`),this.gservCon.sendPlayerActions(this.currentNetworkTurn,t),this._onActionsSent.dispatch(void 0,this.currentNetworkTurn)}processActions(e){[...e].forEach(([i,e])=>e.forEach(e=>{let t=this.actionFactory.create(e.id);t.player=this.game.getPlayer(i),t.unserialize(e.params),t.process();e=t.print();e&&this.actionLogger?.debug(`(${t.player.name})@${this.game.currentTick}: ${e}`)}))}debug(e){this.debugLogger?.(`${this.currentNetworkTurn}-${this.currentSubTurn}-${this.game.currentTick}: ${e}`)}dispose(){this.setErrorState(),this.gservCon.onGameActions.unsubscribe(this.receiveActions),this.gservCon.onGameDesync.unsubscribe(this.handleGameDesync)}}km.PREFERRED_HASH_CHECK_MILLIS=1e3;const Om=__WEBPACK_EXTERNAL_createRequire(import.meta.url)("perf_hooks");class _m{constructor(e){this.gameTurnMgr=e,this.isStarted=!1}start(){this.isStarted||(this.isStarted=!0,this.startTime=void 0,this.lastGameFrame=0)}async waitForTick(){return new Promise((e,t)=>this.doWaitForTick(e,t))}doWaitForTick(e,t){try{this.isStarted||e();var i=Om.performance.now(),s=this.updateDeltaGameFrames(i);if(0<s)if(!(!1===this.gameTurnMgr.doGameTurn(i)))return void e();setImmediate(()=>this.doWaitForTick(e,t))}catch(e){t(e)}}updateDeltaGameFrames(e){var t=this.gameTurnMgr.getTurnMillis(),i=t!==this.lastGameTurnMillis;this.lastGameTurnMillis=t,i&&(this.lastGameFrame=0,this.startTime=e);let s=0;return this.startTime?(i=e-this.startTime,t=Math.round(i/t),s=t-this.lastGameFrame,this.lastGameFrame=t):this.startTime=e,s}stop(){this.isStarted&&(this.isStarted=!1)}destroy(){this.stop()}}const Im=__WEBPACK_EXTERNAL_createRequire(import.meta.url)("fs");var Cm,Am,Bm,xm,Em,Pm,Nm,Dm,Mm=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i},Rm=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)};class Lm{constructor(e,t,i,s,r,a,n,o,h){Cm.set(this,void 0),Am.set(this,void 0),Bm.set(this,void 0),xm.set(this,void 0),Em.set(this,void 0),Pm.set(this,void 0),Nm.set(this,void 0),Dm.set(this,void 0),Mm(this,Cm,e,"f"),Mm(this,Am,t,"f"),Mm(this,Bm,new Rp(t,!1),"f"),Mm(this,xm,new wp(t.events),"f"),Mm(this,Em,i,"f"),Mm(this,Pm,a,"f"),Mm(this,Nm,o,"f"),Mm(this,Dm,h,"f"),Rm(this,xm,"f").subscribe(t=>e.forEach(e=>e.onGameEvent(t,Rm(this,Bm,"f")))),e.forEach(e=>{e.setGameApi(Rm(this,Bm,"f")),e.setActionsApi(new op(t,s,r,e,n)),e.setProductionApi(new Jp(t.getPlayerByName(e.name).production)),e.setLogger(new Vp(Tr.get(e.name),Rm(this,Bm,"f"))),e.onGameStart(Rm(this,Bm,"f"))})}isFinished(){return Rm(this,Am,"f").status===nc.Ended||Rm(this,Pm,"f").getErrorState()}async update(){if(Rm(this,Nm,"f"))await Rm(this,Nm,"f").waitForTick();else{if(!(Rm(this,Pm,"f")instanceof em))throw new Error("Missing animation loop or turn manager");Rm(this,Pm,"f").doGameTurn()}Rm(this,Cm,"f").forEach(e=>e.onGameTick(Rm(this,Bm,"f")))}getCurrentTick(){return Rm(this,Bm,"f").getCurrentTick()}getTickRate(){return Rm(this,Bm,"f").getTickRate()}getPlayerStats(){return Rm(this,Am,"f").getNonNeutralPlayers().filter(e=>!e.isObserver).map(t=>({name:t.name,country:t.country,ai:t.isAi||Rm(this,Cm,"f").some(e=>e.name===t.name),defeated:t.defeated,credits:t.credits,startLocation:t.startLocation}))}saveReplay(e){let t=Rm(this,Em,"f");t.finish(Rm(this,Am,"f").currentTick);var i=`${Rm(this,Am,"f").gameOpts.mapName}_${Date.now()}${um.extension}`,s=t.serialize(),i=a.resolve(e??process.cwd(),i);return Im.writeFileSync(i,s,"utf-8"),process.stdout.write(`Replay saved to "${i}"\n`),i}getDebugStateDump(){return Rm(this,Pm,"f")instanceof km?Rm(this,Pm,"f").debugGameStateHistory:void 0}dispose(){Rm(this,xm,"f").dispose(),Rm(this,Cm,"f").length=0,Rm(this,Dm,"f")?.call(this)}}Cm=new WeakMap,Am=new WeakMap,Bm=new WeakMap,xm=new WeakMap,Em=new WeakMap,Pm=new WeakMap,Nm=new WeakMap,Dm=new WeakMap;class Fm{constructor(e,t,i){this.game=e,this.replayRecorder=t,this.gservCon=i,this.disposables=new Zl,this.handleGservMessage=e=>{e.to.type===vm.Channel&&e.to.name===bm&&this.replayRecorder.recordChatMessage(this.game.currentTick,e.from,e.text)}}init(){this.gservCon.onChatMessage.subscribe(this.handleGservMessage),this.disposables.add(()=>this.gservCon.onChatMessage.unsubscribe(this.handleGservMessage))}sayAll(e,t){this.gservCon.isOpen()?this.gservCon.sayChannel(t):console.warn("Can't send chat message. Network connection is already closed.")}dispose(){this.disposables.dispose()}}class jm{constructor(e,t){this.game=e,this.replayRecorder=t}sayAll(e,t){this.replayRecorder.recordChatMessage(this.game.currentTick,e,t)}}class Um{static getGameRoute(e){return`#/game/${P.encode(JSON.stringify({gameId:e.gameId,gameTimestamp:e.gameTimestamp,gservUrl:e.gservUrl,playerName:e.playerName,gameOpts:e.gameOpts,tournament:e.tournament}))}`}static extractGameParams(e){return JSON.parse(P.decode(e))}}Um.modQueryStringName="mod";var Wm=function(e,t,i,s){if("a"===i&&!s)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?s:"a"===i?s.call(e):s?s.value:t.get(e)},zm=function(e,t,i,s,r){if("m"===s)throw new TypeError("Private method is not writable");if("a"===s&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===s?r.call(e,i):r?r.value=i:t.set(e,i),i};const Vm=a.resolve((0,e.default)(),"./res");class Hm{constructor(){Ym.add(this),Gm.set(this,void 0),$m.set(this,void 0),qm.set(this,void 0),Xm.set(this,void 0),Zm.set(this,!1),Qm.set(this,void 0)}async init(e){Wm(this,Ym,"m",Km).call(this),globalThis.Blob||(globalThis.Blob=(await Promise.resolve().then(__webpack_require__.bind(__webpack_require__,91))).Blob);var t=await(0,n.getOriginPrivateDirectory)(o.default,a.resolve(e)),i=await(0,n.getOriginPrivateDirectory)(o.default,Vm),e=await(0,n.getOriginPrivateDirectory)(o.default,process.cwd());Dt.initGameResSource(vt.Local);let s=await Dt.initRfs(t);s.addDirectoryHandle(i),s.addDirectoryHandle(e);let r=await Dt.initVfs(s,Tr.get("vfs"));await r.loadStandaloneFiles(),await r.loadExtraMixFiles(Dt.getActiveEngine()),await r.addMixFile("ra2cd.mix"),await r.loadImplicitMixFiles(Dt.getActiveEngine()),Dt.loadRules(),zm(this,Qm,await Dt.loadMapList(),"f"),zm(this,Gm,Dt.getMpModes(),"f"),zm(this,Zm,!0,"f")}getAvailableMaps(){if(!Wm(this,Zm,"f"))throw new Error("API is not initialized. Call init() first.");return Wm(this,Qm,"f").getAll().map(e=>e.fileName.toLowerCase())}getAvailableGameModes(e){if(!Wm(this,Zm,"f"))throw new Error("API is not initialized. Call init() first.");let t=Wm(this,Qm,"f").getByName(e);if(!t)throw new Error(`Map "${e}" is not available`);return t.gameModes.map(e=>e.id)}async createGame(e){return e.online?await Wm(this,Ym,"m",e0).call(this,e):await Wm(this,Ym,"m",Jm).call(this,e)}}var Gm=new WeakMap,$m=new WeakMap,qm=new WeakMap,Xm=new WeakMap,Zm=new WeakMap,Qm=new WeakMap,Ym=new WeakSet,Km=function(){Tr.useDefaults(),Tr.setLevel(Tr.ERROR);const e=process.env.DEBUG_LOGGING;var t;if(e)if(isNaN(e))for(t of e.split(","))Tr.get(t).setLevel(Tr.DEBUG);else Tr.setLevel(Number(e)?Tr.DEBUG:Tr.ERROR);zm(this,$m,Tr.get("ini"),"f"),zm(this,qm,Tr.get("action"),"f"),zm(this,Xm,Tr.get("net"),"f")},Jm=async function(e){if(!Wm(this,Zm,"f"))throw new Error("API is not initialized. Call init() first.");if(e.agents.some(e=>!(e instanceof tp)))throw new Error("All players in the agents array must be bots in offline mode");var t=await Wm(this,Ym,"m",i0).call(this,e),i=e.agents.filter(e=>e instanceof tp),s=new Oi(await Dt.vfs.openFileWithRfs(t.mapName)),r=Math.floor(Date.now()/1e3),a=await Wm(this,Ym,"m",t0).call(this,"0",r,t,s,void 0),e=new rp,r=new cd;(new Vg).register(r,a,void 0);let n=new um;n.init(a.id,a.startTimestamp,t,Dt.getVersion(),Dt.getModHash());s=new gm,t=new dm(n,0,a.gameOpts.humanPlayers,s);let o=new em(a,e,t,s,r,Wm(this,qm,"f"));o.init();t=new jm(a,t);return new Lm(i,a,n,r,e,o,t)},e0=async function(e){if(!Wm(this,Zm,"f"))throw new Error("API is not initialized. Call init() first.");if(!e.serverUrl)throw new Error("Must specify a serverUrl");if(!e.clientUrl)throw new Error("Must specify a clientUrl");let t=[];for(var i of e.agents){if(!i.name.match(/^[a-z0-9-_]+$/i))throw new Error(`Agent name "${i.name}" must contain only alphanumeric characters, dash (-) or underscore (_)`);i instanceof tp&&t.push(i)}if(!(e.agents[0]instanceof tp))throw new Error("The first object in the agents array must be a Bot instance in online mode");if(e.agents.slice(1).some(e=>e instanceof tp))throw new Error("Only the first player in the agents array can be a bot in online mode");var s=await Wm(this,Ym,"m",i0).call(this,e);let r=class{get onError(){return this.con.onError}get onClose(){return this.con.onClose}get onLoadInfo(){return this._onLoadInfo.asEvent()}get onGameStart(){return this._onGameStart.asEvent()}get onGameActions(){return this._onGameActions.asEvent()}get onGameDesync(){return this._onGameDesync.asEvent()}get onRateChange(){return this._onRateChange.asEvent()}get onChatMessage(){return this._onChatMessage.asEvent()}get onTaunt(){return this._onTaunt.asEvent()}get onPlayerDisconnect(){return this._onPlayerDisconnect.asEvent()}get onPrivMsgNotAllowed(){return this._onPrivMsgNotAllowed.asEvent()}static factory(e){return new this(new wm({mode:"text",binaryRplPrefix:2,binaryReqPrefix:2,logFilter:e=>e.replace(/^(user [^ ]+) ([^ ]+)/i,"$1 <redacted>").replace(/^((:.+!.+@.+)?privmsg ([^ ]+ )+):(.+)\r?\n?$/i,"$1:<redacted>")},e))}constructor(e){this._onLoadInfo=new wo,this._onGameStart=new wo,this._onGameActions=new wo,this._onGameDesync=new wo,this._onRateChange=new wo,this._onChatMessage=new wo,this._onTaunt=new wo,this._onPlayerDisconnect=new wo,this._onPrivMsgNotAllowed=new wo,this.handleMessage=t=>{if("string"==typeof t){let e=t.split(" ");var i,s;"ping"===e[0]?this.isOpen()&&this.con.sendMessage("pong"+(e[1]?" "+e[1]:"")):"privmsg"===e[1].toLowerCase()?this.handlePrivMsg(t):"600"===e[1]?this.handleLoadInfo(e[3]):"700"===e[1]?this.handleGameStart():"801"===e[1]?this._onGameDesync.dispatch(this):"802"===e[1]?([i,s]=e[3].slice(1).split(","),this._onRateChange.dispatch(this,{rate:Number(i),turnNo:Number(s)})):"803"===e[1]?this._onTaunt.dispatch(this,{from:e[0].replace(/^:/,""),tauntNo:Number(e[3].replace(/^:/,""))}):"804"===e[1]?this._onPlayerDisconnect.dispatch(this,e[3].replace(/^:/,"")):"805"===e[1]&&this._onPrivMsgNotAllowed.dispatch(this)}else 1===t[0]&&this.handlePlayerActions(t.slice(1))},this.con=e}getCurrentUser(){return this.currentUser}getServerName(){return this.serverName}async connect(e,t){return this.con.onMessage.subscribe(this.handleMessage),await this.con.connect(e,t)}close(){this.con.onMessage.unsubscribe(this.handleMessage),this.con.close(),this.currentUser=void 0}isOpen(){return this.con.isOpen()}async cvers(e){let t=await this.con.sendCommand(`cvers ${e} 2`,{replyCodes:[10,11]});if(11===t[0].code){e=t[0].params?t[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new Tm(`Cvers error: ${e}`,Tm.Code.OutdatedClient)}}async login(e,t){let i=await this.con.sendCommand(`user ${e} ${P.encode(t)}`,{replyCodes:[100,103,104,101],timeout:10});if(100!==i[0].code){var s=Sm.get(i[0].code)??Tm.Code.Unknown,t=i[0].params?i[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new Tm(`Login error: ${t}`,s)}this.currentUser=e,this.serverName=i[0].raw.match(/^:([^\s]+)/)?.[1]||""}async createGame(e,t,i,s,r,a=!1){if(i.includes(" "))throw new Error("Game opts string cannot include spaces");let n=await this.con.sendCommand(`create ${e} ${t} ${i} ${s} ${r} ${Number(a)}`,{replyCodes:[200,201,202,402]});if(200!==n[0].code){r=Sm.get(n[0].code)??Tm.Code.Unknown,a=n[0].params?n[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new Tm(`Create error: ${a}`,r)}}async joinGame(e,t,i){let s=await this.con.sendCommand(`join ${e} ${t} ${i}`,{replyCodes:[400,401,402,403,406]});if(400!==s[0].code){t=Sm.get(s[0].code)??Tm.Code.Unknown,i=s[0].params?s[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new Tm(`Join error: ${i}`,t)}}async gameOpts(){let e=await this.con.sendCommand("gameopts",{replyCodes:[500]});if(!e[0].params)throw new Error("Unexpected server reply for getopts command. Missing params.");return e[0].params.splice(1).join(" ").replace(/^:/,"")}sendLoadedPercent(e){this.con.sendMessage(`loaded ${e}`)}requestLoadInfo(){this.con.sendMessage("loadinfo")}sendGameStateHash(e,t){let i=new k(10);i.dynamicSize=!1,i.writeUint8(2),i.writeUint8(2),i.writeUint32(e),i.writeUint32(t),this.con.sendMessage(i.toUint8Array())}sendPlayerActive(e){this.con.sendMessage(`active ${e?1:0}`)}sendTaunt(e){this.con.sendMessage(`taunt ${e}`)}async ping(e){return await this.con.ping(e)}sendPlayerActions(e,t){let i=new k(6);i.writeUint8(2),i.writeUint8(1),i.writeUint32(e),i.writeUint8Array(t),this.con.sendMessage(i.toUint8Array())}sendMap(e){let t=new k(2);t.writeUint8(2),t.writeUint8(3),t.writeUint8Array((new sm).serializeMapData(e)),this.con.sendMessage(t.toUint8Array())}async getMap(){let e=new k(2);e.dynamicSize=!1,e.writeUint8(2),e.writeUint8(4);var t=await this.con.sendBinCommand(e.toUint8Array(),{replyCodes:[2],timeout:15});return(new rm).parseMapData(t.data)}handleLoadInfo(e){this._onLoadInfo.dispatch(this,e.replace(/^:/,""))}handleGameStart(){this._onGameStart.dispatch(this,void 0)}handlePlayerActions(e){this._onGameActions.dispatch(this,e)}sayChannel(e){this.privmsg([bm],e)}privmsg(e,t){if(!this.currentUser)throw new Error("Must login before sending messages");t.length&&(e=e.join(","),this.con.sendMessage(`privmsg ${e} :${t}`))}handlePrivMsg(e){var t=e.match(/^:([A-Za-z0-9-_]+) PRIVMSG ([A-Za-z0-9-_#']+) :(.*)/i);if(!t)throw new Error(`Unexpected PRIVMSG message format "${e}"`);var[,i,s,e]=t;let r;t=new Date;s===bm?r={from:i,to:{type:vm.Channel,name:s},text:e,time:t}:s===this.currentUser&&(r={from:i,to:i===this.getServerName()?{type:vm.Page,name:s}:{type:vm.Channel,name:"#team"},text:e,time:t}),r&&this._onChatMessage.dispatch(this,r)}}.factory(Wm(this,Xm,"f"));await r.connect(e.serverUrl),await r.cvers(Dt.getVersion()),await r.login(e.agents[0].name,e.botPassword);let a=new sm;var n,o=a.serializeOptions(s),h=S.randomUUID(),l=Math.floor(Date.now()/1e3);process.stdout.write("\nYou may use the following link(s) to join, after the game is created:\n\n");let c=new Map;for(n of e.agents.slice(1)){var u=e.clientUrl.replace(/\/$/,"")+`/${Um.getGameRoute({gameId:h,gameTimestamp:l,gservUrl:e.serverUrl,playerName:n.name})}`;c.set(n,u),process.stdout.write(u+"\n")}e.nonInteractive||(process.stdout.write("\n\nPress ENTER to create the game now...\n"),await new Promise(e=>process.stdin.once("data",e)),process.stdin.pause()),process.stdout.write("Creating game...\n"),await r.createGame(h,l,o,Dt.getVersion(),Dt.getModHash());let d=new rm;var g=d.parseOptions(await r.gameOpts());let p=await Dt.vfs.openFileWithRfs(s.mapName);var m=new Oi(p);s.mapOfficial||r.sendMap(p.readAsString());var f=e.agents[0].name;let y=await Wm(this,Ym,"m",t0).call(this,h,l,g,m,f);o=new gm,s=new rp,m=new cd;(new Vg).register(m,y,f);let w=new um;w.init(y.id,y.startTimestamp,g,Dt.getVersion(),Dt.getModHash());g=new dm(w,0,y.gameOpts.humanPlayers,o);let T=new km(y,r,d,a,o,m,s,()=>{console.error("Desync detected."),process.exit(1)},Wm(this,qm,"f"),void 0,void 0,g,e.debugStateDumps??!1);T.init();let b=new _m(T);r.onRateChange.subscribe(e=>T.setRate(e)),y.onEnd.subscribe(()=>{process.stdout.write("Game ended.\n"),b.destroy()}),process.stdout.write("\nGame created."),process.stdout.write("\nWaiting for players to join...\n"),e.onGameCreate?.(c),await new Promise((e,t)=>{r.onGameStart.subscribeOnce(()=>{r.onClose.unsubscribe(t),b.start(),e()}),r.onClose.subscribeOnce(t),r.sendLoadedPercent(100)}),process.stdout.write("Game started.\n");let v=new Fm(y,g,r);v.init();return r.onClose.subscribeOnce(()=>T.dispose()),new Lm(t,y,w,m,s,T,v,b,()=>{b.destroy(),v.dispose(),Wm(this,Xm,"f").setLevel(Tr.OFF),r.close()})},t0=async function(e,t,i,s,r){if(!Wm(this,Zm,"f"))throw new Error("API is not initialized. Call init() first.");var a=Dt.getIni(Wm(this,Gm,"f").getById(i.gameMode).rulesOverride),n=class{static getTypes(e){let t=[];return e.noDogEngiKills&&t.push(At.NoDogEngiKills),t}}.getTypes(i).map(e=>Dt.mixinRulesFileNames.get(e)).filter(Wa).map(e=>Dt.getIni(e));await Dt.loadTheater(s.theaterType);var o=Dt.getActiveEngine(),h=Dt.getTheaterSettings(o,s.theaterType),o=Dt.getTheaterIni(o,s.theaterType);let l=new Y(o);l.loadTileData(Dt.getTileData(),h.extension);let c=class{static create(e,t,i,s,r,a,n,o,h,l,c,u,d,g,p,m,f){let y=i.clone().mergeWith(a);for(var w of n)y.mergeWith(w);y.mergeWith(e);var T=s.clone().mergeWith(e.artOverrides??new D);let b=new io(y,g);a=new no(b,T,e,g),n=new Qg(r);b.applySpecialFlags(e.specialFlags),class{static sanitize(e,t){t=t.mpDialogSettings;e.credits=Math.floor(z(e.credits,t.minMoney,t.maxMoney)),e.gameSpeed=Math.floor(z(e.gameSpeed,0,6)),e.unitCount=Math.floor(z(e.unitCount,t.minUnitCount,t.maxUnitCount))}}.sanitize(l,b);let v=new io(i),S=v.getMultiplayerCountries(),k=[...v.getMultiplayerColors().values()],O=yc.factory(o,h),_=new _l(e,t,b,O.generateRandomInt.bind(O));s=new al,T=c.getById(l.gameMode).type,g=new Al,r=new Cl(g),i=new xl,e=new El(1),t=new rl(_.tiles,_.tileOccupation,_.bridges,e),c=new cd,d=new sp(d),f=class{static factory(e,t,i,s){return new this(e,new rp,t,i,s)}constructor(e,t,i,s,r){this.actionFactory=e,this.actionQueue=t,this.botFactory=i,this.botDebugIndex=s,this.actionLogger=r,this.bots=new Map,this.disposables=new Zl}init(t){this.gameApi=new Rp(t,!0);let e=new wp(t.events);var i,s;for(i of t.getCombatants().filter(e=>e.isAi))this.bots.set(i,this.botFactory.create(i));this.updateDebugBotIndex(this.botDebugIndex.value,t);let r=e=>this.updateDebugBotIndex(e,t);this.botDebugIndex.onChange.subscribe(r),this.disposables.add(()=>this.botDebugIndex.onChange.unsubscribe(r)),e.subscribe(t=>this.bots.forEach(e=>e.onGameEvent(t,this.gameApi))),this.disposables.add(e);for(s of this.bots.values())s.setGameApi(this.gameApi),s.setActionsApi(new op(t,this.actionFactory,this.actionQueue,s)),s.setProductionApi(new Jp(t.getPlayerByName(s.name).production)),s.setLogger(new Vp(Tr.get(s.name),this.gameApi)),s.onGameStart(this.gameApi)}update(e){var t,i;for(t of this.actionQueue.dequeueAll()){t.process();var s=t.print();s&&this.actionLogger.debug(`(${t.player.name})@${e.currentTick}: ${s}`)}for(i of e.getCombatants().filter(e=>e.isAi))this.bots.get(i).onGameTick(this.gameApi)}updateDebugBotIndex(e,t){var i,s=0<e?t.getAiPlayerName(e):void 0;for(i of this.bots.values())i.setDebugMode(i.name===s)}dispose(){this.gameApi=void 0,this.bots.clear(),this.disposables.dispose()}}.factory(c,d,m,f);let I=new hd(s,_,b,a,n,o,h,l,T,g,i,r,e,t,f);(new Vg).register(c,I,void 0),I.traits.add(new jl),I.sellTrait=new Wl(I,b.general),I.traits.add(I.sellTrait),I.traits.add(new Hl);let C=new $l(b,p);I.traits.add(C),I.mapShroudTrait=new ql(_,r),I.traits.add(I.mapShroudTrait),I.mapRadiationTrait=new ld(_),I.traits.add(I.mapRadiationTrait),I.mapLightingTrait=new Zg(b.audioVisual,_.getLighting()),I.traits.add(I.mapLightingTrait),I.traits.add(new un),I.traits.add(new Hg),I.traits.add(new Gg),I.crateGeneratorTrait=new Jn(l.cratesAppear),I.traits.add(I.crateGeneratorTrait),u||(I.stalemateDetectTrait=new qg,I.traits.add(I.stalemateDetectTrait));let A=new Fl(b,l,C.getAvailableObjects()),B=Xg.factory(o,h),x=B.generateColors(l),E=B.generateCountries(l,v),P=B.generateStartLocations(l,_.startingLocations),N=[...l.humanPlayers,...l.aiPlayers].filter(Wa);return N.forEach(e=>{let t,i,s;if(xs(e)?(t=e.name,i=!1):(t=I.getAiPlayerName(e),i=!0,s=e.difficulty),-3!==e.countryId){var r=E.get(e)??e.countryId,a=x.get(e)??e.colorId,e=P.get(e)??e.startPos;if(-2===r)throw new Error("Random country should have been resolved by now");if(-2===a)throw new Error("Random color should have been resolved by now");if(-2===e)throw new Error("Random start location should have been resolved by now");r=S[r].name,r=oo.factory(r,b),a=k[a];I.addPlayer(A.createCombatant(t,r,e,a,i,s))}else I.addPlayer(A.createObserver(t,b))}),I.addPlayer(A.createNeutral(b,"@@NEUTRAL@@")),I}}.create(s,l,Dt.getRules(),Dt.getArt(),Dt.getAi(),a,n,e,t,i,Wm(this,Gm,"f"),!1,{version:"0.0.0"},Wm(this,$m,"f"),new El(!1),new El(0),Wm(this,qm,"f"));return c.init(r?c.getPlayerByName(r):void 0),c.start(),c},i0=async function(t){let e=Wm(this,Qm,"f").getAll().find(e=>e.fileName.toLowerCase()===t.mapName.toLowerCase());if(!e)throw new Error(`Map ${t.mapName} not found.`);if(!e.gameModes.find(e=>e.id===t.gameMode))throw new Error(`Map "${e.fileName}" doesn't support game mode ${t.gameMode}`);let i=await Dt.vfs.openFileWithRfs(t.mapName),s=new io(Dt.getRules()).getMultiplayerCountries();return{gameMode:t.gameMode,shortGame:t.shortGame,mcvRepacks:t.mcvRepacks,cratesAppear:t.cratesAppear,superWeapons:t.superWeapons,gameSpeed:t.gameSpeed,credits:t.credits,unitCount:t.unitCount,buildOffAlly:t.buildOffAlly,destroyableBridges:t.destroyableBridges??!0,multiEngineer:t.multiEngineer??!1,noDogEngiKills:t.noDogEngiKills??!1,humanPlayers:t.agents.map((t,e)=>({name:t.name,countryId:void 0!==t.country?s.findIndex(e=>e.name===t.country):-3,colorId:e,startPos:-2,teamId:-2})),aiPlayers:new Array(8).fill(void 0),mapName:e.fileName,mapDigest:class{static compute(e){return oe.calculateCrc(e.getBytes()).toString(16)}}.compute(i),mapSizeBytes:i.getSize(),mapTitle:e.fileName,maxSlots:e.maxSlots,mapOfficial:e.official}},r=__webpack_require__(949);class s0 extends r.Euler{constructor(){super(...arguments),this.isEuler=!0}setFromRotationMatrix(e,t,i){var s=e.elements,r=s[0],a=s[4],n=s[8],o=s[1],h=s[5],l=s[9],c=s[2],e=s[6],s=s[10];return"XYZ"===(t=t||this._order)?(this._y=Ki.asin(z(n,-1,1)),Math.abs(n)<.99999?(this._x=Ki.atan2(-l,s),this._z=Ki.atan2(-a,r)):(this._x=Ki.atan2(e,h),this._z=0)):"YXZ"===t?(this._x=Ki.asin(-z(l,-1,1)),Math.abs(l)<.99999?(this._y=Ki.atan2(n,s),this._z=Ki.atan2(o,h)):(this._y=Ki.atan2(-c,r),this._z=0)):"ZXY"===t?(this._x=Ki.asin(z(e,-1,1)),Math.abs(e)<.99999?(this._y=Ki.atan2(-c,s),this._z=Ki.atan2(-a,h)):(this._y=0,this._z=Ki.atan2(o,r))):"ZYX"===t?(this._y=Ki.asin(-z(c,-1,1)),Math.abs(c)<.99999?(this._x=Ki.atan2(e,s),this._z=Ki.atan2(o,r)):(this._x=0,this._z=Ki.atan2(-a,h))):"YZX"===t?(this._z=Ki.asin(z(o,-1,1)),Math.abs(o)<.99999?(this._x=Ki.atan2(-l,h),this._y=Ki.atan2(-c,r)):(this._x=0,this._y=Ki.atan2(n,s))):"XZY"===t?(this._z=Ki.asin(-z(a,-1,1)),Math.abs(a)<.99999?(this._x=Ki.atan2(e,h),this._y=Ki.atan2(n,r)):(this._x=Ki.atan2(-l,s),this._y=0)):console.warn("THREE.Euler: .setFromRotationMatrix() given unsupported order: "+t),this._order=t,!1!==i&&this.onChangeCallback(),this}reorder(e){return r0.setFromEuler(this),this.setFromQuaternion(r0,e)}toVector3(e){return e?e.set(this._x,this._y,this._z):new as(this._x,this._y,this._z)}}const r0=new Ji;r=__webpack_require__(949);class a0 extends r.Spherical{setFromVector3(e){return this.radius=e.length(),0===this.radius?(this.theta=0,this.phi=0):(this.theta=Ki.atan2(e.x,e.z),this.phi=Ki.acos(z(e.y/this.radius,-1,1))),this}}r=__webpack_require__(949);class n0 extends r.Cylindrical{setFromVector3(e){return this.radius=Ki.sqrt(e.x*e.x+e.z*e.z),this.theta=Ki.atan2(e.x,e.z),this.y=e.y,this}}const o0=new Hm})();var __webpack_exports__ApiEventType=__webpack_exports__.ApiEventType,__webpack_exports__ArmorType=__webpack_exports__.ArmorType,__webpack_exports__AttackState=__webpack_exports__.AttackState,__webpack_exports__Bot=__webpack_exports__.Bot,__webpack_exports__Box2=__webpack_exports__.Box2,__webpack_exports__BuildCat=__webpack_exports__.BuildCat,__webpack_exports__BuildStatus=__webpack_exports__.BuildStatus,__webpack_exports__Cylindrical=__webpack_exports__.Cylindrical,__webpack_exports__Euler=__webpack_exports__.Euler,__webpack_exports__FactoryStatus=__webpack_exports__.FactoryStatus,__webpack_exports__FactoryType=__webpack_exports__.FactoryType,__webpack_exports__GameInstanceApi=__webpack_exports__.GameInstanceApi,__webpack_exports__GameMath=__webpack_exports__.GameMath,__webpack_exports__InfDeathType=__webpack_exports__.InfDeathType,__webpack_exports__LandTargeting=__webpack_exports__.LandTargeting,__webpack_exports__LandType=__webpack_exports__.LandType,__webpack_exports__LocomotorType=__webpack_exports__.LocomotorType,__webpack_exports__Matrix4=__webpack_exports__.Matrix4,__webpack_exports__MovementZone=__webpack_exports__.MovementZone,__webpack_exports__NavalTargeting=__webpack_exports__.NavalTargeting,__webpack_exports__ObjectType=__webpack_exports__.ObjectType,__webpack_exports__OrderType=__webpack_exports__.OrderType,__webpack_exports__PipColor=__webpack_exports__.PipColor,__webpack_exports__PrereqCategory=__webpack_exports__.PrereqCategory,__webpack_exports__PublicApi=__webpack_exports__.PublicApi,__webpack_exports__Quaternion=__webpack_exports__.Quaternion,__webpack_exports__QueueStatus=__webpack_exports__.QueueStatus,__webpack_exports__QueueType=__webpack_exports__.QueueType,__webpack_exports__RadarEventType=__webpack_exports__.RadarEventType,__webpack_exports__SideType=__webpack_exports__.SideType,__webpack_exports__SpeedType=__webpack_exports__.SpeedType,__webpack_exports__Spherical=__webpack_exports__.Spherical,__webpack_exports__StanceType=__webpack_exports__.StanceType,__webpack_exports__SuperWeaponStatus=__webpack_exports__.SuperWeaponStatus,__webpack_exports__SuperWeaponType=__webpack_exports__.SuperWeaponType,__webpack_exports__TagRepeatType=__webpack_exports__.TagRepeatType,__webpack_exports__TerrainType=__webpack_exports__.TerrainType,__webpack_exports__TheaterType=__webpack_exports__.TheaterType,__webpack_exports__Vector2=__webpack_exports__.Vector2,__webpack_exports__Vector3=__webpack_exports__.Vector3,__webpack_exports__VeteranAbility=__webpack_exports__.VeteranAbility,__webpack_exports__VeteranLevel=__webpack_exports__.VeteranLevel,__webpack_exports__VhpScan=__webpack_exports__.VhpScan,__webpack_exports__WeaponType=__webpack_exports__.WeaponType,__webpack_exports__ZoneType=__webpack_exports__.ZoneType,__webpack_exports__cdapi=__webpack_exports__.cdapi;export{__webpack_exports__ApiEventType as ApiEventType,__webpack_exports__ArmorType as ArmorType,__webpack_exports__AttackState as AttackState,__webpack_exports__Bot as Bot,__webpack_exports__Box2 as Box2,__webpack_exports__BuildCat as BuildCat,__webpack_exports__BuildStatus as BuildStatus,__webpack_exports__Cylindrical as Cylindrical,__webpack_exports__Euler as Euler,__webpack_exports__FactoryStatus as FactoryStatus,__webpack_exports__FactoryType as FactoryType,__webpack_exports__GameInstanceApi as GameInstanceApi,__webpack_exports__GameMath as GameMath,__webpack_exports__InfDeathType as InfDeathType,__webpack_exports__LandTargeting as LandTargeting,__webpack_exports__LandType as LandType,__webpack_exports__LocomotorType as LocomotorType,__webpack_exports__Matrix4 as Matrix4,__webpack_exports__MovementZone as MovementZone,__webpack_exports__NavalTargeting as NavalTargeting,__webpack_exports__ObjectType as ObjectType,__webpack_exports__OrderType as OrderType,__webpack_exports__PipColor as PipColor,__webpack_exports__PrereqCategory as PrereqCategory,__webpack_exports__PublicApi as PublicApi,__webpack_exports__Quaternion as Quaternion,__webpack_exports__QueueStatus as QueueStatus,__webpack_exports__QueueType as QueueType,__webpack_exports__RadarEventType as RadarEventType,__webpack_exports__SideType as SideType,__webpack_exports__SpeedType as SpeedType,__webpack_exports__Spherical as Spherical,__webpack_exports__StanceType as StanceType,__webpack_exports__SuperWeaponStatus as SuperWeaponStatus,__webpack_exports__SuperWeaponType as SuperWeaponType,__webpack_exports__TagRepeatType as TagRepeatType,__webpack_exports__TerrainType as TerrainType,__webpack_exports__TheaterType as TheaterType,__webpack_exports__Vector2 as Vector2,__webpack_exports__Vector3 as Vector3,__webpack_exports__VeteranAbility as VeteranAbility,__webpack_exports__VeteranLevel as VeteranLevel,__webpack_exports__VhpScan as VhpScan,__webpack_exports__WeaponType as WeaponType,__webpack_exports__ZoneType as ZoneType,__webpack_exports__cdapi as cdapi};
|
|
1
|
+
import*as __WEBPACK_EXTERNAL_MODULE_three__ from"three";import*as __WEBPACK_EXTERNAL_MODULE_fetch_blob_71f8024a__ from"fetch-blob";import*as __WEBPACK_EXTERNAL_MODULE_websocket_polyfill_8396782d__ from"websocket-polyfill";import{createRequire as __WEBPACK_EXTERNAL_createRequire}from"node:module";const __WEBPACK_EXTERNAL_createRequire_require=__WEBPACK_EXTERNAL_createRequire(import.meta.url);import*as __WEBPACK_EXTERNAL_MODULE_es_dirname_044d89a0__ from"es-dirname";import*as __WEBPACK_EXTERNAL_MODULE_file_system_access_58c08c7f__ from"file-system-access";import*as __WEBPACK_EXTERNAL_MODULE_file_system_access_lib_adapters_node_js_b1c03fd5__ from"file-system-access/lib/adapters/node.js";var __webpack_modules__={70(e){e.exports=__WEBPACK_EXTERNAL_MODULE_three__},422(e){e.exports=__WEBPACK_EXTERNAL_MODULE_fetch_blob_71f8024a__},750(l,h,c){var u;!function(){"use strict";function e(e,t){return function(){return t.apply(e,arguments)}}function i(){for(var e,t=arguments,i=t[0],r=1;r<t.length;r++)for(e in t[r])e in i||!t[r].hasOwnProperty(e)||(i[e]=t[r][e]);return i}var r,o={VERSION:"1.4.1"},s={},t=function(e,t){return{value:e,name:t}};o.DEBUG=t(1,"DEBUG"),o.INFO=t(2,"INFO"),o.TIME=t(3,"TIME"),o.WARN=t(4,"WARN"),o.ERROR=t(8,"ERROR"),o.OFF=t(99,"OFF");function a(e){this.context=e,this.setLevel(e.filterLevel),this.log=this.info}a.prototype={setLevel:function(e){e&&"value"in e&&(this.context.filterLevel=e)},getLevel:function(){return this.context.filterLevel},enabledFor:function(e){var t=this.context.filterLevel;return e.value>=t.value},debug:function(){this.invoke(o.DEBUG,arguments)},info:function(){this.invoke(o.INFO,arguments)},warn:function(){this.invoke(o.WARN,arguments)},error:function(){this.invoke(o.ERROR,arguments)},time:function(e){"string"==typeof e&&0<e.length&&this.invoke(o.TIME,[e,"start"])},timeEnd:function(e){"string"==typeof e&&0<e.length&&this.invoke(o.TIME,[e,"end"])},invoke:function(e,t){r&&this.enabledFor(e)&&r(t,i({level:e},this.context))}};var n=new a({filterLevel:o.OFF});(t=o).enabledFor=e(n,n.enabledFor),t.debug=e(n,n.debug),t.time=e(n,n.time),t.timeEnd=e(n,n.timeEnd),t.info=e(n,n.info),t.warn=e(n,n.warn),t.error=e(n,n.error),t.log=t.info,o.setHandler=function(e){r=e},o.setLevel=function(e){for(var t in n.setLevel(e),s)s.hasOwnProperty(t)&&s[t].setLevel(e)},o.getLevel=function(){return n.getLevel()},o.get=function(e){return s[e]||(s[e]=new a(i({name:e},n.context)))},o.createDefaultHandler=function(s){(s=s||{}).formatter=s.formatter||function(e,t){t.name&&e.unshift("["+t.name+"]")};function a(e,t){Function.prototype.apply.call(e,console,t)}var n={};return"undefined"==typeof console?function(){}:function(e,t){e=Array.prototype.slice.call(e);var i,r=console.log;t.level===o.TIME?(i=(t.name?"["+t.name+"] ":"")+e[0],"start"===e[1]?console.time?console.time(i):n[i]=(new Date).getTime():console.timeEnd?console.timeEnd(i):a(r,[i+": "+((new Date).getTime()-n[i])+"ms"])):(t.level===o.WARN&&console.warn?r=console.warn:t.level===o.ERROR&&console.error?r=console.error:t.level===o.INFO&&console.info?r=console.info:t.level===o.DEBUG&&console.debug&&(r=console.debug),s.formatter(e,t),a(r,e))}},o.useDefaults=function(e){o.setLevel(e&&e.defaultLevel||o.DEBUG),o.setHandler(o.createDefaultHandler(e))},void 0===(u="function"==typeof(u=o)?u.call(h,c,h,l):u)||(l.exports=u)}()},798(e){function t(e){null==e&&(e=(new Date).getTime()),this.N=624,this.M=397,this.MATRIX_A=2567483615,this.UPPER_MASK=2147483648,this.LOWER_MASK=2147483647,this.mt=new Array(this.N),this.mti=this.N+1,e.constructor==Array?this.init_by_array(e,e.length):this.init_seed(e)}t.prototype.init_seed=function(e){for(this.mt[0]=e>>>0,this.mti=1;this.mti<this.N;this.mti++){e=this.mt[this.mti-1]^this.mt[this.mti-1]>>>30;this.mt[this.mti]=(1812433253*((4294901760&e)>>>16)<<16)+1812433253*(65535&e)+this.mti,this.mt[this.mti]>>>=0}},t.prototype.init_by_array=function(e,t){var i,r,s;for(this.init_seed(19650218),i=1,r=0,s=this.N>t?this.N:t;s;s--){var a=this.mt[i-1]^this.mt[i-1]>>>30;this.mt[i]=(this.mt[i]^(1664525*((4294901760&a)>>>16)<<16)+1664525*(65535&a))+e[r]+r,this.mt[i]>>>=0,r++,++i>=this.N&&(this.mt[0]=this.mt[this.N-1],i=1),t<=r&&(r=0)}for(s=this.N-1;s;s--){a=this.mt[i-1]^this.mt[i-1]>>>30;this.mt[i]=(this.mt[i]^(1566083941*((4294901760&a)>>>16)<<16)+1566083941*(65535&a))-i,this.mt[i]>>>=0,++i>=this.N&&(this.mt[0]=this.mt[this.N-1],i=1)}this.mt[0]=2147483648},t.prototype.random_int=function(){var e,t,i=new Array(0,this.MATRIX_A);if(this.mti>=this.N){for(this.mti==this.N+1&&this.init_seed(5489),t=0;t<this.N-this.M;t++)e=this.mt[t]&this.UPPER_MASK|this.mt[t+1]&this.LOWER_MASK,this.mt[t]=this.mt[t+this.M]^e>>>1^i[1&e];for(;t<this.N-1;t++)e=this.mt[t]&this.UPPER_MASK|this.mt[t+1]&this.LOWER_MASK,this.mt[t]=this.mt[t+(this.M-this.N)]^e>>>1^i[1&e];e=this.mt[this.N-1]&this.UPPER_MASK|this.mt[0]&this.LOWER_MASK,this.mt[this.N-1]=this.mt[this.M-1]^e>>>1^i[1&e],this.mti=0}return e=this.mt[this.mti++],e^=e>>>11,e^=e<<7&2636928640,e^=e<<15&4022730752,(e^=e>>>18)>>>0},t.prototype.random_int31=function(){return this.random_int()>>>1},t.prototype.random_incl=function(){return this.random_int()*(1/4294967295)},t.prototype.random=function(){return this.random_int()*(1/4294967296)},t.prototype.random_excl=function(){return(this.random_int()+.5)*(1/4294967296)},t.prototype.random_long=function(){return 1/9007199254740992*(67108864*(this.random_int()>>>5)+(this.random_int()>>>6))},e.exports=t},895(e,t,i){i.r(t),i.d(t,{default:()=>r});const r=function(){"use strict";var i=new function(){this.blockSize=131072,this.minNewSize=this.blockSize,this.maxSize=0,this.OK=0,this.INPUT_OVERRUN=-4,this.OUTPUT_OVERRUN=-5,this.LOOKBEHIND_OVERRUN=-6,this.EOF_FOUND=-999,this.ret=0,this.buf=null,this.buf32=null,this.out=new Uint8Array(262144),this.cbl=0,this.ip_end=0,this.op_end=0,this.t=0,this.ip=0,this.op=0,this.m_pos=0,this.m_len=0,this.m_off=0,this.dv_hi=0,this.dv_lo=0,this.dindex=0,this.ii=0,this.jj=0,this.tt=0,this.v=0,this.dict=new Uint32Array(16384),this.emptyDict=new Uint32Array(16384),this.skipToFirstLiteralFun=!1,this.returnNewBuffers=!0,this.setBlockSize=function(e){return"number"==typeof e&&!isNaN(e)&&0<parseInt(e)&&(this.blockSize=parseInt(e),!0)},this.setOutputSize=function(e){return"number"==typeof e&&!isNaN(e)&&0<parseInt(e)&&(this.out=new Uint8Array(parseInt(e)),!0)},this.setReturnNewBuffers=function(e){this.returnNewBuffers=!!e},this.applyConfig=function(e){void 0!==e&&(void 0!==e.outputSize&&i.setOutputSize(e.outputSize),void 0!==e.blockSize&&i.setBlockSize(e.blockSize))},this.ctzl=function(e){var t;return 1&e?t=0:(t=1,0==(65535&e)&&(e>>=16,t+=16),0==(255&e)&&(e>>=8,t+=8),0==(15&e)&&(e>>=4,t+=4),0==(3&e)&&(e>>=2,t+=2),t-=1&e),t},this.extendBuffer=function(){var e=new Uint8Array(this.minNewSize+(this.blockSize-this.minNewSize%this.blockSize));e.set(this.out),this.out=e,this.cbl=this.out.length},this.match_next=function(){this.minNewSize=this.op+3,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.buf[this.ip++],1<this.t&&(this.out[this.op++]=this.buf[this.ip++],2<this.t&&(this.out[this.op++]=this.buf[this.ip++])),this.t=this.buf[this.ip++]},this.match_done=function(){return this.t=3&this.buf[this.ip-2],this.t},this.copy_match=function(){for(this.t+=2,this.minNewSize=this.op+this.t,this.minNewSize>this.cbl&&this.extendBuffer();this.out[this.op++]=this.out[this.m_pos++],0<--this.t;);},this.copy_from_buf=function(){for(this.minNewSize=this.op+this.t,this.minNewSize>this.cbl&&this.extendBuffer();this.out[this.op++]=this.buf[this.ip++],0<--this.t;);},this.match=function(){for(;;){if(64<=this.t)this.m_pos=this.op-1-(this.t>>2&7)-(this.buf[this.ip++]<<3),this.t=(this.t>>5)-1,this.copy_match();else if(32<=this.t){if(this.t&=31,0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=31+this.buf[this.ip++]}this.m_pos=this.op-1-(this.buf[this.ip]>>2)-(this.buf[this.ip+1]<<6),this.ip+=2,this.copy_match()}else if(16<=this.t){if(this.m_pos=this.op-((8&this.t)<<11),this.t&=7,0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=7+this.buf[this.ip++]}if(this.m_pos-=(this.buf[this.ip]>>2)+(this.buf[this.ip+1]<<6),this.ip+=2,this.m_pos===this.op)return this.state.outputBuffer=!0===this.returnNewBuffers?new Uint8Array(this.out.subarray(0,this.op)):this.out.subarray(0,this.op),this.EOF_FOUND;this.m_pos-=16384,this.copy_match()}else this.m_pos=this.op-1-(this.t>>2)-(this.buf[this.ip++]<<2),this.minNewSize=this.op+2,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos];if(0===this.match_done())return this.OK;this.match_next()}},this.decompress=function(e){if(this.state=e,this.buf=this.state.inputBuffer,this.cbl=this.out.length,this.ip_end=this.buf.length,this.t=0,this.ip=0,this.op=0,this.m_pos=0,this.skipToFirstLiteralFun=!1,17<this.buf[this.ip])if(this.t=this.buf[this.ip++]-17,this.t<4){if(this.match_next(),this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret}else this.copy_from_buf(),this.skipToFirstLiteralFun=!0;for(;;){if(this.skipToFirstLiteralFun)this.skipToFirstLiteralFun=!1;else{if(this.t=this.buf[this.ip++],16<=this.t){if(this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret;continue}if(0===this.t){for(;0===this.buf[this.ip];)this.t+=255,this.ip++;this.t+=15+this.buf[this.ip++]}this.t+=3,this.copy_from_buf()}if(this.t=this.buf[this.ip++],this.t<16){if(this.m_pos=this.op-2049,this.m_pos-=this.t>>2,this.m_pos-=this.buf[this.ip++]<<2,this.minNewSize=this.op+3,this.minNewSize>this.cbl&&this.extendBuffer(),this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos++],this.out[this.op++]=this.out[this.m_pos],0===this.match_done())continue;this.match_next()}if(this.ret=this.match(),this.ret!==this.OK)return this.ret===this.EOF_FOUND?this.OK:this.ret}return this.OK},this._compressCore=function(){for(this.ip_start=this.ip,this.ip_end=this.ip+this.ll-20,this.jj=this.ip,this.ti=this.t,this.ip+=this.ti<4?4-this.ti:0,this.ip+=1+(this.ip-this.jj>>5);!(this.ip>=this.ip_end);)if(this.dv_lo=this.buf[this.ip]|this.buf[this.ip+1]<<8,this.dv_hi=this.buf[this.ip+2]|this.buf[this.ip+3]<<8,this.dindex=((17053*this.dv_lo>>>16)+17053*this.dv_hi+6180*this.dv_lo&65535)>>>2,this.m_pos=this.ip_start+this.dict[this.dindex],this.dict[this.dindex]=this.ip-this.ip_start,(this.dv_hi<<16)+this.dv_lo==(this.buf[this.m_pos]|this.buf[this.m_pos+1]<<8|this.buf[this.m_pos+2]<<16|this.buf[this.m_pos+3]<<24)){if(this.jj-=this.ti,this.ti=0,this.v=this.ip-this.jj,0!==this.v)if(this.v<=3)for(this.out[this.op-2]|=this.v;this.out[this.op++]=this.buf[this.jj++],0<--this.v;);else{if(this.v<=18)this.out[this.op++]=this.v-3;else{for(this.tt=this.v-18,this.out[this.op++]=0;255<this.tt;)this.tt-=255,this.out[this.op++]=0;this.out[this.op++]=this.tt}for(;this.out[this.op++]=this.buf[this.jj++],0<--this.v;);}if(this.m_len=4,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len])for(;this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&(this.m_len+=1,this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]&&!(this.ip+this.m_len>=this.ip_end)&&this.buf[this.ip+this.m_len]===this.buf[this.m_pos+this.m_len]))))))););if(this.m_off=this.ip-this.m_pos,this.ip+=this.m_len,this.jj=this.ip,this.m_len<=8&&this.m_off<=2048)--this.m_off,this.out[this.op++]=this.m_len-1<<5|(7&this.m_off)<<2,this.out[this.op++]=this.m_off>>3;else if(this.m_off<=16384){if(--this.m_off,this.m_len<=33)this.out[this.op++]=32|this.m_len-2;else{for(this.m_len-=33,this.out[this.op++]=32;255<this.m_len;)this.m_len-=255,this.out[this.op++]=0;this.out[this.op++]=this.m_len}this.out[this.op++]=this.m_off<<2,this.out[this.op++]=this.m_off>>6}else{if(this.m_off-=16384,this.m_len<=9)this.out[this.op++]=16|this.m_off>>11&8|this.m_len-2;else{for(this.m_len-=9,this.out[this.op++]=16|this.m_off>>11&8;255<this.m_len;)this.m_len-=255,this.out[this.op++]=0;this.out[this.op++]=this.m_len}this.out[this.op++]=this.m_off<<2,this.out[this.op++]=this.m_off>>6}}else this.ip+=1+(this.ip-this.jj>>5);this.t=this.ll-(this.jj-this.ip_start-this.ti)},this.compress=function(e){for(this.state=e,this.ip=0,this.buf=this.state.inputBuffer,this.maxSize=this.buf.length+Math.ceil(this.buf.length/16)+64+3,this.maxSize>this.out.length&&(this.out=new Uint8Array(this.maxSize)),this.op=0,this.l=this.buf.length,this.t=0;20<this.l&&(this.ll=this.l<=49152?this.l:49152,!(this.t+this.ll>>5<=0));)this.dict.set(this.emptyDict),this.prev_ip=this.ip,this._compressCore(),this.ip=this.prev_ip+this.ll,this.l-=this.ll;if(this.t+=this.l,0<this.t){if(this.ii=this.buf.length-this.t,0===this.op&&this.t<=238)this.out[this.op++]=17+this.t;else if(this.t<=3)this.out[this.op-2]|=this.t;else if(this.t<=18)this.out[this.op++]=this.t-3;else{for(this.tt=this.t-18,this.out[this.op++]=0;255<this.tt;)this.tt-=255,this.out[this.op++]=0;this.out[this.op++]=this.tt}for(;this.out[this.op++]=this.buf[this.ii++],0<--this.t;);}return this.out[this.op++]=17,this.out[this.op++]=0,this.out[this.op++]=0,this.state.outputBuffer=!0===this.returnNewBuffers?new Uint8Array(this.out.subarray(0,this.op)):this.out.subarray(0,this.op),this.OK}};return{setBlockSize:function(e){return i.setBlockSize(e)},setOutputEstimate:function(e){return i.setOutputSize(e)},setReturnNewBuffers:function(e){i.setReturnNewBuffers(e)},compress:function(e,t){return void 0!==t&&i.applyConfig(t),i.compress(e)},decompress:function(e,t){return void 0!==t&&i.applyConfig(t),i.decompress(e)}}}()}},__webpack_module_cache__={};function __webpack_require__(e){var t=__webpack_module_cache__[e];if(void 0!==t)return t.exports;t=__webpack_module_cache__[e]={exports:{}};return __webpack_modules__[e].call(t.exports,t,t.exports,__webpack_require__),t.exports}__webpack_require__.n=e=>{var t=e&&e.__esModule?()=>e.default:()=>e;return __webpack_require__.d(t,{a:t}),t},__webpack_require__.d=(e,t)=>{for(var i in t)__webpack_require__.o(t,i)&&!__webpack_require__.o(e,i)&&Object.defineProperty(e,i,{enumerable:!0,get:t[i]})},__webpack_require__.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t),__webpack_require__.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var __webpack_exports__={};__webpack_require__.r(__webpack_exports__);const external_websocket_polyfill_namespaceObject=__WEBPACK_EXTERNAL_MODULE_websocket_polyfill_8396782d__,external_node_crypto_namespaceObject=__WEBPACK_EXTERNAL_createRequire_require("node:crypto"),external_path_namespaceObject=__WEBPACK_EXTERNAL_createRequire_require("path"),external_es_dirname_namespaceObject=__WEBPACK_EXTERNAL_MODULE_es_dirname_044d89a0__,external_file_system_access_namespaceObject=__WEBPACK_EXTERNAL_MODULE_file_system_access_58c08c7f__,node_js_namespaceObject=__WEBPACK_EXTERNAL_MODULE_file_system_access_lib_adapters_node_js_b1c03fd5__;class IniSection{constructor(e){this.entries=new Map,this.sections=new Map,this.name=e}fromJson(e){for(var t in e){var i;e.hasOwnProperty(t)&&(i=e[t],Array.isArray(i)||"object"!=typeof i?this.set(t,i):this.sections.set(t,new IniSection(t).fromJson(i)))}return this}clone(){let i=new IniSection(this.name);return this.entries.forEach((e,t)=>{i.set(t,e)}),this.sections.forEach((e,t)=>{i.sections.set(t,e.clone())}),i}set(e,t){this.entries.set(e,t)}get(e){return this.entries.get(e)}has(e){return this.entries.has(e)}getString(e,t=""){e=this.get(e);return e&&"string"==typeof e?e:t}getNumber(e,t=0){var i=this.get(e);if(!i||"string"!=typeof i)return t;var r=this.parseNumber(i);return void 0===r?(console.warn(`Invalid value for key ${e}. "${i}" is not a valid number or percentage string.`),t):r}parseNumber(e){let t;if(t=e.match(/%$/)?Number(e.replace("%",""))/100:Number(e),!isNaN(t))return t}getFixed(e,t=0){return this.toFixedPointPrecision(this.getNumber(e,t))}toFixedPointPrecision(e){return(65536*e|0)/65536}getBool(e,t=!1){let i=this.getString(e).trim();return i=i&&i.toLowerCase(),!(!i||-1===["yes","1","true","on"].indexOf(i))||(!i||-1===["no","0","false","off"].indexOf(i))&&t}getKeyArray(e,t=[]){e=this.get(e);return e&&Array.isArray(e)?e:t}getArray(e,t=/,\s*/,i=[]){let r=this.getString(e).trim();return r=r.replace(/,$/,"").replace(/,+/g,","),r?r.split(t):i}getNumberArray(e,t=/,\s*/,i=[]){let r=this.getString(e).trim();if(!r)return i;let s=[];for(var a of r.split(t)){if(!a)return i;var n=this.parseNumber(a);if(void 0===n)return console.warn(`Invalid value for key ${e}. "${a}" is not a valid number or percentage string.`),i;s.push(n)}return s}getFixedArray(e,t=/,\s*/,i=[]){return this.getNumberArray(e,t,i).map(e=>this.toFixedPointPrecision(e))}getEnum(e,t,i,r=!1){let s=this.getString(e).trim();if(!s)return i;let a;if(r){let e=Object.getOwnPropertyNames(t);r=e.find(e=>e.toLowerCase()===s.toLowerCase());r&&(a=t[r])}else t.hasOwnProperty(s)&&(a=t[s]);return void 0===a?(console.warn(`Invalid value for key "${e}". "${s}" is not an accepted enum value.`),i):a}getEnumNumeric(e,t,i){var r=this.getString(e).trim();if(!r)return i;let s;return Number.isInteger(parseInt(r,10))&&t.hasOwnProperty(r)&&(s=parseInt(r,10)),void 0===s?(console.warn(`Invalid value for key "${e}". "${r}" is not an accepted enum value.`),i):s}getEnumArray(e,r,t=/,\s*/,s=[],a=!1){let n=this.getString(e).trim();if(!n)return s;let o=[];for(let i of n.split(t)){if(!i)return s;let t=!1;if(a){let e=Object.getOwnPropertyNames(r);var l=e.find(e=>e.toLowerCase()===i.toLowerCase());l&&(o.push(r[l]),t=!0)}else r.hasOwnProperty(i)&&(o.push(r[i]),t=!0);if(!t)return console.warn(`Invalid value "${i}" for key "${e}".`),s}return o}getHighestNumericIndex(){let i=0,r;return this.entries.forEach((e,t)=>{r=parseInt(t,10),r>i&&(i=r)}),i}isNumericIndexArray(){return 0<this.getHighestNumericIndex()||this.has("0")}getConcatenatedValues(){let e="";for(var t of this.entries.values())"string"==typeof t&&(e+=t);return e}toString(e){let t=[],i=(e?e+".":"")+this.name;t.push(`[${i}]`);for(var[r,s]of this.entries)if(Array.isArray(s))for(var a of s)t.push(r+"[]="+a);else t.push(r+"="+s);return t.push(""),t.join("\r\n")+[...this.sections.values()].map(e=>e.toString(i)).join("\r\n")}mergeWith(e){if(this.isNumericIndexArray()){let i=this.getHighestNumericIndex()+1;e.entries.forEach((e,t)=>{Number.isNaN(Number(t))||Array.isArray(e)||this.set((i++).toString(),e)})}else e.entries.forEach((e,t)=>{this.set(t,Array.isArray(e)?[...e]:e)});e.sections.forEach((e,t)=>{let i=this.getOrCreateSection(t);i.mergeWith(e)})}getOrCreateSection(e){let t=this.sections.get(e);return t||(t=new IniSection(e),this.sections.set(e,t)),t}getSection(e){return this.sections.get(e)}getOrderedSections(){return[...this.sections.values()]}}class IniParser{parse(e){let a={},i=a,r,s=/^\[([^\]]*)\]\s*$|^([^=]+)(=(.*))?$/i,t=e.split(/[\r\n]+/g);return t.forEach(t=>{if(t&&!t.match(/^\s*[;#]/)){t=(t=t.replace(/]\s*(\/\/|;|#).*$/,"]")).match(s);if(t){if(void 0!==t[1])return r=this.unsafe(t[1]),void(i=a[r]=a[r]||{});let e=this.unsafe(t[2]);t=t[3]?this.unsafe(t[4]||""):"";2<e.length&&"[]"===e.slice(-2)&&(e=e.substring(0,e.length-2),i[e]?Array.isArray(i[e])||(i[e]=[i[e]]):i[e]=[]),Array.isArray(i[e])?i[e].push(t):i[e]=t}}}),Object.keys(a).filter(e=>{if(!a[e]||"object"!=typeof a[e]||Array.isArray(a[e]))return!1;let t=this.dotSplit(e),i=a,r=t.pop();var s=r.replace(/\\\./g,".");return t.forEach(function(e){i[e]&&"object"==typeof i[e]||(i[e]={}),i=i[e]}),(i!==a||s!==r)&&(i[s]=a[e],!0)}).forEach(function(e){delete a[e]}),a}dotSplit(e){return e.replace(/\x01/g,"LITERAL\\1LITERAL").replace(/\\\./g,"").split(/\./).map(e=>e.replace(/\x01/g,"\\.").replace(/\x02LITERAL\\1LITERAL\x02/g,""))}isQuoted(e){return'"'===e.charAt(0)&&'"'===e.slice(-1)||"'"===e.charAt(0)&&"'"===e.slice(-1)}unsafe(s){if(s=(s||"").trim(),this.isQuoted(s))return s=s.substr(1,s.length-2);{let i=!1,r="";for(let e=0,t=s.length;e<t;e++){var a=s.charAt(e);if(i)-1!=="\\;#".indexOf(a)?r+=a:r+="\\"+a,i=!1;else{if(-1!==";#".indexOf(a))break;"\\"===a?i=!0:r+=a}}return i&&(r+="\\"),r=r.trim(),r}}}class DataStream{constructor(e,t,i=DataStream.LITTLE_ENDIAN){this.endianness=i,this.position=0,this._dynamicSize=!0,this._byteLength=0,this._byteOffset=t||0,e instanceof ArrayBuffer?this.buffer=e:"object"==typeof e?(this.dataView=e,t&&(this._byteOffset+=t)):this.buffer=new ArrayBuffer(e||0)}get dynamicSize(){return this._dynamicSize}set dynamicSize(e){e||this._trimAlloc(),this._dynamicSize=e}get byteLength(){return this._byteLength-this._byteOffset}get buffer(){return this._trimAlloc(),this._buffer}set buffer(e){this._buffer=e,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._buffer.byteLength}get byteOffset(){return this._byteOffset}set byteOffset(e){this._byteOffset=e,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._buffer.byteLength}get dataView(){return this._dataView}set dataView(e){this._byteOffset=e.byteOffset,this._buffer=e.buffer,this._dataView=new DataView(this._buffer,this._byteOffset),this._byteLength=this._byteOffset+e.byteLength}bigEndian(){return this.endianness=DataStream.BIG_ENDIAN,this}_realloc(t){if(this._dynamicSize){var i=this._byteOffset+this.position+t;let e=this._buffer.byteLength;if(i<=e)i>this._byteLength&&(this._byteLength=i);else{for(e<1&&(e=1);i>e;)e*=2;var r=new ArrayBuffer(e),t=new Uint8Array(this._buffer);const s=new Uint8Array(r,0,t.length);s.set(t),this.buffer=r,this._byteLength=i}}}_trimAlloc(){if(this._byteLength!==this._buffer.byteLength){var e=new ArrayBuffer(this._byteLength);const i=new Uint8Array(e);var t=new Uint8Array(this._buffer,0,i.length);i.set(t),this.buffer=e}}seek(e){e=Math.max(0,Math.min(this.byteLength,e));this.position=isNaN(e)||!isFinite(e)?0:e}isEof(){return this.position>=this.byteLength}mapInt32Array(e,t){this._realloc(4*e);var i=new Int32Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}mapInt16Array(e,t){this._realloc(2*e);var i=new Int16Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=2*e,i}mapInt8Array(e){this._realloc(e);var t=new Int8Array(this._buffer,this.byteOffset+this.position,e);return this.position+=e,t}mapUint32Array(e,t){this._realloc(4*e);var i=new Uint32Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}mapUint16Array(e,t){this._realloc(2*e);var i=new Uint16Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=2*e,i}mapUint8Array(e){this._realloc(e);var t=new Uint8Array(this._buffer,this.byteOffset+this.position,e);return this.position+=e,t}mapFloat64Array(e,t){this._realloc(8*e);var i=new Float64Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=8*e,i}mapFloat32Array(e,t){this._realloc(4*e);var i=new Float32Array(this._buffer,this.byteOffset+this.position,e);return DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=4*e,i}readInt32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Int32Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readInt16Array(e,t){e=void 0===e?this.byteLength-this.position/2:e;var i=new Int16Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readInt8Array(e){e=void 0===e?this.byteLength-this.position:e;var t=new Int8Array(e);return DataStream.memcpy(t.buffer,0,this.buffer,this.byteOffset+this.position,e*t.BYTES_PER_ELEMENT),this.position+=t.byteLength,t}readUint32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Uint32Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readUint16Array(e,t){e=void 0===e?this.byteLength-this.position/2:e;var i=new Uint16Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readUint8Array(e){e=void 0===e?this.byteLength-this.position:e;var t=new Uint8Array(e);return DataStream.memcpy(t.buffer,0,this.buffer,this.byteOffset+this.position,e*t.BYTES_PER_ELEMENT),this.position+=t.byteLength,t}readFloat64Array(e,t){e=void 0===e?this.byteLength-this.position/8:e;var i=new Float64Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}readFloat32Array(e,t){e=void 0===e?this.byteLength-this.position/4:e;var i=new Float32Array(e);return DataStream.memcpy(i.buffer,0,this.buffer,this.byteOffset+this.position,e*i.BYTES_PER_ELEMENT),DataStream.arrayToNative(i,void 0===t?this.endianness:t),this.position+=i.byteLength,i}writeInt32Array(t,i){if(this._realloc(4*t.length),t instanceof Int32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeInt32(t[e],i);return this}writeInt16Array(t,i){if(this._realloc(2*t.length),t instanceof Int16Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt16Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeInt16(t[e],i);return this}writeInt8Array(t){if(this._realloc(t.length),t instanceof Int8Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapInt8Array(t.length);else for(let e=0;e<t.length;e++)this.writeInt8(t[e]);return this}writeUint32Array(t,i){if(this._realloc(4*t.length),t instanceof Uint32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeUint32(t[e],i);return this}writeUint16Array(t,i){if(this._realloc(2*t.length),t instanceof Uint16Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint16Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeUint16(t[e],i);return this}writeUint8Array(t){if(this._realloc(t.length),t instanceof Uint8Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapUint8Array(t.length);else for(let e=0;e<t.length;e++)this.writeUint8(t[e]);return this}writeFloat64Array(t,i){if(this._realloc(8*t.length),t instanceof Float64Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapFloat64Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeFloat64(t[e],i);return this}writeFloat32Array(t,i){if(this._realloc(4*t.length),t instanceof Float32Array&&(this.byteOffset+this.position)%t.BYTES_PER_ELEMENT==0)DataStream.memcpy(this._buffer,this.byteOffset+this.position,t.buffer,t.byteOffset,t.byteLength),this.mapFloat32Array(t.length,i);else for(let e=0;e<t.length;e++)this.writeFloat32(t[e],i);return this}readInt32(e){e=this._dataView.getInt32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readInt16(e){e=this._dataView.getInt16(this.position,void 0===e?this.endianness:e);return this.position+=2,e}readInt8(){var e=this._dataView.getInt8(this.position);return this.position+=1,e}readUint32(e){e=this._dataView.getUint32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readUint16(e){e=this._dataView.getUint16(this.position,void 0===e?this.endianness:e);return this.position+=2,e}readUint8(){var e=this._dataView.getUint8(this.position);return this.position+=1,e}readFloat32(e){e=this._dataView.getFloat32(this.position,void 0===e?this.endianness:e);return this.position+=4,e}readFloat64(e){e=this._dataView.getFloat64(this.position,void 0===e?this.endianness:e);return this.position+=8,e}writeInt32(e,t){return this._realloc(4),this._dataView.setInt32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeInt16(e,t){return this._realloc(2),this._dataView.setInt16(this.position,e,void 0===t?this.endianness:t),this.position+=2,this}writeInt8(e){return this._realloc(1),this._dataView.setInt8(this.position,e),this.position+=1,this}writeUint32(e,t){return this._realloc(4),this._dataView.setUint32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeUint16(e,t){return this._realloc(2),this._dataView.setUint16(this.position,e,void 0===t?this.endianness:t),this.position+=2,this}writeUint8(e){return this._realloc(1),this._dataView.setUint8(this.position,e),this.position+=1,this}writeFloat32(e,t){return this._realloc(4),this._dataView.setFloat32(this.position,e,void 0===t?this.endianness:t),this.position+=4,this}writeFloat64(e,t){return this._realloc(8),this._dataView.setFloat64(this.position,e,void 0===t?this.endianness:t),this.position+=8,this}static memcpy(e,t,i,r,s){const a=new Uint8Array(e,t,s);s=new Uint8Array(i,r,s);a.set(s)}static arrayToNative(e,t){return t===this.endianness?e:this.flipArrayEndianness(e)}static nativeToEndian(e,t){return this.endianness===t?e:this.flipArrayEndianness(e)}static flipArrayEndianness(r){const s=new Uint8Array(r.buffer,r.byteOffset,r.byteLength);for(let i=0;i<r.byteLength;i+=r.BYTES_PER_ELEMENT)for(let e=i+r.BYTES_PER_ELEMENT-1,t=i;e>t;e--,t++){var a=s[t];s[t]=s[e],s[e]=a}return r}static createStringFromArray(t){const i=[];for(let e=0;e<t.length;e+=32768)i.push(String.fromCharCode.apply(void 0,t.subarray(e,e+32768)));return i.join("")}readUCS2String(e,t){return DataStream.createStringFromArray(this.readUint16Array(e,t))}writeUCS2String(e,t,i){void 0===i&&(i=e.length);let r=0;for(;r<e.length&&r<i;r++)this.writeUint16(e.charCodeAt(r),t);for(;r<i;r++)this.writeUint16(0);return this}readString(e,t){return void 0===t||"ASCII"===t?DataStream.createStringFromArray(this.mapUint8Array(void 0===e?this.byteLength-this.position:e)):new TextDecoder(t).decode(this.mapUint8Array(e))}writeString(t,e,i){if(void 0===e||"ASCII"===e)if(void 0!==i){let e;var r=Math.min(t.length,i);for(e=0;e<r;e++)this.writeUint8(t.charCodeAt(e));for(;e<i;e++)this.writeUint8(0)}else for(let e=0;e<t.length;e++)this.writeUint8(t.charCodeAt(e));else this.writeUint8Array((new TextEncoder).encode(t.substring(0,i)));return this}writeUtf8WithLen(e){e=(new TextEncoder).encode(e);return this.writeUint16(e.length).writeUint8Array(e)}readUtf8WithLen(){var e=this.readUint16();return(new TextDecoder).decode(this.mapUint8Array(e))}readCString(e){var t=this.byteLength-this.position,i=new Uint8Array(this._buffer,this._byteOffset+this.position);let r=t;void 0!==e&&(r=Math.min(e,t));let s=0;for(;s<r&&0!==i[s];s++);var a=DataStream.createStringFromArray(this.mapUint8Array(s));return void 0!==e?this.position+=r-s:s!==t&&(this.position+=1),a}writeCString(t,i){if(void 0!==i){let e;var r=Math.min(t.length,i);for(e=0;e<r;e++)this.writeUint8(t.charCodeAt(e));for(;e<i;e++)this.writeUint8(0)}else{for(let e=0;e<t.length;e++)this.writeUint8(t.charCodeAt(e));this.writeUint8(0)}return this}toUint8Array(){return new Uint8Array(this.buffer,this.byteOffset,this.byteLength)}}DataStream.BIG_ENDIAN=!1,DataStream.LITTLE_ENDIAN=!0,DataStream.endianness=0<new Int8Array(new Int16Array([1]).buffer)[0];class IOError extends Error{constructor(){super(...arguments),this.name="IOError"}}class VirtualFile{static async fromRealFile(t){try{const e=new DataStream(await t.arrayBuffer());return e._trimAlloc=()=>{},new this(e,t.name)}catch(e){if(e instanceof DOMException)throw new IOError(`File "${t.name}" could not be read (${e.name})`,{cause:e});throw e}}static fromBytes(e,t){let i=new DataStream(e);return i._trimAlloc=()=>{},new this(i,t)}static factory(e,t,i=0,r=e.byteLength){r=new DataView(e.buffer,e.byteOffset+i,r);const s=new DataStream(r);return s._trimAlloc=()=>{},new this(s,t)}constructor(e,t){this.stream=e,this.filename=t}readAsString(e){return this.stream.seek(0),this.stream.readString(this.stream.byteLength,e)}getBytes(){return new Uint8Array(this.stream.buffer,this.stream.byteOffset,this.stream.byteLength)}getSize(){return this.stream.byteLength}asFile(e){return new File([this.getBytes()],this.filename,{type:e})}}class IniFile{constructor(e){this.sections=new Map,e instanceof VirtualFile?this.fromVirtualFile(e):"object"==typeof e?this.fromJson(e):"string"==typeof e&&this.fromString(e)}fromVirtualFile(e){return this.fromString(e.readAsString())}fromString(e){return this.fromJson((new IniParser).parse(e))}fromJson(e){for(var t in e){var i;e.hasOwnProperty(t)&&(i=new IniSection(t).fromJson(e[t]),this.sections.set(t,i))}return this}toString(){let e=[];for(var t of this.sections.values())e.push(t.toString());return e.join("\r\n")}clone(){let i=new IniFile;return this.sections.forEach((e,t)=>{i.sections.set(t,e.clone())}),i}getOrCreateSection(e){let t=this.sections.get(e);return t||(t=new IniSection(e),this.sections.set(e,t)),t}getSection(e){return this.sections.get(e)}getOrderedSections(){return[...this.sections.values()]}mergeWith(e){return e.sections.forEach((e,t)=>{let i=this.getOrCreateSection(t);i.mergeWith(e)}),this}}class Format3{static decode(r,s,t){let a=new Uint8Array(s*t),n=0,o=0;for(let e=0;e<t;e++){let t=(r[n+1]<<8|r[n])-2;n+=2;let i=0;for(;0<t--;){let e=r[n++];if(0!==e)i++,a[o++]=e;else for(t--,e=r[n++],i+e>s&&(e=s-i&255),i+=e;0!=e--;)a[o++]=0}}return a}}class ShpImage{constructor(e){this.height=1,this.width=1,this.x=0,this.y=0,this.imageData=e??new Uint8Array(0)}clip(i,e){let t=new ShpImage;t.width=Math.min(this.width,i),t.height=Math.min(this.height,e);let r=new Uint8Array(i*e),s=0;for(let t=0;t<this.height&&!(t>=e);t++)for(let e=0;e<this.width;e++)e>=i||(r[s++]=this.imageData[t*this.width+e]);return t.imageData=r,t.x=this.x,t.y=this.y,t}}class ShpFile{constructor(e){this.height=0,this.width=0,this.numImages=0,this.images=[],e instanceof VirtualFile&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let s=e.stream;if(0===s.readInt16()){this.width=s.readInt16(),this.height=s.readInt16(),this.numImages=s.readInt16();let r=[];for(let e=0;e<this.numImages;++e)r.push(this.readFrameHeader(s));this.images=[];for(let i=0;i<this.numImages;++i){var{compressionType:a,imageDataStartOffset:n,x:o,y:l,width:h,height:c}=r[i];let e=i<this.numImages-1?r[i+1].imageDataStartOffset:s.byteLength;e<n&&(e=s.byteLength);var u=e-n;s.seek(n);u=this.readImageData(s,h,c,a,u);let t=new ShpImage(u);t.x=o,t.y=l,t.width=h,t.height=c,this.images.push(t)}}}readFrameHeader(e){var t=e.readInt16(),i=e.readInt16(),r=e.readInt16(),s=e.readInt16(),a=e.readUint8();return e.readUint8(),e.readUint8(),e.readUint8(),e.readInt32(),e.readInt32(),{x:t,y:i,width:r,height:s,compressionType:a,imageDataStartOffset:e.readInt32()}}readImageData(r,e,s,t,i){var a=e*s;if(t<=1){var n=new Uint8Array(r.buffer,r.byteOffset+r.position,a);return r.position+=a,n}if(2===t){let t=0,i=new Uint8Array(a);for(let e=0;e<s;++e){var o=r.readUint16()-2;i.set(new Uint8Array(r.buffer,r.byteOffset+r.position,o),t),r.position+=o,t+=o}return i}if(3!==t)return new Uint8Array;t=new Uint8Array(r.buffer,r.byteOffset+r.position,i);return r.position+=i,Format3.decode(t,e,s)}getImage(e){if(e<0||this.images.length<=e)throw new RangeError(`Image index out of bounds (file=${this.filename}, index=${e}, length=${this.images.length})`);return this.images[e]}addImage(e){this.images.push(e),this.numImages++}clip(e,t){let i=new ShpFile;return i.filename=this.filename,i.width=Math.min(this.width,e),i.height=Math.min(this.height,t),i.images=this.images.map(e=>e.clip(i.width,i.height)),i.numImages=this.numImages,i}}var THREE=__webpack_require__(70),Vector3=THREE.Vector3;const normals1=[new Vector3(.54946297,-183e-6,-.835518),new Vector3(.00014400001,.54940403,-.83555698),new Vector3(-.54940403,-68000001e-12,-.83555698),new Vector3(106e-6,-.54946297,-.835518),new Vector3(.94900799,.00031599999,-.31525001),new Vector3(-186e-6,.94899702,-.31528401),new Vector3(-.94899702,.00031800001,-.31528401),new Vector3(-447e-6,-.94900799,-.31525001),new Vector3(.95084399,-279e-6,.30967101),new Vector3(202e-6,.95084798,.30965701),new Vector3(-.95084798,-70000002e-12,.30965701),new Vector3(147e-6,-.95084399,.30967101),new Vector3(.55237001,-11e-6,.83359897),new Vector3(19999999e-12,.55238003,.833592),new Vector3(-.55238003,57000001e-12,.83359301),new Vector3(-66000001e-12,-.55237001,.83359897)],normals2=[new Vector3(.67121398,.19849201,-.714194),new Vector3(.26964301,.58439398,-.76536),new Vector3(-.040546,.096988,-.99445897),new Vector3(-.57242799,-.091913998,-.81478697),new Vector3(-.17140099,-.57270998,-.80163902),new Vector3(.36255699,-.30299899,-.88133103),new Vector3(.81034702,-.34897199,-.470698),new Vector3(.103962,.93867201,-.328767),new Vector3(-.324047,.58766901,-.74137598),new Vector3(-.80086499,.34046099,-.49264699),new Vector3(-.66549802,-.59014702,-.45698899),new Vector3(.314767,-.803002,-.506073),new Vector3(.97262901,.151076,-.17655),new Vector3(.680291,.68423599,-.26272699),new Vector3(-.52007902,.82777703,-.210483),new Vector3(-.96164399,-.179001,-.207847),new Vector3(-.262714,-.937451,-.22840101),new Vector3(.219707,-.97130102,.091124997),new Vector3(.92380798,-.229975,.30608699),new Vector3(-.082488999,.97065997,.225866),new Vector3(-.59179801,.69678998,.40528899),new Vector3(-.92529601,.36660099,.097111002),new Vector3(-.705051,-.68777502,.172828),new Vector3(.7324,-.68036699,-.026304999),new Vector3(.85516202,.37458199,.358311),new Vector3(.47300601,.83648002,.276705),new Vector3(-.097617,.65411198,.750072),new Vector3(-.90412402,-.153725,.39865801),new Vector3(-.211916,-.85808998,.46773201),new Vector3(.50022697,-.67440802,.543091),new Vector3(.584539,-.110249,.80384099),new Vector3(.43737301,.45464399,.77588898),new Vector3(-.042440999,.083318003,.995619),new Vector3(-.59625101,.22013199,.77202803),new Vector3(-.506455,-.39697701,.76544899),new Vector3(.070569001,-.47847399,.87526202)],normals3=[new Vector3(.45651099,-.073968001,-.88663799),new Vector3(.50769401,.38511699,-.77067),new Vector3(.095431998,.22666401,-.96928602),new Vector3(-.35876599,.54318798,-.75910097),new Vector3(-.361276,.13299499,-.92292601),new Vector3(-.48311701,-.32406601,-.813375),new Vector3(-.018073,-.197559,-.980124),new Vector3(.3211,-.501477,-.80337799),new Vector3(.79949099,.069615997,-.59662998),new Vector3(.390971,.77130598,-.50222403),new Vector3(.080782004,.61448997,-.784778),new Vector3(-.73275,.41143101,-.54203498),new Vector3(-.73525399,.0091019999,-.67773098),new Vector3(-.80249399,-.39490801,-.44727099),new Vector3(-.13413,-.58915502,-.79680902),new Vector3(.71955299,-.37622699,-.58369303),new Vector3(.96687502,.173593,-.187132),new Vector3(.760831,.51910597,-.38944301),new Vector3(-.114642,.87551898,-.46938601),new Vector3(-.53236699,.76885903,-.354177),new Vector3(-.96226698,.024977,-.27095801),new Vector3(-.46738699,-.721986,-.51018202),new Vector3(.058449998,-.85235399,-.51968902),new Vector3(.49823299,-.74374002,-.44566301),new Vector3(.93915099,-.27024499,-.212044),new Vector3(.58393198,.80944198,-.061857),new Vector3(.183797,.97322798,-.138007),new Vector3(-.88435501,.45221901,-.115822),new Vector3(-.943178,-.33206701,.012138),new Vector3(-.69844002,-.70656699,-.113772),new Vector3(-.228411,-.95470601,-.190694),new Vector3(.73156399,-.675861,-.089588001),new Vector3(.96925098,.046804,.24158201),new Vector3(.85564703,.50347698,.119916),new Vector3(-.25115299,.96794701,-80999998e-12),new Vector3(-.64779502,.75674897,.087711997),new Vector3(-.96916401,.14519399,.1991),new Vector3(-.41479301,-.88896698,.194126),new Vector3(.25077501,-.961178,-.115109),new Vector3(.47862899,-.84259301,.246883),new Vector3(.89004397,-.39614201,.225595),new Vector3(.52405101,.76235998,.37970701),new Vector3(.11962,.94548202,.30291),new Vector3(-.76085001,.49007499,.42536199),new Vector3(-.86978501,-.20215,.450122),new Vector3(-.70946699,-.60242403,.36570701),new Vector3(.019308999,-.95887101,.28318599),new Vector3(.626113,-.564677,.53770101),new Vector3(.769943,-.126663,.62541503),new Vector3(.76419097,.35070199,.54131401),new Vector3(-.001878,.74136698,.67109799),new Vector3(-.37088001,.81836802,.43900099),new Vector3(-.71390897,.12865201,.68831801),new Vector3(-.295165,-.73866397,.60601401),new Vector3(.186195,-.73836899,.648184),new Vector3(.387523,-.35878301,.84917599),new Vector3(.481022,.124846,.86777401),new Vector3(.391808,.54505599,.741216),new Vector3(-.0035359999,.36559799,.93076599),new Vector3(-.42049801,.484961,.76680797),new Vector3(-.35490301,.019470001,.93470001),new Vector3(-.54783702,-.35920799,.75554299),new Vector3(-.106662,-.445115,.88909799),new Vector3(.086796001,-.059307002,.99445897)],normals4=[new Vector3(.52657801,-.35962099,-.77031702),new Vector3(.150482,.43598399,.88728398),new Vector3(.414195,.73825502,-.53237402),new Vector3(.075152002,.91624898,-.393498),new Vector3(-.316149,.93073601,-.18379299),new Vector3(-.77381903,.62333399,-.11251),new Vector3(-.90084201,.42853701,-.069568001),new Vector3(-.99894202,-.010971,.044665001),new Vector3(-.979761,-.15767001,-.123324),new Vector3(-.91127402,-.362371,-.19562),new Vector3(-.62406898,-.72094101,-.301301),new Vector3(-.310173,-.80934501,-.498752),new Vector3(.146613,-.81581903,-.55941403),new Vector3(-.71651602,-.69435602,-.066887997),new Vector3(.50397199,-.114202,-.85613698),new Vector3(.45549101,.87262702,-.176211),new Vector3(-.00501,-.114373,-.99342501),new Vector3(-.104675,-.327701,-.93896502),new Vector3(.56041199,.75258899,-.34575599),new Vector3(-.060575999,.82162797,-.566796),new Vector3(-.30234101,.79700702,-.522847),new Vector3(-.671543,.67074001,-.314863),new Vector3(-.77840102,-.12835699,.61450499),new Vector3(-.92404997,.278382,-.261985),new Vector3(-.69977301,-.55049098,-.45527801),new Vector3(-.56824797,-.51718903,-.64000797),new Vector3(.054097999,-.93286401,-.356143),new Vector3(.75838202,.57289302,-.31088799),new Vector3(.0036200001,.30502599,-.95233703),new Vector3(-.060849998,-.98688602,-.14951099),new Vector3(.63523,.045478001,-.77098298),new Vector3(.52170497,.241309,-.81828701),new Vector3(.26940399,.63542497,-.72364098),new Vector3(.045676,.67275399,-.738455),new Vector3(-.180511,.67465699,-.71571898),new Vector3(-.397131,.63664001,-.66104198),new Vector3(-.55200398,.47251499,-.687038),new Vector3(-.77217001,.08309,-.62996),new Vector3(-.669819,-.119533,-.73284),new Vector3(-.54045498,-.31844401,-.77878201),new Vector3(-.38613501,-.522789,-.75999397),new Vector3(-.261466,-.68856698,-.676395),new Vector3(-.019412,-.69610298,-.71767998),new Vector3(.30356899,-.48184401,-.82199299),new Vector3(.68193901,-.19512901,-.70490003),new Vector3(-.24488901,-.116562,-.96251899),new Vector3(.80075902,-.022979001,-.59854603),new Vector3(-.37027499,.095583998,-.92399102),new Vector3(-.33067101,-.32657799,-.88543999),new Vector3(-.16322,-.52757901,-.83367902),new Vector3(.12639,-.313146,-.941257),new Vector3(.34954801,-.27222601,-.89649802),new Vector3(.23991799,-.085825004,-.96699202),new Vector3(.390845,.081537001,-.91683799),new Vector3(.25526699,.26869699,-.92878503),new Vector3(.146245,.48043799,-.86474901),new Vector3(-.32601601,.47845599,-.81534898),new Vector3(-.46968201,-.112519,-.87563598),new Vector3(.81844002,-.25852001,-.51315099),new Vector3(-.474318,.292238,-.83043301),new Vector3(.778943,.39584199,-.48637101),new Vector3(.62409401,.39377299,-.67487001),new Vector3(.74088597,.203834,-.63995302),new Vector3(.48021701,.565768,-.67029703),new Vector3(.38093001,.42453501,-.82137799),new Vector3(-.093422003,.50112402,-.86031801),new Vector3(-.236485,.29619801,-.92538702),new Vector3(-.131531,.093959004,-.98684901),new Vector3(-.82356203,.29577699,-.48400599),new Vector3(.61106598,-.624304,-.486664),new Vector3(.069495998,-.52033001,-.85113299),new Vector3(.226522,-.66487902,-.711775),new Vector3(.47130799,-.56890398,-.67395699),new Vector3(.38842499,-.74262398,-.54556),new Vector3(.78367501,-.48072901,-.39338499),new Vector3(.962394,.135676,-.235349),new Vector3(.876607,.172034,-.449406),new Vector3(.63340503,.58979303,-.50094098),new Vector3(.182276,.80065799,-.57072097),new Vector3(.177003,.76413399,.62029701),new Vector3(-.544016,.675515,-.49772099),new Vector3(-.67929697,.28646699,-.67564201),new Vector3(-.59039098,.091369003,-.801929),new Vector3(-.82436001,-.13312399,-.55018902),new Vector3(-.71579403,-.33454201,-.61296099),new Vector3(.17428599,-.89248401,.416049),new Vector3(-.082528003,-.83712298,-.54075301),new Vector3(.28333101,-.88087398,-.37918901),new Vector3(.675134,-.42662701,-.60181701),new Vector3(.84372002,-.512335,-.160156),new Vector3(.97730398,-.098555997,-.18752),new Vector3(.846295,.522672,-.102947),new Vector3(.67714101,.72132498,-.145501),new Vector3(.32096499,.87089199,-.37219399),new Vector3(-.178978,.911533,-.37023601),new Vector3(-.44716901,.82670099,-.341474),new Vector3(-.70320302,.496328,-.50908101),new Vector3(-.97718102,.063562997,-.202674),new Vector3(-.87817001,-.412938,.241455),new Vector3(-.83583099,-.35855001,-.415728),new Vector3(-.499174,-.69343299,-.51959199),new Vector3(-.188789,-.92375302,-.33322501),new Vector3(.19225401,-.96936101,-.152896),new Vector3(.51594001,-.783907,-.34539199),new Vector3(.90592498,-.30095199,-.29787099),new Vector3(.99111199,-.127746,.037106998),new Vector3(.99513501,.098424003,-.0043830001),new Vector3(.76012301,.64627701,.067367002),new Vector3(.205221,.95958,-.192591),new Vector3(-.042750001,.97951299,-.19679099),new Vector3(-.43801701,.89892697,.0084920004),new Vector3(-.82199401,.48078501,-.30523899),new Vector3(-.89991701,.081710003,-.42833701),new Vector3(-.92661202,-.144618,-.347096),new Vector3(-.79365999,-.55779201,-.24283899),new Vector3(-.43134999,-.84777898,-.30855799),new Vector3(-.0054919999,-.96499997,.26219299),new Vector3(.58790499,-.80402601,-.088940002),new Vector3(.69949299,-.66768599,-.254765),new Vector3(.88930303,.359795,-.282291),new Vector3(.780972,.197037,.59267199),new Vector3(.52012098,.50669599,.68755698),new Vector3(.40389499,.69396102,.59605998),new Vector3(-.154983,.89923602,.40909001),new Vector3(-.65733802,.53716803,.528543),new Vector3(-.74619502,.33409101,.575827),new Vector3(-.62495202,-.049144,.77911502),new Vector3(.31814101,-.254715,.913185),new Vector3(-.555897,.405294,.725752),new Vector3(-.79443401,.099405997,.59916002),new Vector3(-.64036101,-.68946302,.33849499),new Vector3(-.12671299,-.73409498,.66711998),new Vector3(.105457,-.78081697,.61579502),new Vector3(.40799299,-.48091599,.77605498),new Vector3(.69513601,-.54512,.468647),new Vector3(.97319102,-.0064889998,.229908),new Vector3(.94689399,.317509,-.050799001),new Vector3(.56358302,.82561201,.027183),new Vector3(.325773,.94542301,.0069490001),new Vector3(-.171821,.98509699,-.0078149997),new Vector3(-.67044097,.73993897,.054768998),new Vector3(-.822981,.55496198,.121322),new Vector3(-.96619302,.117857,.229307),new Vector3(-.95376903,-.29470399,.058945),new Vector3(-.86438698,-.50272799,-.010015),new Vector3(-.53060901,-.84200603,-.097365998),new Vector3(-.162618,-.98407501,.071772002),new Vector3(.081446998,-.99601102,.036439002),new Vector3(.74598402,-.66596299,.00076199998),new Vector3(.94205701,-.32926899,-.064106002),new Vector3(.93970197,-.28108999,.194803),new Vector3(.77121401,.55067003,.319363),new Vector3(.641348,.73069,.23402099),new Vector3(.080682002,.99669099,.0098789996),new Vector3(-.046725001,.97664303,.20972501),new Vector3(-.53107601,.82100099,.209562),new Vector3(-.69581503,.65599,.29243499),new Vector3(-.97612202,.216709,-.014913),new Vector3(-.96166098,-.14412899,.23331399),new Vector3(-.772084,-.61364698,.165299),new Vector3(-.44960001,-.83605999,.314426),new Vector3(-.39269999,-.91461599,.096247002),new Vector3(.390589,-.91947001,.044890001),new Vector3(.58252901,-.79919797,.148127),new Vector3(.866431,-.48981199,.096864),new Vector3(.90458697,.111498,.41145),new Vector3(.95353699,.23232999,.191806),new Vector3(.497311,.77080297,.398177),new Vector3(.194066,.95631999,.218611),new Vector3(.422876,.882276,.206797),new Vector3(-.373797,.84956598,.37217399),new Vector3(-.53449702,.71402299,.4522),new Vector3(-.881827,.23716,.40759799),new Vector3(-.904948,-.014069,.42528901),new Vector3(-.751827,-.51281703,.41445801),new Vector3(-.50101501,-.69791698,.51175803),new Vector3(-.23519,-.92592299,.295555),new Vector3(.228983,-.95393997,.193819),new Vector3(.734025,-.63489801,.241062),new Vector3(.91375297,-.063253,-.40131599),new Vector3(.90573502,-.161487,.391875),new Vector3(.85892999,.342446,.38074899),new Vector3(.62448603,.60758102,.49077699),new Vector3(.28926399,.85747898,.42550799),new Vector3(.069968,.90216899,.42567101),new Vector3(-.28617999,.94069999,.182165),new Vector3(-.57401299,.80511898,-.14930899),new Vector3(.111258,.099717997,-.98877603),new Vector3(-.30539301,-.94422799,-.12316),new Vector3(-.60116601,-.78957599,.123163),new Vector3(-.290645,-.81213999,.50591898),new Vector3(-.064920001,-.87716299,.47578499),new Vector3(.408301,-.862216,.29978901),new Vector3(.56609702,-.72556603,.39126399),new Vector3(.83936399,-.427387,.33586901),new Vector3(.81889999,-.041305002,.57244802),new Vector3(.71978402,.41499701,.55649698),new Vector3(.88174403,.45027,.140659),new Vector3(.40182301,-.89822,-.17815199),new Vector3(-.054019999,.79134399,.60898),new Vector3(-.29377401,.76399398,.57446498),new Vector3(-.450798,.61034697,.65135098),new Vector3(-.63822103,.186694,.74687302),new Vector3(-.87287003,-.25712699,.41470799),new Vector3(-.58725703,-.52170998,.618828),new Vector3(-.35365799,-.64197397,.680291),new Vector3(.041648999,-.61127299,.79032302),new Vector3(.348342,-.77918297,.52108699),new Vector3(.499167,-.62244099,.602826),new Vector3(.79001898,-.30383101,.53250003),new Vector3(.66011798,.060733002,.74870199),new Vector3(.60492098,.29416099,.73996001),new Vector3(.38569701,.37934601,.84103203),new Vector3(.239693,.207876,.94833201),new Vector3(.012623,.25853199,.96591997),new Vector3(-.100557,.457147,.88368797),new Vector3(.046967,.62858802,.77631903),new Vector3(-.43039101,-.44540501,.785097),new Vector3(-.43429101,-.196228,.87913901),new Vector3(-.25663701,-.336867,.90590203),new Vector3(-.131372,-.15891001,.97851402),new Vector3(.102379,-.208767,.972592),new Vector3(.195687,-.450129,.87125802),new Vector3(.62731898,-.42314801,.65377098),new Vector3(.68743902,-.171583,.70568198),new Vector3(.27592,-.021255,.96094602),new Vector3(.45936701,.15746599,.87417799),new Vector3(.285395,.583184,.76055598),new Vector3(-.81217402,.46030301,.35846099),new Vector3(-.189068,.64122301,.743698),new Vector3(-.338875,.47648001,.811252),new Vector3(-.92099398,.347186,.176727),new Vector3(.040638998,.024465,.99887401),new Vector3(-.73913199,-.35374701,.57318997),new Vector3(-.60351199,-.28661501,.74405998),new Vector3(-.188676,-.547059,.81555402),new Vector3(-.026045,-.39782,.91709399),new Vector3(.26789701,-.649041,.71202302),new Vector3(.518246,-.28489101,.80638599),new Vector3(.493451,-.066532999,.86722499),new Vector3(-.328188,.140251,.93414301),new Vector3(.328188,.140251,.93414301),new Vector3(-.328188,.140251,.93414301),new Vector3(-.328188,.140251,.93414301),new Vector3(-.328188,.140251,.93414301)];class VoxelField{constructor(e,t,i){this.sizeX=e,this.sizeY=t,this.sizeZ=i,this.arr=new Array(e*t*i)}add(e){this.arr[e.x+e.y*this.sizeX+e.z*this.sizeX*this.sizeY]=e}get(e,t,i){if(!(e>=this.sizeX||t>=this.sizeY||i>=this.sizeZ))return this.arr[e+t*this.sizeX+i*this.sizeX*this.sizeY]}}var Section_THREE=__webpack_require__(70);class Section{get spanX(){return this.maxBounds.x-this.minBounds.x}get spanY(){return this.maxBounds.y-this.minBounds.y}get spanZ(){return this.maxBounds.z-this.minBounds.z}get scaleX(){return this.spanX/this.sizeX}get scaleY(){return this.spanY/this.sizeY}get scaleZ(){return this.spanZ/this.sizeZ}get scale(){return new Section_THREE.Vector3(this.scaleX,this.scaleY,this.scaleZ)}getAllVoxels(){let i=[],r=new VoxelField(this.sizeX+1,this.sizeY+1,this.sizeZ+1);for(let e=0,t=this.spans.length;e<t;e++){var s=this.spans[e].voxels;for(let e=0,t=s.length;e<t;e++){var a=s[e];i.push(a),r.add(a)}}return{voxels:i,voxelField:r}}getNormals(){switch(this.normalsMode){case 1:return normals1;case 2:return normals2;case 3:return normals3;case 4:return normals4;default:throw new Error("Invalid normalsmode "+this.normalsMode)}}scaleHvaMatrix(e){return(e=e.clone()).elements[12]*=this.hvaMultiplier,e.elements[13]*=this.hvaMultiplier,e.elements[14]*=this.hvaMultiplier,e}toPlain(){return{name:this.name,normalsMode:this.normalsMode,minBounds:this.minBounds.toArray(),maxBounds:this.maxBounds.toArray(),sizeX:this.sizeX,sizeY:this.sizeY,sizeZ:this.sizeZ,hvaMultiplier:this.hvaMultiplier,transfMatrix:this.transfMatrix.toArray(),spans:this.spans}}fromPlain(e){return this.name=e.name,this.normalsMode=e.normalsMode,this.minBounds=(new Section_THREE.Vector3).fromArray(e.minBounds),this.maxBounds=(new Section_THREE.Vector3).fromArray(e.maxBounds),this.sizeX=e.sizeX,this.sizeY=e.sizeY,this.sizeZ=e.sizeZ,this.hvaMultiplier=e.hvaMultiplier,this.transfMatrix=(new Section_THREE.Matrix4).fromArray(e.transfMatrix),this.spans=e.spans,this}}class VxlHeader{read(e){this.fileName=e.readCString(16),this.paletteCount=e.readUint32(),this.headerCount=e.readUint32(),this.tailerCount=e.readUint32(),this.bodySize=e.readUint32(),this.paletteRemapStart=e.readUint8(),this.paletteRemapEnd=e.readUint8(),e.seek(e.position+768)}}VxlHeader.size=32;var VxlFile_THREE=__webpack_require__(70);class VxlFile{constructor(e){this.voxelCount=0,e instanceof VirtualFile&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let s=e.stream;if(this.sections=[],!(s.byteLength<VxlHeader.size)){let r=new VxlHeader;if(r.read(s),r.headerCount&&r.tailerCount&&r.tailerCount===r.headerCount){for(let e=0;e<r.headerCount;++e){const n=new Section;this.readSectionHeader(n,s),this.sections.find(e=>e.name===n.name)&&console.warn(`Duplicate section name "${n.name}" found in VXL "${this.filename}".`),this.sections.push(n)}var a=s.position;s.seek(s.position+r.bodySize);let t=[];for(let e=0;e<r.tailerCount;++e)t[e]=this.readSectionTailer(this.sections[e],s);let i=0;for(let e=0;e<r.headerCount;++e)s.seek(a),i+=this.readSectionBodySpans(this.sections[e],t[e],s);this.voxelCount=i}}}readSectionHeader(e,t){e.name=t.readCString(16),t.readUint32(),t.readUint32(),t.readUint32()}readSectionTailer(e,t){var i=t.readUint32(),r=t.readUint32(),s=t.readUint32();return e.hvaMultiplier=t.readFloat32(),e.transfMatrix=this.readTransfMatrix(t),e.minBounds=new VxlFile_THREE.Vector3(t.readFloat32(),t.readFloat32(),t.readFloat32()),e.maxBounds=new VxlFile_THREE.Vector3(t.readFloat32(),t.readFloat32(),t.readFloat32()),e.sizeX=t.readUint8(),e.sizeY=t.readUint8(),e.sizeZ=t.readUint8(),e.normalsMode=t.readUint8(),{startingSpanOffset:i,endingSpanOffset:r,dataSpanOffset:s}}readTransfMatrix(t){let i=[];for(let e=0;e<3;++e)i.push(t.readFloat32(),t.readFloat32(),t.readFloat32(),t.readFloat32());return i.push(0,0,0,1),(new VxlFile_THREE.Matrix4).fromArray(i).transpose()}readSectionBodySpans(e,t,i){i.seek(i.position+t.startingSpanOffset);var{sizeX:r,sizeY:s,sizeZ:a}=e;let n=new Array(s);for(let t=0;t<s;++t){n[t]=new Array(r);for(let e=0;e<r;++e)n[t][e]=i.readInt32()}let o=new Array(s);for(let t=0;t<s;++t){o[t]=new Array(r);for(let e=0;e<r;++e)o[t][e]=i.readInt32()}let l=e.spans=[],h=0;for(let t=0;t<s;++t)for(let e=0;e<r;++e){var c={x:e,y:t,voxels:this.readSpanVoxels(n[t][e],o[t][e],e,t,a,i)};l.push(c),h+=c.voxels.length}return h}readSpanVoxels(e,t,i,r,s,a){if(-1===e||-1===t)return[];let n=[];for(let t=0;t<s;){t+=a.readUint8();var o=a.readUint8();for(let e=0;e<o;++e){var l={x:i,y:r,z:t++,colorIndex:a.readUint8(),normalIndex:a.readUint8()};n.push(l)}a.readUint8()}return n}fromPlain(e){return this.sections=e.sections.map(e=>(new Section).fromPlain(e)),this.voxelCount=e.voxelCount,this}toPlain(){return{sections:this.sections.map(e=>e.toPlain()),voxelCount:this.voxelCount}}getSection(e){return this.sections[e]}}var DataPrecencyFlags,HighBridgeHeadType,PaletteType,TheaterType,MixFileFlags,GameResSource,GameModeType,TmpImage_THREE=__webpack_require__(70);!function(e){e[e.ExtraData=1]="ExtraData",e[e.ZData=2]="ZData",e[e.DamagedData=4]="DamagedData"}(DataPrecencyFlags=DataPrecencyFlags||{});const unsignInt8=e=>e<0?e+256:e;class TmpImage{constructor(e,t,i){this.fromStream(e,t,i)}fromStream(e,t,i){this.x=e.readInt32(),this.y=e.readInt32(),e.readInt32(),e.readInt32();var r=e.readInt32();this.extraX=e.readInt32(),this.extraY=e.readInt32(),this.extraWidth=e.readInt32(),this.extraHeight=e.readInt32();var s=e.readUint32();this.height=e.readUint8(),this.terrainType=e.readUint8(),this.rampType=e.readUint8(),this.radarLeft=this.readRadarRgb(e.readInt8(),e.readInt8(),e.readInt8()),this.radarRight=this.readRadarRgb(e.readInt8(),e.readInt8(),e.readInt8()),e.seek(e.position+3),this.tileData=new Uint8Array(e.buffer,e.byteOffset+e.position,t*i/2),e.position+=t*i/2,this.hasZData=(s&DataPrecencyFlags.ZData)===DataPrecencyFlags.ZData,this.hasZData&&(e.position+=t*i/2),this.hasExtraData=(s&DataPrecencyFlags.ExtraData)===DataPrecencyFlags.ExtraData,this.hasExtraData&&(s=Math.abs(this.extraWidth*this.extraHeight),this.extraData=new Uint8Array(e.buffer,e.byteOffset+e.position,s),e.position+=s),this.hasZData&&this.hasExtraData&&0<r&&r<e.byteLength&&(e.position+=Math.abs(this.extraWidth*this.extraHeight))}readRadarRgb(e,t,i){return new TmpImage_THREE.Color(unsignInt8(e)/255,unsignInt8(t)/255,unsignInt8(i)/255)}}class TmpFile{constructor(e){this.images=[],e instanceof VirtualFile&&this.fromVirtualFile(e)}fromVirtualFile(e){let t=e.stream;this.width=t.readInt32(),this.height=t.readInt32(),this.blockWidth=t.readInt32(),this.blockHeight=t.readInt32();var i=this.width*this.height,r=new Uint8Array(t.buffer,t.byteOffset+t.position,4*i);this.images=[];for(let e=0;e<i;e++){var s=r[4*e+3]<<24|r[4*e+2]<<16|r[4*e+1]<<8|r[4*e];t.seek(s);s=new TmpImage(t,this.blockWidth,this.blockHeight);this.images.push(s)}}}class Base64{static encode(e){return void 0!==globalThis.btoa?globalThis.btoa(e):Buffer.from(e,"binary").toString("base64")}static decode(e){return void 0!==globalThis.atob?globalThis.atob(e):Buffer.from(e,"base64").toString("binary")}static isBase64(e){return!!e.match(/^([A-Za-z0-9+/]{4})*([A-Za-z0-9+/]{3}=|[A-Za-z0-9+/]{2}==)?$/)}}function pad(e,t="0000"){e=""+e;return t.substring(0,t.length-e.length)+e}function equalsIgnoreCase(e,t){return e.toLowerCase()===t.toLowerCase()}function binaryStringToUint8Array(t){var i=t.length;let r=new Uint8Array(i);for(let e=0;e<i;e++)r[e]=t.charCodeAt(e);return r}function base64StringToUint8Array(e){return binaryStringToUint8Array(Base64.decode(e))}function uint8ArrayToBase64String(e){return Base64.encode(uint8ArrayToBinaryString(e))}function uint8ArrayToBinaryString(e){return e.reduce((e,t)=>e+String.fromCharCode(t),"")}function utf16ToBinaryString(t){var i=t.length;let r="";for(let e=0;e<i;e++){var s=t.charCodeAt(e);r+=String.fromCharCode(s>>8),r+=String.fromCharCode(255&s)}return r}function binaryStringToUtf16(t){var i=t.length;let r="";for(let e=0;e<i;e+=2){var s=(t.charCodeAt(e)<<8)+t.charCodeAt(e+1);r+=String.fromCharCode(s)}return r}function bufferToHexString(e){const t=[],i=new DataView(e);for(let e=0;e<i.byteLength;e+=4){const s=i.getUint32(e);var r="00000000",r=(r+s.toString(16)).slice(-r.length);t.push(r)}return t.join("")}class Color{static fromRgb(e,t,i){return new Color(e,t,i)}static fromHsv(e,t,i){let r=0,s=0,a=0;if(e=e/255*360%360,i/=255,0===(t/=255))r=i,s=i,a=i;else{var n=e/60,e=Math.floor(n),n=n-e,o=i*(1-t),l=i*(1-t*n),h=i*(1-t*(1-n));switch(e){case 0:r=i,s=h,a=o;break;case 1:r=l,s=i,a=o;break;case 2:r=o,s=i,a=h;break;case 3:r=o,s=l,a=i;break;case 4:r=h,s=o,a=i;break;case 5:r=i,s=o,a=l}}return Color.fromRgb(Math.floor(255*r),Math.floor(255*s),Math.floor(255*a))}constructor(e,t,i){this.r=e,this.g=t,this.b=i}asHex(){return(this.r<<16)+(this.g<<8)+this.b}asHexString(){return"#"+pad(this.asHex().toString(16),"000000")}clone(){return new Color(this.r,this.g,this.b)}}function getRandomInt(e,t){return Math.floor(Math.random()*(t+1-e))+e}function clamp(e,t,i){return Math.min(i,Math.max(e,t))}function isBetween(e,t,i){return t<=e&&e<=i}function lerp(e,t,i){return(1-i)*e+i*t}function truncToDecimals(e,t){if(!e)return e;t=10**t;return 0<=e?Math.floor(e*t)/t:Math.ceil(e*t)/t}function roundToDecimals(e,t){if(!e)return e;t=10**t;return Math.round(e*t)/t}function floorTo(e,t){return Math.floor(e/t)*t}function fnv32a(i){let r=2166136261;for(let e=0,t=i.length;e<t;++e)r^=i[e],r+=(r<<1)+(r<<4)+(r<<7)+(r<<8)+(r<<24);return r>>>0}class Palette{constructor(e){e instanceof VirtualFile?this.fromVirtualFile(e):"object"==typeof e&&this.fromJson(e)}fromVirtualFile(e){e=e.stream.readUint8Array(768);this.fromJson(e)}fromJson(t){this.colors=[];for(let e=0;e<t.length/3;++e)this.colors.push(Color.fromRgb(4*t[3*e],4*t[3*e+1],4*t[3*e+2]));this._hash=this.computeHash(this.colors)}getColor(e){return this.colors[e]}getColorAsHex(e){return this.getColor(e).asHex()}setColors(e){this.colors=e,this._hash=this.computeHash(this.colors)}get size(){return this.colors.length}get hash(){return this._hash}computeHash(e){let t=new Uint8Array(3*this.size),i=0;for(var r of e)t[i]=r.r,t[i+1]=r.g,t[i+2]=r.b,i+=3;return fnv32a(t)}clone(){let e=new Palette;return e.colors=this.colors.map(e=>e.clone()),e._hash=this._hash,e}remap(t){var i=[63,59,55,52,48,44,41,37,33,30,26,22,19,15,11,8];for(let e=Palette.REMAP_START_IDX;e<Palette.REMAP_START_IDX+i.length;e++)this.colors[e].r=Math.floor(t.r/255*i[e-Palette.REMAP_START_IDX]*4),this.colors[e].g=Math.floor(t.g/255*i[e-Palette.REMAP_START_IDX]*4),this.colors[e].b=Math.floor(t.b/255*i[e-Palette.REMAP_START_IDX]*4);return this._hash=this.computeHash(this.colors),this}}Palette.REMAP_START_IDX=16;class TileSetEntry{constructor(e,t){this.owner=e,this.index=t,this.files=[]}addFile(e){this.files.push(e)}setAnimation(e){this.animation=e}getAnimation(){return this.animation}getTmpFile(e,t,i=!1){if(this.files.length){t=this.files[t(0,this.files.length-1)];return t.images[Math.min(e,t.images.length-1)].hasDamagedData?this.files[Math.min(i?1:0,this.files.length-1)]:t}}}class TileSet{constructor(e,t,i){this.fileName=e,this.setName=t,this.tilesInSet=i,this.entries=[]}}class TileSetAnim{constructor(e,t,i,r){this.name=e,this.subTile=t,this.offsetX=i,this.offsetY=r}}!function(e){e[e.TopLeft=0]="TopLeft",e[e.BottomRight=1]="BottomRight",e[e.TopRight=2]="TopRight",e[e.BottomLeft=3]="BottomLeft",e[e.MiddleTlBr=4]="MiddleTlBr",e[e.MiddleTrBl=5]="MiddleTrBl"}(HighBridgeHeadType=HighBridgeHeadType||{});const highBridgeHeadNames=new Map([[HighBridgeHeadType.TopLeft,["BridgeTopLeft1","BridgeTopLeft2"]],[HighBridgeHeadType.BottomRight,["BridgeBottomRight1","BridgeBottomRight2"]],[HighBridgeHeadType.TopRight,["BridgeTopRight1","BridgeTopRight2"]],[HighBridgeHeadType.BottomLeft,["BridgeBottomLeft1","BridgeBottomLeft2"]],[HighBridgeHeadType.MiddleTlBr,["BridgeMiddle1"]],[HighBridgeHeadType.MiddleTrBl,["BridgeMiddle2"]]]);class TileSets{constructor(e){this.theaterIni=e,this.tileSets=[],this.orderedEntries=[],this.highBridgeSetNums=[this.getGeneralValue("BridgeSet"),this.getGeneralValue("WoodBridgeSet")],this.cliffSetNums=[this.getGeneralValue("CliffSet"),this.getGeneralValue("WaterCliffs"),this.getGeneralValue("DestroyableCliffs")]}getTile(e){return this.orderedEntries[e]}getTileImage(e,t,i){let r=this.getTile(e);if(!r)throw new Error(`TileNum ${e} not found`);i=r.getTmpFile(t,i);if(!i||t>=i.images.length)throw new Error(`SubTile ${t} not found`);return i.images[t]}getSetNum(e){var t=this.orderedEntries[e];if(!t)throw new Error("Invalid tileNum "+e);return this.tileSets.indexOf(t.owner)}getTileNumFromSet(i,r=0){let s=0;return this.tileSets.some((e,t)=>t===i?(s+=r,!0):(s+=e.entries.length,!1)),s}getGeneralValue(e){let t=this.theaterIni.getSection("General");if(!t)throw new Error("Missing [General] section in theather ini");return t.getNumber(e)}loadTileData(e,t){this.tileSets.length=0,this.orderedEntries.length=0,this.initTileSets(e,t),this.initAnimations()}readMaxTileNum(){let t=0,i=0;for(;;){var r="TileSet"+pad(t,"0000");let e=this.theaterIni.getSection(r);if(!e)break;t++,i+=e.getNumber("TilesInSet")}return i}initTileSets(a,n){let e=0,t;for(var i;;){if(i="TileSet"+pad(e,"0000"),t=this.theaterIni.getSection(i),!t)break;e++;let s=new TileSet(t.getString("FileName"),t.getString("SetName"),t.getNumber("TilesInSet"));this.tileSets.push(s);for(let r=1;r<=s.tilesInSet;r++){let i=new TileSetEntry(s,r-1);var o="a".charCodeAt(0);for(let t=o-1;t<="z".charCodeAt(0);t++)if(!(t>=o&&"Bridges"===s.setName)){let e=s.fileName+pad(r,"00");t>=o&&(e+=String.fromCharCode(t)),e+=n;var l=a.get(e);if(!l)break;i.addFile(l)}s.entries.push(i),this.orderedEntries.push(i)}}}initAnimations(){var r=this.theaterIni.getOrderedSections();for(let e=this.tileSets.length;e<r.length;++e){let t=r[e],i=this.tileSets.find(e=>e.setName===t.name);if(i)for(let e=1;e<=i.tilesInSet;++e){var s="Tile"+pad(e,"00"),a=s+"Anim",n=t.getString(a);n?(s=new TileSetAnim(n,t.getNumber(s+"AttachesTo"),t.getNumber(s+"XOffset"),t.getNumber(s+"YOffset")),i.entries[e-1].setAnimation(s)):console.warn(`Missing anim "${a}" for tileset `+i.setName)}}}isLAT(e){return e===this.getGeneralValue("RoughTile")||e===this.getGeneralValue("SandTile")||e===this.getGeneralValue("GreenTile")||e===this.getGeneralValue("PaveTile")}isCLAT(e){return e===this.getGeneralValue("ClearToRoughLat")||e===this.getGeneralValue("ClearToSandLat")||e===this.getGeneralValue("ClearToGreenLat")||e===this.getGeneralValue("ClearToPaveLat")}getLAT(e){return e===this.getGeneralValue("ClearToRoughLat")?this.getGeneralValue("RoughTile"):e===this.getGeneralValue("ClearToSandLat")?this.getGeneralValue("SandTile"):e===this.getGeneralValue("ClearToGreenLat")?this.getGeneralValue("GreenTile"):e===this.getGeneralValue("ClearToPaveLat")?this.getGeneralValue("PaveTile"):-1}getCLATSet(e){return e===this.getGeneralValue("RoughTile")?this.getGeneralValue("ClearToRoughLat"):e===this.getGeneralValue("SandTile")?this.getGeneralValue("ClearToSandLat"):e===this.getGeneralValue("GreenTile")?this.getGeneralValue("ClearToGreenLat"):e===this.getGeneralValue("PaveTile")?this.getGeneralValue("ClearToPaveLat"):-1}canConnectTiles(e,t){if(e===t)return!1;var i=this.getGeneralValue("GreenTile"),r=this.getGeneralValue("PaveTile"),s=this.getGeneralValue("MiscPaveTile"),a=this.getGeneralValue("ShorePieces"),n=this.getGeneralValue("WaterBridge"),o=this.getGeneralValue("PavedRoads"),l=this.getGeneralValue("Medians");return!(e===i&&t===a||t===i&&e===a)&&(!(e===i&&t===n||t===i&&e===n)&&(!(e===r&&t===o||t===r&&e===o)&&(!(e===r&&t===s||t===r&&e===s)&&!(e===r&&t===l||t===r&&e===l))))}getHighBridgeHeadType(e){for(var[t,i]of highBridgeHeadNames)for(var r of i)if(this.getGeneralValue(r)===e+1)return t}getOppositeHighBridgeHeadType(e){switch(e){case HighBridgeHeadType.TopLeft:return HighBridgeHeadType.BottomRight;case HighBridgeHeadType.TopRight:return HighBridgeHeadType.BottomLeft;case HighBridgeHeadType.BottomLeft:return HighBridgeHeadType.TopRight;case HighBridgeHeadType.BottomRight:return HighBridgeHeadType.TopLeft;case HighBridgeHeadType.MiddleTlBr:case HighBridgeHeadType.MiddleTrBl:throw new Error("Middle bridge heads can't have opposites");default:throw new Error("Unhandled headType "+e)}}isCliffTile(e){return this.cliffSetNums.includes(this.getSetNum(e))}isHighBridgeBoundaryTile(e){if(this.highBridgeSetNums.includes(this.getSetNum(e))){e=this.getTile(e),e=this.getHighBridgeHeadType(e.index);return void 0!==e&&![HighBridgeHeadType.MiddleTlBr,HighBridgeHeadType.MiddleTrBl].includes(e)}return!1}isHighBridgeMiddleTile(e){if(this.highBridgeSetNums.includes(this.getSetNum(e))){e=this.getTile(e),e=this.getHighBridgeHeadType(e.index);return void 0!==e&&[HighBridgeHeadType.MiddleTlBr,HighBridgeHeadType.MiddleTrBl].includes(e)}return!1}}!function(e){e[e.None=0]="None",e[e.Iso=1]="Iso",e[e.Unit=2]="Unit",e[e.Overlay=3]="Overlay",e[e.Anim=4]="Anim",e[e.Custom=5]="Custom",e[e.Default=6]="Default"}(PaletteType=PaletteType||{});class Theater{static factory(e,t,i,r,s){var a=s.get(i.isoPaletteName);if(!a)throw new Error(`Missing palette "${i.isoPaletteName}"`);var n=s.get(i.overlayPaletteName);if(!n)throw new Error(`Missing palette "${i.overlayPaletteName}"`);var o=s.get(i.unitPaletteName);if(!o)throw new Error(`Missing palette "${i.unitPaletteName}"`);var l=s.get("anim.pal");if(!l)throw new Error("Missing anim palette");var h=s.get(i.libPaletteName);if(!h)throw new Error("Missing lib palette "+i.libPaletteName);let c=new TileSets(t);return c.loadTileData(r,i.extension),new this(e,i,s,a,n,o,l,h,c)}constructor(e,t,i,r,s,a,n,o,l){this.type=e,this.settings=t,this.palettes=i,this.isoPalette=r,this.ovlPalette=s,this.unitPalette=a,this.animPalette=n,this.libPalette=o,this.tileSets=l}getPalette(e,t){switch(e){case PaletteType.Anim:return this.animPalette;case PaletteType.Overlay:return this.ovlPalette;case PaletteType.Unit:return this.unitPalette;case PaletteType.Custom:if("lib"===t)return this.libPalette;var i=this.palettes.get(t+".pal");if(!i)throw new Error(`Custom palette "${t}" not found`);return i;default:PaletteType.Iso;return this.isoPalette}}}!function(e){e[e.None=0]="None",e[e.Temperate=1]="Temperate",e[e.Urban=2]="Urban",e[e.Snow=4]="Snow",e[e.Lunar=8]="Lunar",e[e.Desert=16]="Desert",e[e.NewUrban=32]="NewUrban",e[e.All=63]="All"}(TheaterType=TheaterType||{});const version="0.79.0-dev.0";class AudioBagFile{constructor(){this.fileData=new Map}fromVirtualFile(e,t){var i,r;for([i,r]of t.entries){var s=this.buildWavData(e.stream,r);this.fileData.set(i,s)}return this}getFileList(){return[...this.fileData.keys()]}containsFile(e){return this.fileData.has(e)}openFile(e){if(!this.containsFile(e))throw new Error(`File "${e}" not found`);return new VirtualFile(this.fileData.get(e),e)}buildWavData(e,t){let i=new DataStream;var r,s,a,n,o=0<(1&t.flags)?2:1;let l=0;0<(2&t.flags)?(i.writeString("RIFF"),i.writeUint32(t.length+36),i.writeString("WAVE"),i.writeString("fmt "),i.writeInt32(16),i.writeInt16(1),i.writeInt16(o),i.writeUint32(t.sampleRate),i.writeUint32(2*o*t.sampleRate),i.writeInt16(2*o),i.writeInt16(16),i.writeString("data"),i.writeUint32(t.length)):0<(8&t.flags)&&(r=11100*o*(t.sampleRate/22050|0),s=t.chunkSize,a=1017*(n=Math.max(2,Math.ceil(t.length/s))),n=n*s,l=n-t.length,i.writeString("RIFF"),i.writeUint32(52+n),i.writeString("WAVE"),i.writeString("fmt "),i.writeUint32(20),i.writeInt16(17),i.writeInt16(o),i.writeUint32(t.sampleRate),i.writeInt32(r),i.writeInt16(s),i.writeInt16(4),i.writeInt16(2),i.writeInt16(1017),i.writeString("fact"),i.writeUint32(4),i.writeInt32(a),i.writeString("data"),i.writeUint32(n)),e.seek(t.offset),i.writeUint8Array(e.readUint8Array(t.length));for(let e=0;e<l;e++)i.writeUint8(0);return i.seek(0),i._trimAlloc=()=>{},i}}class IdxEntry{}class IdxFile{constructor(e){this.entries=new Map,this.parse(e)}parse(t){var e=t.readCString(4);if("GABA"!==e)throw new Error(`Unable to load Idx file, did not find magic id, found ${e} instead`);e=t.readInt32();if(2!==e)throw new Error(`Unable to load Idx file, did not find magic number 2, found ${e} instead`);var i=t.readInt32();for(let e=0;e<i;e++){const s=new IdxEntry;let e=t.readString(16);var r=e.indexOf("\0");0!==r&&(e=e.substr(0,r)),s.filename=e+".wav",s.offset=t.readUint32(),s.length=t.readUint32(),s.sampleRate=t.readUint32(),s.flags=t.readUint32(),s.chunkSize=t.readUint32(),this.entries.set(s.filename,s)}}}function swapBytes(e){return e=((e=(e<<16>>>0|e>>>16)>>>0)<<8>>>0&4278255360|e>>>8&16711935)>>>0}class Blowfish{constructor(i){this.m_p=new Uint32Array([608135816,2242054355,320440878,57701188,2752067618,698298832,137296536,3964562569,1160258022,953160567,3193202383,887688300,3232508343,3380367581,1065670069,3041331479,2450970073,2306472731]),this.m_s=[new Uint32Array([3509652390,2564797868,805139163,3491422135,3101798381,1780907670,3128725573,4046225305,614570311,3012652279,134345442,2240740374,1667834072,1901547113,2757295779,4103290238,227898511,1921955416,1904987480,2182433518,2069144605,3260701109,2620446009,720527379,3318853667,677414384,3393288472,3101374703,2390351024,1614419982,1822297739,2954791486,3608508353,3174124327,2024746970,1432378464,3864339955,2857741204,1464375394,1676153920,1439316330,715854006,3033291828,289532110,2706671279,2087905683,3018724369,1668267050,732546397,1947742710,3462151702,2609353502,2950085171,1814351708,2050118529,680887927,999245976,1800124847,3300911131,1713906067,1641548236,4213287313,1216130144,1575780402,4018429277,3917837745,3693486850,3949271944,596196993,3549867205,258830323,2213823033,772490370,2760122372,1774776394,2652871518,566650946,4142492826,1728879713,2882767088,1783734482,3629395816,2517608232,2874225571,1861159788,326777828,3124490320,2130389656,2716951837,967770486,1724537150,2185432712,2364442137,1164943284,2105845187,998989502,3765401048,2244026483,1075463327,1455516326,1322494562,910128902,469688178,1117454909,936433444,3490320968,3675253459,1240580251,122909385,2157517691,634681816,4142456567,3825094682,3061402683,2540495037,79693498,3249098678,1084186820,1583128258,426386531,1761308591,1047286709,322548459,995290223,1845252383,2603652396,3431023940,2942221577,3202600964,3727903485,1712269319,422464435,3234572375,1170764815,3523960633,3117677531,1434042557,442511882,3600875718,1076654713,1738483198,4213154764,2393238008,3677496056,1014306527,4251020053,793779912,2902807211,842905082,4246964064,1395751752,1040244610,2656851899,3396308128,445077038,3742853595,3577915638,679411651,2892444358,2354009459,1767581616,3150600392,3791627101,3102740896,284835224,4246832056,1258075500,768725851,2589189241,3069724005,3532540348,1274779536,3789419226,2764799539,1660621633,3471099624,4011903706,913787905,3497959166,737222580,2514213453,2928710040,3937242737,1804850592,3499020752,2949064160,2386320175,2390070455,2415321851,4061277028,2290661394,2416832540,1336762016,1754252060,3520065937,3014181293,791618072,3188594551,3933548030,2332172193,3852520463,3043980520,413987798,3465142937,3030929376,4245938359,2093235073,3534596313,375366246,2157278981,2479649556,555357303,3870105701,2008414854,3344188149,4221384143,3956125452,2067696032,3594591187,2921233993,2428461,544322398,577241275,1471733935,610547355,4027169054,1432588573,1507829418,2025931657,3646575487,545086370,48609733,2200306550,1653985193,298326376,1316178497,3007786442,2064951626,458293330,2589141269,3591329599,3164325604,727753846,2179363840,146436021,1461446943,4069977195,705550613,3059967265,3887724982,4281599278,3313849956,1404054877,2845806497,146425753,1854211946]),new Uint32Array([1266315497,3048417604,3681880366,3289982499,290971e4,1235738493,2632868024,2414719590,3970600049,1771706367,1449415276,3266420449,422970021,1963543593,2690192192,3826793022,1062508698,1531092325,1804592342,2583117782,2714934279,4024971509,1294809318,4028980673,1289560198,2221992742,1669523910,35572830,157838143,1052438473,1016535060,1802137761,1753167236,1386275462,3080475397,2857371447,1040679964,2145300060,2390574316,1461121720,2956646967,4031777805,4028374788,33600511,2920084762,1018524850,629373528,3691585981,3515945977,2091462646,2486323059,586499841,988145025,935516892,3367335476,2599673255,2839830854,265290510,3972581182,2759138881,3795373465,1005194799,847297441,406762289,1314163512,1332590856,1866599683,4127851711,750260880,613907577,1450815602,3165620655,3734664991,3650291728,3012275730,3704569646,1427272223,778793252,1343938022,2676280711,2052605720,1946737175,3164576444,3914038668,3967478842,3682934266,1661551462,3294938066,4011595847,840292616,3712170807,616741398,312560963,711312465,1351876610,322626781,1910503582,271666773,2175563734,1594956187,70604529,3617834859,1007753275,1495573769,4069517037,2549218298,2663038764,504708206,2263041392,3941167025,2249088522,1514023603,1998579484,1312622330,694541497,2582060303,2151582166,1382467621,776784248,2618340202,3323268794,2497899128,2784771155,503983604,4076293799,907881277,423175695,432175456,1378068232,4145222326,3954048622,3938656102,3820766613,2793130115,2977904593,26017576,3274890735,3194772133,1700274565,1756076034,4006520079,3677328699,720338349,1533947780,354530856,688349552,3973924725,1637815568,332179504,3949051286,53804574,2852348879,3044236432,1282449977,3583942155,3416972820,4006381244,1617046695,2628476075,3002303598,1686838959,431878346,2686675385,1700445008,1080580658,1009431731,832498133,3223435511,2605976345,2271191193,2516031870,1648197032,4164389018,2548247927,300782431,375919233,238389289,3353747414,2531188641,2019080857,1475708069,455242339,2609103871,448939670,3451063019,1395535956,2413381860,1841049896,1491858159,885456874,4264095073,4001119347,1565136089,3898914787,1108368660,540939232,1173283510,2745871338,3681308437,4207628240,3343053890,4016749493,1699691293,1103962373,3625875870,2256883143,3830138730,1031889488,3479347698,1535977030,4236805024,3251091107,2132092099,1774941330,1199868427,1452454533,157007616,2904115357,342012276,595725824,1480756522,206960106,497939518,591360097,863170706,2375253569,3596610801,1814182875,2094937945,3421402208,1082520231,3463918190,2785509508,435703966,3908032597,1641649973,2842273706,3305899714,1510255612,2148256476,2655287854,3276092548,4258621189,236887753,3681803219,274041037,1734335097,3815195456,3317970021,1899903192,1026095262,4050517792,356393447,2410691914,3873677099,3682840055]),new Uint32Array([3913112168,2491498743,4132185628,2489919796,1091903735,1979897079,3170134830,3567386728,3557303409,857797738,1136121015,1342202287,507115054,2535736646,337727348,3213592640,1301675037,2528481711,1895095763,1721773893,3216771564,62756741,2142006736,835421444,2531993523,1442658625,3659876326,2882144922,676362277,1392781812,170690266,3921047035,1759253602,3611846912,1745797284,664899054,1329594018,3901205900,3045908486,2062866102,2865634940,3543621612,3464012697,1080764994,553557557,3656615353,3996768171,991055499,499776247,1265440854,648242737,3940784050,980351604,3713745714,1749149687,3396870395,4211799374,3640570775,1161844396,3125318951,1431517754,545492359,4268468663,3499529547,1437099964,2702547544,3433638243,2581715763,2787789398,1060185593,1593081372,2418618748,4260947970,69676912,2159744348,86519011,2512459080,3838209314,1220612927,3339683548,133810670,1090789135,1078426020,1569222167,845107691,3583754449,4072456591,1091646820,628848692,1613405280,3757631651,526609435,236106946,48312990,2942717905,3402727701,1797494240,859738849,992217954,4005476642,2243076622,3870952857,3732016268,765654824,3490871365,2511836413,1685915746,3888969200,1414112111,2273134842,3281911079,4080962846,172450625,2569994100,980381355,4109958455,2819808352,2716589560,2568741196,3681446669,3329971472,1835478071,660984891,3704678404,4045999559,3422617507,3040415634,1762651403,1719377915,3470491036,2693910283,3642056355,3138596744,1364962596,2073328063,1983633131,926494387,3423689081,2150032023,4096667949,1749200295,3328846651,309677260,2016342300,1779581495,3079819751,111262694,1274766160,443224088,298511866,1025883608,3806446537,1145181785,168956806,3641502830,3584813610,1689216846,3666258015,3200248200,1692713982,2646376535,4042768518,1618508792,1610833997,3523052358,4130873264,2001055236,3610705100,2202168115,4028541809,2961195399,1006657119,2006996926,3186142756,1430667929,3210227297,1314452623,4074634658,4101304120,2273951170,1399257539,3367210612,3027628629,1190975929,2062231137,2333990788,2221543033,2438960610,1181637006,548689776,2362791313,3372408396,3104550113,3145860560,296247880,1970579870,3078560182,3769228297,1714227617,3291629107,3898220290,166772364,1251581989,493813264,448347421,195405023,2709975567,677966185,3703036547,1463355134,2715995803,1338867538,1343315457,2802222074,2684532164,233230375,2599980071,2000651841,3277868038,1638401717,4028070440,3237316320,6314154,819756386,300326615,590932579,1405279636,3267499572,3150704214,2428286686,3959192993,3461946742,1862657033,1266418056,963775037,2089974820,2263052895,1917689273,448879540,3550394620,3981727096,150775221,3627908307,1303187396,508620638,2975983352,2726630617,1817252668,1876281319,1457606340,908771278,3720792119,3617206836,2455994898,1729034894,1080033504]),new Uint32Array([976866871,3556439503,2881648439,1522871579,1555064734,1336096578,3548522304,2579274686,3574697629,3205460757,3593280638,3338716283,3079412587,564236357,2993598910,1781952180,1464380207,3163844217,3332601554,1699332808,1393555694,1183702653,3581086237,1288719814,691649499,2847557200,2895455976,3193889540,2717570544,1781354906,1676643554,2592534050,3230253752,1126444790,2770207658,2633158820,2210423226,2615765581,2414155088,3127139286,673620729,2805611233,1269405062,4015350505,3341807571,4149409754,1057255273,2012875353,2162469141,2276492801,2601117357,993977747,3918593370,2654263191,753973209,36408145,2530585658,25011837,3520020182,2088578344,530523599,2918365339,1524020338,1518925132,3760827505,3759777254,1202760957,3985898139,3906192525,674977740,4174734889,2031300136,2019492241,3983892565,4153806404,3822280332,352677332,2297720250,60907813,90501309,3286998549,1016092578,2535922412,2839152426,457141659,509813237,4120667899,652014361,1966332200,2975202805,55981186,2327461051,676427537,3255491064,2882294119,3433927263,1307055953,942726286,933058658,2468411793,3933900994,4215176142,1361170020,2001714738,2830558078,3274259782,1222529897,1679025792,2729314320,3714953764,1770335741,151462246,3013232138,1682292957,1483529935,471910574,1539241949,458788160,3436315007,1807016891,3718408830,978976581,1043663428,3165965781,1927990952,4200891579,2372276910,3208408903,3533431907,1412390302,2931980059,4132332400,1947078029,3881505623,4168226417,2941484381,1077988104,1320477388,886195818,18198404,3786409e3,2509781533,112762804,3463356488,1866414978,891333506,18488651,661792760,1628790961,3885187036,3141171499,876946877,2693282273,1372485963,791857591,2686433993,3759982718,3167212022,3472953795,2716379847,445679433,3561995674,3504004811,3574258232,54117162,3331405415,2381918588,3769707343,4154350007,1140177722,4074052095,668550556,3214352940,367459370,261225585,2610173221,4209349473,3468074219,3265815641,314222801,3066103646,3808782860,282218597,3406013506,3773591054,379116347,1285071038,846784868,2669647154,3771962079,3550491691,2305946142,453669953,1268987020,3317592352,3279303384,3744833421,2610507566,3859509063,266596637,3847019092,517658769,3462560207,3443424879,370717030,4247526661,2224018117,4143653529,4112773975,2788324899,2477274417,1456262402,2901442914,1517677493,1846949527,2295493580,3734397586,2176403920,1280348187,1908823572,3871786941,846861322,1172426758,3287448474,3383383037,1655181056,3139813346,901632758,1897031941,2986607138,3066810236,3447102507,1393639104,373351379,950779232,625454576,3124240540,4148612726,2007998917,544563296,2244738638,2330496472,2058025392,1291430526,424198748,50039436,29584100,3605783033,2429876329,2791104160,1057563949,3255363231,3075367218,3463963227,1469046755,985887462])];for(let e=0,t=0;e<18;++e){var r=i[t++%i.length],s=i[t++%i.length],a=i[t++%i.length],n=i[t++%i.length];this.m_p[e]^=r<<24|s<<16|a<<8|n}let o=0,l=0;for(let e=0;e<18;)[o,l]=this._encrypt(o,l),this.m_p[e++]=o,this.m_p[e++]=l;for(let t=0;t<4;++t)for(let e=0;e<256;)[o,l]=this._encrypt(o,l),this.m_s[t][e++]=o,this.m_s[t][e++]=l}encrypt(e){return this.runCipher(e,this._encrypt.bind(this))}decrypt(e){return this.runCipher(e,this._decrypt.bind(this))}runCipher(e,t){let i=new Uint32Array(e.length),r=e.length/2|0,s=0;for(;0<r--;){var a=swapBytes(e[s]),n=swapBytes(e[s+1]);[a,n]=t(a,n),i[s++]=swapBytes(a),i[s++]=swapBytes(n)}return i}_encrypt(e,t){let i=e,r=t;i^=this.m_p[0];let s=!1;for(let e=1;e<=16;e++,s=!s)s?i=this.round(i,r,e):r=this.round(r,i,e);return r^=this.m_p[17],[r,i]}_decrypt(e,t){let i=e,r=t;i^=this.m_p[17];let s=!1;for(let e=16;1<=e;e--,s=!s)s?i=this.round(i,r,e):r=this.round(r,i,e);return r^=this.m_p[0],[r,i]}s(e,t){return this.m_s[t][e>>(3-t<<3)&255]}bf_f(e){return(this.s(e,0)+this.s(e,1)>>>0^this.s(e,2))+this.s(e,3)>>>0}round(e,t,i){return e^(this.bf_f(t)^this.m_p[i])}}const pubkeyStr="AihRvNoIbTn85FZRYNZRcT+i6KpU+maCsEqr3Q5q+LDB5tH7Tz2qQ38V",char2num=new Int8Array([-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,62,-1,-1,-1,63,52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-1,-1,-1,-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1,-1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1]);class PublicKey{constructor(){this.key1=new Uint32Array(64),this.key2=new Uint32Array(64)}}class BlowfishKey{constructor(){this.pubkey=new PublicKey,this.glob1=new Uint32Array(64),this.glob2=new Uint32Array(130),this.glob1_hi=new Uint32Array(4),this.glob1_hi_inv=new Uint32Array(4)}init_bignum(t,e,i){for(let e=0;e<i;e++)t[e]=0;t[0]=e}move_key_to_big(e,t,i,r){let s;s=0!=(128&t[0])?255:0;const a=new Uint8Array(e.buffer,e.byteOffset);let n=4*r;for(;n>i;n--)a[n-1]=s;for(;0<n;n--)a[n-1]=t[i-n]}key_to_bignum(e,t,i){let r,s,a=0;if(2===t[a]){if(a++,0!=(128&t[a])){for(r=0,s=0;s<(127&t[a]);s++)r=(r<<8>>>0|t[a+s+1])>>>0;a+=1+(127&t[a])}else r=t[a],a++;r<=4*i&&this.move_key_to_big(e,t.subarray(a),r,i)}}len_bignum(e,t){let i=t-1;for(;0<=i&&0===e[i];)i--;return i+1}bitlen_bignum(e,t){var i;let r,s;if(0===(i=this.len_bignum(e,t)))return 0;for(r=32*i,s=2147483648;0==(s&e[i-1]);)s>>>=1,r--;return r}init_pubkey(){let e=0,t;var i;const r=new Uint8Array(256);for(this.init_bignum(this.pubkey.key2,65537,64),t=0;e<pubkeyStr.length;)i=(((char2num[pubkeyStr.charCodeAt(e++)]>>>0<<6>>>0|255&char2num[pubkeyStr.charCodeAt(e++)])>>>0<<6>>>0|255&char2num[pubkeyStr.charCodeAt(e++)])>>>0<<6>>>0|255&char2num[pubkeyStr.charCodeAt(e++)])>>>0,r[t++]=i>>16&255,r[t++]=i>>8&255,r[t++]=255&i;this.key_to_bignum(this.pubkey.key1,r,64),this.pubkey.len=this.bitlen_bignum(this.pubkey.key1,64)-1}len_predata(){var e=(this.pubkey.len-1)/8|0;return(1+(55/e|0))*(1+e)>>>0}cmp_bignum(e,t,i){for(;0<i;){if(e[--i]<t[i])return-1;if(e[i]>t[i])return 1}return 0}mov_bignum(t,i,r){for(let e=0;e<r;e++)t[e]=i[e]}shr_bignum(e,t,i){let r;var s=t/32|0;if(0<s){for(r=0;r<i-s;r++)e[r]=e[r+s];for(;r<i;r++)e[r]=0;t%=32}if(0!==t){for(r=0;r<i-1;r++)e[r]=(e[r]>>>t|e[r+1]<<32-t>>>0)>>>0;e[r]=e[r]>>>t}}shl_bignum(e,t,i){let r;var s=t/32|0;if(0<s){for(r=i-1;r>s;r--)e[r]=e[r-s];for(;0<r;r--)e[r]=0;t%=32}if(0!==t){for(r=i-1;0<r;r--)e[r]=(e[r]<<t>>>0|e[r-1]>>>32-t)>>>0;e[0]=e[0]<<t>>>0}}sub_bignum(e,t,i,r,s){var a,n;s+=s;var o=new Uint16Array(t.buffer,t.byteOffset),l=new Uint16Array(i.buffer,i.byteOffset);const h=new Uint16Array(e.buffer,e.byteOffset);let c=0;for(;-1!=--s;)a=o[c],n=l[c],h[c]=a-n-r&65535,r=0!=(a-n-r&65536)?1:0,c++;return r}sub_bignum_word(e,t,i,r,s){var a,n;let o=0;for(;-1!=--s;)a=t[o],n=i[o],e[o]=a-n-r&65535,r=0!=(a-n-r&65536)?1:0,o++;return r}inv_bignum(e,t,i){const r=new Uint32Array(64);var s;let a,n,o=0;for(this.init_bignum(r,0,i),this.init_bignum(e,0,i),n=this.bitlen_bignum(t,i),a=1<<n%32>>>0,o=((n+32)/32|0)-1,s=4*((n-1)/32|0)>>>0,r[s/4|0]=r[s/4|0]|1<<(n-1&31)>>>0;0<n;)n--,this.shl_bignum(r,1,i),-1!==this.cmp_bignum(r,t,i)&&(this.sub_bignum(r,r,t,0,i),e[o]=e[o]|a>>>0),a>>>=1,0===a&&(o--,a=2147483648);this.init_bignum(r,0,i)}inc_bignum(e,t){let i=0;for(;0==++e[i]&&0<--t;)i++}init_two_dw(e,t){this.mov_bignum(this.glob1,e,t),this.glob1_bitlen=this.bitlen_bignum(this.glob1,t),this.glob1_len_x2=(this.glob1_bitlen+15)/16|0,this.mov_bignum(this.glob1_hi,this.glob1.subarray(this.len_bignum(this.glob1,t)-2),2),this.glob1_hi_bitlen=this.bitlen_bignum(this.glob1_hi,2)-32>>>0,this.shr_bignum(this.glob1_hi,this.glob1_hi_bitlen,2),this.inv_bignum(this.glob1_hi_inv,this.glob1_hi,2),this.shr_bignum(this.glob1_hi_inv,1,2),this.glob1_hi_bitlen=(this.glob1_hi_bitlen+15)%16+1>>>0,this.inc_bignum(this.glob1_hi_inv,2),32<this.bitlen_bignum(this.glob1_hi_inv,2)&&(this.shr_bignum(this.glob1_hi_inv,1,2),this.glob1_hi_bitlen--),this.glob1_hi_inv_lo=65535&this.glob1_hi_inv[0],this.glob1_hi_inv_hi=this.glob1_hi_inv[0]>>>16&65535}mul_bignum_word(e,t,i,r){let s,a;var n=new Uint16Array(t.buffer,t.byteOffset);let o=a=0;for(s=0;s<r;s++)a=i*n[o]+e[o]+a,e[o]=65535&a,o++,a>>>=16;e[o]+=65535&a}mul_bignum(e,t,i,r){let s;var a=new Uint16Array(i.buffer,i.byteOffset);let n=new Uint16Array(e.buffer,e.byteOffset);this.init_bignum(e,0,2*r);let o=0;for(s=0;s<2*r;s++)this.mul_bignum_word(n.subarray(o),t,a[o],2*r),o++}not_bignum(e,t){let i;for(i=0;i<t;i++)e[i]=~e[i]>>>0}neg_bignum(e,t){this.not_bignum(e,t),this.inc_bignum(e,t)}get_mulword(e,t){let i=((((65535&(65535^e[t-1]))*this.glob1_hi_inv_lo+65536>>>1)+((65535^e[t-2])*this.glob1_hi_inv_hi+this.glob1_hi_inv_hi>>>1)+1>>>16)+((65535&(65535^e[t-1]))*this.glob1_hi_inv_hi>>>1)+((65535^e[t])*this.glob1_hi_inv_lo>>>1)+1>>>14)+this.glob1_hi_inv_hi*(65535^e[t])*2>>>this.glob1_hi_bitlen>>>0;return 65535<i&&(i=65535),65535&i}dec_bignum(e,t){let i=0;for(;--e[i]>>>0==4294967295&&0<--t;)i++}calc_a_bignum(e,t,r,s){let a;var n=this.glob1,o=this.glob2;if(this.mul_bignum(this.glob2,t,r,s),this.glob2[2*s]=0,(r=2*this.len_bignum(this.glob2,2*s+1))>=this.glob1_len_x2){this.inc_bignum(this.glob2,2*s+1),this.neg_bignum(this.glob2,2*s+1),a=1+r-this.glob1_len_x2;let e=new Uint16Array(o.buffer),t=a,i=1+r;for(;0!==a;a--){i--;var l=this.get_mulword(e,i);t--;var h=e.subarray(t);0<l&&(this.mul_bignum_word(h,this.glob1,l,2*s),0==(32768&e[i])&&0!==this.sub_bignum_word(h,h,new Uint16Array(n.buffer),0,2*s)&&e[i]--)}this.neg_bignum(this.glob2,s),this.dec_bignum(this.glob2,s)}this.mov_bignum(e,this.glob2,s)}clear_tmp_vars(e){this.init_bignum(this.glob1,0,e),this.init_bignum(this.glob2,0,e),this.init_bignum(this.glob1_hi_inv,0,4),this.init_bignum(this.glob1_hi,0,4),this.glob1_bitlen=0,this.glob1_hi_bitlen=0,this.glob1_len_x2=0,this.glob1_hi_inv_lo=0,this.glob1_hi_inv_hi=0}calc_a_key(e,t,i,r,s){var a,n=new Uint32Array(64);let o,l,h=0;for(this.init_bignum(e,1,s),a=this.len_bignum(r,s),this.init_two_dw(r,a),o=this.bitlen_bignum(i,a)<<24>>24,r=((o+31)/32|0)>>>0,l=1<<(o-1)%32>>>1,h+=r-1,o--,this.mov_bignum(e,t,a);-1!=--o;)0===l&&(l=2147483648,h--),this.calc_a_bignum(n,e,e,a),0!=(i[h]&l)?this.calc_a_bignum(e,n,t,a):this.mov_bignum(e,n,a),l>>>=1;this.init_bignum(n,0,a),this.clear_tmp_vars(s)}memcpy(e,t,i){let r=0;for(;0!=i--;)e[r]=t[r],r++}process_predata(e,t,i){var r=new Uint32Array(64),s=new Uint32Array(64);let a=0,n=0;for(var o=(this.pubkey.len-1)/8|0;1+o<=t;)this.init_bignum(r,0,64),this.memcpy(new Uint8Array(r.buffer),e.subarray(a),1+o),this.calc_a_key(s,r,this.pubkey.key2,this.pubkey.key1,64),this.memcpy(i.subarray(n),new Uint8Array(s.buffer),o),t-=1+o,a+=1+o,n+=o}decryptKey(e){this.init_pubkey();let t=new Uint8Array(256);return this.process_predata(e,this.len_predata(),t),t.subarray(0,56)}}class Crc32{static calculateCrc(i,e=4294967295){let r=e;for(let e=0,t=i.length;e<t;e++)r=(r>>>8^this.lookUp[255&r^i[e]])>>>0;return r=(r^e)>>>0,r}constructor(e=4294967295){this.polynomal=e,this.crc=e}append(i){for(let e=0,t=i.length;e<t;e++)this.crc=(this.crc>>>8^Crc32.lookUp[255&this.crc^i[e]])>>>0}get(){return(this.crc^this.polynomal)>>>0}}Crc32.lookUp=new Uint32Array([0,1996959894,3993919788,2567524794,124634137,1886057615,3915621685,2657392035,249268274,2044508324,3772115230,2547177864,162941995,2125561021,3887607047,2428444049,498536548,1789927666,4089016648,2227061214,450548861,1843258603,4107580753,2211677639,325883990,1684777152,4251122042,2321926636,335633487,1661365465,4195302755,2366115317,997073096,1281953886,3579855332,2724688242,1006888145,1258607687,3524101629,2768942443,901097722,1119000684,3686517206,2898065728,853044451,1172266101,3705015759,2882616665,651767980,1373503546,3369554304,3218104598,565507253,1454621731,3485111705,3099436303,671266974,1594198024,3322730930,2970347812,795835527,1483230225,3244367275,3060149565,1994146192,31158534,2563907772,4023717930,1907459465,112637215,2680153253,3904427059,2013776290,251722036,2517215374,3775830040,2137656763,141376813,2439277719,3865271297,1802195444,476864866,2238001368,4066508878,1812370925,453092731,2181625025,4111451223,1706088902,314042704,2344532202,4240017532,1658658271,366619977,2362670323,4224994405,1303535960,984961486,2747007092,3569037538,1256170817,1037604311,2765210733,3554079995,1131014506,879679996,2909243462,3663771856,1141124467,855842277,2852801631,3708648649,1342533948,654459306,3188396048,3373015174,1466479909,544179635,3110523913,3462522015,1591671054,702138776,2966460450,3352799412,1504918807,783551873,3082640443,3233442989,3988292384,2596254646,62317068,1957810842,3939845945,2647816111,81470997,1943803523,3814918930,2489596804,225274430,2053790376,3826175755,2466906013,167816743,2097651377,4027552580,2265490386,503444072,1762050814,4150417245,2154129355,426522225,1852507879,4275313526,2312317920,282753626,1742555852,4189708143,2394877945,397917763,1622183637,3604390888,2714866558,953729732,1340076626,3518719985,2797360999,1068828381,1219638859,3624741850,2936675148,906185462,1090812512,3747672003,2825379669,829329135,1181335161,3412177804,3160834842,628085408,1382605366,3423369109,3138078467,570562233,1426400815,3317316542,2998733608,733239954,1555261956,3268935591,3050360625,752459403,1541320221,2607071920,3965973030,1969922972,40735498,2617837225,3943577151,1913087877,83908371,2512341634,3803740692,2075208622,213261112,2463272603,3855990285,2094854071,198958881,2262029012,4057260610,1759359992,534414190,2176718541,4139329115,1873836001,414664567,2282248934,4279200368,1711684554,285281116,2405801727,4167216745,1634467795,376229701,2685067896,3608007406,1308918612,956543938,2808555105,3495958263,1231636301,1047427035,2932959818,3654703836,1088359270,936918e3,2847714899,3736837829,1202900863,817233897,3183342108,3401237130,1404277552,615818150,3134207493,3453421203,1423857449,601450431,3009837614,3294710456,1567103746,711928724,3020668471,3272380065,1510334235,755167117]);class MixEntry{static hashFilename(t){var i=(t=t.toUpperCase()).length,r=i>>2;if(0!=(3&i)){t+=String.fromCharCode(i-(r<<2));let e=3-(3&i);for(;0!=e--;)t+=t[r<<2]}return Crc32.calculateCrc(binaryStringToUint8Array(t))}constructor(e,t,i){this.hash=e,this.offset=t,this.length=i}}MixEntry.size=12,function(e){e[e.Checksum=65536]="Checksum",e[e.Encrypted=131072]="Encrypted"}(MixFileFlags=MixFileFlags||{});class MixFile{constructor(e){this.stream=e,this.headerStart=84,this.index=new Map,this.parseHeader()}parseHeader(){var e=this.stream.readUint32(),t=0==(e&~(MixFileFlags.Checksum|MixFileFlags.Encrypted));if(t){if(0!=(e&MixFileFlags.Encrypted))return void(this.dataStart=this.parseRaHeader())}else this.stream.seek(0);this.dataStart=this.parseTdHeader(this.stream)}parseRaHeader(){const e=this.stream;var t=e.readUint8Array(80),i=(new BlowfishKey).decryptKey(t),r=e.readUint32Array(2);const s=new Blowfish(i);let a=new DataStream(s.decrypt(r));t=a.readUint16();a.readUint32(),e.position=this.headerStart;i=6+t*MixEntry.size,t=(3+i)/4|0,r=e.readUint32Array(t+t%2);a=new DataStream(s.decrypt(r));i=this.headerStart+i+(1+(~i>>>0)&7);return this.parseTdHeader(a),i}parseTdHeader(t){var i=t.readUint16();t.readUint32();for(let e=0;e<i;e++){var r=new MixEntry(t.readUint32(),t.readUint32(),t.readUint32());this.index.set(r.hash,r)}return t.position}containsFile(e){return this.index.has(MixEntry.hashFilename(e))}openFile(e){var t=this.index.get(MixEntry.hashFilename(e));if(!t)throw new Error(`File "${e}" not found`);return VirtualFile.factory(this.stream,e,this.dataStart+t.offset,t.length)}}class FileNotFoundError extends Error{constructor(){super(...arguments),this.name="FileNotFoundError"}}class MemArchive{constructor(){this.entries=new Map}addFile(e){this.entries.set(e.filename,e)}containsFile(e){return this.entries.has(e)}openFile(e){if(!this.containsFile(e))throw new Error(`File "${e}" not found`);return this.entries.get(e)}}class VirtualFileSystem{constructor(e,t){this.rfs=e,this.logger=t,this.allArchives=new Map,this.archivesByPriority=[]}fileExists(e){for(const t of this.archivesByPriority)if(t.containsFile(e))return!0;return!1}openFile(e){for(const t of this.archivesByPriority)if(t.containsFile(e))return t.openFile(e);throw new FileNotFoundError(`File "${e}" not found in VFS`)}addArchive(e,t){this.allArchives.has(t)||(this.allArchives.set(t,e),this.archivesByPriority.push(e)),this.logger.info(`Added archive "${t}" to VFS`)}hasArchive(e){return this.allArchives.has(e)}removeArchive(e){var t=this.allArchives.get(e);t&&(this.allArchives.delete(e),this.archivesByPriority.splice(this.archivesByPriority.indexOf(t),1),this.logger.info(`Removed archive "${e}" from VFS`))}listArchives(){return[...this.allArchives.keys()]}async addMixFile(e){await this.addArchiveByFilename(e,e=>new MixFile(e.stream))}async addBagFile(e){const i=await this.openFileWithRfs(e.replace(".bag",".idx"));await this.addArchiveByFilename(e,e=>{var t=new IdxFile(i.stream);return(new AudioBagFile).fromVirtualFile(e,t)})}async addArchiveByFilename(e,t){var i;this.allArchives.has(e)||(i=await this.openFileWithRfs(e))&&this.addArchive(t(i),e)}async openFileWithRfs(e){let t;try{t=await this.rfs.openFile(e)}catch(e){if(!(e instanceof FileNotFoundError))throw e}if(!t){if(!this.fileExists(e))throw new FileNotFoundError(`File "${e}" not found`);t=this.openFile(e)}return t}async loadImplicitMixFiles(e){this.logger.info("Initializing implicit mix files..."),e===EngineType.YurisRevenge&&await this.addMixFile("langmd.mix"),await this.addMixFile("language.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("ra2md.mix"),await this.addMixFile("ra2.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("cachemd.mix"),await this.addMixFile("cache.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("loadmd.mix"),await this.addMixFile("load.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("localmd.mix"),await this.addMixFile("local.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("ntrlmd.mix"),await this.addMixFile("neutral.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("audiomd.mix"),await this.addMixFile("audio.mix"),await this.addBagFile("audio.bag"),e===EngineType.YurisRevenge&&await this.addMixFile("conqmd.mix"),await this.addMixFile("conquer.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("genermd.mix"),await this.addMixFile("generic.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("isogenmd.mix"),await this.addMixFile("isogen.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("cameomd.mix"),await this.addMixFile("cameo.mix"),e===EngineType.YurisRevenge&&await this.addMixFile("multimd.mix"),await this.addMixFile("multi.mix")}async loadExtraMixFiles(i){let r=new Set;for await(var e of this.rfs.getEntries())r.add(e.toLowerCase());for(var s of["ecache","expand","elocal"])for(let t=99;0<=t;t--){let e=[""+s+pad(t,"00")+".mix"];i===EngineType.YurisRevenge&&e.push(`${s}md${pad(t,"00")}.mix`);for(var a of e)r.has(a)&&await this.addMixFile(a)}let t=[".mmx"];i===EngineType.YurisRevenge&&t.push(".yro");for(const n of t)for(const o of r)o.endsWith(n)&&this.addArchive(new MixFile((await this.rfs.openFile(o)).stream),o)}async loadStandaloneFiles(e){let i=["ini","csf"],r=new Set(e?.exclude),s=[];for await(var a of this.rfs.getEntries()){let t=a.toLowerCase();i.some(e=>t.endsWith("."+e))&&!r.has(t)&&s.push(await this.rfs.openFile(a,!0))}if(s.length){let e=new MemArchive;for(var t of s)e.addFile(t);this.addArchive(e,"mem.archive")}}}class StorageQuotaError extends Error{constructor(e){super("Storage quota exceeded",e),this.name="StorageQuotaError"}}class NameNotAllowedError extends IOError{constructor(){super(...arguments),this.name="NameNotAllowedError"}}class RealFileSystemDir{constructor(e,t=!1){this.handle=e,this.caseSensitive=t}get name(){return this.handle.name}async*getEntries(){try{for await(var e of this.handle.keys())yield e}catch(e){if("NotFoundError"===e.name)throw new FileNotFoundError(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof DOMException)throw new IOError(`Directory "${this.handle.name}" could not be read (${e.name})`,{cause:e});throw e}}async listEntries(){let e=[];for await(var t of this.getEntries())e.push(t);return e}async*getFileHandles(){try{for await(const e of this.handle.values())"file"===e.kind&&(yield e)}catch(e){if("NotFoundError"===e.name)throw new FileNotFoundError(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof DOMException)throw new IOError(`Directory "${this.handle.name}" could not be read (${e.name})`,{cause:e});throw e}}async*getRawFiles(){for await(const e of this.getFileHandles())yield await e.getFile()}async containsEntry(e){return void 0!==await this.resolveEntryName(e)}async resolveEntryName(e){if(this.caseSensitive)return(await this.handle.getFileHandle(e).catch(()=>this.handle.getDirectoryHandle(e)).catch(()=>{}))?.name;for await(const t of this.getEntries())if(equalsIgnoreCase(t,e))return t}async fixEntryCase(e){if(!this.caseSensitive)for await(var t of this.getEntries())if(equalsIgnoreCase(t,e)){e=t;break}return e}async getRawFile(t,e=!1,i){let r;try{var s=e?t:await this.fixEntryCase(t);r=await this.handle.getFileHandle(s)}catch(e){if("NotFoundError"===e.name)throw new FileNotFoundError(`File "${t}" not found in directory "${this.handle.name}"`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`File name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`File "${t}" could not be read (${e.name})`,{cause:e});throw e}t=await r.getFile();return i?new File([t],t.name,{type:i}):t}async openFile(e,t=!1){t=await this.getRawFile(e,t);return VirtualFile.fromRealFile(t)}async writeFile(i,r){r=r??(i instanceof File?i.name:i.filename);try{var s=await this.fixEntryCase(r);await this.deleteFile(s,!0);let e=await this.handle.getFileHandle(s,{create:!0}),t=await e.createWritable();try{await t.write(i instanceof File?i:new Uint8Array(i.stream.buffer,i.stream.byteOffset,i.stream.byteLength)),await t.close()}catch(e){throw await t.abort(),e}}catch(e){if("QuotaExceededError"===e.name)throw new StorageQuotaError({cause:e});if("NotFoundError"===e.name)throw new FileNotFoundError(`Directory "${this.handle.name}" not found`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`File name "${r}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`File "${r}" could not be written (${e.name})`,{cause:e});throw e}}async deleteFile(t,i=!1){t=i?t:await this.resolveEntryName(t);if(t)try{await this.handle.removeEntry(t)}catch(e){if(i&&"NotFoundError"===e.name)return;if("QuotaExceededError"===e.name)throw new StorageQuotaError({cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`File name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`File "${t}" could not be deleted (${e.name})`,{cause:e});throw e}}async getDirectory(t,e=this.caseSensitive){var i=e?t:await this.fixEntryCase(t);let r;try{r=await this.handle.getDirectoryHandle(i)}catch(e){if("NotFoundError"===e.name)throw new FileNotFoundError(`Directory "${t}" not found or parent directory "${this.handle.name}" is gone`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`Directory "${t}" could not be read (${e.name})`,{cause:e});throw e}return new RealFileSystemDir(r,e)}async getOrCreateDirectory(t,e=this.caseSensitive){var i=e?t:await this.fixEntryCase(t);try{return new RealFileSystemDir(await this.handle.getDirectoryHandle(i,{create:!0}),e)}catch(e){if("QuotaExceededError"===e.name)throw new StorageQuotaError({cause:e});if("NotFoundError"===e.name)throw new FileNotFoundError(`Directory "${this.handle.name}" not found"`,{cause:e});if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`Directory "${t}" could not be created (${e.name})`,{cause:e});throw e}}async deleteDirectory(t,e=!1){t=await this.resolveEntryName(t);if(t)try{await this.handle.removeEntry(t,{recursive:e})}catch(e){if("QuotaExceededError"===e.name)throw new StorageQuotaError({cause:e});if("InvalidModificationError"===e.name)throw new IOError("Can't delete non-empty directory when recursive = false");if(e instanceof TypeError&&e.message.includes("not allowed"))throw new NameNotAllowedError(`Directory name "${t}" is not allowed`,{cause:e});if(e instanceof DOMException)throw new IOError(`Directory "${t}" could not be deleted (${e.name})`,{cause:e});throw e}}}class RealFileSystem{constructor(){this.directories=[]}addRootDirectoryHandle(e){this.rootDirectory=this.addDirectoryHandle(e),this.rootDirectoryHandle=e}getRootDirectoryHandle(){return this.rootDirectoryHandle}addDirectoryHandle(e){e=new RealFileSystemDir(e);return this.directories.push(e),e}addDirectory(e){this.directories.push(e)}async getDirectory(e){var t=await this.findDirectory(e);if(!t)throw new Error(`Directory "${e}" not found in real file system`);return t}async findDirectory(e){for(const t of this.directories)if(await t.containsEntry(e))return await t.getDirectory(e)}getRootDirectory(){return this.rootDirectory}async containsEntry(e){for(const t of this.directories)if(await t.containsEntry(e))return!0;return!1}async openFile(e,t=!1){for(const i of this.directories)try{return await i.openFile(e,t)}catch(e){if(!(e instanceof FileNotFoundError))throw e}throw new FileNotFoundError(`File "${e}" not found in real file system`)}async getRawFile(e){for(const t of this.directories)if(await t.containsEntry(e))return await t.getRawFile(e);throw new Error(`File "${e}" not found in real file system`)}async*getEntries(){for(var e of this.directories)for await(var t of e.getEntries())yield t}}class LazyResourceCollection{constructor(e){this.resourceFactory=e,this.resources=new Map}setVfs(e){this.vfs=e}set(e,t){this.resources.set(e,t)}has(e){return!!this.resources.has(e)||(this.vfs?.fileExists(e)??!1)}get(e){let t;return t=this.resources.get(e),!t&&this.vfs?.fileExists(e)&&(t=this.resourceFactory(this.vfs.openFile(e)),this.resources.set(e,t)),t}clear(e){e?this.resources.delete(e):this.resources.clear()}}const chars="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";function encode(t){let i="";for(let e=0;e<t.length;e+=3)i+=chars[t[e]>>2],i+=chars[(3&t[e])<<4|t[e+1]>>4],i+=chars[(15&t[e+1])<<2|t[e+2]>>6],i+=chars[63&t[e+2]];return t.length%3==2?i=i.substring(0,i.length-1)+"=":t.length%3==1&&(i=i.substring(0,i.length-2)+"=="),i}function decode(i){let r=new Uint8Array(256);for(let e=0;e<chars.length;e++)r[chars.charCodeAt(e)]=e;let e=.75*i.length;"="===i[i.length-1]&&(e--,"="===i[i.length-2]&&e--);let s=new Uint8Array(e);for(let e=0,t=0;e<i.length;e+=4){var a=r[i.charCodeAt(e)],n=r[i.charCodeAt(e+1)],o=r[i.charCodeAt(e+2)],l=r[i.charCodeAt(e+3)];s[t++]=a<<2|n>>4,s[t++]=(15&n)<<4|o>>2,s[t++]=(3&o)<<6|63&l}return s}function changeBitDepth(r,e,s,t){if(-1<["32f","64"].indexOf(e)&&-1<["32f","64"].indexOf(t))s.set(r);else{validateBitDepth_(e),validateBitDepth_(t);let i=getBitDepthFunction_(e,t);var a={oldMin:Math.pow(2,parseInt(e,10))/2,newMin:Math.pow(2,parseInt(t,10))/2,oldMax:Math.pow(2,parseInt(e,10))/2-1,newMax:Math.pow(2,parseInt(t,10))/2-1};sign8Bit_(e,r,!0);for(let e=0,t=r.length;e<t;e++)s[e]=i(r[e],a);sign8Bit_(t,s,!1)}}function intToInt_(e,t){return e=0<e?parseInt(e/t.oldMax*t.newMax,10):parseInt(e/t.oldMin*t.newMin,10)}function floatToInt_(e,t){return parseInt(0<e?e*t.newMax:e*t.newMin,10)}function intToFloat_(e,t){return 0<e?e/t.oldMax:e/t.oldMin}function getBitDepthFunction_(e,t){let i=function(e){return e};return e!=t&&(i=["32f","64"].includes(e)?floatToInt_:["32f","64"].includes(t)?intToFloat_:intToInt_),i}function validateBitDepth_(e){if("32f"!=e&&"64"!=e&&(parseInt(e,10)<"8"||"53"<parseInt(e,10)))throw new Error("Invalid bit depth.")}function sign8Bit_(e,i,t){if("8"==e){var r=t?-128:128;for(let e=0,t=i.length;e<t;e++)i[e]=i[e]+=r}}const INDEX_TABLE=[-1,-1,-1,-1,2,4,6,8,-1,-1,-1,-1,2,4,6,8],STEP_TABLE=[7,8,9,10,11,12,13,14,16,17,19,21,23,25,28,31,34,37,41,45,50,55,60,66,73,80,88,97,107,118,130,143,157,173,190,209,230,253,279,307,337,371,408,449,494,544,598,658,724,796,876,963,1060,1166,1282,1411,1552,1707,1878,2066,2272,2499,2749,3024,3327,3660,4026,4428,4871,5358,5894,6484,7132,7845,8630,9493,10442,11487,12635,13899,15289,16818,18500,20350,22385,24623,27086,29794,32767];function imaadpcm_encode(i){var r={index:0,predicted:0,step:7};let s=new Uint8Array(i.length),a=[],n=0,o=0;for(let e=0,t=i.length;e<t;e++)e%505==0&&0!=e&&(s.set(encodeBlock(a,r),n),n+=256,a=[],o++),a.push(i[e]);let e=i.length/2;return e%2&&e++,s.slice(0,e+512+4*o)}function imaadpcm_decode(t,e=256){var i={index:0,predicted:0,step:7};let r=new Int16Array(2*t.length),s=[],a=0,n=t.length,o=0;for(;0<n;){var l=Math.min(n,e);for(let e=0;e<l;e++)s.push(t[o]),o++;var h=decodeBlock(s,i);r.set(h,a),a+=h.length,s=[],n-=e}return r.slice(0,a)}function encodeBlock(i,r){let s=blockHead_(i[0],r);for(let e=3,t=i.length;e<t;e+=2){var a=encodeSample_(i[e],r),n=encodeSample_(i[e+1],r);s.push(n<<4|a)}return s}function decodeBlock(i,r){r.predicted=sign_(i[1]<<8|i[0]),r.index=i[2],r.step=STEP_TABLE[r.index];let s=[r.predicted];for(let e=4,t=i.length;e<t;e++){var a=i[e],n=a>>4;s.push(decodeSample_(n<<4^a,r)),s.push(decodeSample_(n,r))}return s}function sign_(e){return 32767<e?e-65536:e}function encodeSample_(e,t){let i=e-t.predicted,r=0;0<=i?r=0:(r=8,i=-i);let s=STEP_TABLE[t.index],a=s>>3;return i>s&&(r|=4,i-=s,a+=s),s>>=1,i>s&&(r|=2,i-=s,a+=s),s>>=1,i>s&&(r|=1,a+=s),updateEncoder_(r,a,t),r}function updateEncoder_(e,t,i){8&e?i.predicted-=t:i.predicted+=t,i.predicted<-32768?i.predicted=-32768:32767<i.predicted&&(i.predicted=32767),i.index+=INDEX_TABLE[7&e],i.index<0?i.index=0:88<i.index&&(i.index=88)}function decodeSample_(e,t){let i=0;return 4&e&&(i+=t.step),2&e&&(i+=t.step>>1),1&e&&(i+=t.step>>2),i+=t.step>>3,8&e&&(i=-i),t.predicted+=i,32767<t.predicted?t.predicted=32767:t.predicted<-32768&&(t.predicted=-32768),updateDecoder_(e,t),t.predicted}function updateDecoder_(e,t){t.index+=INDEX_TABLE[e],t.index<0?t.index=0:88<t.index&&(t.index=88),t.step=STEP_TABLE[t.index]}function blockHead_(e,t){encodeSample_(e,t);let i=[];return i.push(255&e),i.push(e>>8&255),i.push(t.index),i.push(0),i}const LOG_TABLE=[1,1,2,2,3,3,3,3,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7];function encodeSample(e){let t;var i,r=~(e=-32768==e?-32767:e)>>8&128;return r||(e*=-1),32635<e&&(e=32635),t=256<=e?(i=LOG_TABLE[e>>8&127])<<4|e>>i+3&15:e>>4,85^t^r}function decodeSample(e){let t=0;0!=(128&(e^=85))&&(e&=-129,t=-1);var i=4+((240&e)>>4);let r=0;return r=4!=i?1<<i|(15&e)<<i-4|1<<i-5:e<<1|1,r=0===t?r:-r,8*r*-1}function alaw_encode(i){let r=new Uint8Array(i.length);for(let e=0,t=i.length;e<t;e++)r[e]=encodeSample(i[e]);return r}function alaw_decode(i){let r=new Int16Array(i.length);for(let e=0,t=i.length;e<t;e++)r[e]=decodeSample(i[e]);return r}const BIAS=132,CLIP=32635,encodeTable=[0,0,1,1,2,2,2,2,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7],decodeTable=[0,132,396,924,1980,4092,8316,16764];function mulaw_encodeSample(e){var t=e>>8&128;return 0!=t&&(e=-e),(e+=BIAS)>CLIP&&(e=CLIP),~(t|(t=encodeTable[e>>7&255])<<4|e>>t+3&15)}function mulaw_decodeSample(e){var t,i;let r;return t=128&(e=~e),i=e>>4&7,e=15&e,r=decodeTable[i]+(e<<3+i),0!=t&&(r=-r),r}function mulaw_encode(i){let r=new Uint8Array(i.length);for(let e=0,t=i.length;e<t;e++)r[e]=mulaw_encodeSample(i[e]);return r}function mulaw_decode(i){let r=new Int16Array(i.length);for(let e=0,t=i.length;e<t;e++)r[e]=mulaw_decodeSample(i[e]);return r}function endianness(t,i,r=0,s=t.length){for(let e=r;e<s;e+=i)swap_(t,i,e)}function swap_(t,i,r){i--;for(let e=0;e<i;e++){var s=t[r+e];t[r+e]=t[r+i],t[r+i]=s,i--}}function unpack(o,e=0,t=o.length){let l="";for(let n=e;n<t;){let i=128,r=191,s=!1,a=o[n++];if(0<=a&&a<=127)l+=String.fromCharCode(a);else{let t=0;194<=a&&a<=223?t=1:224<=a&&a<=239?(t=2,224===o[n]&&(i=160),237===o[n]&&(r=159)):240<=a&&a<=244?(t=3,240===o[n]&&(i=144),244===o[n]&&(r=143)):s=!0,a&=(1<<8-t-1)-1;for(let e=0;e<t;e++)(o[n]<i||o[n]>r)&&(s=!0),a=a<<6|63&o[n],n++;s?l+=String.fromCharCode(65533):a<=65535?l+=String.fromCharCode(a):(a-=65536,l+=String.fromCharCode(55296+(a>>10&1023),56320+(1023&a)))}}return l}function pack(e,i,r=0){let s=0;for(var t=e.length;s<t;){var a=e.codePointAt(s);if(a<128)i[r]=a,r++;else{let e=0,t=0;for(a<=2047?(e=1,t=192):a<=65535?(e=2,t=224):a<=1114111&&(e=3,t=240,s++),i[r]=(a>>6*e)+t,r++;0<e;)i[r]=128|a>>6*(e-1)&63,r++,e--}s++}return r}const BYTE_POW_TABLE=new Array(8).fill(0).map((e,t)=>Math.pow(2,8*t));class IntParser{constructor(e,t=!1){this.bits=e,this.offset=Math.ceil(e/8),this.max=Math.pow(2,e)-1,this.min=0,this.unpack=this.unpack_,t&&(this.max=Math.pow(2,e)/2-1,this.min=-this.max-1,this.unpack=this.unpackSigned_)}pack(i,r,s=0){r=this.clamp_(Math.round(r));for(let e=0,t=this.offset;e<t;e++)i[s]=255&Math.floor(r/BYTE_POW_TABLE[e]),s++;return s}unpack_(t,i=0){let r=0;for(let e=0;e<this.offset;e++)r+=t[i+e]*BYTE_POW_TABLE[e];return r}unpackSigned_(e,t=0){return this.sign_(this.unpack_(e,t))}clamp_(e){return e>this.max?this.max:e<this.min?this.min:e}sign_(e){return e>this.max&&(e-=2*this.max+2),e}}class FloatParser{constructor(e,t){this.offset=Math.ceil((e+t)/8),this.ebits=e,this.fbits=t,this.bias=(1<<e-1)-1,this.biasP2=Math.pow(2,this.bias+1),this.ebitsFbits=e+t,this.fbias=Math.pow(2,-(8*this.offset-1-e))}pack(e,t,i){var r=((t=+(t=Math.abs(t)>this.biasP2-2*this.ebitsFbits?t<0?-1/0:1/0:t))||1/t)<0||t<0?1:0;t=Math.abs(t);let s=Math.min(Math.floor(Math.log(t)/Math.LN2),1023),a=roundToEven(t/Math.pow(2,s)*Math.pow(2,this.fbits));return t!=t?(a=Math.pow(2,this.fbits-1),s=(1<<this.ebits)-1):0!==t&&(t>=Math.pow(2,1-this.bias)?(2<=a/Math.pow(2,this.fbits)&&(s+=1,a=1),a=s>this.bias?(s=(1<<this.ebits)-1,0):(s+=this.bias,roundToEven(a)-Math.pow(2,this.fbits))):(a=roundToEven(t/Math.pow(2,1-this.bias-this.fbits)),s=0)),this.packFloatBits_(e,i,r,s,a)}unpack(t,i){var e=(1<<this.ebits)-1;let r,s="";for(let e=this.offset-1;0<=e;e--){var a=t[e+i].toString(2);s+="00000000".substring(a.length)+a}var n="1"==s.charAt(0)?-1:1;s=s.substring(1);let o=parseInt(s.substring(0,this.ebits),2);return s=s.substring(this.ebits),o==e?0!==parseInt(s,2)?NaN:1/0*n:(r=0===o?(o+=1,parseInt(s,2)):parseInt("1"+s,2),n*r*this.fbias*Math.pow(2,o-this.bias))}packFloatBits_(e,t,i,r,s){let a=[];a.push(i);for(let e=this.ebits;0<e;--e)a[e]=r%2?1:0,r=Math.floor(r/2);var n=a.length;for(let e=this.fbits;0<e;--e)a[n+e]=s%2?1:0,s=Math.floor(s/2);let o=a.join(""),l=this.offset+t-1,h=t;for(;l>=t;)e[l]=parseInt(o.substring(0,8),2),o=o.substring(8),l--,h++;return h}}function roundToEven(e){var t=Math.floor(e),e=e-t;return!(e<.5)&&(.5<e||t%2)?t+1:t}function unpackString(e,t=0,i=e.length){return unpack(e,t,i)}function packString(e){var t=[];return pack(e,t),t}function packStringTo(e,t,i=0){return pack(e,t,i)}function packArrayTo(e,t,i,r=0){let s=getParser_((t=t||{}).bits,t.fp,t.signed);var a=Math.ceil(t.bits/8);let n=0;for(var o=r,l=e.length;n<l;n++)r=s.pack(i,e[n],r);return t.be&&endianness(i,a,o,r),r}function unpackArrayTo(e,t,i,r=0,s=e.length){var a,n=getParser_((t=t||{}).bits,t.fp,t.signed);s=getUnpackLen_(e,r,s,n.offset),t.be?(a=copyBuffer_(e),t.be&&endianness(a,n.offset,r,s),unpack_(a,i,r,s,n)):unpack_(e,i,r,s,n)}function packTo(e,t,i,r=0){return packArrayTo([e],t,i,r)}function binary_pack(e,t){var i=[];return packTo(e,t,i,0),i}function binary_unpack(e,t,i=0){var r=[];return unpackArrayTo(e,t,r,i,i+Math.ceil(t.bits/8)),r[0]}function unpack_(i,r,s,a,n){var o=n.offset;for(let e=0,t=s;t<a;t+=o,e++)r[e]=n.unpack(i,t)}function copyBuffer_(e){return new Uint8Array(e)}function getUnpackLen_(e,t,i,r){return i-(i-t)%r}function getParser_(e,t,i){return t&&32==e?new FloatParser(8,23):t&&64==e?new FloatParser(11,52):new IntParser(e,i)}class RIFFFile{constructor(){this.container="",this.chunkSize=0,this.format="",this.signature=null,this.head=0,this.uInt32={bits:32,be:!1},this.supported_containers=["RIFF","RIFX"]}setSignature(e){if(this.head=0,this.container=this.readString(e,4),-1===this.supported_containers.indexOf(this.container))throw Error("Not a supported format.");this.uInt32.be="RIFX"===this.container,this.chunkSize=this.readUInt32(e),this.format=this.readString(e,4),this.signature={chunkId:this.container,chunkSize:this.chunkSize,format:this.format,subChunks:this.getSubChunksIndex_(e)}}findChunk(t,i=!1){var r=this.signature.subChunks;let s=[];for(let e=0;e<r.length;e++)if(r[e].chunkId==t){if(!i)return r[e];s.push(r[e])}return"LIST"==t&&s.length?s:null}readString(e,t){var i=unpackString(e,this.head,this.head+t);return this.head+=t,i}readUInt32(e){e=binary_unpack(e,this.uInt32,this.head);return this.head+=4,e}getSubChunksIndex_(e){let t=[],i=this.head;for(;i<=e.length-8;)t.push(this.getSubChunkIndex_(e,i)),i+=8+t[t.length-1].chunkSize,i=i%2?i+1:i;return t}getSubChunkIndex_(e,t){let i={chunkId:this.getChunkId_(e,t),chunkSize:this.getChunkSize_(e,t)};return"LIST"==i.chunkId?(i.format=unpackString(e,t+8,t+12),this.head+=4,i.subChunks=this.getSubChunksIndex_(e)):(e=i.chunkSize%2?i.chunkSize+1:i.chunkSize,this.head=t+8+e,i.chunkData={start:t+8,end:this.head}),i}getChunkId_(e,t){return this.head+=4,unpackString(e,t,t+4)}getChunkSize_(e,t){return this.head+=4,binary_unpack(e,this.uInt32,t+4)}}class WaveFileReader extends RIFFFile{constructor(){super(),this.supported_containers.push("RF64"),this.fmt={chunkId:"",chunkSize:0,audioFormat:0,numChannels:0,sampleRate:0,byteRate:0,blockAlign:0,bitsPerSample:0,cbSize:0,validBitsPerSample:0,dwChannelMask:0,subformat:[]},this.fact={chunkId:"",chunkSize:0,dwSampleLength:0},this.cue={chunkId:"",chunkSize:0,dwCuePoints:0,points:[]},this.smpl={chunkId:"",chunkSize:0,dwManufacturer:0,dwProduct:0,dwSamplePeriod:0,dwMIDIUnityNote:0,dwMIDIPitchFraction:0,dwSMPTEFormat:0,dwSMPTEOffset:0,dwNumSampleLoops:0,dwSamplerData:0,loops:[]},this.bext={chunkId:"",chunkSize:0,description:"",originator:"",originatorReference:"",originationDate:"",originationTime:"",timeReference:[0,0],version:0,UMID:"",loudnessValue:0,loudnessRange:0,maxTruePeakLevel:0,maxMomentaryLoudness:0,maxShortTermLoudness:0,reserved:"",codingHistory:""},this.iXML={chunkId:"",chunkSize:0,value:""},this.ds64={chunkId:"",chunkSize:0,riffSizeHigh:0,riffSizeLow:0,dataSizeHigh:0,dataSizeLow:0,originationTime:0,sampleCountHigh:0,sampleCountLow:0},this.data={chunkId:"",chunkSize:0,samples:new Uint8Array(0)},this.LIST=[],this.junk={chunkId:"",chunkSize:0,chunkData:[]},this._PMX={chunkId:"",chunkSize:0,value:""},this.uInt16={bits:16,be:!1,signed:!1,fp:!1}}fromBuffer(e,t=!0){if(this.clearHeaders(),this.setSignature(e),this.uInt16.be=this.uInt32.be,"WAVE"!=this.format)throw Error('Could not find the "WAVE" format identifier');this.readDs64Chunk_(e),this.readFmtChunk_(e),this.readFactChunk_(e),this.readBextChunk_(e),this.readiXMLChunk_(e),this.readCueChunk_(e),this.readSmplChunk_(e),this.readDataChunk_(e,t),this.readJunkChunk_(e),this.readLISTChunk_(e),this.read_PMXChunk_(e)}clearHeaders(){var e=new WaveFileReader;Object.assign(this.fmt,e.fmt),Object.assign(this.fact,e.fact),Object.assign(this.cue,e.cue),Object.assign(this.smpl,e.smpl),Object.assign(this.bext,e.bext),Object.assign(this.iXML,e.iXML),Object.assign(this.ds64,e.ds64),Object.assign(this.data,e.data),this.LIST=[],Object.assign(this.junk,e.junk),Object.assign(this._PMX,e._PMX)}readFmtChunk_(e){var t=this.findChunk("fmt ");if(!t)throw Error('Could not find the "fmt " chunk');this.head=t.chunkData.start,this.fmt.chunkId=t.chunkId,this.fmt.chunkSize=t.chunkSize,this.fmt.audioFormat=this.readUInt16_(e),this.fmt.numChannels=this.readUInt16_(e),this.fmt.sampleRate=this.readUInt32(e),this.fmt.byteRate=this.readUInt32(e),this.fmt.blockAlign=this.readUInt16_(e),this.fmt.bitsPerSample=this.readUInt16_(e),this.readFmtExtension_(e)}readFmtExtension_(e){16<this.fmt.chunkSize&&(this.fmt.cbSize=this.readUInt16_(e),18<this.fmt.chunkSize&&(this.fmt.validBitsPerSample=this.readUInt16_(e),20<this.fmt.chunkSize&&(this.fmt.dwChannelMask=this.readUInt32(e),this.fmt.subformat=[this.readUInt32(e),this.readUInt32(e),this.readUInt32(e),this.readUInt32(e)])))}readFactChunk_(e){var t=this.findChunk("fact");t&&(this.head=t.chunkData.start,this.fact.chunkId=t.chunkId,this.fact.chunkSize=t.chunkSize,this.fact.dwSampleLength=this.readUInt32(e))}readCueChunk_(t){var e=this.findChunk("cue ");if(e){this.head=e.chunkData.start,this.cue.chunkId=e.chunkId,this.cue.chunkSize=e.chunkSize,this.cue.dwCuePoints=this.readUInt32(t);for(let e=0;e<this.cue.dwCuePoints;e++)this.cue.points.push({dwName:this.readUInt32(t),dwPosition:this.readUInt32(t),fccChunk:this.readString(t,4),dwChunkStart:this.readUInt32(t),dwBlockStart:this.readUInt32(t),dwSampleOffset:this.readUInt32(t)})}}readSmplChunk_(t){var e=this.findChunk("smpl");if(e){this.head=e.chunkData.start,this.smpl.chunkId=e.chunkId,this.smpl.chunkSize=e.chunkSize,this.smpl.dwManufacturer=this.readUInt32(t),this.smpl.dwProduct=this.readUInt32(t),this.smpl.dwSamplePeriod=this.readUInt32(t),this.smpl.dwMIDIUnityNote=this.readUInt32(t),this.smpl.dwMIDIPitchFraction=this.readUInt32(t),this.smpl.dwSMPTEFormat=this.readUInt32(t),this.smpl.dwSMPTEOffset=this.readUInt32(t),this.smpl.dwNumSampleLoops=this.readUInt32(t),this.smpl.dwSamplerData=this.readUInt32(t);for(let e=0;e<this.smpl.dwNumSampleLoops;e++)this.smpl.loops.push({dwName:this.readUInt32(t),dwType:this.readUInt32(t),dwStart:this.readUInt32(t),dwEnd:this.readUInt32(t),dwFraction:this.readUInt32(t),dwPlayCount:this.readUInt32(t)})}}readDataChunk_(e,t){var i=this.findChunk("data");if(!i)throw Error('Could not find the "data" chunk');this.data.chunkId="data",this.data.chunkSize=i.chunkSize,t&&(this.data.samples=e.slice(i.chunkData.start,i.chunkData.end))}readBextChunk_(e){var t=this.findChunk("bext");t&&(this.head=t.chunkData.start,this.bext.chunkId=t.chunkId,this.bext.chunkSize=t.chunkSize,this.bext.description=this.readString(e,256),this.bext.originator=this.readString(e,32),this.bext.originatorReference=this.readString(e,32),this.bext.originationDate=this.readString(e,10),this.bext.originationTime=this.readString(e,8),this.bext.timeReference=[this.readUInt32(e),this.readUInt32(e)],this.bext.version=this.readUInt16_(e),this.bext.UMID=this.readString(e,64),this.bext.loudnessValue=this.readUInt16_(e),this.bext.loudnessRange=this.readUInt16_(e),this.bext.maxTruePeakLevel=this.readUInt16_(e),this.bext.maxMomentaryLoudness=this.readUInt16_(e),this.bext.maxShortTermLoudness=this.readUInt16_(e),this.bext.reserved=this.readString(e,180),this.bext.codingHistory=this.readString(e,this.bext.chunkSize-602))}readiXMLChunk_(e){var t=this.findChunk("iXML");t&&(this.head=t.chunkData.start,this.iXML.chunkId=t.chunkId,this.iXML.chunkSize=t.chunkSize,this.iXML.value=unpackString(e,this.head,this.head+this.iXML.chunkSize))}readDs64Chunk_(e){var t=this.findChunk("ds64");if(t)this.head=t.chunkData.start,this.ds64.chunkId=t.chunkId,this.ds64.chunkSize=t.chunkSize,this.ds64.riffSizeHigh=this.readUInt32(e),this.ds64.riffSizeLow=this.readUInt32(e),this.ds64.dataSizeHigh=this.readUInt32(e),this.ds64.dataSizeLow=this.readUInt32(e),this.ds64.originationTime=this.readUInt32(e),this.ds64.sampleCountHigh=this.readUInt32(e),this.ds64.sampleCountLow=this.readUInt32(e);else if("RF64"==this.container)throw Error('Could not find the "ds64" chunk')}readLISTChunk_(t){var i=this.findChunk("LIST",!0);if(null!==i)for(let e=0;e<i.length;e++){var r=i[e];this.LIST.push({chunkId:r.chunkId,chunkSize:r.chunkSize,format:r.format,subChunks:[]});for(let e=0;e<r.subChunks.length;e++)this.readLISTSubChunks_(r.subChunks[e],r.format,t)}}readLISTSubChunks_(e,t,i){"adtl"==t?-1<["labl","note","ltxt"].indexOf(e.chunkId)&&this.readLISTadtlSubChunks_(i,e):"INFO"==t&&this.readLISTINFOSubChunks_(i,e)}readLISTadtlSubChunks_(e,t){this.head=t.chunkData.start;let i={chunkId:t.chunkId,chunkSize:t.chunkSize,dwName:this.readUInt32(e)};"ltxt"==t.chunkId?(i.dwSampleLength=this.readUInt32(e),i.dwPurposeID=this.readUInt32(e),i.dwCountry=this.readUInt16_(e),i.dwLanguage=this.readUInt16_(e),i.dwDialect=this.readUInt16_(e),i.dwCodePage=this.readUInt16_(e),i.value=""):i.value=this.readZSTR_(e,this.head),this.LIST[this.LIST.length-1].subChunks.push(i)}readLISTINFOSubChunks_(e,t){this.head=t.chunkData.start,this.LIST[this.LIST.length-1].subChunks.push({chunkId:t.chunkId,chunkSize:t.chunkSize,value:this.readZSTR_(e,this.head)})}readJunkChunk_(e){var t=this.findChunk("junk");t&&(this.junk={chunkId:t.chunkId,chunkSize:t.chunkSize,chunkData:[].slice.call(e.slice(t.chunkData.start,t.chunkData.end))})}read_PMXChunk_(e){var t=this.findChunk("_PMX");t&&(this.head=t.chunkData.start,this._PMX.chunkId=t.chunkId,this._PMX.chunkSize=t.chunkSize,this._PMX.value=unpackString(e,this.head,this.head+this._PMX.chunkSize))}readZSTR_(t,i=0){for(let e=i;e<t.length&&(this.head++,0!==t[e]);e++);return unpackString(t,i,this.head-1)}readUInt16_(e){e=binary_unpack(e,this.uInt16,this.head);return this.head+=2,e}}function writeString(e,t){let i=packString(e);for(let e=i.length;e<t;e++)i.push(0);return i}class WaveFileParser extends WaveFileReader{toBuffer(){this.uInt16.be="RIFX"===this.container,this.uInt32.be=this.uInt16.be;var t=[this.getJunkBytes_(),this.getDs64Bytes_(),this.getBextBytes_(),this.getiXMLBytes_(),this.getFmtBytes_(),this.getFactBytes_(),packString(this.data.chunkId),binary_pack(this.data.samples.length,this.uInt32),this.data.samples,this.getCueBytes_(),this.getSmplBytes_(),this.getLISTBytes_(),this.get_PMXBytes_()];let i=0;for(let e=0;e<t.length;e++)i+=t[e].length;let r=new Uint8Array(i+12),s=0;s=packStringTo(this.container,r,s),s=packTo(i+4,this.uInt32,r,s),s=packStringTo(this.format,r,s);for(let e=0;e<t.length;e++)r.set(t[e],s),s+=t[e].length;return r}getBextBytes_(){let e=[];return this.enforceBext_(),this.bext.chunkId&&(this.bext.chunkSize=602+this.bext.codingHistory.length,e=e.concat(packString(this.bext.chunkId),binary_pack(602+this.bext.codingHistory.length,this.uInt32),writeString(this.bext.description,256),writeString(this.bext.originator,32),writeString(this.bext.originatorReference,32),writeString(this.bext.originationDate,10),writeString(this.bext.originationTime,8),binary_pack(this.bext.timeReference[0],this.uInt32),binary_pack(this.bext.timeReference[1],this.uInt32),binary_pack(this.bext.version,this.uInt16),writeString(this.bext.UMID,64),binary_pack(this.bext.loudnessValue,this.uInt16),binary_pack(this.bext.loudnessRange,this.uInt16),binary_pack(this.bext.maxTruePeakLevel,this.uInt16),binary_pack(this.bext.maxMomentaryLoudness,this.uInt16),binary_pack(this.bext.maxShortTermLoudness,this.uInt16),writeString(this.bext.reserved,180),writeString(this.bext.codingHistory,this.bext.codingHistory.length))),this.enforceByteLen_(e),e}enforceBext_(){for(var e in this.bext)if(this.bext.hasOwnProperty(e)&&this.bext[e]&&"timeReference"!=e){this.bext.chunkId="bext";break}(this.bext.timeReference[0]||this.bext.timeReference[1])&&(this.bext.chunkId="bext")}getiXMLBytes_(){let e=[];var t;return this.iXML.chunkId&&(t=packString(this.iXML.value),this.iXML.chunkSize=t.length,e=e.concat(packString(this.iXML.chunkId),binary_pack(this.iXML.chunkSize,this.uInt32),t)),this.enforceByteLen_(e),e}getDs64Bytes_(){let e=[];return this.ds64.chunkId&&(e=e.concat(packString(this.ds64.chunkId),binary_pack(this.ds64.chunkSize,this.uInt32),binary_pack(this.ds64.riffSizeHigh,this.uInt32),binary_pack(this.ds64.riffSizeLow,this.uInt32),binary_pack(this.ds64.dataSizeHigh,this.uInt32),binary_pack(this.ds64.dataSizeLow,this.uInt32),binary_pack(this.ds64.originationTime,this.uInt32),binary_pack(this.ds64.sampleCountHigh,this.uInt32),binary_pack(this.ds64.sampleCountLow,this.uInt32))),this.enforceByteLen_(e),e}getCueBytes_(){let e=[];var t;return this.cue.chunkId&&(t=this.getCuePointsBytes_(),e=e.concat(packString(this.cue.chunkId),binary_pack(t.length+4,this.uInt32),binary_pack(this.cue.dwCuePoints,this.uInt32),t)),this.enforceByteLen_(e),e}getCuePointsBytes_(){let t=[];for(let e=0;e<this.cue.dwCuePoints;e++)t=t.concat(binary_pack(this.cue.points[e].dwName,this.uInt32),binary_pack(this.cue.points[e].dwPosition,this.uInt32),packString(this.cue.points[e].fccChunk),binary_pack(this.cue.points[e].dwChunkStart,this.uInt32),binary_pack(this.cue.points[e].dwBlockStart,this.uInt32),binary_pack(this.cue.points[e].dwSampleOffset,this.uInt32));return t}getSmplBytes_(){let e=[];var t;return this.smpl.chunkId&&(t=this.getSmplLoopsBytes_(),e=e.concat(packString(this.smpl.chunkId),binary_pack(t.length+36,this.uInt32),binary_pack(this.smpl.dwManufacturer,this.uInt32),binary_pack(this.smpl.dwProduct,this.uInt32),binary_pack(this.smpl.dwSamplePeriod,this.uInt32),binary_pack(this.smpl.dwMIDIUnityNote,this.uInt32),binary_pack(this.smpl.dwMIDIPitchFraction,this.uInt32),binary_pack(this.smpl.dwSMPTEFormat,this.uInt32),binary_pack(this.smpl.dwSMPTEOffset,this.uInt32),binary_pack(this.smpl.dwNumSampleLoops,this.uInt32),binary_pack(this.smpl.dwSamplerData,this.uInt32),t)),this.enforceByteLen_(e),e}getSmplLoopsBytes_(){let t=[];for(let e=0;e<this.smpl.dwNumSampleLoops;e++)t=t.concat(binary_pack(this.smpl.loops[e].dwName,this.uInt32),binary_pack(this.smpl.loops[e].dwType,this.uInt32),binary_pack(this.smpl.loops[e].dwStart,this.uInt32),binary_pack(this.smpl.loops[e].dwEnd,this.uInt32),binary_pack(this.smpl.loops[e].dwFraction,this.uInt32),binary_pack(this.smpl.loops[e].dwPlayCount,this.uInt32));return t}getFactBytes_(){let e=[];return this.fact.chunkId&&(e=e.concat(packString(this.fact.chunkId),binary_pack(this.fact.chunkSize,this.uInt32),binary_pack(this.fact.dwSampleLength,this.uInt32))),this.enforceByteLen_(e),e}getFmtBytes_(){if(this.fmt.chunkId){var e=[].concat(packString(this.fmt.chunkId),binary_pack(this.fmt.chunkSize,this.uInt32),binary_pack(this.fmt.audioFormat,this.uInt16),binary_pack(this.fmt.numChannels,this.uInt16),binary_pack(this.fmt.sampleRate,this.uInt32),binary_pack(this.fmt.byteRate,this.uInt32),binary_pack(this.fmt.blockAlign,this.uInt16),binary_pack(this.fmt.bitsPerSample,this.uInt16),this.getFmtExtensionBytes_());return this.enforceByteLen_(e),e}throw Error('Could not find the "fmt " chunk')}getFmtExtensionBytes_(){let e=[];return 16<this.fmt.chunkSize&&(e=e.concat(binary_pack(this.fmt.cbSize,this.uInt16))),18<this.fmt.chunkSize&&(e=e.concat(binary_pack(this.fmt.validBitsPerSample,this.uInt16))),20<this.fmt.chunkSize&&(e=e.concat(binary_pack(this.fmt.dwChannelMask,this.uInt32))),24<this.fmt.chunkSize&&(e=e.concat(binary_pack(this.fmt.subformat[0],this.uInt32),binary_pack(this.fmt.subformat[1],this.uInt32),binary_pack(this.fmt.subformat[2],this.uInt32),binary_pack(this.fmt.subformat[3],this.uInt32))),e}getLISTBytes_(){let t=[];for(let e=0;e<this.LIST.length;e++){var i=this.getLISTSubChunksBytes_(this.LIST[e].subChunks,this.LIST[e].format);t=t.concat(packString(this.LIST[e].chunkId),binary_pack(i.length+4,this.uInt32),packString(this.LIST[e].format),i)}return this.enforceByteLen_(t),t}getLISTSubChunksBytes_(i,r){let s=[];for(let e=0,t=i.length;e<t;e++)"INFO"==r?s=s.concat(this.getLISTINFOSubChunksBytes_(i[e])):"adtl"==r&&(s=s.concat(this.getLISTadtlSubChunksBytes_(i[e]))),this.enforceByteLen_(s);return s}getLISTINFOSubChunksBytes_(e){let t=[];var i=writeString(e.value,e.value.length);return t=t.concat(packString(e.chunkId),binary_pack(i.length+1,this.uInt32),i),t.push(0),t}getLISTadtlSubChunksBytes_(e){let t=[];var i;return-1<["labl","note"].indexOf(e.chunkId)?(i=writeString(e.value,e.value.length),t=t.concat(packString(e.chunkId),binary_pack(i.length+4+1,this.uInt32),binary_pack(e.dwName,this.uInt32),i),t.push(0)):"ltxt"==e.chunkId&&(t=t.concat(this.getLtxtChunkBytes_(e))),t}getLtxtChunkBytes_(e){return[].concat(packString(e.chunkId),binary_pack(e.value.length+20,this.uInt32),binary_pack(e.dwName,this.uInt32),binary_pack(e.dwSampleLength,this.uInt32),binary_pack(e.dwPurposeID,this.uInt32),binary_pack(e.dwCountry,this.uInt16),binary_pack(e.dwLanguage,this.uInt16),binary_pack(e.dwDialect,this.uInt16),binary_pack(e.dwCodePage,this.uInt16),writeString(e.value,e.value.length))}get_PMXBytes_(){let e=[];var t;return this._PMX.chunkId&&(t=packString(this._PMX.value),this._PMX.chunkSize=t.length,e=e.concat(packString(this._PMX.chunkId),binary_pack(this._PMX.chunkSize,this.uInt32),t)),this.enforceByteLen_(e),e}getJunkBytes_(){let e=[];return this.junk.chunkId?e.concat(packString(this.junk.chunkId),binary_pack(this.junk.chunkData.length,this.uInt32),this.junk.chunkData):(this.enforceByteLen_(e),e)}enforceByteLen_(e){e.length%2&&e.push(0)}}function interleave(s){let a=[];if(0<s.length)if(s[0].constructor!==Number){a=new Float64Array(s[0].length*s.length);for(let i=0,e=s[0].length,r=0;i<e;i++)for(let e=0,t=s.length;e<t;e++,r++)a[r]=s[e][i]}else a=s;return a}function deInterleave(r,s,t=Float64Array){let a=[];for(let e=0;e<s;e++)a[e]=new t(r.length/s);for(let i=0;i<s;i++)for(let e=i,t=0;e<r.length;e+=s,t++)a[i][t]=r[e];return a}function validateNumChannels(e,t){return!(e<1||65535<e*t/8)}function validateSampleRate(e,t,i){return!(i<1||4294967295<e*(t/8)*i)}class WaveFileCreator extends WaveFileParser{constructor(){super(),this.bitDepth="0",this.dataType={bits:0,be:!1},this.WAV_AUDIO_FORMATS={4:17,8:1,"8a":6,"8m":7,16:1,24:1,32:1,"32f":3,64:3}}fromScratch(e,t,i,r,s){s=s||{},this.clearHeaders(),this.newWavFile_(e,t,i,r,s)}fromBuffer(e,t=!0){super.fromBuffer(e,t),this.bitDepthFromFmt_(),this.updateDataType_()}toBuffer(){return this.validateWavHeader_(),super.toBuffer()}getSamples(e=!1,t=Float64Array){var i=new t(this.data.samples.length/(this.dataType.bits/8));return unpackArrayTo(this.data.samples,this.dataType,i,0,this.data.samples.length),!e&&1<this.fmt.numChannels?deInterleave(i,this.fmt.numChannels,t):i}getSample(e){if((e*=this.dataType.bits/8)+this.dataType.bits/8>this.data.samples.length)throw new Error("Range error");return binary_unpack(this.data.samples.slice(e,e+this.dataType.bits/8),this.dataType)}setSample(e,t){if((e*=this.dataType.bits/8)+this.dataType.bits/8>this.data.samples.length)throw new Error("Range error");packTo(t,this.dataType,this.data.samples,e,!0)}getiXML(){return this.iXML.value}setiXML(e){if("string"!=typeof e)throw new TypeError("iXML value must be a string.");this.iXML.value=e,this.iXML.chunkId="iXML"}get_PMX(){return this._PMX.value}set_PMX(e){if("string"!=typeof e)throw new TypeError("_PMX value must be a string.");this._PMX.value=e,this._PMX.chunkId="_PMX"}newWavFile_(e,t,i,r,s){s.container||(s.container="RIFF"),this.container=s.container,this.bitDepth=i,r=interleave(r),this.updateDataType_();var a=this.dataType.bits/8;this.data.samples=new Uint8Array(r.length*a),packArrayTo(r,this.dataType,this.data.samples,0,!0),this.makeWavHeader_(i,e,t,a,this.data.samples.length,s),this.data.chunkId="data",this.data.chunkSize=this.data.samples.length,this.validateWavHeader_()}makeWavHeader_(e,t,i,r,s,a){"4"==e?this.createADPCMHeader_(e,t,i,r,s,a):"8a"==e||"8m"==e?this.createALawMulawHeader_(e,t,i,r,s,a):-1==Object.keys(this.WAV_AUDIO_FORMATS).indexOf(e)||2<t?this.createExtensibleHeader_(e,t,i,r,s,a):this.createPCMHeader_(e,t,i,r,s,a)}createPCMHeader_(e,t,i,r,s,a){this.container=a.container,this.chunkSize=36+s,this.format="WAVE",this.bitDepth=e,this.fmt={chunkId:"fmt ",chunkSize:16,audioFormat:this.WAV_AUDIO_FORMATS[e]||65534,numChannels:t,sampleRate:i,byteRate:t*r*i,blockAlign:t*r,bitsPerSample:parseInt(e,10),cbSize:0,validBitsPerSample:0,dwChannelMask:0,subformat:[]}}createADPCMHeader_(e,t,i,r,s,a){this.createPCMHeader_(e,t,i,r,s,a),this.chunkSize=40+s,this.fmt.chunkSize=20,this.fmt.byteRate=4055,this.fmt.blockAlign=256,this.fmt.bitsPerSample=4,this.fmt.cbSize=2,this.fmt.validBitsPerSample=505,this.fact={chunkId:"fact",chunkSize:4,dwSampleLength:2*s}}createExtensibleHeader_(e,t,i,r,s,a){this.createPCMHeader_(e,t,i,r,s,a),this.chunkSize=60+s,this.fmt.chunkSize=40,this.fmt.bitsPerSample=1+(parseInt(e,10)-1|7),this.fmt.cbSize=22,this.fmt.validBitsPerSample=parseInt(e,10),this.fmt.dwChannelMask=dwChannelMask_(t),this.fmt.subformat=[1,1048576,2852126848,1905997824]}createALawMulawHeader_(e,t,i,r,s,a){this.createPCMHeader_(e,t,i,r,s,a),this.chunkSize=40+s,this.fmt.chunkSize=20,this.fmt.cbSize=2,this.fmt.validBitsPerSample=8,this.fact={chunkId:"fact",chunkSize:4,dwSampleLength:s}}bitDepthFromFmt_(){3===this.fmt.audioFormat&&32===this.fmt.bitsPerSample?this.bitDepth="32f":6===this.fmt.audioFormat?this.bitDepth="8a":7===this.fmt.audioFormat?this.bitDepth="8m":this.bitDepth=this.fmt.bitsPerSample.toString()}validateBitDepth_(){if(this.WAV_AUDIO_FORMATS[this.bitDepth])return!0;if(8<parseInt(this.bitDepth,10)&&parseInt(this.bitDepth,10)<54)return!0;throw new Error("Invalid bit depth.")}updateDataType_(){this.dataType={bits:1+(parseInt(this.bitDepth,10)-1|7),fp:"32f"==this.bitDepth||"64"==this.bitDepth,signed:"8"!=this.bitDepth,be:"RIFX"==this.container},-1<["4","8a","8m"].indexOf(this.bitDepth)&&(this.dataType.bits=8,this.dataType.signed=!1)}validateWavHeader_(){if(this.validateBitDepth_(),!validateNumChannels(this.fmt.numChannels,this.fmt.bitsPerSample))throw new Error("Invalid number of channels.");if(!validateSampleRate(this.fmt.numChannels,this.fmt.bitsPerSample,this.fmt.sampleRate))throw new Error("Invalid sample rate.")}}function dwChannelMask_(e){let t=0;return 1===e?t=4:2===e?t=3:4===e?t=51:6===e?t=63:8===e&&(t=1599),t}class WaveFileTagEditor extends WaveFileCreator{getTag(e){e=this.getTagIndex_(e);return null!==e.TAG?this.LIST[e.LIST].subChunks[e.TAG].value:null}setTag(e,t){e=fixRIFFTag_(e);var i=this.getTagIndex_(e);null!==i.TAG?(this.LIST[i.LIST].subChunks[i.TAG].chunkSize=t.length+1,this.LIST[i.LIST].subChunks[i.TAG].value=t):null!==i.LIST?this.LIST[i.LIST].subChunks.push({chunkId:e,chunkSize:t.length+1,value:t}):(this.LIST.push({chunkId:"LIST",chunkSize:8+t.length+1,format:"INFO",subChunks:[]}),this.LIST[this.LIST.length-1].subChunks.push({chunkId:e,chunkSize:t.length+1,value:t}))}deleteTag(e){e=this.getTagIndex_(e);return null!==e.TAG&&(this.LIST[e.LIST].subChunks.splice(e.TAG,1),!0)}listTags(){var i=this.getLISTIndex("INFO");let r={};if(null!==i)for(let e=0,t=this.LIST[i].subChunks.length;e<t;e++)r[this.LIST[i].subChunks[e].chunkId]=this.LIST[i].subChunks[e].value;return r}getLISTIndex(i){for(let e=0,t=this.LIST.length;e<t;e++)if(this.LIST[e].format==i)return e;return null}getTagIndex_(r){let s={LIST:null,TAG:null};for(let i=0,e=this.LIST.length;i<e;i++)if("INFO"==this.LIST[i].format){s.LIST=i;for(let e=0,t=this.LIST[i].subChunks.length;e<t;e++)if(this.LIST[i].subChunks[e].chunkId==r){s.TAG=e;break}break}return s}}function fixRIFFTag_(i){if(i.constructor!==String)throw new Error("Invalid tag name.");if(i.length<4)for(let e=0,t=4-i.length;e<t;e++)i+=" ";return i}class WaveFileCueEditor extends WaveFileTagEditor{listCuePoints(){let i=this.getCuePoints_();for(let e=0,t=i.length;e<t;e++)i[e].position=i[e].dwSampleOffset/this.fmt.sampleRate*1e3,i[e].dwSampleLength?(i[e].end=i[e].dwSampleLength/this.fmt.sampleRate*1e3,i[e].end+=i[e].position):i[e].end=null,delete i[e].value;return i}setCuePoint(e){this.cue.chunkId="cue ",e.label||(e.label="");var t=this.getCuePoints_();this.clearLISTadtl_(),this.cue.points=[],e.dwSampleOffset=e.position*this.fmt.sampleRate/1e3,e.dwSampleLength=0,e.end&&(e.dwSampleLength=e.end*this.fmt.sampleRate/1e3-e.dwSampleOffset),0===t.length?this.setCuePoint_(e,1):this.setCuePointInOrder_(t,e),this.cue.dwCuePoints=this.cue.points.length}deleteCuePoint(t){this.cue.chunkId="cue ";var i=this.getCuePoints_();this.clearLISTadtl_();var r=this.cue.points.length;this.cue.points=[];for(let e=0;e<r;e++)e+1!==t&&this.setCuePoint_(i[e],e+1);this.cue.dwCuePoints=this.cue.points.length,this.cue.dwCuePoints?this.cue.chunkId="cue ":(this.cue.chunkId="",this.clearLISTadtl_())}updateLabel(i,r){var s=this.getLISTIndex("adtl");if(null!==s)for(let e=0,t=this.LIST[s].subChunks.length;e<t;e++)this.LIST[s].subChunks[e].dwName==i&&(this.LIST[s].subChunks[e].value=r)}getCuePoints_(){let i=[];for(let t=0;t<this.cue.points.length;t++){var r=this.cue.points[t];let e=this.getDataForCuePoint_(r.dwName);e.label=e.value||"",e.dwPosition=r.dwPosition,e.fccChunk=r.fccChunk,e.dwChunkStart=r.dwChunkStart,e.dwBlockStart=r.dwBlockStart,e.dwSampleOffset=r.dwSampleOffset,i.push(e)}return i}getDataForCuePoint_(e){var t=this.getLISTIndex("adtl"),i={};return null!==t&&this.getCueDataFromLIST_(i,t,e),i}getCueDataFromLIST_(i,r,s){for(let e=0,t=this.LIST[r].subChunks.length;e<t;e++){var a;this.LIST[r].subChunks[e].dwName==s&&(a=this.LIST[r].subChunks[e],i.value=a.value||i.value,i.dwName=a.dwName||0,i.dwSampleLength=a.dwSampleLength||0,i.dwPurposeID=a.dwPurposeID||0,i.dwCountry=a.dwCountry||0,i.dwLanguage=a.dwLanguage||0,i.dwDialect=a.dwDialect||0,i.dwCodePage=a.dwCodePage||0)}}setCuePoint_(e,t){this.cue.points.push({dwName:t,dwPosition:e.dwPosition||0,fccChunk:e.fccChunk||"data",dwChunkStart:e.dwChunkStart||0,dwBlockStart:e.dwBlockStart||0,dwSampleOffset:e.dwSampleOffset}),this.setLabl_(e,t)}setCuePointInOrder_(t,i){let r=!1;for(let e=0;e<t.length;e++)t[e].dwSampleOffset>i.dwSampleOffset&&!r?(this.setCuePoint_(i,e+1),this.setCuePoint_(t[e],e+2),r=!0):this.setCuePoint_(t[e],r?e+2:e+1);r||this.setCuePoint_(i,this.cue.points.length+1)}clearLISTadtl_(){for(let e=0,t=this.LIST.length;e<t;e++)"adtl"==this.LIST[e].format&&this.LIST.splice(e)}setLabl_(e,t){let i=this.getLISTIndex("adtl");null===i&&(this.LIST.push({chunkId:"LIST",chunkSize:4,format:"adtl",subChunks:[]}),i=this.LIST.length-1),this.setLabelText_(i,e,t),e.dwSampleLength&&this.setLtxtChunk_(i,e,t)}setLabelText_(e,t,i){this.LIST[e].subChunks.push({chunkId:"labl",chunkSize:4,dwName:i,value:t.label}),this.LIST[e].chunkSize+=12}setLtxtChunk_(e,t,i){this.LIST[e].subChunks.push({chunkId:"ltxt",chunkSize:20,dwName:i,dwSampleLength:t.dwSampleLength,dwPurposeID:t.dwPurposeID||0,dwCountry:t.dwCountry||0,dwLanguage:t.dwLanguage||0,dwDialect:t.dwDialect||0,dwCodePage:t.dwCodePage||0,value:t.label}),this.LIST[e].chunkSize+=28}}class Interpolator{constructor(e,t,i){this.length_=e,this.scaleFactor_=(e-1)/t,this.interpolate=this.sinc,"point"===i.method?this.interpolate=this.point:"linear"===i.method?this.interpolate=this.linear:"cubic"===i.method&&(this.interpolate=this.cubic),this.tangentFactor_=1-Math.max(0,Math.min(1,i.tension||0)),this.sincFilterSize_=i.sincFilterSize||1,this.kernel_=sincKernel_(i.sincWindow||window_)}point(e,t){return this.getClippedInput_(Math.round(this.scaleFactor_*e),t)}linear(e,t){e=this.scaleFactor_*e;var i=Math.floor(e);return(1-(e-=i))*this.getClippedInput_(i,t)+e*this.getClippedInput_(i+1,t)}cubic(e,t){e=this.scaleFactor_*e;var i=Math.floor(e),r=[this.getTangent_(i,t),this.getTangent_(i+1,t)],s=[this.getClippedInput_(i,t),this.getClippedInput_(i+1,t)],t=(e-=i)*e,i=e*t;return(2*i-3*t+1)*s[0]+(i-2*t+e)*r[0]+(-2*i+3*t)*s[1]+(i-t)*r[1]}sinc(t,i){t=this.scaleFactor_*t;var e=Math.floor(t),r=e-this.sincFilterSize_+1,s=e+this.sincFilterSize_;let a=0;for(let e=r;e<=s;e++)a+=this.kernel_(t-e)*this.getClippedInput_(e,i);return a}getTangent_(e,t){return this.tangentFactor_*(this.getClippedInput_(e+1,t)-this.getClippedInput_(e-1,t))/2}getClippedInput_(e,t){return 0<=e&&e<this.length_?t[e]:0}}function window_(e){return Math.exp(-e/2*e/2)}function sincKernel_(t){return function(e){return sinc_(e)*t(e)}}function sinc_(e){return 0===e?1:Math.sin(Math.PI*e)/(Math.PI*e)}class FIRLPF{constructor(t,e,i){var r=2*Math.PI*i/e;let s=0;this.filters=[];for(let e=0;e<=t;e++)e-t/2==0?this.filters[e]=r:(this.filters[e]=Math.sin(r*(e-t/2))/(e-t/2),this.filters[e]*=.54-.46*Math.cos(2*Math.PI*e/t)),s+=this.filters[e];for(let e=0;e<=t;e++)this.filters[e]/=s;this.z=this.initZ_()}filter(e){this.z.buf[this.z.pointer]=e;let i=0;for(let e=0,t=this.z.buf.length;e<t;e++)i+=this.filters[e]*this.z.buf[(this.z.pointer+e)%this.z.buf.length];return this.z.pointer=(this.z.pointer+1)%this.z.buf.length,i}reset(){this.z=this.initZ_()}initZ_(){let t=[];for(let e=0;e<this.filters.length-1;e++)t.push(0);return{buf:t,pointer:0}}}class ButterworthLPF{constructor(t,i,r){let s=[];for(let e=0;e<t;e++)s.push(this.getCoeffs_({Fs:i,Fc:r,Q:.5/Math.sin(Math.PI/(2*t)*(e+.5))}));this.stages=[];for(let e=0;e<s.length;e++)this.stages[e]={b0:s[e].b[0],b1:s[e].b[1],b2:s[e].b[2],a1:s[e].a[0],a2:s[e].a[1],k:s[e].k,z:[0,0]}}filter(e){let i=e;for(let e=0,t=this.stages.length;e<t;e++)i=this.runStage_(e,i);return i}getCoeffs_(e){let t={a:[],b:[]};e=this.preCalc_(e,t);return t.k=1,t.b.push((1-e.cw)/(2*e.a0)),t.b.push(2*t.b[0]),t.b.push(t.b[0]),t}preCalc_(e,t){let i={};var r=2*Math.PI*e.Fc/e.Fs;return i.alpha=Math.sin(r)/(2*e.Q),i.cw=Math.cos(r),i.a0=1+i.alpha,t.a0=i.a0,t.a.push(-2*i.cw/i.a0),t.k=1,t.a.push((1-i.alpha)/i.a0),i}runStage_(e,t){var i=t*this.stages[e].k-this.stages[e].a1*this.stages[e].z[0]-this.stages[e].a2*this.stages[e].z[1],t=this.stages[e].b0*i+this.stages[e].b1*this.stages[e].z[0]+this.stages[e].b2*this.stages[e].z[1];return this.stages[e].z[1]=this.stages[e].z[0],this.stages[e].z[0]=i,t}reset(){for(let e=0;e<this.stages.length;e++)this.stages[e].z=[0,0]}}const DEFAULT_LPF_USE={point:!1,linear:!1,cubic:!0,sinc:!0},DEFAULT_LPF_ORDER={IIR:16,FIR:71},DEFAULT_LPF={IIR:ButterworthLPF,FIR:FIRLPF};function resample(e,t,i,r=null){r=r||{};var s=new Float64Array(e.length*((i-t)/t+1));r.method=r.method||"cubic";var a=new Interpolator(e.length,s.length,{method:r.method,tension:r.tension||0,sincFilterSize:r.sincFilterSize||6,sincWindow:r.sincWindow||void 0,clip:r.clip||"mirror"});if(void 0===r.LPF&&(r.LPF=DEFAULT_LPF_USE[r.method]),r.LPF){r.LPFType=r.LPFType||"IIR";const n=DEFAULT_LPF[r.LPFType];t<i?upsample_(e,s,a,new n(r.LPForder||DEFAULT_LPF_ORDER[r.LPFType],i,t/2)):downsample_(e,s,a,new n(r.LPForder||DEFAULT_LPF_ORDER[r.LPFType],t,i/2))}else resample_(e,s,a);return s}function resample_(i,r,s){for(let e=0,t=r.length;e<t;e++)r[e]=s.interpolate(e,i)}function upsample_(i,r,s,a){for(let e=0,t=r.length;e<t;e++)r[e]=a.filter(s.interpolate(e,i));a.reset();for(let e=r.length-1;0<=e;e--)r[e]=a.filter(r[e])}function downsample_(i,e,t,r){for(let e=0,t=i.length;e<t;e++)i[e]=r.filter(i[e]);r.reset();for(let e=i.length-1;0<=e;e--)i[e]=r.filter(i[e]);resample_(i,e,t)}class WaveFileConverter extends WaveFileCueEditor{toRIFF(){var e=new Float64Array(outputSize_(this.data.samples.length,this.dataType.bits/8));unpackArrayTo(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,this.bitDepth,e,{container:"RIFF"})}toRIFX(){var e=new Float64Array(outputSize_(this.data.samples.length,this.dataType.bits/8));unpackArrayTo(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,this.bitDepth,e,{container:"RIFX"})}toIMAADPCM(){if(8e3!==this.fmt.sampleRate)throw new Error("Only 8000 Hz files can be compressed as IMA-ADPCM.");if(1!==this.fmt.numChannels)throw new Error("Only mono files can be compressed as IMA-ADPCM.");this.assure16Bit_();var e=new Int16Array(outputSize_(this.data.samples.length,2));unpackArrayTo(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"4",imaadpcm_encode(e),{container:this.correctContainer_()})}fromIMAADPCM(e="16"){let s;if(1<this.fmt.numChannels){if(2<this.fmt.numChannels)throw new Error("Only 1 or 2 channels are supported");var a=this.data.samples.length/2;let t=new Uint8Array(a),i=new Uint8Array(a),r=0;for(let e=0;e<a;e++)e&&e%4==0&&(r+=4),t[e]=this.data.samples[r+e],i[e]=this.data.samples[r+e+4];s=[imaadpcm_decode(t,this.fmt.blockAlign/2),imaadpcm_decode(i,this.fmt.blockAlign/2)]}else s=imaadpcm_decode(this.data.samples,this.fmt.blockAlign);this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",s,{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toALaw(){this.assure16Bit_();var e=new Int16Array(outputSize_(this.data.samples.length,2));unpackArrayTo(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"8a",alaw_encode(e),{container:this.correctContainer_()})}fromALaw(e="16"){this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",alaw_decode(this.data.samples),{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toMuLaw(){this.assure16Bit_();var e=new Int16Array(outputSize_(this.data.samples.length,2));unpackArrayTo(this.data.samples,this.dataType,e,0,this.data.samples.length),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"8m",mulaw_encode(e),{container:this.correctContainer_()})}fromMuLaw(e="16"){this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,"16",mulaw_decode(this.data.samples),{container:this.correctContainer_()}),"16"!=e&&this.toBitDepth(e)}toBitDepth(e,t=!0){let i=e,r=this.bitDepth;t||("32f"!=e&&(i=this.dataType.bits.toString()),r=""+this.dataType.bits),this.assureUncompressed_();var s=this.getSamples(!0),t=new Float64Array(s.length);changeBitDepth(s,r,t,i),this.fromExisting_(this.fmt.numChannels,this.fmt.sampleRate,e,t,{container:this.correctContainer_()})}toSampleRate(t,i){this.validateResample_(t);var r=this.getSamples();let s=[];if(r.constructor===Float64Array)s=resample(r,this.fmt.sampleRate,t,i);else for(let e=0;e<r.length;e++)s.push(resample(r[e],this.fmt.sampleRate,t,i));this.fromExisting_(this.fmt.numChannels,t,this.bitDepth,s,{container:this.correctContainer_()})}validateResample_(e){if(!validateSampleRate(this.fmt.numChannels,this.fmt.bitsPerSample,e))throw new Error("Invalid sample rate.");if(-1<["4","8a","8m"].indexOf(this.bitDepth))throw new Error("wavefile can't change the sample rate of compressed files.")}assure16Bit_(){this.assureUncompressed_(),"16"!=this.bitDepth&&this.toBitDepth("16")}assureUncompressed_(){"8a"==this.bitDepth?this.fromALaw():"8m"==this.bitDepth?this.fromMuLaw():"4"==this.bitDepth&&this.fromIMAADPCM()}correctContainer_(){return"RF64"==this.container?"RIFF":this.container}fromExisting_(e,t,i,r,s){var a=new WaveFileCueEditor;Object.assign(this.fmt,a.fmt),Object.assign(this.fact,a.fact),Object.assign(this.ds64,a.ds64),Object.assign(this.data,a.data),this.newWavFile_(e,t,i,r,s)}}function outputSize_(e,t){let i=e/t;return i%2&&i++,i}class WaveFile extends WaveFileConverter{constructor(e){super(),e&&this.fromBuffer(e)}fromBase64(e){this.fromBuffer(decode(e))}toBase64(){return encode(this.toBuffer())}toDataURI(){return"data:audio/wav;base64,"+this.toBase64()}fromDataURI(e){this.fromBase64(e.replace("data:audio/wav;base64,",""))}}class WavFile{constructor(e){e instanceof Uint8Array?this.fromRawData(e):e instanceof VirtualFile&&this.fromVirtualFile(e)}fromRawData(e){return this.rawData=e,this}fromVirtualFile(e){e=e.stream;return this.rawData=new Uint8Array(e.buffer,e.byteOffset,e.byteLength),this}getRawData(){return this.rawData}getData(){if(!this.decodedData){if(!this.rawData)throw new Error("No data loaded");this.decodedData=this.decodeData(this.rawData),this.rawData=void 0}return this.decodedData}setData(e){this.rawData=void 0,this.decodedData=e}decodeData(e){let t=new WaveFile(e);return"4"===t.bitDepth&&t.fromIMAADPCM(),t.toBuffer()}isRawImaAdpcm(){return this.rawData&&"4"===new WaveFile(this.rawData).bitDepth}}class LazyAsyncResourceCollection{constructor(e,t=!0){this.resourceFactory=e,this.cache=t,this.resources=new Map}setDir(e){this.rfsDir=e}set(e,t){this.resources.set(e,t)}async has(e){return!!this.resources.has(e)||(await this.rfsDir?.containsEntry(e)??!1)}async get(e){let t;return t=this.resources.get(e),!t&&await this.rfsDir?.containsEntry(e)&&(t=await this.resourceFactory(await this.rfsDir.getRawFile(e)),this.cache&&this.resources.set(e,t)),t}clear(){this.resources.clear()}}class Mp3File{constructor(e){this.file=e}asFile(){return new File([this.file],this.file.name,{type:"audio/mp3"})}}const mixDatabase=(new Map).set("cameo.mix",["adogicon.shp","adoguico.shp","aengicon.shp","aenguico.shp","agapgen.shp","agisicon.shp","ahrvicon.shp","ahrvuico.shp","aparicon.shp","apchicon.shp","apcicon.shp","artyicon.shp","asaticon.shp","ayaricon.shp","batricon.shp","beagicon.shp","bggyicon.shp","bolticon.shp","brrkicon.shp","carricon.shp","ccomicon.shp","ccomuico.shp","chemicon.shp","chroicon.shp","clckicon.shp","clegicon.shp","cleguico.shp","clonicon.shp","cnsticon.shp","crryicon.shp","csphicon.shp","darken.shp","desoicon.shp","desouico.shp","desticon.shp","detnicon.shp","dlphicon.shp","dlphuico.shp","dogicon.shp","doguico.shp","dredicon.shp","dronicon.shp","e1icon.shp","e1uico.shp","e2icon.shp","e2uico.shp","e4icon.shp","empicon.shp","engnicon.shp","facticon.shp","falcicon.shp","fixicon.shp","flakicon.shp","flkticon.shp","flktuico.shp","forticon.shp","fsdicon.shp","fspicon.shp","fstdicon.shp","fvicon.shp","fvuico.shp","gapicon.shp","gat2icon.shp","gateicon.shp","gbayicon.shp","gcanicon.shp","giicon.shp","giuico.shp","gorep.shp","gtnkicon.shp","gtnkuico.shp","gwepicon.shp","handicon.shp","harvicon.shp","harvuico.shp","heliicon.shp","hindicon.shp","hmecicon.shp","hovricon.shp","htkicon.shp","htkuico.shp","htnkicon.shp","htnkuico.shp","ioncicon.shp","ircricon.shp","ironicon.shp","ivanicon.shp","ivanuico.shp","ivncicon.shp","ivncuico.shp","jjeticon.shp","jjetuico.shp","landicon.shp","lasricon.shp","liteicon.shp","lpsticon.shp","mcvicon.shp","mcvuico.shp","metricon.shp","mltiicon.shp","mmchicon.shp","msslicon.shp","mtnkicon.shp","mtnkuico.shp","mutcicon.shp","nga2icon.shp","ngaticon.shp","nhpdicon.shp","npsiicon.shp","npwricon.shp","nradicon.shp","nrcticon.shp","nreficon.shp","ntchicon.shp","nukeicon.shp","nwalicon.shp","nwepicon.shp","obliicon.shp","obmbicon.shp","orcaicon.shp","otrnicon.shp","paraicon.shp","pillicon.shp","plticon.shp","plugicon.shp","podsicon.shp","powricon.shp","prisicon.shp","proicon.shp","psicicon.shp","psicuico.shp","psisicon.shp","psiticon.shp","psituico.shp","rad1icon.shp","rad2icon.shp","rad3icon.shp","radricon.shp","rboticon.shp","reficon.shp","rfixicon.shp","rtnkicon.shp","rtnkuico.shp","samicon.shp","sapcicon.shp","sapicon.shp","sbagicon.shp","sealicon.shp","sealuico.shp","seekicon.shp","shadicon.shp","shaduico.shp","shkicon.shp","shkuico.shp","smchicon.shp","smcvicon.shp","smcvuico.shp","snipicon.shp","snipuico.shp","soniicon.shp","spoticon.shp","spyicon.shp","spyuico.shp","sqdicon.shp","sreficon.shp","srefuico.shp","stnkicon.shp","subicon.shp","subticon.shp","tanyicon.shp","tanyuico.shp","techicon.shp","tempicon.shp","teslaicon.shp","tickicon.shp","tnkdicon.shp","tnkduico.shp","towricon.shp","trkaicon.shp","trsticon.shp","trstuico.shp","tslaicon.shp","ttnkicon.shp","ttnkuico.shp","turbicon.shp","twr1icon.shp","twr2icon.shp","twr3icon.shp","v3icon.shp","v3uico.shp","wallicon.shp","weapicon.shp","weaticon.shp","weedicon.shp","wethicon.shp","xxicon.shp","yardicon.shp","yuriicon.shp","yuriuico.shp","yurpicon.shp","yurpuico.shp","zepicon.shp","zepuico.shp"]).set("theme.mix",["200meter.wav","blowitup.wav","burn.wav","destroy.wav","eaglehun.wav","fortific.wav","grinder.wav","hm2.wav","indeep.wav","industro.wav","jank.wav","motorize.wav","power.wav","ra2-opt.wav","ra2-sco.wav","tension.wav"]).set("thememd.mix",["brainfre.wav","bully.wav","deceiver.wav","defend.wav","drok.wav","optionx.wav","phatatta.wav","scorex.wav","tactics.wav","trancelv.wav"]);let sidecResources=["addon.shp","bkgdlg.shp","bkgdmd.shp","bkgdsm.shp","bttnbkgd.shp","button00.shp","button01.shp","button02.shp","button03.shp","button04.shp","button05.shp","button06.shp","button07.shp","button08.shp","button09.shp","button10.shp","button11.shp","credits.shp","diplobtn.shp","gclock2.shp","key.ini","lendcap.shp","lspacer.shp","optbtn.shp","pbeacon.shp","power.shp","powerp.shp","pwrlvl.shp","radar.shp","radar01.shp","radar02.shp","r-dn.shp","rdrbeacn.shp","rendcap.shp","repair.shp","r-up.shp","sell.shp","side1.shp","side2.shp","side2b.shp","side3.shp","sidebar.pal","sidebttn.shp","tab00.shp","tab01.shp","tab02.shp","tab03.shp","tabs.shp","top.shp","uibkgd.pal","wayp.shp"];mixDatabase.set("sidec01.mix",sidecResources).set("sidec02.mix",sidecResources);let sideccdResources=["reportbug.shp"];mixDatabase.set("sidec01cd.mix",sideccdResources).set("sidec02cd.mix",sideccdResources),function(e){e[e.Archive=0]="Archive",e[e.Cdn=1]="Cdn",e[e.Local=2]="Local"}(GameResSource=GameResSource||{});class MpDialogSettings{readIni(e){return this.minMoney=e.getNumber("MinMoney"),this.money=e.getNumber("Money"),this.maxMoney=e.getNumber("MaxMoney"),this.moneyIncrement=e.getNumber("MoneyIncrement"),this.minUnitCount=e.getNumber("MinUnitCount"),this.unitCount=e.getNumber("UnitCount"),this.maxUnitCount=e.getNumber("MaxUnitCount"),this.crates=e.getBool("Crates"),this.gameSpeed=e.getNumber("GameSpeed"),this.mcvRedeploys=e.getBool("MCVRedeploys"),this.shortGame=e.getBool("ShortGame"),this.superWeapons=e.getBool("SuperWeapons"),this.techLevel=e.getNumber("TechLevel"),this.alliesAllowed=e.getBool("AlliesAllowed",!0),this.allyChangeAllowed=e.getBool("AllyChangeAllowed",!0),this.mustAlly=e.getBool("MustAlly"),this.bridgeDestruction=e.getBool("BridgeDestruction",!0),this.multiEngineer=e.getBool("MultiEngineer"),this}}!function(e){e[e.Battle=0]="Battle",e[e.ManBattle=1]="ManBattle",e[e.FreeForAll=2]="FreeForAll",e[e.Unholy=3]="Unholy",e[e.Cooperative=4]="Cooperative"}(GameModeType=GameModeType||{});class GameModes{constructor(e,t){this.modeIniLoader=t,this.entries=new Map,this.loadIni(e)}loadIni(e){e.getOrderedSections().forEach(r=>{let s=GameModeType[r.name]??GameModeType.Battle;[...r.entries.keys()].forEach(e=>{let t=r.getArray(e);if(t.length<5)throw new Error(`Invalid format for mp mode entry "${e}".`);var i=Number(e),e=t[2].toLowerCase(),e={id:i,type:s,label:t[0],description:t[1],rulesOverride:e,mapFilter:t[3],randomMapsAllowed:t[4],aiAllowed:i<3,mpDialogSettings:(new MpDialogSettings).readIni(this.modeIniLoader(e).getOrCreateSection("MultiplayerDialogSettings"))};this.entries.set(i,e)})})}getById(e){if(!this.entries.has(e))throw new Error("No game mode found with id "+e);return this.entries.get(e)}hasId(e){return this.entries.has(e)}getAll(){return[...this.entries.values()]}}class MapManifest{fromIni(t,e){return this.fileName=t.getString("File")||t.name.toLowerCase()+".map",this.uiName=t.getString("Description"),this.maxSlots=t.getNumber("MaxPlayers"),this.official=!0,this.gameModes=e.filter(e=>t.getArray("GameMode").includes(e.mapFilter)),this}getFullMapTitle(e){return this.addTitleSlotsSuffix(e.get(this.uiName),this.maxSlots)}addTitleSlotsSuffix(e,t){return e.match(/(\(|()\s*\d(-\d)?\s*(\)|))\s*$/)||(e+=` (2${2<t?"-"+t:""})`),e}fromMapFile(e,t){var i=e.readAsString();let r=e.filename;const s=new IniFile(this.extractIniSection("Basic",i)).getSection("Basic");if(!s)throw new Error(`Map "${r}" is missing the [Basic] section`);this.fileName=r,this.uiName="NOSTR:"+(s.getString("Name")||r.replace(/\.[^.]+$/,""));i=this.extractIniSection("Waypoints",i);let a=i?new IniFile(i).getSection("Waypoints"):void 0;this.maxSlots=[...a?.entries.keys()??[]].filter(e=>Number(e)<8).length,this.official=s.getBool("Official");let n=s.getArray("GameMode",void 0,["standard"]);return this.gameModes=t.filter(e=>n.includes(e.mapFilter)),this}extractIniSection(t,i){t=i.indexOf(`[${t}]`);if(-1!==t){let e=t+1;for(;e<i.length&&("["!==i[e]||"\n"!==i[e-1]);e++);return i.slice(t,e)}}}class MapList{constructor(e){this.gameModes=e,this.manifests=[]}addFromIni(i){let e=i.getSection("MultiMaps");if(!e)throw new Error("Invalid map list. Missing [MultiMaps] section.");return this.manifests=this.manifests.concat([...e.entries.values()].map(e=>{var t=i.getSection(e);if(!t)throw new Error(`Invalid map list. Missing [${e}] section.`);return(new MapManifest).fromIni(t,this.gameModes.getAll())})),this.dedupeEntries(),this}add(e){this.manifests.push(e)}addFromMapFile(e){this.add((new MapManifest).fromMapFile(e,this.gameModes.getAll()))}getAll(){return this.manifests}getByName(t){return this.manifests.find(e=>e.fileName.toLowerCase()===t.toLowerCase())}sortByName(){this.manifests.sort((e,t)=>e.fileName.localeCompare(t.fileName))}clone(){let e=new MapList(this.gameModes);return e.manifests=[...this.manifests],e}mergeWith(e){return this.manifests.push(...e.manifests),this.dedupeEntries(),this}dedupeEntries(){this.manifests=[...new Map(this.manifests.map(e=>[e.fileName.toLowerCase(),e])).values()]}}class Section_Section{getMatrix(e){return this.matrices[e]}}var MixinRulesType,_a,EngineType,ObjectType,HvaFile_THREE=__webpack_require__(70);class HvaFile{constructor(e){e instanceof VirtualFile&&this.fromVirtualFile(e)}fromVirtualFile(e){this.filename=e.filename;let i=e.stream;this.sections=[],i.readCString(16);var r=i.readInt32(),s=i.readInt32();for(let e=0;e<s;++e){let e=new Section_Section;e.name=i.readCString(16),e.matrices=new Array(r),this.sections.push(e)}for(let t=0;t<r;++t)for(let e=0;e<s;++e)this.sections[e].matrices[t]=this.readMatrix(i)}readMatrix(t){let i=[];for(let e=0;e<3;++e)i.push(t.readFloat32(),t.readFloat32(),t.readFloat32(),t.readFloat32());return i.push(0,0,0,1),(new HvaFile_THREE.Matrix4).fromArray(i).transpose()}}!function(e){e[e.NoDogEngiKills=0]="NoDogEngiKills"}(MixinRulesType=MixinRulesType||{}),function(e){e[e.AutoDetect=0]="AutoDetect",e[e.TiberianSun=1]="TiberianSun",e[e.Firestorm=2]="Firestorm",e[e.RedAlert2=3]="RedAlert2",e[e.YurisRevenge=4]="YurisRevenge"}(EngineType=EngineType||{});class Engine{static getVersion(){return version.split(".").slice(0,2).join(".")}static getModHash(){if(!this.modHash)throw new Error("Rules must be loaded first");return this.modHash}static getActiveMod(){return this.activeMod}static setActiveMod(e){this.activeMod=e}static initGameResSource(e){this.gameResSource=e}static async initRfs(e){let t=this.rfs=new RealFileSystem;return t.addRootDirectoryHandle(e),t}static async initVfs(e,t){return this.vfs=new VirtualFileSystem(e,t),_a.iniFiles.setVfs(this.vfs),_a.palettes.setVfs(this.vfs),_a.images.setVfs(this.vfs),_a.voxels.setVfs(this.vfs),_a.voxelAnims.setVfs(this.vfs),_a.tileData.setVfs(this.vfs),_a.sounds.setVfs(this.vfs),_a.themes.setDir(await this.rfs?.findDirectory(_a.rfsSettings.musicDir)),_a.taunts.setDir(await this.rfs?.findDirectory(_a.rfsSettings.tauntsDir)),this.vfs}static supportsTheater(t){var e=this.getActiveEngine();return this.theaterSettings.get(e)?.some(e=>e.type===t)||!1}static getTheaterSettings(e,t){if(!this.theaterSettings.has(e))throw new Error('Unknown engineType "'+e);e=this.theaterSettings.get(e).find(e=>e.type===t);if(!e)throw new Error(`Unsupported theater "${TheaterType[t]}"`);return e}static async loadTheater(e){if(!_a.rules||!_a.art)throw new Error("Rules and art should be loaded first");if(void 0===_a.gameResSource)throw new Error("No gameResSource is set");var t=_a.getActiveEngine();let i;var r,s=_a.getTheaterSettings(t,e);if(_a.gameResSource!==GameResSource.Cdn)for(var a of s.mixes)await _a.vfs.addMixFile(a);return _a.theaters.has(e)?i=_a.theaters.get(e):(r=_a.getTheaterIni(t,e),t=_a.getTileData(),i=Theater.factory(e,r,s,t,_a.palettes),_a.theaters.set(e,i)),_a.activeTheater=i,i}static unloadTheater(e){if(_a.vfs){var t,i=_a.getActiveEngine();for(t of _a.getTheaterSettings(i,e).mixes)_a.vfs.removeArchive(t)}}static unloadSideMixData(){for(var e of["sidec01.mix","sidec01cd.mix"]){var t,i=mixDatabase.get(e);if(!i)return void console.warn(`Mix "${e}" not found in mix database`);for(t of i)("pal"===t.split(".").pop()?_a.palettes:_a.images).clear(t)}}static getTheaterIni(e,t){t=_a.getTheaterSettings(e,t).theaterIni;return _a.getIni(t)}static loadRules(){var e=this.getFileNameVariant("rules.ini"),t=this.getFileNameVariant("art.ini"),i=this.getFileNameVariant("ai.ini");let r=this.iniFiles.get(e),s=this.iniFiles.get(t);var a=this.iniFiles.get(i);if(!r)throw new Error(`Rules "${e}" not found`);if(!s)throw new Error(`Art "${t}" not found`);if(!a)throw new Error(`AI "${i}" not found`);t=this.iniFiles.get(_a.customRulesFileName),i=this.iniFiles.get(_a.customArtFileName);if(!t)throw new Error(`Rules "${_a.customRulesFileName}" not found`);if(!i)throw new Error(`Art "${_a.customArtFileName}" not found`);_a.art=s.clone().mergeWith(i),_a.rules=_a.patchAudioVisualRules(r.clone().mergeWith(t)),_a.ai=a,_a.modHash=_a.computeModHash()}static patchAudioVisualRules(i){if(this.activeEngine===EngineType.YurisRevenge){let t=i.getSection("General");if(t){let e=i.getSection("AudioVisual");var r;for(r of["DamageFireTypes","OreTwinkle","BarrelExplode","BarrelDebris","BarrelParticle","NukeTakeOff","Wake","DropPod","DeadBodies","MetallicDebris","BridgeExplosions","IonBlast","IonBeam","WeatherConClouds","WeatherConBolts","WeatherConBoltExplosion","DominatorWarhead","DominatorDamage","DominatorCaptureRange","DominatorFirstAnim","DominatorSecondAnim","DominatorFireAtPercentage","ChronoPlacement","ChronoBeam","ChronoBlast","ChronoBlastDest","WarpIn","WarpOut","WarpAway","IronCurtainInvokeAnim","ForceShieldInvokeAnim","WeaponNullifyAnim","ChronoSparkle1","InfantryExplode","FlamingInfantry","InfantryHeadPop","InfantryNuked","InfantryVirus","InfantryBrute","InfantryMutate","Behind","MoveFlash","Parachute","BombParachute","DropZoneAnim","EMPulseSparkles"])e?.set(r,t.getString(r))}}return i}static computeModHash(){if(!this.vfs)throw new Error("VFS not initialized");let e=[this.customRulesFileName,this.customArtFileName,this.customMpModesFileName,this.shroudFileName,this.getFileNameVariant("rules.ini"),this.getFileNameVariant("art.ini"),this.getFileNameVariant("ai.ini"),..._a.mixinRulesFileNames.values()];var t,i,r,s=this.theaterSettings.get(this.getActiveEngine());if(!s)throw new Error('Unsupported engineType "'+this.getActiveEngine());for(t of s)e.push(t.theaterIni);let a=this.getMpModes();for(i of a.getAll())e.push(i.rulesOverride);let n=new Crc32;for(r of e){if(!this.vfs.fileExists(r))throw new Error(`File ${r} not found`);var o=this.vfs.openFile(r).stream;n.append(new Uint8Array(o.buffer,o.byteOffset,o.byteLength))}return n.append(binaryStringToUint8Array(this.getVersion())),n.get()}static getRules(){if(!_a.rules)throw new Error("Rules must be loaded first");return _a.rules}static getArt(){if(!_a.art)throw new Error("Art must be loaded first");return _a.art}static getAi(){if(!_a.ai)throw new Error("AI must be loaded first");return _a.ai}static getFileNameVariant(e){var t=this.getActiveEngine();let i;if(t===EngineType.YurisRevenge)i="md";else{if(t!==EngineType.RedAlert2)throw new Error("Unsupported engine type "+EngineType[t]);i=""}return i?e.replace(/\.([^.]+)$/,i+".$1"):e}static getMpModes(){return new GameModes(this.getIni(this.customMpModesFileName),e=>this.getIni(e))}static getUiIni(){var e=this.getFileNameVariant("ui.ini");return this.getIni(e)}static getIni(e){if(!this.iniFiles.has(e))throw new Error(`INI file ${e} not found.`);return this.iniFiles.get(e)}static async loadMapList(){if(!this.vfs)throw new Error("File system not initialized");var e,i,r,t=this.getMpModes();let s=new MapList(t);s.addFromIni(this.getIni(this.getFileNameVariant("missions.pkt")));for(e of this.vfs.listArchives()){var a=e.toLowerCase().replace(/\.[^.]+$/,"")+".pkt";this.vfs.fileExists(a)&&s.addFromIni(new IniFile(this.vfs.openFile(a)))}let n=new MapList(t),o=this.supportedMapTypes.get(this.getActiveEngine());if(!o)throw new Error(`No map types defined for engine type "${_a.getActiveEngine()}"`);if(this.rfs)for await(var l of this.rfs.getEntries()){let t=l.toLowerCase();try{t.endsWith(".pkt")?(i=new IniFile(await this.rfs.openFile(l,!0)),s.addFromIni(i)):o.some(e=>t.endsWith("."+e))&&(r=await this.rfs.openFile(l,!0),n.addFromMapFile(r))}catch(e){console.warn(`Couldn't read file "${l}"`,e)}}return n.sortByName(),s.mergeWith(n),this.mapList=s,s}static getTileData(){return _a.tileData}static getImages(){return _a.images}static getVoxels(){return _a.voxels}static getVoxelAnims(){return _a.voxelAnims}static getPalettes(){return _a.palettes}static getSounds(){return _a.sounds}static getThemes(){return _a.themes}static getTaunts(){return _a.taunts}static getActiveEngine(){if(!this.activeEngine)throw new Error("Engine type not initialized");return this.activeEngine}static setActiveEngine(e){this.activeEngine=e}static getLastTheaterType(){return _a.activeTheater?.type}static getCacheDir(){try{return this.getOrCreateDir(this.rfsSettings.cacheDir,!0)}catch(e){return void console.error("Couldn't get cache directory",[e])}}static async getReplayDir(){var i=this.getActiveMod();if(i){let e=await this.getModDir(),t=await e?.getDirectory(i);return t?.getOrCreateDirectory(_a.rfsSettings.replayDir)}return this.getOrCreateDir(this.rfsSettings.replayDir)}static getModDir(){return this.getOrCreateDir(_a.rfsSettings.modDir)}static getMapDir(){return this.getOrCreateDir(_a.rfsSettings.mapDir)}static async getOrCreateDir(e,t=!1){let i=this.rfs?.getRootDirectory();if(i)return await i.getOrCreateDirectory(e,t)}static getMapList(){return this.mapList}static destroy(){this.activeEngine=void 0,this.activeTheater=void 0,this.activeMod=void 0,this.modHash=void 0,this.mapList=void 0,this.rfs=void 0,this.vfs=void 0,this.art=void 0,this.iniFiles.clear(),this.images.clear(),this.palettes.clear(),this.rules=void 0,this.ai=void 0,this.theaters.clear(),this.tileData.clear(),this.voxels.clear(),this.voxelAnims.clear()}}_a=Engine,Engine.UI_ANIM_SPEED=2,Engine.rfsSettings={menuVideoFileName:"ra2ts_l.webm",splashImgFileName:"glsl.png",mapDir:"maps",modDir:"mods",musicDir:"music",tauntsDir:"Taunts",cacheDir:"cache",replayDir:"replays"},Engine.supportedMapTypes=new Map([[EngineType.RedAlert2,["mpr","map"]],[EngineType.YurisRevenge,["mpr","map","yrm"]]]),Engine.images=new LazyResourceCollection(e=>new ShpFile(e)),Engine.voxels=new LazyResourceCollection(e=>new VxlFile(e)),Engine.voxelAnims=new LazyResourceCollection(e=>new HvaFile(e)),Engine.sounds=new LazyResourceCollection(e=>new WavFile(e)),Engine.themes=new LazyAsyncResourceCollection(e=>new Mp3File(e),!1),Engine.taunts=new LazyAsyncResourceCollection(async e=>new WavFile(new Uint8Array(await e.arrayBuffer()))),Engine.iniFiles=new LazyResourceCollection(e=>new IniFile(e)),Engine.tileData=new LazyResourceCollection(e=>new TmpFile(e)),Engine.palettes=new LazyResourceCollection(e=>new Palette(e)),Engine.theaters=new Map,Engine.theaterSettings=(new Map).set(EngineType.RedAlert2,[{type:TheaterType.Temperate,theaterIni:"temperat.ini",mixes:["isotemp.mix","temperat.mix","tem.mix"],extension:".tem",newTheaterChar:"T",isoPaletteName:"isotem.pal",unitPaletteName:"unittem.pal",overlayPaletteName:"temperat.pal",libPaletteName:"libtem.pal"},{type:TheaterType.Snow,theaterIni:"snow.ini",mixes:["isosnow.mix","snow.mix","sno.mix"],extension:".sno",newTheaterChar:"A",isoPaletteName:"isosno.pal",unitPaletteName:"unitsno.pal",overlayPaletteName:"snow.pal",libPaletteName:"libsno.pal"},{type:TheaterType.Urban,theaterIni:"urban.ini",mixes:["isourb.mix","urb.mix","urban.mix"],extension:".urb",newTheaterChar:"U",isoPaletteName:"isourb.pal",unitPaletteName:"uniturb.pal",overlayPaletteName:"urban.pal",libPaletteName:"liburb.pal"}]).set(EngineType.YurisRevenge,[{type:TheaterType.Temperate,theaterIni:"temperatmd.ini",mixes:["isotemp.mix","isotemmd.mix","temperat.mix","tem.mix"],extension:".tem",newTheaterChar:"T",isoPaletteName:"isotem.pal",unitPaletteName:"unittem.pal",overlayPaletteName:"temperat.pal",libPaletteName:"libtem.pal"},{type:TheaterType.Snow,theaterIni:"snowmd.ini",mixes:["isosnomd.mix","snowmd.mix","isosnow.mix","snow.mix","sno.mix"],extension:".sno",newTheaterChar:"A",isoPaletteName:"isosno.pal",unitPaletteName:"unitsno.pal",overlayPaletteName:"snow.pal",libPaletteName:"libsno.pal"},{type:TheaterType.Urban,theaterIni:"urbanmd.ini",mixes:["isourbmd.mix","isourb.mix","urb.mix","urban.mix"],extension:".urb",newTheaterChar:"U",isoPaletteName:"isourb.pal",unitPaletteName:"uniturb.pal",overlayPaletteName:"urban.pal",libPaletteName:"liburb.pal"},{type:TheaterType.NewUrban,theaterIni:"urbannmd.ini",mixes:["isoubnmd.mix","isoubn.mix","ubn.mix","urbann.mix"],extension:".ubn",newTheaterChar:"N",isoPaletteName:"isoubn.pal",unitPaletteName:"unitubn.pal",overlayPaletteName:"urbann.pal",libPaletteName:"libubn.pal"},{type:TheaterType.Desert,theaterIni:"desertmd.ini",mixes:["isodesmd.mix","desert.mix","des.mix","isodes.mix"],extension:".des",newTheaterChar:"D",isoPaletteName:"isodes.pal",unitPaletteName:"unitdes.pal",overlayPaletteName:"desert.pal",libPaletteName:"libdes.pal"},{type:TheaterType.Lunar,theaterIni:"lunarmd.ini",mixes:["isolunmd.mix","isolun.mix","lun.mix","lunar.mix"],extension:".lun",newTheaterChar:"L",isoPaletteName:"isolun.pal",unitPaletteName:"unitlun.pal",overlayPaletteName:"lunar.pal",libPaletteName:"liblun.pal"}]),Engine.customRulesFileName="rulescd.ini",Engine.customArtFileName="artcd.ini",Engine.customMpModesFileName="mpmodescd.ini",Engine.shroudFileName="shroud.shp",Engine.mixinRulesFileNames=(new Map).set(MixinRulesType.NoDogEngiKills,"nodogengikills.ini"),function(e){e[e.None=0]="None",e[e.Aircraft=1]="Aircraft",e[e.Building=2]="Building",e[e.Infantry=3]="Infantry",e[e.Overlay=4]="Overlay",e[e.Smudge=5]="Smudge",e[e.Terrain=6]="Terrain",e[e.Vehicle=7]="Vehicle",e[e.Animation=8]="Animation",e[e.Projectile=9]="Projectile",e[e.VoxelAnim=10]="VoxelAnim",e[e.Debris=11]="Debris"}(ObjectType=ObjectType||{});class MapObject{constructor(e){this.type=e}isStructure(){return this.type===ObjectType.Building}isVehicle(){return this.type===ObjectType.Vehicle}isInfantry(){return this.type===ObjectType.Infantry}isAircraft(){return this.type===ObjectType.Aircraft}isTerrain(){return this.type===ObjectType.Terrain}isSmudge(){return this.type===ObjectType.Smudge}isOverlay(){return this.type===ObjectType.Overlay}isNamed(){return"name"in this}isTechno(){return"health"in this}}class NamedMapObject extends MapObject{}class Techno extends NamedMapObject{}class Structure extends Techno{constructor(){super(ObjectType.Building)}}class Vehicle extends Techno{constructor(){super(ObjectType.Vehicle)}}class Infantry extends Techno{constructor(){super(ObjectType.Infantry)}}class Aircraft extends Techno{constructor(){super(ObjectType.Aircraft)}}class Terrain extends NamedMapObject{constructor(){super(ObjectType.Terrain)}}class Smudge extends NamedMapObject{constructor(){super(ObjectType.Smudge)}}class Overlay extends MapObject{constructor(){super(ObjectType.Overlay)}}class Format80{static decode(e,t){t=new Uint8Array(t);return this.decodeInto(e,t),t}static decodeInto(e,t){let i=new DataStream(new DataView(e.buffer,e.byteOffset,e.byteLength)),r=0;for(;;){var s=i.readUint8();if(0==(128&s)){var a=i.readUint8(),n=3+((112&s)>>4);this.replicatePrevious(t,r,r-(((15&s)<<8)+a),n),r+=n}else if(0==(64&s)){n=63&s;if(0==n)return r;t.set(i.readUint8Array(n),r),r+=n}else{s=63&s;if(62==s)for(var o=i.readInt16(),l=i.readUint8(),h=r+o;r<h;r++)t[r]=l;else if(63==s){o=i.readInt16();let e=i.readInt16();if(e>=r)throw new Error(`srcIndex >= destIndex ${e} `+r);for(var c=r+o;r<c;r++)t[r]=t[e++]}else{s=3+s;let e=i.readInt16();if(e>=r)throw new Error(`srcIndex >= destIndex ${e} `+r);for(var u=r+s;r<u;r++)t[r]=t[e++]}}}}static replicatePrevious(t,i,r,s){if(i<r)throw new Error(`srcIndex > destIndex ${r} `+i);if(i-r==1)for(let e=0;e<s;e++)t[i+e]=t[i-1];else for(let e=0;e<s;e++)t[i+e]=t[r+e]}}var PixelFormat,TagRepeatType,TriggerEventType,TriggerActionType,SideType,RadarEventType,PrereqCategory,TerrainType,LandType,SpeedType,InfDeathType,PipColor,LocomotorType,MovementZone,ArmorType,LandTargeting,NavalTargeting,WeaponType,VeteranAbility,VhpScan,lzo1x=__webpack_require__(895).default;class MiniLzo{static decompress(e,t){e={inputBuffer:e,outputBuffer:null},t=lzo1x.decompress(e,{outputSize:t});if(0!==t)throw new Error("MiniLzo decode failed with code "+t);return e.outputBuffer}}class Format5{static decode(e,t,i=5){t=new Uint8Array(t);return this.decodeInto(e,t,i),t}static decodeInto(e,i,r=5){var t=i.length;let s=0,a=0;for(;a<t;){var n=e[s+1]<<8|e[s];s+=2;var o=e[s+1]<<8|e[s];if(s+=2,!n||!o)break;let t;t=80===r?Format80.decode(e.subarray(s,s+n),o):MiniLzo.decompress(e.subarray(s,s+n),o);for(let e=0;e<o;++e)i[a+e]=t[e];s+=n,a+=o}}}function getChannelCount(e){switch(e){case PixelFormat.Indexed:return 1;case PixelFormat.Rgb:return 3;case PixelFormat.Rgba:return 4;default:throw new Error("Unsupported pixel format "+e)}}!function(e){e[e.Rgb=1]="Rgb",e[e.Rgba=2]="Rgba",e[e.Indexed=3]="Indexed"}(PixelFormat=PixelFormat||{});class Bitmap{constructor(e,t,i,r=PixelFormat.Rgba){var s=getChannelCount(r);this.data=i||new Uint8Array(s*e*t),this.pixelFormat=r,this.width=e,this.height=t}drawIndexedImage(t,e,i){var r=getChannelCount(this.pixelFormat);const s=this.data;var a=this.width,n=r*a,o=r*a*this.height;let l=0+n*i+r*e,h=0;for(let e=0;e<t.height;e++){for(let e=0;e<t.width;e++){var c=t.data[h];0!==c&&0<=l&&l<o&&(s[l]=c,3<=r&&(s[l+1]=0,s[l+2]=0),4===r&&(s[l+3]=255)),l+=r,h++}l+=n-t.width*r}}}class IndexedBitmap extends Bitmap{constructor(e,t,i){super(e,t,i,PixelFormat.Indexed)}}class RgbBitmap extends Bitmap{constructor(e,t,i){super(e,t,i,PixelFormat.Rgb)}}class RgbaBitmap extends Bitmap{constructor(e,t,i){super(e,t,i,PixelFormat.Rgba)}drawRgbaImage(t,e,i){const r=this.data;var s=this.width,a=4*s,n=4*s*this.height;let o=0+a*i+4*e,l=0;for(let e=0;e<t.height;e++){for(let e=0;e<t.width;e++)0<=o&&o<n&&(r[o]=t.data[l],r[o+1]=t.data[l+1],r[o+2]=t.data[l+2],r[o+3]=t.data[l+3]),o+=4,l+=4;o+=a-4*t.width}}}!function(e){e[e.OnceAny=0]="OnceAny",e[e.OnceAll=1]="OnceAll",e[e.Repeat=2]="Repeat"}(TagRepeatType=TagRepeatType||{});class TagsReader{read(e){let t=[];for(var[i,r]of e.entries){var s=r.split(",");s.length<3?console.warn(`Invalid tag ${i}=${r}. Skipping.`):(r=Number(s[0]),void 0!==TagRepeatType[r]?(s={id:i,repeatType:r,name:s[1],triggerId:s[2]},t.push(s)):console.warn(`Invalid repeat value ${r} for tag id ${i}. Skipping.`))}return t}}!function(e){e[e.NoEvent=0]="NoEvent",e[e.EnteredBy=1]="EnteredBy",e[e.SpiedBy=2]="SpiedBy",e[e.AttackedByAny=6]="AttackedByAny",e[e.DestroyedByAny=7]="DestroyedByAny",e[e.AnyEvent=8]="AnyEvent",e[e.DestroyedAllUnits=9]="DestroyedAllUnits",e[e.DestroyedAllBuildings=10]="DestroyedAllBuildings",e[e.DestroyedAll=11]="DestroyedAll",e[e.CreditsExceed=12]="CreditsExceed",e[e.ElapsedTime=13]="ElapsedTime",e[e.MissionTimerExpired=14]="MissionTimerExpired",e[e.DestroyedBuildings=15]="DestroyedBuildings",e[e.DestroyedUnits=16]="DestroyedUnits",e[e.NoFactoriesLeft=17]="NoFactoriesLeft",e[e.BuildBuilding=19]="BuildBuilding",e[e.BuildUnit=20]="BuildUnit",e[e.BuildInfantry=21]="BuildInfantry",e[e.BuildAircraft=22]="BuildAircraft",e[e.CrossesHorizontalLine=25]="CrossesHorizontalLine",e[e.CrossesVerticalLine=26]="CrossesVerticalLine",e[e.GlobalIsSet=27]="GlobalIsSet",e[e.GlobalIsCleared=28]="GlobalIsCleared",e[e.DestroyedOrCaptured=29]="DestroyedOrCaptured",e[e.LowPower=30]="LowPower",e[e.DestroyedBridge=31]="DestroyedBridge",e[e.BuildingExists=32]="BuildingExists",e[e.ComesNearWaypoint=34]="ComesNearWaypoint",e[e.LocalIsSet=36]="LocalIsSet",e[e.LocalIsCleared=37]="LocalIsCleared",e[e.FirstDamagedCombat=38]="FirstDamagedCombat",e[e.HalfHealthCombat=39]="HalfHealthCombat",e[e.QuarterHealthCombat=40]="QuarterHealthCombat",e[e.FirstDamagedAny=41]="FirstDamagedAny",e[e.HalfHealthAny=42]="HalfHealthAny",e[e.QuarterHealthAny=43]="QuarterHealthAny",e[e.AttackedByHouse=44]="AttackedByHouse",e[e.AmbientLightBelow=45]="AmbientLightBelow",e[e.AmbientLightAbove=46]="AmbientLightAbove",e[e.ElapsedScenarioTime=47]="ElapsedScenarioTime",e[e.DestroyedOrCapturedOrInfiltrated=48]="DestroyedOrCapturedOrInfiltrated",e[e.PickupCrate=49]="PickupCrate",e[e.PickupCrateAny=50]="PickupCrateAny",e[e.RandomDelay=51]="RandomDelay",e[e.CreditsBelow=52]="CreditsBelow",e[e.SpyEnteringAsHouse=53]="SpyEnteringAsHouse",e[e.SpyEnteringAsInfantry=54]="SpyEnteringAsInfantry",e[e.DestroyedAllUnitsNaval=55]="DestroyedAllUnitsNaval",e[e.DestroyedAllUnitsLand=56]="DestroyedAllUnitsLand",e[e.BuildingNotExists=57]="BuildingNotExists"}(TriggerEventType=TriggerEventType||{}),function(e){e[e.NoAction=0]="NoAction",e[e.FireSale=9]="FireSale",e[e.TextTrigger=11]="TextTrigger",e[e.DestroyTrigger=12]="DestroyTrigger",e[e.ChangeHouse=14]="ChangeHouse",e[e.RevealMap=16]="RevealMap",e[e.RevealAroundWaypoint=17]="RevealAroundWaypoint",e[e.PlaySoundFx=19]="PlaySoundFx",e[e.PlaySpeech=21]="PlaySpeech",e[e.ForceTrigger=22]="ForceTrigger",e[e.TimerStart=23]="TimerStart",e[e.TimerStop=24]="TimerStop",e[e.TimerExtend=25]="TimerExtend",e[e.TimerShorten=26]="TimerShorten",e[e.TimerSet=27]="TimerSet",e[e.GlobalSet=28]="GlobalSet",e[e.GlobalClear=29]="GlobalClear",e[e.DestroyObject=32]="DestroyObject",e[e.AddOneTimeSuperWeapon=33]="AddOneTimeSuperWeapon",e[e.AddRepeatingSuperWeapon=34]="AddRepeatingSuperWeapon",e[e.AllChangeHouse=36]="AllChangeHouse",e[e.ResizePlayerView=40]="ResizePlayerView",e[e.PlayAnimAt=41]="PlayAnimAt",e[e.DetonateWarhead=42]="DetonateWarhead",e[e.ReshroudMap=51]="ReshroudMap",e[e.EnableTrigger=53]="EnableTrigger",e[e.DisableTrigger=54]="DisableTrigger",e[e.CreateRadarEvent=55]="CreateRadarEvent",e[e.LocalSet=56]="LocalSet",e[e.LocalClear=57]="LocalClear",e[e.SellBuilding=60]="SellBuilding",e[e.TurnOffBuilding=61]="TurnOffBuilding",e[e.TurnOnBuilding=62]="TurnOnBuilding",e[e.ApplyOneHundredDamage=63]="ApplyOneHundredDamage",e[e.ForceEnd=69]="ForceEnd",e[e.DestroyTag=70]="DestroyTag",e[e.SetAmbientStep=71]="SetAmbientStep",e[e.SetAmbientRate=72]="SetAmbientRate",e[e.SetAmbientLight=73]="SetAmbientLight",e[e.NukeStrike=95]="NukeStrike",e[e.PlaySoundFxAt=99]="PlaySoundFxAt",e[e.UnrevealAroundWaypoint=101]="UnrevealAroundWaypoint",e[e.LightningStrike=102]="LightningStrike",e[e.TimerText=103]="TimerText",e[e.CreateCrate=108]="CreateCrate",e[e.IronCurtainAt=109]="IronCurtainAt",e[e.EvictOccupiers=111]="EvictOccupiers",e[e.Cheer=113]="Cheer",e[e.StopSoundsAt=116]="StopSoundsAt"}(TriggerActionType=TriggerActionType||{});class TriggerReader{read(e,t,i,r){let s=this.readTriggers(e),{events:a,unknownEventTypes:n}=this.readEvents(t),{actions:o,unknownActionTypes:l}=this.readActions(i),h=[...r.values()],c=new Set(s);for(let t of s.values()){var u=a.get(t.id);u&&t.events.push(...u);u=o.get(t.id);u&&t.actions.push(...u),!t.attachedTriggerId||(u=s.find(e=>e.id===t.attachedTriggerId))&&(t.attachedTrigger=u,c.delete(u))}for(let t of c){var d=h.find(e=>e.triggerId===t.id);if(d){let e=t;for(;e;)e.tag=d,e=e.attachedTrigger}else{let e=t;for(;e;){console.warn(`Trigger ${e.id} has no associated tag or valid root trigger. Skipping.`);var p=s.indexOf(e);-1!==p&&s.splice(p,1),e=e.attachedTrigger}}}return{triggers:s,unknownEventTypes:n,unknownActionTypes:l}}readTriggers(e){let t=[];for(var[i,r]of e.entries){var s=r.split(",");s.length<8?console.warn(`Invalid trigger ${i}=${r}. Skipping.`):(s={id:i,houseName:s[0],attachedTriggerId:"<none>"!==s[1]?s[1]:void 0,attachedTrigger:void 0,name:s[2],disabled:Boolean(Number(s[3])),difficulties:{easy:Boolean(Number(s[4])),medium:Boolean(Number(s[5])),hard:Boolean(Number(s[6]))},events:[],actions:[],tag:void 0},t.push(s))}return t}readEvents(e){let t=new Map,s=new Set;for(var[a,i]of e.entries){let r=i.split(",");if(r.length<4)console.warn(`Invalid event ${a}=${i}. Skipping.`);else{var n=Number(r.shift());let i=[];for(let t=0;t<n;t++){var o=Number(r.shift()),l=Number(r.shift());let e=r.splice(0,2===l?2:1);void 0!==TriggerEventType[o]?(l={triggerId:a,eventIndex:t,type:o,params:[l,...e.map(e=>e||"0")]},i.push(l)):(s.add(o),console.warn(`Unknown event type ${o} for trigger id ${a}. Skipping.`))}t.set(a,i)}}return{events:t,unknownEventTypes:s}}readActions(e){let r=new Map,s=new Set;for(var[a,t]of e.entries){let i=t.split(",");if(i.length<9)console.warn(`Invalid action ${a}=${t}. Skipping.`);else{var n=Number(i.shift());if(i.length<8*n)console.warn(`Invalid action ${a}=${t}. Skipping.`);else{let t=[];for(let e=0;e<n;e++){var o=Number(i.shift()),l=i.splice(0,7);void 0!==TriggerActionType[o]?(l={triggerId:a,index:e,type:o,params:[Number(l[0]||"0"),l[1]||"0",l[2]||"0",l[3]||"0",l[4]||"0",l[5]||"0",l[6]?this.readAZActionParam(l[6]):0]},t.push(l)):(s.add(o),console.warn(`Unknown action type ${o} for trigger id "${a}". Skipping.`))}r.set(a,t)}}}return{actions:r,unknownActionTypes:s}}readAZActionParam(e){var t="Z".charCodeAt(0),i="A".charCodeAt(0),t=t-i+1;return 1<e.length?e.charCodeAt(1)-i+(e.charCodeAt(0)-i+1)*t:e.charCodeAt(0)-i}}class MapLighting{constructor(){this.level=0,this.ambient=1,this.red=1,this.green=1,this.blue=1,this.ground=0,this.forceTint=!1}read(e,t=""){return this.level=e.getNumber(t+"Level",.032),this.ambient=e.getNumber(t+"Ambient",1),this.red=e.getNumber(t+"Red",1),this.green=e.getNumber(t+"Green",1),this.blue=e.getNumber(t+"Blue",1),this.ground=e.getNumber(t+"Ground",0),this}copy(e){return this.level=e.level,this.ambient=e.ambient,this.red=e.red,this.green=e.green,this.blue=e.blue,this.ground=e.ground,this.forceTint=e.forceTint,this}}class CellTagsReader{read(e,t){let i=[];for(var[r,s]of e.entries){r={tagId:s,coords:this.readCoords(Number(r),t)};i.push(r)}return i}readCoords(e,t){t=t<4?128:1e3;return{x:e%t,y:Math.floor(e/t)}}}class Variable{constructor(e,t){this.name=e,this.value=t}clone(){return new Variable(this.name,this.value)}}class SpecialFlags{read(e){return this.initialVeteran=e.getBool("InitialVeteran"),this}}class MapFile extends IniFile{fromString(e){super.fromString(e);let t=this.getSection("Map");if(!t)throw new Error("[Map] section not found");e=t.getNumberArray("Size");if(this.fullSize={x:e[0],y:e[1],width:e[2],height:e[3]},e=t.getNumberArray("LocalSize"),this.localSize={x:e[0],y:e[1],width:e[2],height:e[3]},this.theaterType=t.getEnum("Theater",TheaterType,TheaterType.None,!0),this.theaterType===TheaterType.None)throw new Error(`Unsupported theater type "${t.getString("Theater")}"`);let i=this.getSection("Basic");e=this.iniFormat=i?.getNumber("NewINIFormat")??0;return this.readTiles(),this.readWaypoints(this.getOrCreateSection("Waypoints")),this.readStructures(this.getOrCreateSection("Structures")),this.readVehicles(),this.readInfantries(),this.readAircrafts(),this.readTerrains(this.getOrCreateSection("Terrain")),this.readOverlays(),this.readSmudges(),this.readLighting(),this.readTagsAndTriggers(),this.readCellTags(e),this.readVariableNames(),this.startingLocations=this.readStartingLocations(this.waypoints),this.specialFlags=(new SpecialFlags).read(this.getOrCreateSection("SpecialFlags")),this}fromJson(i){if(i[MapFile.artSectionPrefix]){let{[MapFile.artSectionPrefix]:e,...t}=i;this.artOverrides=new IniFile(e),i=t}return super.fromJson(i)}readStartingLocations(e){let t=[];var i;for(i of e.filter(e=>e.number<8).sort((e,t)=>e.number<t.number?-1:1))t.push({x:i.rx,y:i.ry});return t}readLighting(){var e=this.getOrCreateSection("Lighting");this.lighting=(new MapLighting).read(e),this.ionLighting=(new MapLighting).read(e,"Ion"),this.ionLighting.forceTint=!0}readTagsAndTriggers(){this.tags=(new TagsReader).read(this.getOrCreateSection("Tags"));var e=this.getOrCreateSection("Triggers"),t=this.getOrCreateSection("Events"),i=this.getOrCreateSection("Actions"),{triggers:e,unknownEventTypes:t,unknownActionTypes:i}=(new TriggerReader).read(e,t,i,this.tags);this.triggers=e,this.unknownEventTypes=t,this.unknownActionTypes=i}readCellTags(e){this.cellTags=(new CellTagsReader).read(this.getOrCreateSection("CellTags"),e)}readVariableNames(){var e,t,i=this.getOrCreateSection("VariableNames");let r=new Map;for([e,t]of i.entries){var s,a,n=Number(e);Number.isNaN(n)?console.warn(`Map [VariableNames] contains non-numeric index "${e}". Skipping.`):([s,a]=t.split(","),a=new Variable(s,Boolean(Number(a))),r.set(n,a))}this.variables=r}readTiles(){let e=this.getSection("IsoMapPack5");if(!e)throw new Error("[IsoMapPack5] section not found");var t=base64StringToUint8Array(e.getConcatenatedValues()),i=(2*this.fullSize.width-1)*this.fullSize.height,r=new Uint8Array(11*i+4);Format5.decodeInto(t,r);let s=new DataStream(r.buffer),a=2*this.fullSize.width-1;var n,o,l,h,r=this.fullSize.height,c=(e,t)=>t*a+e;this.tiles=new Array(a*r);for(let e=this.maxTileNum=0;e<i;e++){var u=s.readUint16(),d=s.readUint16(),p=Math.max(0,s.readInt16());this.maxTileNum=Math.max(this.maxTileNum,p),s.readInt16();var g=s.readUint8(),m=s.readUint8();s.readUint8();var y=u-d+this.fullSize.width-1,T=u+d-this.fullSize.width-1;0<=y&&y<2*this.fullSize.width&&0<=T&&T<2*this.fullSize.height&&(g={dx:y,dy:T,rx:u,ry:d,z:m,tileNum:p,subTile:g},this.tiles[c(y,Math.floor(T/2))]=g)}for(let t=0;t<this.fullSize.height;t++)for(let e=0;e<=2*this.fullSize.width-2;e++)this.tiles[c(e,t)]||(n=e,h=(o=2*t+e%2)-(l=(n+o)/2+1)+this.fullSize.width+1,this.tiles[c(e,t)]={dx:n,dy:o,rx:l,ry:h,z:0,tileNum:0,subTile:0})}readWaypoints(e){this.waypoints=[];for(var[t,i]of e.entries){var r;let e;isNaN(r=parseInt(t,10))||isNaN(e=parseInt(i,10))||(t=Math.floor(e/1e3),i=e-1e3*t,this.waypoints.push({number:r,rx:i,ry:t}))}}readStructures(e){this.structures=[];for(var[,t]of e.entries){t=t.split(",");if(!(t.length<=15)){let e=new Structure;e.owner=t[0],e.name=t[1],e.health=Number(t[2]),e.rx=Number(t[3]),e.ry=Number(t[4]),e.tag=this.readTagId(t[6]),e.poweredOn=Boolean(Number(t[9])),this.structures.push(e)}}}readTagId(e){return"none"!==e.toLowerCase()?e:void 0}readVehicles(){this.vehicles=[];let e=this.getSection("Units");if(e)for(var t of e.entries.values()){var i=t.split(",");if(i.length<=11)console.warn(`Invalid Vehicle entry: "${t}"`);else{let e=new Vehicle;e.owner=i[0],e.name=i[1],e.health=Number(i[2]),e.rx=Number(i[3]),e.ry=Number(i[4]),e.direction=Number(i[5]),e.tag=this.readTagId(i[7]),e.veterancy=Number(i[8]),e.onBridge="1"===i[10],this.vehicles.push(e)}}}readInfantries(){this.infantries=[];let e=this.getSection("Infantry");if(e)for(var t of e.entries.values()){var i=t.split(",");let e=new Infantry;i.length<=8?console.warn(`Invalid Infantry entry: "${t}"`):(e.owner=i[0],e.name=i[1],e.health=Number(i[2]),e.rx=Number(i[3]),e.ry=Number(i[4]),e.subCell=Number(i[5]),e.direction=Number(i[7]),e.tag=this.readTagId(i[8]),e.veterancy=Number(i[9]),e.onBridge="1"===i[11],this.infantries.push(e))}}readAircrafts(){this.aircrafts=[];let e=this.getSection("Aircraft");if(e)for(var t of e.entries.values()){t=t.split(",");let e=new Aircraft;e.owner=t[0],e.name=t[1],e.health=Number(t[2]),e.rx=Number(t[3]),e.ry=Number(t[4]),e.direction=Number(t[5]),e.tag=this.readTagId(t[7]),e.veterancy=Number(t[8]),e.onBridge="1"===t[t.length-4],this.aircrafts.push(e)}}readTerrains(e){this.terrains=[];for(var[t,i]of e.entries){t=Number(t);if(!isNaN(t)){let e=new Terrain;e.name=i,e.rx=t%1e3,e.ry=Math.floor(t/1e3),this.terrains.push(e)}}}readOverlays(){this.overlays=[],this.maxOverlayId=0;let t=this.getSection("OverlayPack");if(t){var i=base64StringToUint8Array(t.getConcatenatedValues()),r=new Uint8Array(1<<18);Format5.decodeInto(i,r,80);let e=this.getSection("OverlayDataPack");if(e){var i=base64StringToUint8Array(e.getConcatenatedValues()),s=new Uint8Array(1<<18);Format5.decodeInto(i,s,80);for(let t=0;t<this.fullSize.height;t++)for(let e=2*this.fullSize.width-2;0<=e;e--){var a=e,n=2*t+e%2,o=(a+n)/2+1,l=n-o+this.fullSize.width+1,a=o+512*l,n=r[a];if(255!==n){a=s[a];let e=new Overlay;e.id=n,e.value=a,e.rx=o,e.ry=l,this.overlays.push(e),this.maxOverlayId=Math.max(this.maxOverlayId,n)}}}else console.warn("[OverlayDataPack] section not found. Skipping.")}else console.warn("[Overlay] section not found. Skipping.")}readSmudges(){this.smudges=[];let e=this.getSection("Smudge");if(e)for(var t of e.entries.values()){var i=t.split(",");if(i.length<=2)console.warn(`Invalid Smudge entry: "${t}"`);else{let e=new Smudge;e.name=i[0],e.rx=Number(i[1]),e.ry=Number(i[2]),this.smudges.push(e)}}}decodePreviewImage(){let e=this.getSection("Preview"),t=this.getSection("PreviewPack");if(e&&t){var[,,i,r]=e.getArray("Size").map(e=>Number(e)),s=base64StringToUint8Array(t.getConcatenatedValues()),r=new RgbBitmap(i,r);return Format5.decodeInto(s,r.data),r}}}MapFile.artSectionPrefix="ART",function(e){e[e.GDI=0]="GDI",e[e.Nod=1]="Nod",e[e.ThirdSide=2]="ThirdSide",e[e.Civilian=3]="Civilian",e[e.Mutant=4]="Mutant"}(SideType=SideType||{});const sideMap=(new Map).set("GDI",SideType.GDI).set("Nod",SideType.Nod).set("Civilian",SideType.Civilian).set("Mutant",SideType.Mutant).set("ThirdSide",SideType.ThirdSide),defaultUiTooltips=new Map([["Americans","STT:PlayerSideAmerica"],["Alliance","STT:PlayerSideKorea"],["French","STT:PlayerSideFrance"],["Germans","STT:PlayerSideGermany"],["British","STT:PlayerSideBritain"],["Africans","STT:PlayerSideLibya"],["Arabs","STT:PlayerSideIraq"],["Confederation","STT:PlayerSideCuba"],["Russians","STT:PlayerSideRussia"],["YuriCountry","STT:PlayerSideYuriCountry"]]);class CountryRules{constructor(e){this.id=e}readIni(e){this.name=e.name,this.uiName=e.getString("UIName"),this.uiTooltip=e.getString("UITooltip")||defaultUiTooltips.get(this.name);var t=e.getString("Side");if(!t)throw new Error(`Missing Side for country "${this.name}"`);var i=sideMap.get(t);if(void 0===i)throw new Error(`Unknown side "${t}" for country "${this.name}"`);this.side=i,this.multiplay=e.getBool("Multiplay"),this.multiplayPassive=e.getBool("MultiplayPassive"),this.veteranAircraft=e.getArray("VeteranAircraft"),this.veteranInfantry=e.getArray("VeteranInfantry"),this.veteranUnits=e.getArray("VeteranUnits")}}class ObjectRules{static iniSpeedToLeptonsPerTick(e,t){return Math.min(256,256*e/t)}static iniRotToDegsPerTick(e){return e/256*360}constructor(e,t,i=-1,r){this.type=e,this.ini=t,this.index=i,this.generalRules=r,this.parse()}parse(){this.alphaImage=this.ini.getString("AlphaImage")||void 0,this.alternateArcticArt=this.ini.getBool("AlternateArcticArt"),this.crushable=this.ini.getBool("Crushable",this.type===ObjectType.Infantry),this.crushSound=this.ini.getString("CrushSound")||void 0,this.dontScore=this.ini.getBool("DontScore"),this.insignificant=this.ini.getBool("Insignificant"),this.legalTarget=this.ini.getBool("LegalTarget",!0),this.noShadow=this.ini.getBool("NoShadow"),this.uiName=this.ini.getString("UIName")}get name(){return this.ini.name}get imageName(){let e=this.ini.getString("Image");return e&&"null"!==e||(e=this.name),e}}ObjectRules.IMAGE_NONE="none";class WeaponRules{constructor(e){this.rules=e,this.parse()}parse(){this.ambientDamage=this.rules.getNumber("AmbientDamage"),this.anim=this.rules.getArray("Anim"),this.areaFire=this.rules.getBool("AreaFire"),this.burst=this.rules.getNumber("Burst",1),this.cellRangefinding=this.rules.getBool("CellRangefinding"),this.damage=this.rules.getNumber("Damage"),this.decloakToFire=this.rules.getBool("DecloakToFire",!0),this.fireOnce=this.rules.getBool("FireOnce"),this.isAlternateColor=this.rules.getBool("IsAlternateColor"),this.isElectricBolt=this.rules.getBool("IsElectricBolt"),this.isHouseColor=this.rules.getBool("IsHouseColor"),this.isLaser=this.rules.getBool("IsLaser"),this.isRadBeam=this.rules.getBool("IsRadBeam"),this.isSonic=this.rules.getBool("IsSonic"),this.laserDuration=this.rules.getNumber("LaserDuration"),this.limboLaunch=this.rules.getBool("LimboLaunch"),this.minimumRange=this.rules.getNumber("MinimumRange"),this.name=this.rules.name,this.neverUse=this.rules.getBool("NeverUse"),this.omniFire=this.rules.getBool("OmniFire"),this.projectile=this.rules.getString("Projectile"),this.radLevel=this.rules.getNumber("RadLevel"),this.range=this.rules.getNumber("Range"),-2===this.range&&(this.range=Number.POSITIVE_INFINITY),this.report=this.rules.getArray("Report"),this.revealOnFire=this.rules.getBool("RevealOnFire",!0),this.rof=this.rules.getNumber("ROF"),this.sabotageCursor=this.rules.getBool("SabotageCursor"),this.spawner=this.rules.getBool("Spawner");var e=this.rules.getNumber("Speed");this.iniSpeed=e,this.speed=ObjectRules.iniSpeedToLeptonsPerTick(e,100),this.suicide=this.rules.getBool("Suicide"),this.useSparkParticles=this.rules.getBool("UseSparkParticles"),this.warhead=this.rules.getString("Warhead")}}class AudioVisualRules{readIni(e){this.ini=e,this.ambientChangeRate=e.getNumber("AmbientChangeRate"),this.ambientChangeStep=e.getNumber("AmbientChangeStep"),this.behind=e.getString("Behind"),this.bridgeExplosions=e.getArray("BridgeExplosions"),this.chronoBeamColor=e.getNumberArray("ChronoBeamColor"),this.chronoBlast=e.getString("ChronoBlast"),this.chronoBlastDest=e.getString("ChronoBlastDest"),this.chronoPlacement=e.getString("ChronoPlacement"),this.chronoSparkle1=e.getString("ChronoSparkle1"),this.conditionRed=e.getNumber("ConditionRed"),this.conditionYellow=e.getNumber("ConditionYellow"),this.creditTicks=e.getArray("CreditTicks"),this.extraAircraftLight=e.getNumber("ExtraAircraftLight"),this.extraInfantryLight=e.getNumber("ExtraInfantryLight"),this.extraUnitLight=e.getNumber("ExtraUnitLight");let t=e.getString("DamageFireTypes");t=t||"FIRE01,FIRE02,FIRE03",this.fireNames=t.split(/\.|,/).filter(e=>""!==e),this.flyerHelper=e.getString("FlyerHelper"),this.gravity=e.getNumber("Gravity"),this.idleActionFrequency=60*e.getNumber("IdleActionFrequency"),this.impactLandSound=e.getString("ImpactLandSound")||void 0,this.impactWaterSound=e.getString("ImpactWaterSound")||void 0,this.infantryExplode=e.getString("InfantryExplode"),this.flamingInfantry=e.getString("FlamingInfantry"),this.infantryHeadPop=e.getString("InfantryHeadPop"),this.infantryNuked=e.getString("InfantryNuked"),this.ironCurtainInvokeAnim=e.getString("IronCurtainInvokeAnim"),this.messageDuration=e.getNumber("MessageDuration",10),this.metallicDebris=e.getArray("MetallicDebris"),this.nukeTakeOff=e.getString("NukeTakeOff"),this.deadBodies=e.getArray("DeadBodies"),this.wake=e.getString("Wake"),this.parachute=e.getString("Parachute"),this.moveFlash=e.getString("MoveFlash"),this.warpOut=e.getString("WarpOut"),this.warpAway=e.getString("WarpAway"),this.weaponNullifyAnim=e.getString("WeaponNullifyAnim"),this.weatherConClouds=e.getArray("WeatherConClouds"),this.weatherConBoltExplosion=e.getString("WeatherConBoltExplosion"),this.weatherConBolts=e.getArray("WeatherConBolts")}}!function(e){e[e.GenericCombat=0]="GenericCombat",e[e.GenericNonCombat=1]="GenericNonCombat",e[e.DropZone=2]="DropZone",e[e.BaseUnderAttack=3]="BaseUnderAttack",e[e.HarvesterUnderAttack=4]="HarvesterUnderAttack",e[e.EnemyObjectSensed=5]="EnemyObjectSensed"}(RadarEventType=RadarEventType||{});class RadarRules{readIni(e){return this.eventSuppressionDistances=e.getNumberArray("RadarEventSuppressionDistances"),this.eventVisibilityDurations=e.getNumberArray("RadarEventVisibilityDurations"),this.eventDurations=e.getNumberArray("RadarEventDurations"),this.flashFrameTime=e.getNumber("FlashFrameTime"),this.combatFlashTime=e.getNumber("RadarCombatFlashTime"),this.eventMinRadius=e.getNumber("RadarEventMinRadius"),this.eventSpeed=e.getNumber("RadarEventSpeed"),this.eventRotationSpeed=e.getNumber("RadarEventRotationSpeed"),this.eventColorSpeed=e.getNumber("RadarEventColorSpeed"),this}getEventSuppresionDistance(e){if(e>this.eventSuppressionDistances.length-1)throw new RangeError("No event suppression distance is defined for type "+RadarEventType[e]);return this.eventSuppressionDistances[e]}getEventVisibilityDuration(e){if(e>this.eventVisibilityDurations.length-1)throw new RangeError("No event visibility duration is defined for type "+RadarEventType[e]);return this.eventVisibilityDurations[e]}getEventDuration(e){if(e>this.eventDurations.length-1)throw new RangeError("No event duration is defined for type "+RadarEventType[e]);return this.eventDurations[e]}}class RepairRules{readIni(e){return this.reloadRate=e.getNumber("ReloadRate"),this.repairPercent=e.getNumber("RepairPercent"),this.repairRate=e.getNumber("RepairRate"),this.repairStep=e.getNumber("RepairStep"),this.uRepairRate=e.getNumber("URepairRate"),this.iRepairRate=e.getNumber("IRepairRate"),this.iRepairStep=e.getNumber("IRepairStep"),this}}class VeteranRules{readIni(e){return this.veteranRatio=e.getNumber("VeteranRatio",3),this.veteranCombat=e.getNumber("VeteranCombat",1),this.veteranSpeed=e.getNumber("VeteranSpeed",1),this.veteranSight=Math.max(1,e.getNumber("VeteranSight",1)),this.veteranArmor=e.getNumber("VeteranArmor",1),this.veteranROF=e.getNumber("VeteranROF",1),this.veteranCap=e.getNumber("VeteranCap",2),this.initialVeteran=e.getBool("InitialVeteran"),this}}class CrewRules{readIni(e){return this.alliedCrew=e.getString("AlliedCrew"),this.alliedSurvivorDivisor=e.getNumber("AlliedSurvivorDivisor"),this.crewEscape=e.getNumber("CrewEscape"),this.sovietCrew=e.getString("SovietCrew"),this.sovietSurvivorDivisor=e.getNumber("SovietSurvivorDivisor"),this.survivorRate=e.getNumber("SurvivorRate"),this.thirdCrew=e.getString("ThirdCrew"),this.thirdSurvivorDivisor=e.getNumber("ThirdSurvivorDivisor"),this}}class PrismRules{readIni(e){return this.type=e.getString("PrismType"),this.supportHeight=e.getNumber("PrismSupportHeight"),this.supportMax=e.getNumber("PrismSupportMax"),this.supportModifier=e.getNumber("PrismSupportModifier",1),this}}class ThreatRules{readIni(e){return this.myEffectivenessCoefficientDefault=e.getNumber("MyEffectivenessCoefficientDefault"),this.targetEffectivenessCoefficientDefault=e.getNumber("TargetEffectivenessCoefficientDefault"),this.targetSpecialThreatCoefficientDefault=e.getNumber("TargetSpecialThreatCoefficientDefault"),this.targetStrengthCoefficientDefault=e.getNumber("TargetStrengthCoefficientDefault"),this.targetDistanceCoefficientDefault=e.getNumber("TargetDistanceCoefficientDefault"),this}}class ParadropRules{readIni(e){if(this.allyParaDrop=this.readParadropSquad(e.getArray("AllyParaDropInf"),e.getNumberArray("AllyParaDropNum"),"Ally"),this.amerParaDrop=this.readParadropSquad(e.getArray("AmerParaDropInf"),e.getNumberArray("AmerParaDropNum"),"Amer"),this.sovParaDrop=this.readParadropSquad(e.getArray("SovParaDropInf"),e.getNumberArray("SovParaDropNum"),"Sov"),this.yuriParaDrop=this.readParadropSquad(e.getArray("YuriParaDropInf"),e.getNumberArray("YuriParaDropNum"),"Yuri"),this.paradropPlane=e.getString("ParadropPlane"),!this.paradropPlane)throw new Error("Missing rules [General]->ParadropPlane");return this.paradropRadius=e.getNumber("ParadropRadius"),this}readParadropSquad(t,i,e){if(t.length!==i.length)throw new RangeError(`${e}ParaDropInf/Num size mismatch (${t.length}, ${i.length})`);let r=[];for(let e=0;e<t.length;++e)0<i[e]&&r.push({inf:t[e],num:i[e]});return r}getParadropSquads(e){switch(e){case SideType.GDI:return this.allyParaDrop;case SideType.Nod:return this.sovParaDrop;case SideType.ThirdSide:return this.yuriParaDrop;default:throw new Error(`Unhandled side type "${e}"`)}}}class LightningStormRules{readIni(e){return this.deferment=e.getNumber("LightningDeferment"),this.damage=e.getNumber("LightningDamage"),this.duration=e.getNumber("LightningStormDuration"),this.warhead=e.getString("LightningWarhead"),this.hitDelay=e.getNumber("LightningHitDelay"),this.scatterDelay=e.getNumber("LightningScatterDelay"),this.cellSpread=e.getNumber("LightningCellSpread"),this.separation=e.getNumber("LightningSeparation"),this}}class MissileRules{}class V3RocketRules extends MissileRules{readIni(e){return this.pauseFrames=e.getNumber("V3RocketPauseFrames"),this.tiltFrames=e.getNumber("V3RocketTiltFrames"),this.pitchInitial=e.getNumber("V3RocketPitchInitial"),this.pitchFinal=e.getNumber("V3RocketPitchFinal"),this.turnRate=e.getNumber("V3RocketTurnRate"),this.acceleration=e.getNumber("V3RocketAcceleration"),this.altitude=e.getNumber("V3RocketAltitude"),this.damage=e.getNumber("V3RocketDamage"),this.eliteDamage=e.getNumber("V3RocketEliteDamage"),this.bodyLength=e.getNumber("V3RocketBodyLength"),this.lazyCurve=e.getBool("V3RocketLazyCurve"),this.type=e.getString("V3RocketType"),this}}class DMislRules extends MissileRules{readIni(e){return this.pauseFrames=e.getNumber("DMislPauseFrames"),this.tiltFrames=e.getNumber("DMislTiltFrames"),this.pitchInitial=e.getNumber("DMislPitchInitial"),this.pitchFinal=e.getNumber("DMislPitchFinal"),this.turnRate=e.getNumber("DMislTurnRate"),this.acceleration=e.getNumber("DMislAcceleration"),this.altitude=e.getNumber("DMislAltitude"),this.damage=e.getNumber("DMislDamage"),this.eliteDamage=e.getNumber("DMislEliteDamage"),this.bodyLength=e.getNumber("DMislBodyLength"),this.lazyCurve=e.getBool("DMislLazyCurve"),this.type=e.getString("DMislType"),this}}class HoverRules{readIni(e){return this.height=e.getNumber("HoverHeight"),this.dampen=e.getNumber("HoverDampen"),this.bob=e.getNumber("HoverBob"),this.boost=e.getNumber("HoverBoost"),this.acceleration=e.getNumber("HoverAcceleration"),this.brake=e.getNumber("HoverBrake"),this}}!function(e){e[e.Power=0]="Power",e[e.Factory=1]="Factory",e[e.Barracks=2]="Barracks",e[e.Radar=3]="Radar",e[e.Tech=4]="Tech",e[e.Proc=5]="Proc"}(PrereqCategory=PrereqCategory||{});const prereqCategIniKeys=(new Map).set(PrereqCategory.Power,"PrerequisitePower").set(PrereqCategory.Factory,"PrerequisiteFactory").set(PrereqCategory.Barracks,"PrerequisiteBarracks").set(PrereqCategory.Radar,"PrerequisiteRadar").set(PrereqCategory.Tech,"PrerequisiteTech").set(PrereqCategory.Proc,"PrerequisiteProc");class GeneralRules{constructor(){this.prereqCategories=new Map}readIni(e){this.aircraftFogReveal=e.getNumber("AircraftFogReveal"),this.alliedDisguise=e.getString("AlliedDisguise"),this.baseUnit=e.getArray("BaseUnit"),this.bridgeVoxelMax=e.getNumber("BridgeVoxelMax"),this.buildSpeed=e.getFixed("BuildSpeed"),this.buildupTime=e.getNumber("BuildupTime"),this.chronoDelay=e.getNumber("ChronoDelay"),this.chronoDistanceFactor=e.getNumber("ChronoDistanceFactor",32),this.chronoHarvTooFarDistance=e.getNumber("ChronoHarvTooFarDistance"),this.chronoMinimumDelay=e.getNumber("ChronoMinimumDelay"),this.chronoRangeMinimum=e.getNumber("ChronoRangeMinimum"),this.chronoTrigger=e.getBool("ChronoTrigger",!0),this.cliffBackImpassability=e.getNumber("CliffBackImpassability",2),this.cloakDelay=e.getNumber("CloakDelay"),this.closeEnough=e.getNumber("CloseEnough"),this.crew=(new CrewRules).readIni(e),this.defaultMirageDisguises=e.getArray("DefaultMirageDisguises"),this.dMisl=(new DMislRules).readIni(e),this.dropPodWeapon=e.getString("DropPodWeapon"),this.engineer=e.getString("Engineer"),this.engineerCaptureLevel=e.getFixed("EngineerCaptureLevel",.25),this.engineerDamage=e.getFixed("EngineerDamage",.437),this.engineerAlwaysCaptureTech=e.getBool("EngineerAlwaysCaptureTech",!0),this.flightLevel=e.getNumber("FlightLevel"),this.guardAreaTargetingDelay=e.getNumber("GuardAreaTargetingDelay"),this.harvesterTooFarDistance=e.getNumber("HarvesterTooFarDistance"),this.harvesterUnit=e.getArray("HarvesterUnit"),this.hover=(new HoverRules).readIni(e),this.infantryBlinkDisguiseTime=e.getNumber("InfantryBlinkDisguiseTime"),this.lightningStorm=(new LightningStormRules).readIni(e),this.lowPowerPenaltyModifier=e.getNumber("LowPowerPenaltyModifier",1),this.minLowPowerProductionSpeed=e.getFixed("MinLowPowerProductionSpeed",.5),this.maxLowPowerProductionSpeed=e.getFixed("MaxLowPowerProductionSpeed",1),this.maximumCheerRate=e.getNumber("MaximumCheerRate"),this.maximumQueuedObjects=e.getNumber("MaximumQueuedObjects"),this.maxWaypointPathLength=e.getNumber("MaxWaypointPathLength"),this.multipleFactory=e.getFixed("MultipleFactory",1),this.normalTargetingDelay=e.getNumber("NormalTargetingDelay"),this.padAircraft=e.getArray("PadAircraft"),this.parachuteMaxFallRate=e.getNumber("ParachuteMaxFallRate"),this.paradrop=(new ParadropRules).readIni(e),this.prism=(new PrismRules).readIni(e),this.purifierBonus=e.getNumber("PurifierBonus"),this.radar=(new RadarRules).readIni(e),this.refundPercent=clamp(e.getNumber("RefundPercent"),0,1),this.repair=(new RepairRules).readIni(e),this.returnStructures=e.getBool("ReturnStructures"),this.revealTriggerRadius=Math.min(10,e.getNumber("RevealTriggerRadius")),this.shipSinkingWeight=e.getNumber("ShipSinkingWeight"),this.sovietDisguise=e.getString("SovietDisguise"),this.spyMoneyStealPercent=e.getNumber("SpyMoneyStealPercent"),this.spyPowerBlackout=e.getNumber("SpyPowerBlackout"),this.technician=e.getString("Technician"),this.thirdDisguise=e.getString("ThirdDisguise"),this.threat=(new ThreatRules).readIni(e),this.treeStrength=e.getNumber("TreeStrength"),this.unitsUnsellable=e.getBool("UnitsUnsellable"),this.v3Rocket=(new V3RocketRules).readIni(e),this.veteran=(new VeteranRules).readIni(e),this.wallBuildSpeedCoefficient=e.getFixed("WallBuildSpeedCoefficient"),this.readPrereqCategories(e)}readPrereqCategories(e){for(var[t,i]of prereqCategIniKeys){if(!e.has(i))throw new Error(`Missing prerequisite category ${i} in [General] section`);this.prereqCategories.set(t,e.getArray(i))}}getMissileRules(e){switch(e){case this.v3Rocket.type:return this.v3Rocket;case this.dMisl.type:return this.dMisl;default:throw new Error(`Unsupported missile type "${e}"`)}}}!function(e){e[e.Default=0]="Default",e[e.Tunnel=5]="Tunnel",e[e.Railroad=6]="Railroad",e[e.Rock1=7]="Rock1",e[e.Rock2=8]="Rock2",e[e.Water=9]="Water",e[e.Shore=10]="Shore",e[e.Pavement=11]="Pavement",e[e.Dirt=12]="Dirt",e[e.Clear=13]="Clear",e[e.Rough=14]="Rough",e[e.Cliff=15]="Cliff"}(TerrainType=TerrainType||{}),function(e){e[e.Clear=0]="Clear",e[e.Road=1]="Road",e[e.Rock=2]="Rock",e[e.Beach=3]="Beach",e[e.Rough=4]="Rough",e[e.Railroad=5]="Railroad",e[e.Weeds=6]="Weeds",e[e.Water=7]="Water",e[e.Wall=8]="Wall",e[e.Tiberium=9]="Tiberium",e[e.Cliff=10]="Cliff"}(LandType=LandType||{});const terrainToLandType=new Map([[TerrainType.Default,LandType.Clear],[TerrainType.Clear,LandType.Clear],[TerrainType.Tunnel,LandType.Cliff],[TerrainType.Railroad,LandType.Railroad],[TerrainType.Rock1,LandType.Rock],[TerrainType.Rock2,LandType.Rock],[TerrainType.Water,LandType.Water],[TerrainType.Shore,LandType.Beach],[TerrainType.Pavement,LandType.Road],[TerrainType.Dirt,LandType.Road],[TerrainType.Rough,LandType.Rough],[TerrainType.Cliff,LandType.Cliff]]);function getLandType(e){if(!terrainToLandType.has(e))throw new Error("Unknown terrain type "+e);return terrainToLandType.get(e)}!function(e){e[e.Foot=0]="Foot",e[e.Track=1]="Track",e[e.Wheel=2]="Wheel",e[e.Hover=3]="Hover",e[e.Float=4]="Float",e[e.FloatBeach=5]="FloatBeach",e[e.Amphibious=6]="Amphibious",e[e.Winged=7]="Winged"}(SpeedType=SpeedType||{});class LandRules{constructor(){this.speedModifiers=new Map}readIni(t){return this.buildable=t.getBool("Buildable",!1),[...t.entries.keys()].forEach(e=>{void 0!==SpeedType[e]&&this.speedModifiers.set(SpeedType[e],t.getNumber(e))}),this}getSpeedModifier(e){if(e===SpeedType.Foot&&0===this.speedModifiers.get(SpeedType.Track))return 0;let t=this.speedModifiers.get(e);return void 0===t&&(t=1),e!==SpeedType.Track&&e!==SpeedType.Wheel&&0<t&&(t=1),t}}!function(e){e[e.None=0]="None",e[e.Gunfire=1]="Gunfire",e[e.Explode=2]="Explode",e[e.ExplodeAlt=3]="ExplodeAlt",e[e.Fire=4]="Fire",e[e.Electro=5]="Electro",e[e.HeadExplode=6]="HeadExplode",e[e.Nuke=7]="Nuke"}(InfDeathType=InfDeathType||{});class WarheadRules{constructor(e){this.rules=e,this.verses=new Map,this.parse()}get name(){return this.rules.name}parse(){this.affectsAllies=this.rules.getBool("AffectsAllies",!0),this.animList=this.rules.getArray("AnimList"),this.bombDisarm=this.rules.getBool("BombDisarm"),this.bullets=this.rules.getBool("Bullets"),this.causesDelayKill=this.rules.getBool("CausesDelayKill"),this.cellSpread=this.rules.getNumber("CellSpread"),this.conventional=this.rules.getBool("Conventional"),this.culling=this.rules.getBool("Culling"),this.delayKillAtMax=this.rules.getNumber("DelayKillAtMax"),this.delayKillFrames=this.rules.getNumber("DelayKillFrames"),this.electricAssault=this.rules.getBool("ElectricAssault"),this.emEffect=this.rules.getBool("EMEffect"),this.infDeath=this.rules.getEnumNumeric("InfDeath",InfDeathType,InfDeathType.None),this.ivanBomb=this.rules.getBool("IvanBomb"),this.makesDisguise=this.rules.getBool("MakesDisguise"),this.mindControl=this.rules.getBool("MindControl"),this.nukeMaker=this.rules.getBool("NukeMaker"),this.paralyzes=this.rules.getNumber("Paralyzes"),this.parasite=this.rules.getBool("Parasite"),this.percentAtMax=this.rules.getNumber("PercentAtMax",1),this.proneDamage=this.rules.getFixed("ProneDamage",1),this.psychicDamage=this.rules.getBool("PsychicDamage"),this.radiation=this.rules.getBool("Radiation"),this.rocker=this.rules.getBool("Rocker"),this.sonic=this.rules.getBool("Sonic"),this.temporal=this.rules.getBool("Temporal");let e=this.rules.getFixedArray("Verses");e.forEach((e,t)=>this.verses.set(t,e)),this.wallAbsoluteDestroyer=this.rules.getBool("WallAbsoluteDestroyer"),this.wall=this.rules.getBool("Wall"),this.wood=this.rules.getBool("Wood")}}class ProjectileRules extends ObjectRules{parse(){super.parse();var e=this.ini.getNumber("ROT",0);let t=this.ini.getNumber("Acceleration");1!==e||t||(t=Number.POSITIVE_INFINITY),t=t||3,this.acceleration=t,this.arcing=this.ini.getBool("Arcing"),this.courseLockDuration=this.ini.getNumber("CourseLockDuration"),this.detonationAltitude=this.ini.getNumber("DetonationAltitude"),this.firersPalette=this.ini.getBool("FirersPalette"),this.flakScatter=this.ini.getBool("FlakScatter"),this.inaccurate=this.ini.getBool("Inaccurate"),this.inviso=this.ini.getBool("Inviso"),this.isAntiAir=this.ini.getBool("AA"),this.isAntiGround=this.ini.getBool("AG",!0),this.level=this.ini.getBool("Level"),this.rot=ObjectRules.iniRotToDegsPerTick(e),this.iniRot=e,this.shadow=this.ini.getBool("Shadow",!0),this.shrapnelWeapon=this.ini.getString("ShrapnelWeapon")||void 0,this.shrapnelCount=this.ini.getNumber("ShrapnelCount"),this.subjectToCliffs=this.ini.getBool("SubjectToCliffs"),this.subjectToElevation=this.ini.getBool("SubjectToElevation"),this.subjectToWalls=this.ini.getBool("SubjectToWalls"),this.vertical=this.ini.getBool("Vertical")}}!function(e){e[e.Green=0]="Green",e[e.Yellow=1]="Yellow",e[e.White=2]="White",e[e.Red=3]="Red",e[e.Blue=4]="Blue"}(PipColor=PipColor||{}),function(e){e[e.Statue=0]="Statue",e[e.Aircraft=1]="Aircraft",e[e.Chrono=2]="Chrono",e[e.Hover=3]="Hover",e[e.Infantry=4]="Infantry",e[e.Jumpjet=5]="Jumpjet",e[e.Missile=6]="Missile",e[e.Ship=7]="Ship",e[e.Vehicle=8]="Vehicle"}(LocomotorType=LocomotorType||{});const locomotorTypesByClsId=new Map([["{4A582746-9839-11d1-B709-00A024DDAFD1}",LocomotorType.Aircraft],["{4A582747-9839-11d1-B709-00A024DDAFD1}",LocomotorType.Chrono],["{4A582742-9839-11d1-B709-00A024DDAFD1}",LocomotorType.Hover],["{4A582744-9839-11d1-B709-00A024DDAFD1}",LocomotorType.Infantry],["{92612C46-F71F-11d1-AC9F-006008055BB5}",LocomotorType.Jumpjet],["{B7B49766-E576-11d3-9BD9-00104B972FE8}",LocomotorType.Missile],["{2BEA74E1-7CCA-11d3-BE14-00104B62A16C}",LocomotorType.Ship],["{4A582741-9839-11d1-B709-00A024DDAFD1}",LocomotorType.Vehicle]]),defaultSpeedsByLocomotor=new Map([[LocomotorType.Infantry,SpeedType.Foot],[LocomotorType.Ship,SpeedType.Float],[LocomotorType.Hover,SpeedType.Hover],[LocomotorType.Jumpjet,SpeedType.Winged],[LocomotorType.Aircraft,SpeedType.Winged],[LocomotorType.Missile,SpeedType.Winged]]);!function(e){e[e.Amphibious=0]="Amphibious",e[e.AmphibiousCrusher=1]="AmphibiousCrusher",e[e.AmphibiousDestroyer=2]="AmphibiousDestroyer",e[e.Crusher=3]="Crusher",e[e.CrusherAll=4]="CrusherAll",e[e.Destroyer=5]="Destroyer",e[e.Fly=6]="Fly",e[e.Infantry=7]="Infantry",e[e.InfantryDestroyer=8]="InfantryDestroyer",e[e.Normal=9]="Normal",e[e.Subterranean=10]="Subterranean",e[e.Water=11]="Water"}(MovementZone=MovementZone||{}),function(e){e[e.None=0]="None",e[e.Flak=1]="Flak",e[e.Plate=2]="Plate",e[e.Light=3]="Light",e[e.Medium=4]="Medium",e[e.Heavy=5]="Heavy",e[e.Wood=6]="Wood",e[e.Steel=7]="Steel",e[e.Concrete=8]="Concrete",e[e.Special_1=9]="Special_1",e[e.Special_2=10]="Special_2"}(ArmorType=ArmorType||{}),function(e){e[e.LandOk=0]="LandOk",e[e.LandNotOk=1]="LandNotOk",e[e.LandSecondary=2]="LandSecondary"}(LandTargeting=LandTargeting||{}),function(e){e[e.UnderwaterNever=0]="UnderwaterNever",e[e.UnderwaterSecondary=1]="UnderwaterSecondary",e[e.UnderwaterOnly=2]="UnderwaterOnly",e[e.OrganicSecondary=3]="OrganicSecondary",e[e.SealSpecial=4]="SealSpecial",e[e.NavalAll=5]="NavalAll",e[e.NavalNone=6]="NavalNone"}(NavalTargeting=NavalTargeting||{}),function(e){e[e.Primary=0]="Primary",e[e.Secondary=1]="Secondary",e[e.DeathWeapon=2]="DeathWeapon"}(WeaponType=WeaponType||{}),function(e){e[e.FASTER=0]="FASTER",e[e.STRONGER=1]="STRONGER",e[e.FIREPOWER=2]="FIREPOWER",e[e.SCATTER=3]="SCATTER",e[e.ROF=4]="ROF",e[e.SIGHT=5]="SIGHT",e[e.SELF_HEAL=6]="SELF_HEAL",e[e.CLOAK=7]="CLOAK",e[e.EXPLODES=8]="EXPLODES",e[e.RADAR_INVISIBLE=9]="RADAR_INVISIBLE",e[e.SENSORS=10]="SENSORS",e[e.FEARLESS=11]="FEARLESS",e[e.C4=12]="C4",e[e.GUARD_AREA=13]="GUARD_AREA",e[e.CRUSHER=14]="CRUSHER"}(VeteranAbility=VeteranAbility||{}),function(e){e[e.None=0]="None",e[e.Normal=1]="Normal",e[e.Strong=2]="Strong"}(VhpScan=VhpScan||{});class GameMath{static reverseSinTableLookup(e,t,i,r){for(;t<=i;){var s=Math.floor((t+i)/2),a=this.SIN_TABLE[s];if(a===e)return s;(r?e<a:a<e)?t=s+1:i=s-1}return Math.abs(e-this.SIN_TABLE[t])<Math.abs(e-this.SIN_TABLE[i])?t:i}static pow(e,t){if(!Number.isFinite(e)||!Number.isFinite(t)||Number.isSafeInteger(e)&&Number.isSafeInteger(t))return e**t;if(!Number.isSafeInteger(t))throw new Error("Exponent must be a safe integer");return Math.floor(e*this.EXP_10_PRECISION)**t/this.EXP_10_PRECISION**t}static sqrt(e){if(0===e)return 0;var t;let i=e/3;for(;t=i,i=(e/i+i)/2,5e-15<Math.abs(t-i););return i}static sin(e){if(!Number.isFinite(e))return NaN;if(!e)return e;e=e/(2*Math.PI)-Math.floor(e/(2*Math.PI)),e=Math.floor(e*this.SIN_TABLE.length);return this.SIN_TABLE[e]}static cos(e){return this.sin(e+Math.PI/2)}static asin(e){if(!isBetween(e,-1,1))return NaN;if(!e)return 0;let t;var i=this.SIN_TABLE.length;return t=0<e?2*Math.PI*this.reverseSinTableLookup(e,0,i/4,!1)/i:Math.PI-2*Math.PI*this.reverseSinTableLookup(e,i/2,.75*i,!0)/i,t}static acos(e){return Math.PI/2-this.asin(e)}static atan2(e,t){if(Number.isNaN(t)||Number.isNaN(e))return NaN;let i;return i=Number.isFinite(e)||Number.isFinite(t)?Number.isFinite(t)&&0!==e?Number.isFinite(e)&&0!==t?this.atan2FiniteNonZero(e,t):this.signIncZero(e)*Math.PI*.5:this.signIncZero(e)*(this.signIncZero(t)<0?Math.PI:0):Math.sign(e)*Math.PI*(0<Math.sign(t)?.25:.75),i}static atan2FiniteNonZero(e,t){var i=Math.abs(t),r=Math.abs(e),s=Math.min(i,r)/Math.max(i,r),a=s*s;let n=((-.0464964749*a+.15931422)*a-.327622764)*a*s+s;return i<r&&(n=Math.PI/2-n),t<0&&(n=Math.PI-n),e<0&&(n=-n),n}static signIncZero(e){return e===-1/0||1/e<0?-1:1}}GameMath.PRECISION=6,GameMath.EXP_10_PRECISION=10**GameMath.PRECISION,GameMath.SIN_TABLE=[0,.004848117819001859,.009696121685978396,.014543897651582654,.01939133177182437,.024238310110748135,.0290847187431114,.03393044375706223,.03877537125681671,.043619387365336,.04846237822700296,.05330423001029823,.05814482891047582,.06298406115223795,.06782181299240934,.0726579707226106,.07749242067193093,.08232504920959989,.08715574274765817,.09198438774362744,.09681087070317909,.10163507818280187,.10645689679246824,.11127621319829964,.11609291412523022,.12090688635966935,.12571801675216268,.13052619222005157,.13533129975013108,.14013322640130627,.14493185930724672,.1497270856790396,.15451879280784048,.15930686806752256,.16409119891732396,.1688716729044928,.17364817766693033,.17842060093583212,.18318883053832663,.18795275440011186,.19271226054808968,.19746723711299752,.20221757233203794,.20696315455150538,.2117038722294107,.21643961393810288,.22117026836688775,.2258957243246448,.23061587074244014,.2353305966761376,.24003979130900588,.2447433439543238,.24944114405798126,.25413308120107847,.25881904510252074,.26349892562161076,.2681726127606373,.272839996667461,.27750096763809573,.28215541611928774,.2868032327110902,.29144430816943495,.2960785334086999,.3007057995042731,.3053259976951131,.30993901938630514,.31454475615161365,.31914309973603083,.323733942058321,.328317175213561,.33289269147567657,.3374603832999741,.3420201433256687,.34657186437840753,.3511154394727888,.3556507618148765,.3601777248047104,.36469622203881186,.3692061473126844,.3737073946233105,.3781998581716425,.3826834323650898,.3871580118200006,.3916234913641391,.3960797660391568,.4005267311030606,.4049642820326736,.4093923145260926,.4138107245051391,.4182194081178064,.42261826174069944,.4270071819814715,.4313860656812534,.4357548099170794,.4401133120043048,.44446146949902104,.4487991802004621,.4531263421534082,.4574428536505808,.4617486132350339,.46604351970253877,.4703274721039625,.4746003697476404,.4788621122017435,.4831125992966384,.48735173112724234,.49157940805537054,.49579553071207916,.49999999999999994,.5041927170956704,.5083735834518556,.5125425007998652,.5166993711518628,.5208440968031697,.5249765803345602,.5290967246145525,.5332044328016912,.5372996083468239,.5413821549953696,.5454519767895825,.549508978070806,.5535530634817223,.5575841379685927,.5616021067834929,.5656068754865385,.5695983499481065,.573576436351046,.5775410411928851,.5814920712880266,.5854294337699405,.5893530360933448,.593262786036382,.5971585917027862,.6010403615240428,.6049080042615417,.6087614290087207,.6126005451932028,.6164252625789254,.62023549126826,.6240311417041269,.6278121246720986,.6315783513024975,.6353297330724851,.6390661818081416,.6427876096865393,.6464939292378065,.6501850533471834,.6538608952570697,.6575213685690636,.6611663872459932,.6647958656139378,.6684097183642425,.6720078605555224,.6755902076156601,.6791566753437932,.6827071799122926,.6862416378687335,.6897599661378576,.6932620820235242,.696747903210655,.7002173477671685,.7036703341459059,.7071067811865475,.710526608117521,.713929734557899,.7173160805192894,.7206855664077146,.7240381130254825,.7273736415730487,.7306920736508674,.7339933312612352,.7372773368101241,.7405440131090046,.7437932833766612,.747025071240996,.7502393007408245,.7534358963276606,.7566147828674927,.7597758856425494,.7629191303530553,.766044443118978,.7691517504817651,.7722409794060692,.7753120572814658,.7783649119241599,.7813994715786823,.7844156649195757,.7874134210530723,.7903926695187593,.7933533402912352,.7962953637817558,.7992186708398696,.8021231927550437,.8050088612582783,.8078756085237111,.8107233671702122,.8135520702629676,.8163616513150519,.8191520442889918,.821923183598318,.8246750041091067,.8274074411415104,.8301204304712788,.8328139083312671,.8354878114129364,.8381420768678404,.8407766423091032,.8433914458128856,.845986425919841,.848561521636559,.8511166724369997,.8536518182639162,.8561668995302665,.8586618571206132,.8611366323925137,.8635911671778986,.8660254037844386,.8684392849969005,.870832754078492,.8732057547721958,.8755582313020908,.8778901283746645,.8802013911801111,.8824919653936212,.8847617971766577,.8870108331782216,.8892390205361062,.8914463068781385,.8936326403234122,.8957979694835052,.8979422434636881,.9000654118641211,.9021674247810376,.9042482328079179,.9063077870366499,.9083460390586793,.9103629409661466,.9123584453530141,.9143325053161794,.9162850744565779,.918216106880274,.9201255571995389,.9220133805339185,.9238795325112867,.9257239692688903,.9275466474543786,.9293475242268224,.9311265572577219,.9328837047320004,.9346189253489884,.9363321783233931,.9380234233862578,.9396926207859083,.9413397312888874,.942964716180876,.9445675372676047,.9461481568757504,.947706537853822,.9492426435730339,.9507564379281666,.9522478853384153,.9537169507482269,.955163599628123,.9565877979755122,.9579895123154889,.9593687097016201,.9607253577167205,.9620594244736131,.9633708786158803,.9646596893185995,.9659258262890683,.9671692597675166,.9683899605278059,.969587899878116,.97076304966162,.9719153822571454,.9730448705798238,.9741514880817275,.9752352087524931,.9762960071199334,.9773338582506355,.9783487377505475,.9793406217655515,.980309486982024,.9812553106273847,.9821780704706308,.98307774482286,.9839543125377807,.984807753012208,.9856380461865492,.9864451725452739,.987229113117374,.987989849476809,.9887273637429388,.9894416385809445,.9901326572022359,.9908004033648453,.9914448613738104,.9920660160815423,.9926638528881819,.993238357741943,.9937895171394426,.9943173181260184,.9948217482960331,.9953027957931658,.9957604493106914,.9961946980917455,.9966055319295779,.996992941167792,.9973569167005722,.9976974499728977,.9980145329807433,.9983081582712682,.9985783189429907,.9988250086459504,.9990482215818578,.99924795250423,.9994241967185149,.9995769500822006,.9997062090049132,.9998119704485015,.9998942319271075,.9999529915072262,.9999882478077495,1,.9999882478077495,.9999529915072262,.9998942319271075,.9998119704485015,.9997062090049132,.9995769500822006,.9994241967185149,.99924795250423,.9990482215818578,.9988250086459504,.9985783189429907,.9983081582712682,.9980145329807433,.9976974499728977,.9973569167005722,.996992941167792,.9966055319295779,.9961946980917455,.9957604493106914,.9953027957931658,.9948217482960331,.9943173181260184,.9937895171394426,.993238357741943,.9926638528881819,.9920660160815423,.9914448613738105,.9908004033648453,.9901326572022359,.9894416385809446,.9887273637429388,.987989849476809,.987229113117374,.9864451725452739,.9856380461865492,.984807753012208,.9839543125377807,.98307774482286,.9821780704706307,.9812553106273847,.9803094869820241,.9793406217655516,.9783487377505476,.9773338582506356,.9762960071199334,.9752352087524931,.9741514880817276,.9730448705798238,.9719153822571455,.9707630496616201,.969587899878116,.9683899605278059,.9671692597675166,.9659258262890683,.9646596893185995,.9633708786158803,.9620594244736133,.9607253577167205,.9593687097016202,.9579895123154889,.9565877979755123,.9551635996281231,.9537169507482269,.9522478853384153,.9507564379281666,.949242643573034,.9477065378538221,.9461481568757505,.9445675372676048,.942964716180876,.9413397312888873,.9396926207859084,.9380234233862579,.9363321783233931,.9346189253489885,.9328837047320006,.9311265572577219,.9293475242268225,.9275466474543786,.9257239692688904,.9238795325112867,.9220133805339185,.920125557199539,.918216106880274,.916285074456578,.9143325053161794,.9123584453530141,.9103629409661467,.9083460390586793,.90630778703665,.904248232807918,.9021674247810377,.9000654118641213,.8979422434636883,.8957979694835051,.8936326403234123,.8914463068781386,.8892390205361062,.8870108331782218,.8847617971766579,.8824919653936212,.8802013911801111,.8778901283746644,.8755582313020909,.8732057547721958,.8708327540784921,.8684392849969006,.8660254037844387,.8635911671778987,.8611366323925138,.858661857120613,.8561668995302665,.8536518182639163,.8511166724369997,.8485615216365591,.8459864259198412,.8433914458128856,.8407766423091031,.8381420768678404,.8354878114129364,.8328139083312672,.8301204304712789,.8274074411415107,.8246750041091069,.8219231835983182,.819152044288992,.8163616513150518,.8135520702629675,.8107233671702123,.8078756085237112,.8050088612582784,.802123192755044,.7992186708398695,.7962953637817556,.7933533402912352,.7903926695187593,.7874134210530723,.7844156649195758,.7813994715786824,.7783649119241601,.775312057281466,.7722409794060693,.769151750481765,.766044443118978,.7629191303530551,.7597758856425494,.756614782867493,.7534358963276608,.7502393007408243,.7470250712409959,.7437932833766611,.7405440131090045,.7372773368101241,.7339933312612353,.7306920736508675,.7273736415730488,.7240381130254827,.7206855664077148,.7173160805192896,.713929734557899,.710526608117521,.7071067811865476,.703670334145906,.7002173477671687,.6967479032106549,.6932620820235241,.6897599661378576,.6862416378687336,.6827071799122926,.6791566753437933,.6755902076156604,.6720078605555225,.6684097183642426,.6647958656139381,.6611663872459935,.6575213685690636,.6538608952570697,.6501850533471835,.6464939292378067,.6427876096865395,.6390661818081418,.635329733072485,.6315783513024975,.6278121246720986,.6240311417041269,.6202354912682602,.6164252625789255,.612600545193203,.6087614290087209,.6049080042615419,.6010403615240432,.5971585917027862,.593262786036382,.5893530360933449,.5854294337699406,.5814920712880268,.5775410411928852,.5735764363510459,.5695983499481064,.5656068754865385,.5616021067834929,.5575841379685929,.5535530634817224,.5495089780708062,.5454519767895827,.5413821549953699,.5372996083468241,.5332044328016912,.5290967246145525,.5249765803345602,.5208440968031698,.516699371151863,.5125425007998654,.5083735834518555,.5041927170956703,.49999999999999994,.49579553071207916,.49157940805537065,.48735173112724245,.48311259929663863,.4788621122017437,.47460036974764064,.47032747210396275,.46604351970253877,.4617486132350339,.45744285365058085,.4531263421534083,.44879918020046233,.4444614694990212,.4401133120043047,.43575480991707927,.43138606568125343,.4270071819814714,.4226182617406995,.4182194081178065,.4138107245051393,.40939231452609276,.4049642820326738,.40052673110306086,.3960797660391572,.39162349136413904,.38715801182000065,.3826834323650899,.37819985817164264,.3737073946233107,.3692061473126843,.36469622203881175,.3601777248047104,.3556507618148765,.35111543947278884,.34657186437840765,.3420201433256689,.3374603832999743,.33289269147567685,.32831717521356135,.3237339420583214,.31914309973603083,.3145447561516137,.30993901938630525,.30532599769511326,.30070579950427334,.29607853340870016,.2914443081694349,.2868032327110902,.28215541611928774,.2775009676380958,.2728399966674611,.26817261276063753,.263498925621611,.258819045102521,.2541330812010788,.24944114405798165,.24474334395432376,.24003979130900596,.2353305966761377,.23061587074244033,.225895724324645,.22117026836688802,.21643961393810274,.21170387222941067,.20696315455150538,.20221757233203796,.19746723711299763,.19271226054808982,.18795275440011205,.18318883053832688,.17842060093583242,.17364817766693072,.16887167290449276,.16409119891732402,.15930686806752267,.15451879280784062,.1497270856790398,.14493185930724697,.14013322640130613,.135331299750131,.13052619222005157,.12571801675216274,.12090688635966945,.11609291412523036,.11127621319829985,.1064568967924685,.10163507818280217,.09681087070317945,.09198438774362741,.0871557427476582,.08232504920959997,.07749242067193107,.07265797072261079,.0678218129924096,.06298406115223781,.05814482891047573,.0533042300102982,.04846237822700297,.04361938736533607,.038775371256816835,.03393044375706242,.029084718743111644,.02423831011074843,.01939133177182472,.014543897651583058,.009696121685978408,.004848117819001927,12246467991473532e-32,-.004848117819001238,-.009696121685978163,-.01454389765158237,-.019391331771824474,-.02423831011074774,-.029084718743111398,-.03393044375706173,-.03877537125681659,-.04361938736533583,-.048462378227003174,-.05330423001029795,-.05814482891047593,-.06298406115223758,-.06782181299240934,-.07265797072261056,-.07749242067193128,-.08232504920959974,-.08715574274765794,-.09198438774362716,-.09681087070317876,-.10163507818280193,-.10645689679246781,-.1112762131982996,-.11609291412523012,-.12090688635966965,-.1257180167521625,-.13052619222005177,-.13533129975013078,-.14013322640130632,-.14493185930724675,-.14972708567904,-.1545187928078404,-.15930686806752198,-.16409119891732377,-.16887167290449254,-.17364817766693047,-.17842060093583176,-.18318883053832663,-.1879527544001114,-.1927122605480896,-.19746723711299738,-.20221757233203816,-.20696315455150513,-.21170387222941087,-.21643961393810252,-.2211702683668878,-.22589572432464475,-.23061587074244053,-.23533059667613745,-.2400397913090053,-.2447433439543235,-.24944114405798098,-.2541330812010786,-.25881904510252035,-.2634989256216107,-.26817261276063686,-.2728399966674609,-.27750096763809556,-.2821554161192879,-.28680323271108993,-.29144430816943506,-.29607853340869994,-.30070579950427306,-.30532599769511304,-.3099390193863046,-.3145447561516135,-.3191430997360306,-.3237339420583211,-.3283171752135607,-.33289269147567657,-.3374603832999737,-.34202014332566866,-.3465718643784074,-.35111543947278906,-.35565076181487626,-.36017772480471055,-.3646962220388115,-.3692061473126845,-.3737073946233105,-.3781998581716428,-.38268343236508967,-.38715801182000004,-.3916234913641388,-.39607976603915657,-.40052673110306064,-.4049642820326732,-.40939231452609254,-.41381072450513867,-.4182194081178062,-.4226182617406993,-.4270071819814716,-.4313860656812532,-.43575480991707943,-.4401133120043045,-.444461469499021,-.4487991802004621,-.4531263421534085,-.4574428536505806,-.46174861323503374,-.46604351970253854,-.47032747210396214,-.4746003697476404,-.47886211220174313,-.4831125992966384,-.4873517311272422,-.4915794080553708,-.49579553071207894,-.5000000000000001,-.50419271709567,-.5083735834518556,-.5125425007998652,-.5166993711518633,-.5208440968031696,-.5249765803345596,-.5290967246145523,-.533204432801691,-.5372996083468239,-.5413821549953693,-.5454519767895825,-.5495089780708056,-.5535530634817222,-.5575841379685926,-.5616021067834931,-.5656068754865384,-.5695983499481065,-.5735764363510458,-.577541041192885,-.5814920712880266,-.5854294337699408,-.5893530360933448,-.5932627860363815,-.597158591702786,-.6010403615240426,-.6049080042615417,-.6087614290087203,-.6126005451932028,-.6164252625789249,-.6202354912682599,-.6240311417041268,-.6278121246720987,-.6315783513024973,-.6353297330724852,-.6390661818081416,-.6427876096865393,-.6464939292378065,-.6501850533471829,-.6538608952570695,-.6575213685690635,-.6611663872459933,-.6647958656139376,-.6684097183642425,-.6720078605555221,-.6755902076156601,-.6791566753437931,-.6827071799122927,-.6862416378687334,-.6897599661378577,-.693262082023524,-.696747903210655,-.7002173477671685,-.7036703341459061,-.7071067811865475,-.7105266081175206,-.7139297345578989,-.7173160805192892,-.7206855664077146,-.7240381130254823,-.7273736415730487,-.7306920736508671,-.7339933312612352,-.737277336810124,-.7405440131090048,-.743793283376661,-.747025071240996,-.7502393007408242,-.7534358963276607,-.7566147828674927,-.7597758856425493,-.7629191303530554,-.7660444431189779,-.7691517504817651,-.7722409794060688,-.7753120572814659,-.7783649119241597,-.7813994715786822,-.7844156649195754,-.7874134210530722,-.7903926695187589,-.7933533402912349,-.7962953637817558,-.79921867083987,-.8021231927550437,-.8050088612582785,-.8078756085237111,-.8107233671702119,-.8135520702629674,-.8163616513150515,-.8191520442889916,-.8219231835983181,-.8246750041091064,-.8274074411415104,-.830120430471279,-.8328139083312671,-.8354878114129365,-.8381420768678401,-.8407766423091032,-.8433914458128855,-.8459864259198411,-.8485615216365587,-.8511166724369996,-.8536518182639165,-.8561668995302664,-.8586618571206132,-.8611366323925135,-.8635911671778986,-.8660254037844385,-.8684392849969005,-.8708327540784918,-.8732057547721956,-.8755582313020905,-.8778901283746643,-.8802013911801112,-.8824919653936215,-.8847617971766578,-.8870108331782218,-.889239020536106,-.8914463068781383,-.8936326403234122,-.8957979694835049,-.897942243463688,-.9000654118641208,-.9021674247810375,-.9042482328079179,-.90630778703665,-.9083460390586792,-.9103629409661468,-.912358445353014,-.9143325053161795,-.9162850744565778,-.918216106880274,-.9201255571995388,-.9220133805339183,-.9238795325112865,-.9257239692688903,-.9275466474543786,-.9293475242268223,-.9311265572577219,-.9328837047320003,-.9346189253489884,-.9363321783233929,-.9380234233862578,-.9396926207859082,-.9413397312888873,-.9429647161808761,-.9445675372676049,-.9461481568757504,-.9477065378538222,-.9492426435730339,-.9507564379281666,-.9522478853384153,-.9537169507482267,-.9551635996281229,-.956587797975512,-.9579895123154888,-.9593687097016201,-.9607253577167205,-.9620594244736131,-.9633708786158804,-.9646596893185994,-.9659258262890683,-.9671692597675166,-.9683899605278059,-.9695878998781159,-.97076304966162,-.9719153822571452,-.9730448705798238,-.9741514880817276,-.975235208752493,-.9762960071199334,-.9773338582506355,-.9783487377505475,-.9793406217655514,-.980309486982024,-.9812553106273846,-.9821780704706307,-.98307774482286,-.9839543125377805,-.984807753012208,-.9856380461865493,-.9864451725452739,-.9872291131173742,-.9879898494768089,-.9887273637429387,-.9894416385809445,-.9901326572022358,-.9908004033648452,-.9914448613738104,-.9920660160815423,-.9926638528881818,-.993238357741943,-.9937895171394426,-.9943173181260184,-.994821748296033,-.9953027957931658,-.9957604493106913,-.9961946980917455,-.9966055319295779,-.996992941167792,-.9973569167005722,-.9976974499728977,-.9980145329807433,-.9983081582712682,-.9985783189429907,-.9988250086459504,-.9990482215818578,-.99924795250423,-.9994241967185149,-.9995769500822006,-.9997062090049132,-.9998119704485015,-.9998942319271076,-.9999529915072262,-.9999882478077495,-1,-.9999882478077495,-.9999529915072262,-.9998942319271076,-.9998119704485015,-.9997062090049132,-.9995769500822006,-.9994241967185149,-.99924795250423,-.9990482215818578,-.9988250086459504,-.9985783189429907,-.9983081582712682,-.9980145329807433,-.9976974499728977,-.9973569167005724,-.996992941167792,-.9966055319295779,-.9961946980917455,-.9957604493106914,-.9953027957931658,-.9948217482960331,-.9943173181260185,-.9937895171394426,-.993238357741943,-.9926638528881819,-.9920660160815424,-.9914448613738105,-.9908004033648453,-.9901326572022358,-.9894416385809446,-.9887273637429387,-.987989849476809,-.9872291131173742,-.986445172545274,-.9856380461865493,-.9848077530122081,-.9839543125377807,-.9830777448228601,-.9821780704706308,-.9812553106273846,-.9803094869820241,-.9793406217655515,-.9783487377505476,-.9773338582506355,-.9762960071199335,-.9752352087524931,-.9741514880817276,-.9730448705798239,-.9719153822571454,-.9707630496616201,-.969587899878116,-.968389960527806,-.9671692597675167,-.9659258262890684,-.9646596893185995,-.9633708786158806,-.9620594244736133,-.9607253577167206,-.9593687097016202,-.9579895123154889,-.9565877979755121,-.955163599628123,-.9537169507482268,-.9522478853384154,-.9507564379281668,-.949242643573034,-.9477065378538223,-.9461481568757506,-.944567537267605,-.9429647161808762,-.9413397312888874,-.9396926207859083,-.9380234233862579,-.936332178323393,-.9346189253489885,-.9328837047320004,-.9311265572577221,-.9293475242268224,-.9275466474543788,-.9257239692688904,-.9238795325112866,-.9220133805339186,-.9201255571995389,-.9182161068802742,-.9162850744565779,-.9143325053161796,-.9123584453530141,-.9103629409661469,-.9083460390586794,-.9063077870366503,-.9042482328079181,-.9021674247810376,-.9000654118641209,-.8979422434636882,-.895797969483505,-.8936326403234123,-.8914463068781384,-.8892390205361063,-.887010833178222,-.8847617971766579,-.8824919653936216,-.8802013911801113,-.8778901283746645,-.8755582313020907,-.8732057547721959,-.870832754078492,-.8684392849969007,-.8660254037844386,-.8635911671778989,-.8611366323925137,-.8586618571206134,-.8561668995302666,-.8536518182639167,-.8511166724369998,-.848561521636559,-.8459864259198413,-.8433914458128857,-.8407766423091034,-.8381420768678404,-.8354878114129367,-.8328139083312672,-.8301204304712791,-.8274074411415107,-.8246750041091067,-.8219231835983183,-.8191520442889918,-.8163616513150517,-.8135520702629676,-.8107233671702121,-.8078756085237113,-.8050088612582788,-.802123192755044,-.7992186708398701,-.796295363781756,-.7933533402912352,-.7903926695187591,-.7874134210530724,-.7844156649195756,-.7813994715786825,-.7783649119241599,-.7753120572814661,-.7722409794060691,-.7691517504817653,-.7660444431189781,-.7629191303530556,-.7597758856425495,-.7566147828674927,-.753435896327661,-.7502393007408246,-.7470250712409963,-.7437932833766612,-.740544013109005,-.7372773368101242,-.7339933312612357,-.7306920736508676,-.7273736415730492,-.7240381130254828,-.7206855664077145,-.7173160805192891,-.7139297345578991,-.7105266081175208,-.7071067811865477,-.7036703341459063,-.7002173477671687,-.6967479032106556,-.6932620820235246,-.6897599661378577,-.6862416378687334,-.6827071799122926,-.679156675343793,-.6755902076156605,-.6720078605555223,-.6684097183642427,-.6647958656139378,-.6611663872459935,-.6575213685690637,-.6538608952570701,-.6501850533471836,-.6464939292378064,-.6427876096865396,-.6390661818081416,-.6353297330724854,-.6315783513024976,-.627812124672099,-.624031141704127,-.6202354912682606,-.6164252625789255,-.6126005451932034,-.6087614290087209,-.6049080042615417,-.6010403615240425,-.5971585917027863,-.5932627860363818,-.589353036093345,-.585429433769941,-.5814920712880269,-.5775410411928856,-.5735764363510465,-.5695983499481065,-.5656068754865391,-.561602106783493,-.5575841379685926,-.5535530634817225,-.5495089780708059,-.5454519767895828,-.5413821549953696,-.5372996083468242,-.5332044328016913,-.5290967246145529,-.5249765803345603,-.5208440968031696,-.5166993711518632,-.5125425007998651,-.5083735834518559,-.5041927170956704,-.5000000000000004,-.49579553071207927,-.49157940805537115,-.48735173112724256,-.48311259929663913,-.4788621122017438,-.47460036974764036,-.4703274721039621,-.4660435197025389,-.46174861323503363,-.45744285365058096,-.4531263421534088,-.44879918020046244,-.4444614694990217,-.4401133120043052,-.43575480991708015,-.4313860656812539,-.42700718198147153,-.4226182617406992,-.4182194081178066,-.413810724505139,-.40939231452609287,-.40496428203267354,-.400526731103061,-.3960797660391569,-.39162349136413954,-.38715801182000076,-.3826834323650904,-.37819985817164276,-.3737073946233104,-.3692061473126848,-.36469622203881186,-.3601777248047109,-.3556507618148766,-.3511154394727894,-.34657186437840776,-.34202014332566943,-.3374603832999744,-.3328926914756765,-.32831717521356063,-.32373394205832107,-.31914309973603056,-.3145447561516138,-.3099390193863049,-.30532599769511337,-.30070579950427384,-.2960785334087003,-.29144430816943584,-.2868032327110907,-.28215541611928785,-.2775009676380955,-.2728399966674612,-.2681726127606372,-.2634989256216111,-.2588190451025207,-.2541330812010789,-.24944114405798135,-.24474334395432432,-.24003979130900607,-.23533059667613823,-.23061587074244044,-.2258957243246447,-.22117026836688813,-.21643961393810288,-.21170387222941123,-.2069631545515055,-.20221757233203852,-.19746723711299774,-.19271226054809037,-.1879527544001122,-.18318883053832655,-.17842060093583256,-.1736481776669304,-.16887167290449245,-.16409119891732413,-.15930686806752234,-.15451879280784075,-.14972708567904036,-.1449318593072471,-.14013322640130713,-.13533129975013158,-.13052619222005168,-.1257180167521624,-.12090688635966958,-.11609291412523004,-.11127621319829996,-.10645689679246818,-.10163507818280229,-.09681087070317913,-.09198438774362797,-.08715574274765832,-.08232504920960054,-.0774924206719312,-.07265797072261047,-.06782181299240972,-.06298406115223794,-.0581448289104763,-.05330423001029832,-.04846237822700354,-.043619387365336194,-.038775371256817404,-.03393044375706254,-.02908471874311221,-.02423831011074855,-.019391331771824397,-.014543897651582293,-.009696121685978531,-.004848117819001606];var Quaternion_THREE=__webpack_require__(70);class Quaternion extends Quaternion_THREE.Quaternion{setFromEuler(e,t){if(!e||!e.isEuler)throw new Error("THREE.Quaternion: .setFromEuler() now expects an Euler rotation rather than a Vector3 and order.");var i=e.x,r=e.y,s=e.z,a=e.order,n=GameMath.cos(i/2),o=GameMath.cos(r/2),e=GameMath.cos(s/2),i=GameMath.sin(i/2),r=GameMath.sin(r/2),s=GameMath.sin(s/2);return"XYZ"===a?(this._x=i*o*e+n*r*s,this._y=n*r*e-i*o*s,this._z=n*o*s+i*r*e,this._w=n*o*e-i*r*s):"YXZ"===a?(this._x=i*o*e+n*r*s,this._y=n*r*e-i*o*s,this._z=n*o*s-i*r*e,this._w=n*o*e+i*r*s):"ZXY"===a?(this._x=i*o*e-n*r*s,this._y=n*r*e+i*o*s,this._z=n*o*s+i*r*e,this._w=n*o*e-i*r*s):"ZYX"===a?(this._x=i*o*e-n*r*s,this._y=n*r*e+i*o*s,this._z=n*o*s-i*r*e,this._w=n*o*e+i*r*s):"YZX"===a?(this._x=i*o*e+n*r*s,this._y=n*r*e+i*o*s,this._z=n*o*s-i*r*e,this._w=n*o*e-i*r*s):"XZY"===a&&(this._x=i*o*e-n*r*s,this._y=n*r*e-i*o*s,this._z=n*o*s+i*r*e,this._w=n*o*e+i*r*s),!1!==t&&this.onChangeCallback(),this}setFromAxisAngle(e,t){var i=t/2,t=GameMath.sin(i);return this._x=e.x*t,this._y=e.y*t,this._z=e.z*t,this._w=GameMath.cos(i),this.onChangeCallback(),this}setFromRotationMatrix(e){let t=e.elements,i=t[0],r=t[4],s=t[8],a=t[1],n=t[5],o=t[9],l=t[2],h=t[6],c=t[10],u=i+n+c,d;return 0<u?(d=.5/GameMath.sqrt(u+1),this._w=.25/d,this._x=(h-o)*d,this._y=(s-l)*d,this._z=(a-r)*d):n<i&&c<i?(d=2*GameMath.sqrt(1+i-n-c),this._w=(h-o)/d,this._x=.25*d,this._y=(r+a)/d,this._z=(s+l)/d):c<n?(d=2*GameMath.sqrt(1+n-i-c),this._w=(s-l)/d,this._x=(r+a)/d,this._y=.25*d,this._z=(o+h)/d):(d=2*GameMath.sqrt(1+c-i-n),this._w=(a-r)/d,this._x=(s+l)/d,this._y=(o+h)/d,this._z=.25*d),this.onChangeCallback(),this}length(){return GameMath.sqrt(this._x*this._x+this._y*this._y+this._z*this._z+this._w*this._w)}slerp(e,t){if(0===t)return this;if(1===t)return this.copy(e);var i=this._x,r=this._y,s=this._z,a=this._w;let n=a*e._w+i*e._x+r*e._y+s*e._z;if(n<0?(this._w=-e._w,this._x=-e._x,this._y=-e._y,this._z=-e._z,n=-n):this.copy(e),1<=n)return this._w=a,this._x=i,this._y=r,this._z=s,this;var o=1-n*n;if(o<=Number.EPSILON){var l=1-t;return this._w=l*a+t*this._w,this._x=l*i+t*this._x,this._y=l*r+t*this._y,this._z=l*s+t*this._z,this.normalize()}e=GameMath.sqrt(o),l=GameMath.atan2(e,n),o=GameMath.sin((1-t)*l)/e,e=GameMath.sin(t*l)/e;return this._w=a*o+this._w*e,this._x=i*o+this._x*e,this._y=r*o+this._y*e,this._z=s*o+this._z*e,this.onChangeCallback(),this}}var BuildCat,FactoryType,OccupationBits,SuperWeaponType,EventType,Vector3_THREE=__webpack_require__(70);class Vector3_Vector3 extends Vector3_THREE.Vector3{applyEuler(e){return e&&e.isEuler||console.error("THREE.Vector3: .applyEuler() now expects an Euler rotation rather than a Vector3 and order."),this.applyQuaternion(_quaternion.setFromEuler(e))}applyAxisAngle(e,t){return this.applyQuaternion(_quaternion.setFromAxisAngle(e,t))}length(){return GameMath.sqrt(this.x*this.x+this.y*this.y+this.z*this.z)}projectOnPlane(e){return _vector.copy(this).projectOnVector(e),this.sub(_vector)}reflect(e){return this.sub(_vector.copy(e).multiplyScalar(2*this.dot(e)))}angleTo(e){e=this.dot(e)/GameMath.sqrt(this.lengthSq()*e.lengthSq());return GameMath.acos(clamp(e,-1,1))}distanceTo(e){return GameMath.sqrt(this.distanceToSquared(e))}setFromSpherical(e){var t=GameMath.sin(e.phi)*e.radius;return this.x=t*GameMath.sin(e.theta),this.y=GameMath.cos(e.phi)*e.radius,this.z=t*GameMath.cos(e.theta),this}setFromCylindrical(e){return this.x=e.radius*GameMath.sin(e.theta),this.y=e.y,this.z=e.radius*GameMath.cos(e.theta),this}}const _quaternion=new Quaternion,_vector=new Vector3_Vector3;!function(e){e[e.Combat=0]="Combat",e[e.Tech=1]="Tech",e[e.Resource=2]="Resource",e[e.Power=3]="Power"}(BuildCat=BuildCat||{}),function(e){e[e.None=0]="None",e[e.BuildingType=1]="BuildingType",e[e.InfantryType=2]="InfantryType",e[e.UnitType=3]="UnitType",e[e.NavalUnitType=4]="NavalUnitType",e[e.AircraftType=5]="AircraftType"}(FactoryType=FactoryType||{});class TechnoRules extends ObjectRules{constructor(e,t,i,r){super(e,t,i,r)}parse(){super.parse(),this.owner=this.ini.getArray("Owner");var e=this.ini.getNumber("AIBasePlanningSide");this.aiBasePlanningSide=-1!==e&&void 0!==SideType[e]?e:void 0,this.requiredHouses=this.ini.getArray("RequiredHouses"),this.forbiddenHouses=this.ini.getArray("ForbiddenHouses"),this.requiresStolenAlliedTech=this.ini.getBool("RequiresStolenAlliedTech"),this.requiresStolenSovietTech=this.ini.getBool("RequiresStolenSovietTech"),this.requiresStolenThirdTech=this.ini.getBool("RequiresStolenThirdTech"),this.techLevel=this.ini.getNumber("TechLevel",-1),this.cost=this.ini.getNumber("Cost"),this.points=this.ini.getNumber("Points"),this.power=this.ini.getNumber("Power"),this.powered=this.ini.getBool("Powered"),this.prerequisite=this.ini.getArray("Prerequisite"),this.prerequisiteOverride=this.ini.getArray("PrerequisiteOverride"),this.soylent=this.ini.getNumber("Soylent"),this.crateGoodie=this.ini.getBool("CrateGoodie"),this.buildCat=this.ini.getEnum("BuildCat",BuildCat,BuildCat.Combat),this.adjacent=this.ini.getNumber("Adjacent",1),this.baseNormal=this.ini.getBool("BaseNormal",!0),this.buildLimit=this.ini.getNumber("BuildLimit",Number.POSITIVE_INFINITY),this.airRangeBonus=this.ini.getNumber("AirRangeBonus"),this.guardRange=this.ini.getNumber("GuardRange"),this.defaultToGuardArea=this.ini.getBool("DefaultToGuardArea"),this.eligibileForAllyBuilding=this.ini.getBool("EligibileForAllyBuilding"),this.numberImpassableRows=this.ini.getNumber("NumberImpassableRows"),this.bridgeRepairHut=this.ini.getBool("BridgeRepairHut"),this.constructionYard=this.ini.getBool("ConstructionYard"),this.refinery=this.ini.getBool("Refinery"),this.unitRepair=this.ini.getBool("UnitRepair"),this.unitReload=this.ini.getBool("UnitReload"),this.unitSell=this.ini.getBool("UnitSell"),this.isBaseDefense=this.ini.getBool("IsBaseDefense"),this.superWeapon=this.parseWeaponName(this.ini.getString("SuperWeapon")),this.chargedAnimTime=this.ini.getNumber("ChargedAnimTime");var t=this.ini.getBool("Naval");this.naval=t,this.underwater=this.ini.getBool("Underwater"),this.waterBound=this.ini.getBool("WaterBound"),this.orePurifier=this.ini.getBool("OrePurifier"),this.cloning=this.ini.getBool("Cloning"),this.grinding=this.ini.getBool("Grinding"),this.nukeSilo=this.ini.getBool("NukeSilo"),this.repairable=this.ini.getBool("Repairable",this.type===ObjectType.Building),this.clickRepairable=this.ini.getBool("ClickRepairable",this.type===ObjectType.Building),this.unsellable=this.ini.getBool("Unsellable",this.type!==ObjectType.Building&&this.generalRules.unitsUnsellable),this.returnable=this.ini.getBool("Returnable",this.generalRules.returnStructures),this.gdiBarracks=this.ini.getBool("GDIBarracks"),this.nodBarracks=this.ini.getBool("NODBarracks"),this.numberOfDocks=this.ini.getNumber("NumberOfDocks"),this.unitRepair&&!this.numberOfDocks&&(this.numberOfDocks=1),this.factory=this.ini.getEnum("Factory",FactoryType,FactoryType.None),this.factory===FactoryType.UnitType&&t&&(this.factory=FactoryType.NavalUnitType),this.weaponsFactory=this.ini.getBool("WeaponsFactory"),this.helipad=this.ini.getBool("Helipad"),this.hospital=this.ini.getBool("Hospital"),this.landTargeting=this.ini.getEnumNumeric("LandTargeting",LandTargeting,LandTargeting.LandOk),this.navalTargeting=this.ini.getEnumNumeric("NavalTargeting",NavalTargeting,NavalTargeting.UnderwaterNever),this.tooBigToFitUnderBridge=this.ini.getBool("TooBigToFitUnderBridge",this.type===ObjectType.Building),this.canBeOccupied=this.ini.getBool("CanBeOccupied"),this.maxNumberOccupants=this.ini.getNumber("MaxNumberOccupants"),this.leaveRubble=this.ini.getBool("LeaveRubble"),this.undeploysInto=this.ini.getString("UndeploysInto"),this.deploysInto=this.ini.getString("DeploysInto"),this.deployTime=this.ini.getNumber("DeployTime"),this.capturable=this.ini.getBool("Capturable"),this.spyable=this.ini.getBool("Spyable"),this.needsEngineer=this.ini.getBool("NeedsEngineer"),this.c4=this.ini.getBool("C4"),this.canC4=this.ini.getBool("CanC4",!0),this.eligibleForDelayKill=this.ini.getBool("EligibleForDelayKill"),this.produceCashStartup=this.ini.getNumber("ProduceCashStartup"),this.produceCashAmount=this.ini.getNumber("ProduceCashAmount"),this.produceCashDelay=this.ini.getNumber("ProduceCashDelay"),this.explosion=this.ini.getArray("Explosion"),this.explodes=this.ini.getBool("Explodes"),this.ifvMode=this.ini.getNumber("IFVMode"),this.turretIndexesByIfvMode=this.parseTurretIndexes(),this.turret=this.ini.getBool("Turret"),this.turretCount=this.ini.getNumber("TurretCount",this.turret?1:0),this.turretAnim=this.ini.getString("TurretAnim"),this.turretAnimIsVoxel=this.ini.getBool("TurretAnimIsVoxel"),this.turretAnimX=this.ini.getNumber("TurretAnimX"),this.turretAnimY=this.ini.getNumber("TurretAnimY"),this.turretAnimZAdjust=this.ini.getNumber("TurretAnimZAdjust"),this.isChargeTurret=this.ini.getBool("IsChargeTurret"),this.overpowerable=this.ini.getBool("Overpowerable"),this.freeUnit=this.ini.getString("FreeUnit"),this.primary=this.parseWeaponName(this.ini.getString("Primary")),this.secondary=this.parseWeaponName(this.ini.getString("Secondary")),this.elitePrimary=this.parseWeaponName(this.ini.getString("ElitePrimary")),this.eliteSecondary=this.parseWeaponName(this.ini.getString("EliteSecondary")),this.weaponCount=this.ini.getNumber("WeaponCount"),this.deathWeapon=this.parseWeaponName(this.ini.getString("DeathWeapon")),this.deathWeaponDamageModifier=this.ini.getNumber("DeathWeaponDamageModifier",1),this.occupyWeapon=this.parseWeaponName(this.ini.getString("OccupyWeapon")),this.eliteOccupyWeapon=this.parseWeaponName(this.ini.getString("EliteOccupyWeapon")),this.veteranAbilities=new Set(this.ini.getEnumArray("VeteranAbilities",VeteranAbility)),this.eliteAbilities=new Set([...this.veteranAbilities,...this.ini.getEnumArray("EliteAbilities",VeteranAbility)]),this.selfHealing=this.ini.getBool("SelfHealing"),this.wall=this.ini.getBool("Wall"),this.gate=this.ini.getBool("Gate"),this.armor=this.ini.getEnum("Armor",ArmorType,ArmorType.None,!0),this.strength=Math.floor(this.ini.getNumber("Strength")),this.immune=this.ini.getBool("Immune"),this.immuneToRadiation=this.ini.getBool("ImmuneToRadiation"),this.immuneToPsionics=this.ini.getBool("ImmuneToPsionics"),this.typeImmune=this.ini.getBool("TypeImmune"),this.warpable=this.ini.getBool("Warpable",!0),this.isTilter=this.ini.getBool("IsTilter",!0),this.walkRate=this.ini.getNumber("WalkRate",1),this.idleRate=this.ini.getNumber("IdleRate",0),this.noSpawnAlt=this.ini.getBool("NoSpawnAlt"),this.crusher=this.ini.getBool("Crusher"),this.consideredAircraft=this.ini.getBool("ConsideredAircraft"),this.crashable=this.ini.getBool("Crashable");var i=this.ini.getBool("Landable");this.landable=i,this.airportBound=this.ini.getBool("AirportBound"),this.balloonHover=this.ini.getBool("BalloonHover"),this.hoverAttack=this.ini.getBool("HoverAttack"),this.omniFire=this.ini.getBool("OmniFire"),this.fighter=this.ini.getBool("Fighter"),this.flightLevel=this.ini.getNumber("FlightLevel")||void 0;var r=this.ini.getString("Locomotor"),e=this.type===ObjectType.Building?LocomotorType.Statue:LocomotorType.Chrono;if(r?(t=locomotorTypesByClsId.get(r))?this.locomotor=t:(console.warn(`Object rules "${this.name}" has invalid Locomotor "${r}"`),this.locomotor=e):this.locomotor=e,this.locomotor!==LocomotorType.Statue){let e=defaultSpeedsByLocomotor.get(this.locomotor);void 0===e&&(this.type===ObjectType.Aircraft||this.consideredAircraft?e=SpeedType.Winged:this.type===ObjectType.Vehicle?e=this.crusher?SpeedType.Track:SpeedType.Wheel:this.type===ObjectType.Infantry&&(e=SpeedType.Foot)),this.speedType=this.ini.getEnum("SpeedType",SpeedType,e,!0)}e=[LocomotorType.Ship,LocomotorType.Vehicle,LocomotorType.Chrono].includes(this.locomotor)?65:100;this.speed=ObjectRules.iniSpeedToLeptonsPerTick(this.ini.getNumber("Speed"),e),this.movementZone=this.ini.getEnum("MovementZone",MovementZone,MovementZone.Normal),this.fearless=this.ini.getBool("Fearless"),this.deployer=this.ini.getBool("Deployer"),this.deployFire=this.ini.getBool("DeployFire"),this.deployFireWeapon=this.ini.getNumber("DeployFireWeapon",WeaponType.Secondary),this.undeployDelay=this.ini.getNumber("UndeployDelay"),this.fraidycat=this.ini.getBool("Fraidycat",!1),this.isHuman=!this.ini.getBool("NotHuman"),this.organic=this.type===ObjectType.Infantry||this.ini.getBool("Organic"),this.occupier=this.ini.getBool("Occupier"),this.engineer=this.ini.getBool("Engineer"),this.ivan=this.ini.getBool("Ivan"),this.civilian=this.ini.getBool("Civilian"),this.agent=this.ini.getBool("Agent"),this.infiltrate=this.ini.getBool("Infiltrate"),this.threatPosed=this.ini.getNumber("ThreatPosed"),this.specialThreatValue=this.ini.getNumber("SpecialThreatValue"),this.canPassiveAquire=this.ini.getBool("CanPassiveAquire",!0),this.canRetaliate=this.ini.getBool("CanRetaliate",!0),this.preventAttackMove=this.ini.getBool("PreventAttackMove"),this.opportunityFire=this.ini.getBool("OpportunityFire"),this.distributedFire=this.ini.getBool("DistributedFire"),this.radialFireSegments=this.ini.getNumber("RadialFireSegments"),this.attackCursorOnFriendlies=this.ini.getBool("AttackCursorOnFriendlies"),this.bombable=this.ini.getBool("Bombable",!0),this.trainable=this.ini.getBool("Trainable",this.type!==ObjectType.Building),this.crewed=this.ini.getBool("Crewed"),this.parasiteable=this.ini.getBool("Parasiteable",this.type!==ObjectType.Building),this.suppressionThreshold=this.ini.getNumber("SuppressionThreshold"),this.reselectIfLimboed=this.ini.getBool("ReselectIfLimboed"),this.rejoinTeamIfLimboed=this.ini.getBool("RejoinTeamIfLimboed"),this.weight=this.ini.getNumber("Weight"),this.accelerates=this.ini.getBool("Accelerates",!0),this.accelerationFactor=this.ini.getNumber("AccelerationFactor",.03),this.teleporter=this.ini.getBool("Teleporter"),this.canDisguise=this.ini.getBool("CanDisguise"),this.disguiseWhenStill=this.ini.getBool("DisguiseWhenStill"),this.permaDisguise=this.ini.getBool("PermaDisguise"),this.detectDisguise=this.ini.getBool("DetectDisguise"),this.detectDisguiseRange=this.ini.getNumber("DetectDisguiseRange"),this.cloakable=this.ini.getBool("Cloakable"),this.sensors=this.ini.getBool("Sensors"),this.sensorArray=this.ini.getBool("SensorArray"),this.sensorsSight=this.ini.getNumber("SensorsSight"),this.burstDelay=this.parseBurstDelay(),this.vhpScan=this.ini.getEnum("VHPScan",VhpScan,VhpScan.None,!0),this.pip=this.ini.getEnum("Pip",PipColor,PipColor.Green,!0),this.passengers=this.ini.getNumber("Passengers"),this.gunner=this.ini.getBool("Gunner"),this.ammo=this.ini.getNumber("Ammo",-1),this.initialAmmo=this.ini.getNumber("InitialAmmo",-1),this.manualReload=this.ini.getBool("ManualReload",this.type===ObjectType.Aircraft),this.storage=this.ini.getNumber("Storage"),this.spawned=this.ini.getBool("Spawned"),this.spawns=this.ini.getString("Spawns"),this.spawnsNumber=this.ini.getNumber("SpawnsNumber"),this.spawnRegenRate=this.ini.getNumber("SpawnRegenRate"),this.spawnReloadRate=this.ini.getNumber("SpawnReloadRate"),this.missileSpawn=this.ini.getBool("MissileSpawn"),this.size=this.ini.getNumber("Size",1),this.sizeLimit=this.ini.getNumber("SizeLimit"),this.sight=Math.min(TechnoRules.MAX_SIGHT,this.needsEngineer?6:this.ini.getNumber("Sight",1)),this.spySat=this.ini.getBool("SpySat"),this.gapGenerator=this.ini.getBool("GapGenerator"),this.gapRadiusInCells=this.ini.getNumber("GapRadiusInCells"),this.psychicDetectionRadius=this.ini.getNumber("PsychicDetectionRadius"),this.hasRadialIndicator=this.ini.getBool("HasRadialIndicator"),this.harvester=this.ini.getBool("Harvester"),this.unloadingClass=this.ini.getString("UnloadingClass"),this.dock=this.ini.getArray("Dock"),this.radar=this.ini.getBool("Radar"),this.radarInvisible=this.ini.getBool("RadarInvisible"),this.revealToAll=this.ini.getBool("RevealToAll"),this.selectable=!(this.type===ObjectType.Aircraft&&!i)&&this.ini.getBool("Selectable",!0),this.isSelectableCombatant=this.ini.getBool("IsSelectableCombatant"),this.invisibleInGame=this.ini.getBool("InvisibleInGame"),this.moveToShroud=this.ini.getBool("MoveToShroud",this.type!==ObjectType.Aircraft),this.leadershipRating=this.ini.getNumber("LeadershipRating",5),this.unnatural=this.ini.getBool("Unnatural"),this.natural=this.ini.getBool("Natural"),this.buildTimeMultiplier=this.ini.getFixed("BuildTimeMultiplier",1),this.allowedToStartInMultiplayer=this.ini.getBool("AllowedToStartInMultiplayer",!0),this.rot=ObjectRules.iniRotToDegsPerTick(this.ini.getNumber("ROT",0)),this.jumpjetAccel=this.ini.getNumber("JumpJetAccel",2),this.jumpjetClimb=this.ini.getNumber("JumpjetClimb",5),this.jumpjetCrash=this.ini.getNumber("JumpjetCrash",5),this.jumpjetDeviation=this.ini.getNumber("JumpjetDeviation",40),this.jumpjetHeight=this.ini.getNumber("JumpjetHeight",500),this.jumpjetNoWobbles=this.ini.getBool("JumpjetNoWobbles"),this.jumpjetSpeed=this.ini.getNumber("JumpjetSpeed",14),this.jumpjetTurnRate=ObjectRules.iniRotToDegsPerTick(this.ini.getNumber("JumpJetTurnRate",4)),this.jumpjetWobbles=this.ini.getNumber("JumpjetWobbles",.15),this.pitchSpeed=this.ini.getNumber("PitchSpeed",.25),this.pitchAngle=1<=this.pitchSpeed?0:20,this.damageParticleSystems=this.ini.getArray("DamageParticleSystems");i=this.ini.getNumberArray("DamageSmokeOffset",void 0,[0,0,0]);this.damageSmokeOffset=new Vector3_Vector3(i[0],i[2]/Math.SQRT2,i[1]),this.minDebris=this.ini.getNumber("MinDebris"),this.maxDebris=this.ini.getNumber("MaxDebris"),this.debrisTypes=this.ini.getArray("DebrisTypes"),this.debrisAnims=this.ini.getArray("DebrisAnims"),this.isLightpost="GALITE"===this.imageName,this.lightVisibility=this.ini.getNumber("LightVisibility",5e3),this.lightIntensity=this.ini.getNumber("LightIntensity"),this.lightRedTint=this.ini.getNumber("LightRedTint",1),this.lightGreenTint=this.ini.getNumber("LightGreenTint",1),this.lightBlueTint=this.ini.getNumber("LightBlueTint",1),this.ambientSound=this.ini.getString("AmbientSound")||void 0,this.createSound=this.ini.getString("CreateSound")||void 0,this.deploySound=this.ini.getString("DeploySound")||void 0,this.undeploySound=this.ini.getString("UndeploySound")||void 0,this.voiceSelect=this.ini.getString("VoiceSelect")||void 0,this.voiceMove=this.ini.getString("VoiceMove")||void 0,this.voiceAttack=this.ini.getString("VoiceAttack")||void 0,this.voiceFeedback=this.ini.getString("VoiceFeedback")||void 0,this.voiceSpecialAttack=this.ini.getString("VoiceSpecialAttack")||void 0,this.voiceEnter=this.ini.getString("VoiceEnter")||void 0,this.voiceCapture=this.ini.getString("VoiceCapture")||void 0,this.voiceCrashing=this.ini.getString("VoiceCrashing")||void 0,this.crashingSound=this.ini.getString("CrashingSound")||void 0,this.impactLandSound=this.ini.getString("ImpactLandSound")||void 0,this.auxSound1=this.ini.getString("AuxSound1")||void 0,this.auxSound2=this.ini.getString("AuxSound2")||void 0,this.dieSound=this.ini.getString("DieSound")||void 0,this.moveSound=this.ini.getString("MoveSound")||void 0,this.enterWaterSound=this.ini.getString("EnterWaterSound")||void 0,this.leaveWaterSound=this.ini.getString("LeaveWaterSound")||void 0,this.turretRotateSound=this.ini.getString("TurretRotateSound")||void 0,this.workingSound=this.ini.getString("WorkingSound")||void 0,this.notWorkingSound=this.ini.getString("NotWorkingSound")||void 0,this.chronoInSound=this.ini.getString("ChronoInSound")||void 0,this.chronoOutSound=this.ini.getString("ChronoOutSound")||void 0,this.enterTransportSound=this.ini.getString("EnterTransportSound")||void 0,this.leaveTransportSound=this.ini.getString("LeaveTransportSound")||void 0}parseWeaponName(e){return e&&"none"!==e.toLowerCase()?e:void 0}parseTurretIndexes(){let i=new Map;return this.ini.getBool("Gunner")&&this.ini.entries.forEach((e,t)=>{t=t.match(/^(.*)TurretWeapon$/i);t&&(t=t[1]+"TurretIndex",this.ini.has(t)&&i.set(Number(e),this.ini.getNumber(t)))}),i}parseBurstDelay(){let t=[];for(let e=0;e<4;++e)t.push(this.ini.has("BurstDelay"+e)?this.ini.getNumber("BurstDelay"+e):void 0);return t}hasOwner(e){return!!this.owner.length&&-1!==this.owner.indexOf(e.name)}isAvailableTo(e){return(!this.requiredHouses.length||-1!==this.requiredHouses.indexOf(e.name))&&-1===this.forbiddenHouses.indexOf(e.name)}getWeaponAtIndex(e){return this.parseWeaponName(this.ini.getString("Weapon"+(e+1)))}getEliteWeaponAtIndex(e){return this.parseWeaponName(this.ini.getString("EliteWeapon"+(e+1)))}}TechnoRules.MAX_SIGHT=11;class OverlayRules extends ObjectRules{parse(){super.parse(),this.armor=this.ini.getEnum("Armor",ArmorType,ArmorType.None,!0),this.crate=this.ini.getBool("Crate");var e=this.ini.getBool("IsARock");this.isARock=e,this.isRubble=this.ini.getBool("IsRubble"),this.isVeinholeMonster=this.ini.getBool("IsVeinholeMonster"),this.isVeins=this.ini.getBool("IsVeins"),this.land=this.ini.getEnum("Land",LandType,LandType.Clear),this.noUseTileLandType=!!this.ini.getString("NoUseTileLandType"),this.strength=this.ini.getNumber("Strength"),this.tiberium=this.ini.getBool("Tiberium");var t=this.ini.getBool("Wall");this.wall=t,this.radarInvisible=this.ini.getBool("RadarInvisible",!t&&!e)}}function testOccupationBit(e,t){switch(e){case 0:case 1:return!0;case 2:return 0!=(t&OccupationBits.Right);case 3:return 0!=(t&OccupationBits.Left);case 4:return 0!=(t&OccupationBits.Bottom);default:throw new Error('Invalid subCell "'+e)}}!function(e){e[e.All=7]="All",e[e.Right=1]="Right",e[e.Left=2]="Left",e[e.Bottom=4]="Bottom"}(OccupationBits=OccupationBits||{});class TerrainRules extends ObjectRules{parse(){super.parse(),this.animationRate=this.ini.getNumber("AnimationRate"),this.animationProbability=this.ini.getNumber("AnimationProbability"),this.gate=this.ini.getBool("Gate"),this.immune=this.ini.getBool("Immune"),this.isAnimated=this.ini.getBool("IsAnimated"),this.snowOccupationBits=this.normalizeOccupationBits(this.ini.getNumber("SnowOccupationBits",OccupationBits.All)),this.spawnsTiberium=this.ini.getBool("SpawnsTiberium"),this.strength=this.ini.getNumber("Strength"),this.radarInvisible=this.ini.getBool("RadarInvisible"),this.temperateOccupationBits=this.normalizeOccupationBits(this.ini.getNumber("TemperateOccupationBits",OccupationBits.All))}normalizeOccupationBits(e){return(e+8*Math.abs(Math.floor(e/8)))%8}getOccupationBits(e){return e!==TheaterType.Snow?this.temperateOccupationBits:this.snowOccupationBits}getOccupiedSubCells(e){var t,i=this.getOccupationBits(e),e=[0,1,2,3,4];if(i===OccupationBits.All)return e;let r=[];for(t of e)testOccupationBit(t,i)&&r.push(t);return r}}class SmudgeRules extends ObjectRules{parse(){super.parse(),this.burn=this.ini.getBool("Burn"),this.crater=this.ini.getBool("Crater"),this.width=this.ini.getNumber("Width",1),this.height=this.ini.getNumber("Height",1)}}class DebrisRules extends ObjectRules{parse(){super.parse(),this.damage=this.ini.getNumber("Damage"),this.damageRadius=this.ini.getNumber("DamageRadius"),this.duration=this.ini.getNumber("Duration"),this.elasticity=clamp(this.ini.getNumber("Elasticity",.75),0,1),this.expireAnim=this.ini.getString("ExpireAnim")||void 0,this.minAngularVelocity=this.ini.getNumber("MinAngularVelocity"),this.maxAngularVelocity=this.ini.getNumber("MaxAngularVelocity"),this.maxXYVel=this.ini.getNumber("MaxXYVel"),this.minZVel=this.ini.getNumber("MinZVel"),this.maxZVel=this.ini.getNumber("MaxZVel"),this.shareTurretData=this.ini.getBool("ShareTurretData"),this.shareBodyData=this.ini.getBool("ShareBodyData"),this.shareBarrelData=this.ini.getBool("ShareBarrelData"),this.shareSource=this.ini.getString("ShareSource")||void 0,this.trailerAnim=this.ini.getString("TrailerAnim")||void 0,this.trailerSeparation=this.ini.getNumber("TrailerSeperation"),this.warhead=this.ini.getString("Warhead")||void 0}}class ObjectRulesFactory{create(e,t,i,r){switch(e){case ObjectType.Aircraft:case ObjectType.Building:case ObjectType.Infantry:case ObjectType.Vehicle:return new TechnoRules(e,t,r,i);case ObjectType.Overlay:return new OverlayRules(e,t,r);case ObjectType.Terrain:return new TerrainRules(e,t,r);case ObjectType.Smudge:return new SmudgeRules(e,t,r);case ObjectType.VoxelAnim:return new DebrisRules(e,t,r);default:return new ObjectRules(e,t,r)}}}class CombatDamageRules{readIni(e){this.ballisticScatter=e.getNumber("BallisticScatter"),this.bridgeStrength=e.getNumber("BridgeStrength"),this.c4Delay=e.getNumber("C4Delay"),this.c4Warhead=e.getString("C4Warhead"),this.deathWeapon=e.getString("DeathWeapon"),this.dMislEliteWarhead=e.getString("DMislEliteWarhead"),this.dMislWarhead=e.getString("DMislWarhead"),this.flameDamage=e.getString("FlameDamage"),this.ironCurtainDuration=e.getNumber("IronCurtainDuration"),this.ivanDamage=e.getNumber("IvanDamage"),this.ivanIconFlickerRate=e.getNumber("IvanIconFlickerRate"),this.ivanTimedDelay=e.getNumber("IvanTimedDelay"),this.ivanWarhead=e.getString("IvanWarhead"),this.splashList=e.getArray("SplashList"),this.v3EliteWarhead=e.getString("V3EliteWarhead"),this.v3Warhead=e.getString("V3Warhead")}}class TiberiumRules{readIni(e){return this.value=e.getNumber("Value"),this}}class AiRules{readIni(e){this.buildPower=e.getArray("BuildPower"),this.buildRefinery=e.getArray("BuildRefinery"),this.buildTech=e.getArray("BuildTech"),this.tiberiumFarScan=e.getNumber("TiberiumFarScan",50),this.tiberiumNearScan=e.getNumber("TiberiumNearScan",5)}}class ElevationModelRules{readIni(e){return this.increment=e.getNumber("ElevationIncrement"),this.incrementBonus=e.getNumber("ElevationIncrementBonus",1),this.bonusCap=e.getNumber("ElevationBonusCap"),this}getBonus(e,t){return e<=t?0:Math.min(this.bonusCap,Math.floor((e-t)/this.increment))*this.incrementBonus}}class RadiationRules{readIni(e){this.radDurationMultiple=e.getNumber("RadDurationMultiple"),this.radApplicationDelay=e.getNumber("RadApplicationDelay"),this.radLevelMax=e.getNumber("RadLevelMax"),this.radLevelDelay=e.getNumber("RadLevelDelay"),this.radLightDelay=e.getNumber("RadLightDelay"),this.radLevelFactor=e.getNumber("RadLevelFactor"),this.radLightFactor=e.getNumber("RadLightFactor"),this.radTintFactor=e.getNumber("RadTintFactor"),this.radColor=e.getNumberArray("RadColor"),this.radSiteWarhead=e.getString("RadSiteWarhead")}}!function(e){e[e.MultiMissile=0]="MultiMissile",e[e.IronCurtain=1]="IronCurtain",e[e.LightningStorm=2]="LightningStorm",e[e.ChronoSphere=3]="ChronoSphere",e[e.ChronoWarp=4]="ChronoWarp",e[e.ParaDrop=5]="ParaDrop",e[e.AmerParaDrop=6]="AmerParaDrop"}(SuperWeaponType=SuperWeaponType||{});class SuperWeaponRules{constructor(e){this.index=e}readIni(e){return this.disableableFromShell=e.getBool("DisableableFromShell"),this.isPowered=e.getBool("IsPowered",!0),this.name=e.name,this.preClick=e.getBool("PreClick"),this.preDependent=e.getEnum("PreDependent",SuperWeaponType,void 0),this.postClick=e.getBool("PostClick"),this.rechargeTime=e.getNumber("RechargeTime",5),this.showTimer=e.getBool("ShowTimer"),this.sidebarImage=e.getString("SidebarImage").toLowerCase(),this.type=e.getEnum("Type",SuperWeaponType,void 0),this.uiName=e.getString("UIName"),this.weaponType=e.getString("WeaponType")||void 0,this}}class CrateRules{readIni(e){this.crateMaximum=e.getNumber("CrateMaximum"),this.crateMinimum=e.getNumber("CrateMinimum"),this.crateRadius=e.getNumber("CrateRadius"),this.crateRegen=e.getNumber("CrateRegen");let t=e.getString("UnitCrateType");return this.unitCrateType="none"!==t.toLowerCase()?t:void 0,this.healCrateSound=e.getString("HealCrateSound"),this.crateImg=e.getString("CrateImg"),this.waterCrateImg=e.getString("WaterCrateImg"),this.freeMCV=e.getBool("FreeMCV"),this}}!function(e){e[e.Cheer=0]="Cheer",e[e.UnitDeployUndeploy=1]="UnitDeployUndeploy",e[e.WeaponFire=2]="WeaponFire",e[e.ObjectDestroy=3]="ObjectDestroy",e[e.ObjectSpawn=4]="ObjectSpawn",e[e.ObjectUnspawn=5]="ObjectUnspawn",e[e.ObjectMorph=6]="ObjectMorph",e[e.ObjectLiftOff=7]="ObjectLiftOff",e[e.ObjectLand=8]="ObjectLand",e[e.ObjectCrashing=9]="ObjectCrashing",e[e.ObjectDisguiseChange=10]="ObjectDisguiseChange",e[e.ObjectCloakChange=11]="ObjectCloakChange",e[e.ObjectAttacked=12]="ObjectAttacked",e[e.ShipSubmergeChange=13]="ShipSubmergeChange",e[e.BridgeRepair=14]="BridgeRepair",e[e.BuildStatusChange=15]="BuildStatusChange",e[e.BuildingPlace=16]="BuildingPlace",e[e.BuildingFailedPlace=17]="BuildingFailedPlace",e[e.ObjectSell=18]="ObjectSell",e[e.BuildingRepairFull=19]="BuildingRepairFull",e[e.BuildingCapture=20]="BuildingCapture",e[e.BuildingInfiltration=21]="BuildingInfiltration",e[e.BuildingGarrison=22]="BuildingGarrison",e[e.BuildingEvacuate=23]="BuildingEvacuate",e[e.BuildingRepairStart=24]="BuildingRepairStart",e[e.UnitRepairStart=25]="UnitRepairStart",e[e.UnitRepairFinish=26]="UnitRepairFinish",e[e.UnitRecycle=27]="UnitRecycle",e[e.InflictDamage=28]="InflictDamage",e[e.HealthChange=29]="HealthChange",e[e.WarheadDetonate=30]="WarheadDetonate",e[e.PlayerDefeated=31]="PlayerDefeated",e[e.PlayerResigned=32]="PlayerResigned",e[e.PlayerDropped=33]="PlayerDropped",e[e.DeployNotAllowed=34]="DeployNotAllowed",e[e.PowerChange=35]="PowerChange",e[e.PowerLow=36]="PowerLow",e[e.PowerRestore=37]="PowerRestore",e[e.RadarOnOff=38]="RadarOnOff",e[e.ObjectOwnerChange=39]="ObjectOwnerChange",e[e.RadarEvent=40]="RadarEvent",e[e.InsufficientFunds=41]="InsufficientFunds",e[e.RallyPointChange=42]="RallyPointChange",e[e.PrimaryFactoryChange=43]="PrimaryFactoryChange",e[e.FactoryProduceUnit=44]="FactoryProduceUnit",e[e.ObjectTeleport=45]="ObjectTeleport",e[e.AllianceChange=46]="AllianceChange",e[e.UnitPromote=47]="UnitPromote",e[e.EnterTransport=48]="EnterTransport",e[e.LeaveTransport=49]="LeaveTransport",e[e.EnterObject=50]="EnterObject",e[e.EnterTile=51]="EnterTile",e[e.SuperWeaponReady=52]="SuperWeaponReady",e[e.SuperWeaponActivate=53]="SuperWeaponActivate",e[e.LightningStormManifest=54]="LightningStormManifest",e[e.LightningStormCloud=55]="LightningStormCloud",e[e.CratePickup=56]="CratePickup",e[e.PingLocation=57]="PingLocation",e[e.StalemateDetect=58]="StalemateDetect",e[e.TriggerSoundFx=59]="TriggerSoundFx",e[e.TriggerStopSoundFx=60]="TriggerStopSoundFx",e[e.TriggerEva=61]="TriggerEva",e[e.TriggerAnim=62]="TriggerAnim",e[e.TriggerText=63]="TriggerText",e[e.TimerExpire=64]="TimerExpire"}(EventType=EventType||{});class CratePickupEvent{constructor(e,t,i,r){this.target=e,this.player=t,this.source=i,this.tile=r,this.type=EventType.CratePickup}}var ZoneType,AiDifficulty,PowerupType,NotifyTick,NotifyWarpChange,SuperWeaponStatus,EffectStatus,NotifyPower,NotifySuperWeaponActivate,StanceType,TaskStatus,Vector2_THREE=__webpack_require__(70);class Vector2 extends Vector2_THREE.Vector2{length(){return GameMath.sqrt(this.x*this.x+this.y*this.y)}angle(){let e=GameMath.atan2(this.y,this.x);return e<0&&(e+=2*Math.PI),e}distanceTo(e){return GameMath.sqrt(this.distanceToSquared(e))}rotateAround(e,t){var i=GameMath.cos(t),r=GameMath.sin(t),s=this.x-e.x,t=this.y-e.y;return this.x=s*i-t*r+e.x,this.y=s*r+t*i+e.y,this}}class Coords{static tileToWorld(e,t){return{x:e*Coords.LEPTONS_PER_TILE,y:t*Coords.LEPTONS_PER_TILE}}static vecWorldToGround(e){return new Vector2(e.x,e.z)}static vecGroundToWorld(e){return new Vector3_Vector3(e.x,0,e.y)}static tileHeightToWorld(e){return e*(Coords.LEPTONS_PER_TILE/2)*Coords.zScale}static worldToTileHeight(e){return e/(Coords.LEPTONS_PER_TILE/2*Coords.zScale)}static tile3dToWorld(e,t,i){t=Coords.tileToWorld(e,t),i=Coords.tileHeightToWorld(i);return new Vector3_Vector3(t.x,i,t.y)}static screenDistanceToWorld(e,t){return{x:Math.floor((e+2*t)/2*Coords.ISO_WORLD_SCALE),y:Math.floor((2*t-e)/2*Coords.ISO_WORLD_SCALE)}}static getWorldTileSize(){return Coords.LEPTONS_PER_TILE}}function getZoneType(e){return[LandType.Water,LandType.Beach].includes(e)?ZoneType.Water:ZoneType.Ground}Coords.ISO_TILE_SIZE=30,Coords.LEPTONS_PER_TILE=256,Coords.ISO_WORLD_SCALE=Coords.LEPTONS_PER_TILE/Coords.ISO_TILE_SIZE,Coords.ISO_CAMERA_ALPHA=Math.PI/6,Coords.ISO_CAMERA_BETA=Math.PI/4,Coords.COS_ISO_CAMERA_BETA=GameMath.cos(Coords.ISO_CAMERA_BETA),Coords.zScale=Coords.COS_ISO_CAMERA_BETA/GameMath.cos(Coords.ISO_CAMERA_ALPHA),function(e){e[e.Ground=0]="Ground",e[e.Air=1]="Air",e[e.Water=2]="Water"}(ZoneType=ZoneType||{});const isGameObject=e=>void 0!==e.position,isVector3=e=>void 0!==e.addScalar;class RangeHelper{constructor(e){this.tileOccupation=e}isInWeaponRange(e,t,i,r,s){var a=s??e;if(i.rules.limboLaunch&&2<Math.abs((isGameObject(a)?a.position.tileElevation+a.tile.z:a.z)-(isGameObject(t)?t.position.tileElevation+t.tile.z:t.z)))return!1;var{minRange:s,range:r}=this.computeWeaponRangeVsTarget(a,t,i,r);return i.rules.cellRangefinding?this.isInTileRange(a,t,s,r):e.isUnit()&&e.rules.movementZone===MovementZone.Fly?this.isInRange2(a,t,s,r):this.isInRange3(a,t,s,r)}computeWeaponRangeVsTarget(e,t,i,r){let s=0;var a,n;return!isGameObject(t)||!t.isBuilding()||i.projectileRules.arcing||i.projectileRules.vertical||i.warhead.rules.ivanBomb||1<(n=t.getFoundation()).width&&1<n.height&&(s+=Math.ceil(Math.min(n.width,n.height)/2)),!i.projectileRules.subjectToElevation||i.projectileRules.arcing&&!isGameObject(t)||(a=isGameObject(e)?e.tile.z+e.tileElevation:e.z,(n=isGameObject(t)?t.tile.z+t.tileElevation:t.z)<a&&(s+=r.elevationModel.getBonus(a,n))),i.projectileRules.isAntiAir&&isGameObject(e)&&e.isTechno()&&isGameObject(t)&&t.isUnit()&&t.zone===ZoneType.Air&&(s+=e.rules.airRangeBonus),{minRange:i.minRange,range:i.range+s}}isInRange(e,t,i,r,s=!1){return s?this.isInTileRange(e,t,i,r):e.isUnit()&&e.rules.movementZone===MovementZone.Fly?this.isInRange2(e,t,i,r):this.isInRange3(e,t,i,r)}isInRange3(e,t,i,r){return isBetween(this.distance3(e,t)/Coords.LEPTONS_PER_TILE,i,r)}isInRange2(e,t,i,r){return isBetween(this.distance2(e,t)/Coords.LEPTONS_PER_TILE,i,r)}distance3(e,t){let i=isGameObject(e)?e.position.worldPosition:isVector3(e)?e:Coords.tile3dToWorld(e.rx+.5,e.ry+.5,e.z);t=isGameObject(t)?t.position.worldPosition:isVector3(t)?t:Coords.tile3dToWorld(t.rx+.5,t.ry+.5,t.z);return i.distanceTo(t)}distance2(e,t){let i=isGameObject(e)?new Vector2(e.position.worldPosition.x,e.position.worldPosition.z):isVector3(e)?new Vector2(e.x,e.z):new Vector2(e.rx+.5,e.ry+.5).multiplyScalar(Coords.LEPTONS_PER_TILE);t=isGameObject(t)?new Vector2(t.position.worldPosition.x,t.position.worldPosition.z):isVector3(t)?new Vector2(t.x,t.z):new Vector2(t.rx+.5,t.ry+.5).multiplyScalar(Coords.LEPTONS_PER_TILE);return i.distanceTo(t)}isInTileRange(e,t,i,r){return isBetween(this.tileDistance(e,t),i,r)}tileDistance(e,t){var i,e=isGameObject(e)?this.tileOccupation.calculateTilesForGameObject(e.tile,e):Array.isArray(e)?e:[e],r=isGameObject(t)?this.tileOccupation.calculateTilesForGameObject(t.tile,t):Array.isArray(t)?t:[t];let s=new Vector2,a=new Vector2,n=Number.POSITIVE_INFINITY;for(i of e)for(var o of r){s.set(i.rx,i.ry),a.set(o.rx,o.ry);o=s.distanceTo(a);o<=n&&(n=o)}return n}}const isHumanPlayerInfo=e=>"name"in e;!function(e){e[e.Brutal=0]="Brutal",e[e.Medium=1]="Medium",e[e.Easy=2]="Easy"}(AiDifficulty=AiDifficulty||{});const RANDOM_COUNTRY_ID=-2,RANDOM_COLOR_ID=-2,RANDOM_START_POS=-2,NO_TEAM_ID=-2,OBS_COUNTRY_ID=-3,OBS_COLOR_ID=-2,RANDOM_COUNTRY_NAME="Random",OBS_COUNTRY_NAME="Observer",aiUiNames=(new Map).set(AiDifficulty.Easy,"GUI:AIDummy").set(AiDifficulty.Medium,"GUI:AIEasyBeta"),aiUiTooltips=new Map,RANDOM_COUNTRY_UI_NAME="GUI:RandomEx",RANDOM_COUNTRY_UI_TOOLTIP="STT:PlayerSideRandom",OBS_COUNTRY_UI_NAME="GUI:Observer",OBS_COUNTRY_UI_TOOLTIP="STT:PlayerSideObserver",RANDOM_COLOR_NAME="";class GameSpeed{static computeGameSpeed(e){let t;return t=6===e?60:5===e?45:60/(6-e),t/GameSpeed.BASE_TICKS_PER_SECOND}}GameSpeed.BASE_TICKS_PER_SECOND=15;class RadialTileFinder{constructor(e,t,i,r,s,a,n,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.foundation=r,this.maxDistance=a,this.predicate=n,this.checkBounds=o,this.distance=s,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){var r=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t))return t};do{var s=this.startTile.rx-this.distance,a=this.startTile.ry-this.distance,n=this.startTile.rx+this.foundation.width-1+this.distance,o=this.startTile.ry+this.foundation.height-1+this.distance;let e,t,i;if(0<this.distance){for(e=n;e>=s;e--)i=r(e,o),i&&(yield i);for(t=o-1;t>=a;t--)i=r(n,t),i&&(yield i);for(e=s;e<n;e++)i=r(e,a),i&&(yield i);for(t=1+a;t<o;t++)i=r(s,t),i&&(yield i)}else this.predicate(this.startTile)&&(yield this.startTile)}while(this.distance++,this.distance<=this.maxDistance)}}!function(e){e[e.Armor=0]="Armor",e[e.Firepower=1]="Firepower",e[e.HealBase=2]="HealBase",e[e.Money=3]="Money",e[e.Reveal=4]="Reveal",e[e.Speed=5]="Speed",e[e.Veteran=6]="Veteran",e[e.Unit=7]="Unit",e[e.Invulnerability=8]="Invulnerability",e[e.IonStorm=9]="IonStorm",e[e.Gas=10]="Gas",e[e.Tiberium=11]="Tiberium",e[e.Pod=12]="Pod",e[e.Cloak=13]="Cloak",e[e.Darkness=14]="Darkness",e[e.Explosion=15]="Explosion",e[e.ICBM=16]="ICBM",e[e.Napalm=17]="Napalm",e[e.Squad=18]="Squad"}(PowerupType=PowerupType||{}),(NotifyTick=NotifyTick||{}).onTick=Symbol(),(NotifyWarpChange=NotifyWarpChange||{}).onChange=Symbol();class SuperWeaponReadyEvent{constructor(e){this.target=e,this.type=EventType.SuperWeaponReady}}!function(e){e[e.Charging=0]="Charging",e[e.Paused=1]="Paused",e[e.Ready=2]="Ready"}(SuperWeaponStatus=SuperWeaponStatus||{});class SuperWeapon{constructor(e,t,i,r=!1){this.name=e,this.rules=t,this.owner=i,this.oneTimeOnly=r,this.status=SuperWeaponStatus.Charging,this.isGift=!1,this.rechargeTicks=60*t.rechargeTime*GameSpeed.BASE_TICKS_PER_SECOND,this.chargeTicks=this.rechargeTicks,r&&(this.status=SuperWeaponStatus.Ready,this.chargeTicks=0)}update(e){0<this.chargeTicks&&this.status!==SuperWeaponStatus.Paused&&(this.chargeTicks--,0===this.chargeTicks&&(this.status=SuperWeaponStatus.Ready,e.events.dispatch(new SuperWeaponReadyEvent(this))))}pauseTimer(){this.status=SuperWeaponStatus.Paused}resumeTimer(){this.status=0<this.chargeTicks?SuperWeaponStatus.Charging:SuperWeaponStatus.Ready}resetTimer(){this.chargeTicks=this.rechargeTicks,this.status===SuperWeaponStatus.Ready&&(this.status=SuperWeaponStatus.Charging)}getTimerSeconds(){return this.chargeTicks/GameSpeed.BASE_TICKS_PER_SECOND}getChargeProgress(){return(this.rechargeTicks-this.chargeTicks)/this.rechargeTicks}}!function(e){e[e.NotStarted=0]="NotStarted",e[e.Running=1]="Running",e[e.Finished=2]="Finished"}(EffectStatus=EffectStatus||{});class SuperWeaponEffect{constructor(e,t,i){this.type=e,this.owner=t,this.tile=i,this.status=EffectStatus.NotStarted}onStart(e){}onTick(e){return!0}}!function(e){e.onPowerLow=Symbol(),e.onPowerRestore=Symbol(),e.onPowerChange=Symbol()}(NotifyPower=NotifyPower||{}),(NotifySuperWeaponActivate=NotifySuperWeaponActivate||{}).onActivate=Symbol();class SuperWeaponActivateEvent{constructor(e,t,i,r,s){this.target=e,this.owner=t,this.atTile=i,this.atTile2=r,this.noSfxWarning=s,this.type=EventType.SuperWeaponActivate}}!function(e){e[e.None=0]="None",e[e.Guard=1]="Guard",e[e.Prone=2]="Prone",e[e.Deployed=3]="Deployed",e[e.Paradrop=4]="Paradrop",e[e.Cheer=5]="Cheer"}(StanceType=StanceType||{}),function(e){e[e.NotStarted=0]="NotStarted",e[e.Running=1]="Running",e[e.Finished=2]="Finished",e[e.Cancelling=3]="Cancelling",e[e.Cancelled=4]="Cancelled"}(TaskStatus=TaskStatus||{});class Task{constructor(){this.status=TaskStatus.NotStarted,this.children=[],this.cancellable=!0,this.useChildTargetLines=!1,this.blocking=!0,this.waitingForChildrenToFinish=!1,this.preventOpportunityFire=!0,this.preventLanding=!0,this.isAttackMove=!1}isRunning(){return this.status===TaskStatus.Running}isCancelling(){return this.status===TaskStatus.Cancelling}setCancellable(e){return this.cancellable=e,this}setBlocking(e){return this.blocking=e,this}onStart(e){}onEnd(e){}cancel(){if(this.cancellable)if(this.status===TaskStatus.Running)this.status=TaskStatus.Cancelling,this.children.length&&this.children.forEach(e=>e.cancel());else if(this.status===TaskStatus.NotStarted&&(this.status=TaskStatus.Cancelled,this.children.length))throw new Error("Should't have any children before starting a task")}getTargetLinesConfig(e){}}function findReverse(t,i){for(let e=t.length-1;0<=e;e--)if(i(t[e],e,t))return t[e]}function findIndexReverse(t,i){for(let e=t.length-1;0<=e;e--)if(i(t[e],e,t))return e;return-1}function equals(i,r){if(i.length!==r.length)return!1;for(let e=0,t=i.length;e<t;e++)if(i[e]!==r[e])return!1;return!0}class WaitTicksTask extends Task{constructor(e){super(),this.ticks=e}onTick(){return!!this.isCancelling()||!(0<this.ticks--)}}class MovePositionHelper{constructor(e){this.map=e}findPositions(e,r,s,a){let n=new Map,t=this.clusterObjects(e);if(!t.length)throw new Error("We should have found at least one cluster");let i=t.reduce((e,t)=>t.objects.size>e.objects.size?t:e,t[0]);t.splice(t.indexOf(i),1);let o=[],l=this.findCenterTile([...i.objects]);i.objects.forEach(t=>{var i=this.map.tiles.getByMapCoords(r.rx+t.tile.rx-l.rx,r.ry+t.tile.ry-l.ry),e=i?.onBridgeLandType?this.map.tileOccupation.getBridgeOnTile(i):void 0;if(!i||!this.map.mapBounds.isWithinBounds(i)||n.has(i)&&!this.tileHasRoom(t,n.get(i))||t.rules.movementZone===MovementZone.Fly&&!(t.rules.airportBound||a&&t.rules.balloonHover&&!t.rules.hoverAttack)&&!this.map.terrain.getPassableSpeed(i,SpeedType.Amphibious,!1,!!e)||t.rules.movementZone!==MovementZone.Fly&&!this.isEligibleTile(i,e,s,r))o.push(t);else{let e=n.get(i);void 0===e&&(e=[],n.set(i,e)),e.push(t)}}),t.forEach(e=>o.push(...e.objects));let h=new RadialTileFinder(this.map.tiles,this.map.mapBounds,r,{width:1,height:1},1,5,()=>!0),c;for(;o.length&&(c=h.getNextTile());){var u=o[0],d=this.map.tileOccupation.getBridgeOnTile(c);if((!n.has(c)||this.tileHasRoom(u,n.get(c)))&&((u.rules.movementZone!==MovementZone.Fly||u.rules.airportBound||this.map.terrain.getPassableSpeed(c,SpeedType.Amphibious,!1,!!d))&&(u.rules.movementZone===MovementZone.Fly||this.isEligibleTile(c,d,s,r)))){let e=n.get(c);void 0===e&&(e=[],n.set(c,e)),e.push(o.shift())}}let p=new Map;if(n.forEach((e,t)=>{e.forEach(e=>p.set(e,t))}),o.forEach(e=>p.set(e,r)),p.size!==e.length)throw new Error("We should have computed a number of positions equal to the number of input objects");return p}tileHasRoom(e,t){if(e.isInfantry()){if(t.find(e=>!e.isInfantry()))return!1;e=e.rules.movementZone===MovementZone.Fly?1:3;return t.filter(e=>e.isInfantry()).length>=e?!1:!0}return!t.length}isEligibleTile(e,t,i,r){return i?.isHighBridge()||t?.isHighBridge()?e.z+(t?.tileElevation??0)===r.z+(i?.tileElevation??0):!(!i&&!t)||Math.abs(e.z-r.z)<2}clusterObjects(e){let s=new Map;e.forEach(e=>{var t=e.tile.rx+"_"+e.tile.ry;s.set(t,[...s.get(t)||[],e])});let t=[],a=new Set(e);for(;a.size;){let e=new Set,r=[];var i=[...a][0].tile;for(s.get(i.rx+"_"+i.ry).forEach(e=>{r.push(e)});r.length;){var n=r.shift();e.add(n),a.delete(n);for(let i=-1;i<=1;i++)for(let t=-1;t<=1;t++)if(i||t){let e=s.get(n.tile.rx+i+"_"+(n.tile.ry+t));e&&e.length&&e.forEach(e=>{a.has(e)&&(a.delete(e),r.push(e))})}}t.push({objects:e})}return t}findCenterTile(e){let t=0,i=0;e.forEach(e=>{t+=e.tile.rx,i+=e.tile.ry}),t=Math.round(t/e.length),i=Math.round(i/e.length);let r=this.map.tiles.getByMapCoords(t,i);if(!r&&(r=e.find(e=>Math.abs(e.tile.rx-t)<=1&&Math.abs(e.tile.ry-i)<=1)?.tile,!r))throw new Error("At least one adjacent object should have been found");return r}}var Matrix4_THREE=__webpack_require__(70);class Matrix4 extends Matrix4_THREE.Matrix4{extractRotation(e){let t=this.elements;var i=e.elements,r=1/_vector3.setFromMatrixColumn(e,0).length(),s=1/_vector3.setFromMatrixColumn(e,1).length(),e=1/_vector3.setFromMatrixColumn(e,2).length();return t[0]=i[0]*r,t[1]=i[1]*r,t[2]=i[2]*r,t[3]=0,t[4]=i[4]*s,t[5]=i[5]*s,t[6]=i[6]*s,t[7]=0,t[8]=i[8]*e,t[9]=i[9]*e,t[10]=i[10]*e,t[11]=0,t[12]=0,t[13]=0,t[14]=0,t[15]=1,this}makeRotationFromEuler(e){e&&e.isEuler||console.error("THREE.Matrix4: .makeRotationFromEuler() now expects a Euler rotation rather than a Vector3 and order.");let t=this.elements;var i,r,s,a,n,o,l,h,c,u,d,p=e.x,g=e.y,m=e.z,y=GameMath.cos(p),T=GameMath.sin(p),f=GameMath.cos(g),v=GameMath.sin(g),p=GameMath.cos(m),g=GameMath.sin(m);return"XYZ"===e.order?(i=y*p,s=y*g,r=T*p,m=T*g,t[0]=f*p,t[4]=-f*g,t[8]=v,t[1]=s+r*v,t[5]=i-m*v,t[9]=-T*f,t[2]=m-i*v,t[6]=r+s*v,t[10]=y*f):"YXZ"===e.order?(a=f*p,i=f*g,r=v*p,s=v*g,t[0]=a+s*T,t[4]=r*T-i,t[8]=y*v,t[1]=y*g,t[5]=y*p,t[9]=-T,t[2]=i*T-r,t[6]=s+a*T,t[10]=y*f):"ZXY"===e.order?(l=f*p,a=f*g,n=v*p,o=v*g,t[0]=l-o*T,t[4]=-y*g,t[8]=n+a*T,t[1]=a+n*T,t[5]=y*p,t[9]=o-l*T,t[2]=-y*v,t[6]=T,t[10]=y*f):"ZYX"===e.order?(n=y*p,o=y*g,h=T*p,l=T*g,t[0]=f*p,t[4]=h*v-o,t[8]=n*v+l,t[1]=f*g,t[5]=l*v+n,t[9]=o*v-h,t[2]=-v,t[6]=T*f,t[10]=y*f):"YZX"===e.order?(u=y*f,h=y*v,c=T*f,d=T*v,t[0]=f*p,t[4]=d-u*g,t[8]=c*g+h,t[1]=g,t[5]=y*p,t[9]=-T*p,t[2]=-v*p,t[6]=h*g+c,t[10]=u-d*g):"XZY"===e.order&&(c=y*f,u=y*v,d=T*f,e=T*v,t[0]=f*p,t[4]=-g,t[8]=v*p,t[1]=c*g+e,t[5]=y*p,t[9]=u*g-d,t[2]=d*g-u,t[6]=T*p,t[10]=e*g+c),t[3]=0,t[7]=0,t[11]=0,t[12]=0,t[13]=0,t[14]=0,t[15]=1,this}lookAt(e,t,i){_x.set(0,0,0),_y.set(0,0,0),_z.set(0,0,0);const r=this.elements;return _z.subVectors(e,t),0===_z.lengthSq()&&(_z.z=1),_z.normalize(),_x.crossVectors(i,_z),0===_x.lengthSq()&&(1===Math.abs(i.z)?_z.x+=1e-4:_z.z+=1e-4,_z.normalize(),_x.crossVectors(i,_z)),_x.normalize(),_y.crossVectors(_z,_x),r[0]=_x.x,r[4]=_y.x,r[8]=_z.x,r[1]=_x.y,r[5]=_y.y,r[9]=_z.y,r[2]=_x.z,r[6]=_y.z,r[10]=_z.z,this}getMaxScaleOnAxis(){var e=this.elements,t=e[0]*e[0]+e[1]*e[1]+e[2]*e[2],i=e[4]*e[4]+e[5]*e[5]+e[6]*e[6],e=e[8]*e[8]+e[9]*e[9]+e[10]*e[10];return GameMath.sqrt(Math.max(t,i,e))}makeRotationX(e){var t=GameMath.cos(e),e=GameMath.sin(e);return this.set(1,0,0,0,0,t,-e,0,0,e,t,0,0,0,0,1),this}makeRotationY(e){var t=GameMath.cos(e),e=GameMath.sin(e);return this.set(t,0,e,0,0,1,0,0,-e,0,t,0,0,0,0,1),this}makeRotationZ(e){var t=GameMath.cos(e),e=GameMath.sin(e);return this.set(t,-e,0,0,e,t,0,0,0,0,1,0,0,0,0,1),this}makeRotationAxis(e,t){var i=GameMath.cos(t),r=GameMath.sin(t),s=1-i,a=e.x,n=e.y,o=e.z,t=s*a,e=s*n;return this.set(t*a+i,t*n-r*o,t*o+r*n,0,t*n+r*o,e*n+i,e*o-r*a,0,t*o-r*n,e*o+r*a,s*o*o+i,0,0,0,0,1),this}decompose(e,t,i){var r=this.elements;let s=_vector3.set(r[0],r[1],r[2]).length();var a=_vector3.set(r[4],r[5],r[6]).length(),n=_vector3.set(r[8],r[9],r[10]).length();this.determinant()<0&&(s=-s),e.x=r[12],e.y=r[13],e.z=r[14],_matrix.copy(this);var o=1/s,e=1/a,r=1/n;return _matrix.elements[0]*=o,_matrix.elements[1]*=o,_matrix.elements[2]*=o,_matrix.elements[4]*=e,_matrix.elements[5]*=e,_matrix.elements[6]*=e,_matrix.elements[8]*=r,_matrix.elements[9]*=r,_matrix.elements[10]*=r,t.setFromRotationMatrix(_matrix),i.x=s,i.y=a,i.z=n,this}}const _vector3=new Vector3_Vector3,_x=new Vector3_Vector3,_y=new Vector3_Vector3,_z=new Vector3_Vector3,_matrix=new Matrix4;var geometry_THREE=__webpack_require__(70);function radToDeg(e){return e*geometry_THREE.Math.RAD2DEG}function degToRad(e){return e*geometry_THREE.Math.DEG2RAD}const zeroVec=new Vector2;function rotateVec2(e,t){t=degToRad(Math.floor(t));return e.rotateAround(zeroVec,t)}function angleDegFromVec2(e){return Math.round(radToDeg(e.angle()))}function angleDegBetweenQuaternions(e,t){t=radToDeg(2*GameMath.acos(Math.abs(clamp(e.dot(t),-1,1))));return Math.round(t)}function angleDegBetweenVec2(e,t){e=angleDegFromVec2(e),t=angleDegFromVec2(t);return Math.min((e-t+360)%360,(t-e+360)%360)}function angleDegBetweenVec3(e,t){return angleDegBetweenQuaternions(quaternionFromVec3(e,_q1),quaternionFromVec3(t,_q2))}function quaternionFromVec3(e,t=new Quaternion){return t.setFromRotationMatrix(_m4.lookAt(e,_zeroVec3,_upVec3))}const _m4=new Matrix4,_zeroVec3=new Vector3_Vector3(0,0,0),_upVec3=new Vector3_Vector3(0,1,0);function rotateVec3Towards(e,t,i){var r=e.length(),s=quaternionFromVec3(t,_q1),t=quaternionFromVec3(e,_q2);rotateTowards(t,s,i),e.set(0,0,1).applyQuaternion(t).setLength(r)}const _q1=new Quaternion,_q2=new Quaternion;function rotateTowards(e,t,i){var r=angleDegBetweenQuaternions(e,t);if(0!==r){r=Math.min(1,i/r);return e.slerp(t,r)}}const BAILOUT_TICKS=200,RETRY_TICKS=5;class MoveAsideTask extends Task{constructor(e,t){super(),this.game=e,this.fromDirection=t,this.resolved=!1,this.chainPushIssued=!1}onEnd(e){e.moveTrait.collisionState=CollisionState.Resolved}onTick(i){if(this.timeoutTicks=void 0===this.timeoutTicks?0:this.timeoutTicks+1,this.timeoutTicks>BAILOUT_TICKS/RETRY_TICKS||this.resolved||this.isCancelling())return!0;let r=this.game.map,t=new MovePositionHelper(r);var s=i.onBridge?r.tileOccupation.getBridgeOnTile(i.tile):void 0;let a,n;for(let e=0;e<360;e+=45)if((0!==e||this.chainPushIssued)&&180!==e){var o=rotateVec2(this.fromDirection.clone(),e).round(),o=r.tiles.getByMapCoords(i.tile.rx+Math.sign(o.x),i.tile.ry+Math.sign(o.y));if(o&&r.mapBounds.isWithinBounds(o)&&(n=r.tileOccupation.getBridgeOnTile(o),i.rules.movementZone===MovementZone.Fly||!r.terrain.findObstacles({tile:o,onBridge:n},i).length&&t.isEligibleTile(o,n,s,i.tile))){a=o;break}}if(a)return this.resolved=!0,i.isInfantry()&&i.deployerTrait&&i.deployerTrait.isDeployed()&&i.deployerTrait.setDeployed(!1),!!i.moveTrait.isDisabled()||(this.children.push(new MoveTask(this.game,a,!!n,{closeEnoughTiles:0,strictCloseEnough:!0})),!1);{if(this.chainPushIssued)return this.children.push(new WaitTicksTask(RETRY_TICKS)),!1;let t=r.tiles.getByMapCoords(i.tile.rx+Math.sign(this.fromDirection.x),i.tile.ry+Math.sign(this.fromDirection.y));if(!t||!r.mapBounds.isWithinBounds(t))return!0;n=r.tileOccupation.getBridgeOnTile(t);let e=r.tileOccupation.getGroundObjectsOnTile(t).filter(e=>e.isUnit()&&e.owner===i.owner&&e.tile===t&&e.onBridge===!!n&&!(e.isInfantry()&&e.stance===StanceType.Paradrop)&&!(e.isAircraft()&&e.missileSpawnTrait));return e.find(e=>e.moveTrait.collisionState===CollisionState.Waiting||e.unitOrderTrait.hasTasks())?(this.children.push(new WaitTicksTask(RETRY_TICKS)),i.moveTrait.collisionState=CollisionState.Waiting,i.moveTrait.moveState=MoveState.PlanMove,!1):(e.forEach(e=>{e.unitOrderTrait.addTask(new MoveAsideTask(this.game,this.fromDirection))}),this.children.push(new WaitTicksTask(1)),i.moveTrait.collisionState=CollisionState.Waiting,i.moveTrait.moveState=MoveState.PlanMove,!(this.chainPushIssued=!0))}}}var logger=__webpack_require__(750);const AppLogger=logger;class ChronoLocomotor{constructor(e){this.game=e,this.ignoresTerrain=!0,this.distanceToWaypoint=new Vector2}onNewWaypoint(e,t){}tick(e,t,i,r){if(r)return{distance:new Vector3_Vector3,done:!0};this.distanceToWaypoint.copy(t).sub(e.position.getMapPosition());r=this.game.rules.general;return r.chronoTrigger&&(r=(t=this.distanceToWaypoint.length())<r.chronoRangeMinimum?r.chronoMinimumDelay:t/r.chronoDistanceFactor,e.warpedOutTrait.setTimed(r,!1,this.game)),{distance:new Vector3_Vector3(this.distanceToWaypoint.x,0,this.distanceToWaypoint.y),done:!0,isTeleport:!0}}}class FacingUtil{static tick(e,t,i){if(e===t)return{facing:e,delta:0};var r=(e-t+360)%360,s=(t-e+360)%360;if(Math.min(r,s)<i)return{facing:t,delta:0};i*=s<=r?1:-1;return{facing:(e+i+360)%360,delta:i}}static fromMapCoords(e){return(-angleDegFromVec2(e)-90+720)%360}static toMapCoords(e){return rotateVec2(new Vector2(1e3,0),FacingUtil.toWorldDeg(e)).round().normalize()}static toWorldDeg(e){return-(e+90)}}class TurnTask extends Task{constructor(e){super(),this.direction=e,this.cancellable=!1}onTick(e){if(e.direction===this.direction)return!(e.spinVelocity=0);var t=e.rules.rot,{facing:i,delta:t}=FacingUtil.tick(e.direction,this.direction,t);return e.direction=i,e.spinVelocity=t,!1}}var LineCurve_THREE=__webpack_require__(70);class LineCurve extends LineCurve_THREE.LineCurve{constructor(e,t){super(e||new Vector2,t||new Vector2)}getPoint(e,t){return super.getPoint(e,t||new Vector2)}}var CurvePath_THREE=__webpack_require__(70);class CurvePath extends CurvePath_THREE.CurvePath{closePath(){let e=this.curves[0].getPoint(0);var t=this.curves[this.curves.length-1].getPoint(1);e.equals(t)||this.curves.push(new LineCurve(t,e))}}var WaypointType,HoverLocomotor_WaypointType,QuadraticBezierCurve_THREE=__webpack_require__(70);class QuadraticBezierCurve extends QuadraticBezierCurve_THREE.QuadraticBezierCurve{constructor(e,t,i){super(e||new Vector2,t||new Vector2,i||new Vector2)}getPoint(e,t){return super.getPoint(e,t||new Vector2)}}!function(e){e[e.None=0]="None",e[e.Start=1]="Start",e[e.Normal=2]="Normal",e[e.End=3]="End",e[e.Single=4]="Single"}(WaypointType=WaypointType||{});class DriveLocomotor{constructor(e){this.game=e,this.hasMomentum=!1,this.moveOnCurve=!1,this.currentSpeed=0,this.distanceTravelled=0,this.carryOverDistance=0,this.currentWaypointType=WaypointType.None}selectNextWaypoint(i,r){if(this.currentWaypointType=this.currentWaypointType&&this.currentWaypointType!==WaypointType.End?WaypointType.Normal:WaypointType.Start,this.initialPosition=i.position.getMapPosition(),this.currentWaypointType!==WaypointType.Start?i.moveTrait.speedPenalty=0:this.currentSpeed=0,1<r.length){var s=r[r.length-1],a=r[r.length-2],e=new Vector2(s.tile.rx-i.tile.rx,s.tile.ry-i.tile.ry),n=Math.abs(angleDegFromVec2(e)-angleDegFromVec2(new Vector2(a.tile.rx-s.tile.rx,a.tile.ry-s.tile.ry)));if(!Math.abs(FacingUtil.fromMapCoords(e)-i.direction)&&0<n&&n<90&&this.hasMomentum){this.moveOnCurve=!0,this.currentWaypointType=2===r.length?this.currentWaypointType===WaypointType.Start?WaypointType.Single:WaypointType.End:WaypointType.Normal;let e=this.initialPosition;i=new Vector2(s.tile.rx+.5,s.tile.ry+.5).multiplyScalar(Coords.LEPTONS_PER_TILE);let t=new Vector2(a.tile.rx+.5,a.tile.ry+.5).multiplyScalar(Coords.LEPTONS_PER_TILE);n=e.clone().lerp(i,.5),s=t.clone().lerp(i,.5);return this.steerCurve=new CurvePath,this.steerCurve.add(new LineCurve(e,n)),this.steerCurve.add(new QuadraticBezierCurve(n,i,s)),this.steerCurve.add(new LineCurve(s,t)),this.lastPosition=e,a}}else this.currentWaypointType=this.currentWaypointType===WaypointType.Start?WaypointType.Single:WaypointType.End;return this.hasMomentum=!0,this.moveOnCurve=!1,r[r.length-1]}onNewWaypoint(e,t,i){let r=(new Vector2).copy(t).sub(this.initialPosition);this.distanceTravelled=0,this.totalDistanceToTravel=this.moveOnCurve?this.steerCurve.getLength():r.length();t=FacingUtil.fromMapCoords(r);if(t!==e.direction&&(this.pointTurretToTarget(e,i),!this.moveOnCurve))return e.moveTrait.velocity.set(0,0,0),[new TurnTask(t)]}tick(i,r,s){this.pointTurretToTarget(i,s);let a=this.currentSpeed;a=i.rules.accelerates?(l=this.distanceTravelled/this.totalDistanceToTravel,this.currentSpeed=this.applyAcceleration(i,a,i.moveTrait.baseSpeed,l)):this.currentSpeed=i.moveTrait.baseSpeed,1<a&&(a=Math.floor(a));let e=this.game.map.terrain.getPassableSpeed(i.tile,i.rules.speedType,i.isInfantry(),i.onBridge,void 0,!0);e?i.moveTrait.lastTileSpeed=e:e=i.moveTrait.lastTileSpeed||1,a*=e,1<a&&(a=Math.floor(a)),this.carryOverDistance&&(a=this.carryOverDistance);var n=i.position.getMapPosition();let o;if(this.moveOnCurve){var s=this.steerCurve.getLength(),l=Math.min(this.distanceTravelled+a,s);this.carryOverDistance=Math.max(0,this.distanceTravelled+a-s),this.distanceTravelled=l;let e=this.steerCurve.getPointAt(this.distanceTravelled/s),t=this.steerCurve.getTangentAt(this.distanceTravelled/s);l=t.clone().setLength(a);i.moveTrait.velocity.set(l.x,0,l.y);var s=i.rules.rot,{facing:l,delta:s}=FacingUtil.tick(i.direction,FacingUtil.fromMapCoords(t),s);i.direction=l,i.spinVelocity=s;s=this.lastPosition;this.lastPosition=e.clone(),o=e.sub(s)}else{let e=(new Vector2).copy(r).sub(n);n=Math.min(e.length(),a);o=e.clone().setLength(n);let t=o.clone();this.carryOverDistance&&t.add(Coords.vecWorldToGround(i.moveTrait.velocity)),i.moveTrait.velocity.set(t.x,0,t.y),this.distanceTravelled+=n,this.carryOverDistance=Math.max(0,a-e.length())}return{distance:new Vector3_Vector3(o.x,0,o.y),done:!o.length()||!!this.carryOverDistance}}pointTurretToTarget(t,i){if(t.turretTrait){t.attackTrait?.currentTarget?.obj&&(i=t.attackTrait.currentTarget.obj.position.getMapPosition());var r=t.position.getMapPosition();let e=(new Vector2).copy(i).sub(r);e.length()&&(r=FacingUtil.fromMapCoords(e),t.turretTrait.desiredFacing=r)}}applyAcceleration(e,t,i,r){if(this.currentWaypointType===WaypointType.Single)return i/2;if(this.currentWaypointType!==WaypointType.End)return Math.min(t+e.rules.accelerationFactor*i,i);return lerp(1,i,1-(r=this.moveOnCurve&&this.currentWaypointType===WaypointType.End?r<=.5?0:2*(r-.5):r))}}class FootLocomotor{constructor(e){this.game=e,this.currentMoveDirection=new Vector2,this.distanceToWaypoint=new Vector2,this.endPauseFrames=0}onNewWaypoint(e,t){this.currentMoveDirection.copy(t).sub(e.position.getMapPosition());t=FacingUtil.fromMapCoords(this.currentMoveDirection);t!==e.direction&&(e.direction=t),this.endPauseFrames=1}onWaypointUpdate(e,t){this.onNewWaypoint(e,t)}tick(e,t,i){let r=e.moveTrait.baseSpeed;r=Math.floor(r),e.stance===StanceType.Prone&&(r*=e.art.crawls?.5:2),e.isPanicked&&(r*=2);let s=this.game.map.terrain.getPassableSpeed(e.tile,e.rules.speedType,e.isInfantry(),e.onBridge,void 0,!0);s?e.moveTrait.lastTileSpeed=s:s=e.moveTrait.lastTileSpeed||1,r*=s,r=Math.floor(r),this.distanceToWaypoint.copy(t).sub(e.position.getMapPosition());let a=this.distanceToWaypoint.clone().setLength(r);(a.length()||t.equals(i))&&e.moveTrait.velocity.set(a.x,0,a.y);i=Math.min(this.distanceToWaypoint.length(),r),e=!i&&0<this.endPauseFrames--;return this.distanceToWaypoint.setLength(i),{distance:new Vector3_Vector3(this.distanceToWaypoint.x,0,this.distanceToWaypoint.y),done:!this.distanceToWaypoint.length()&&!e}}}!function(e){e[e.None=0]="None",e[e.Start=1]="Start",e[e.Normal=2]="Normal",e[e.End=3]="End",e[e.Single=4]="Single"}(HoverLocomotor_WaypointType=HoverLocomotor_WaypointType||{});class HoverLocomotor{constructor(e){this.hoverRules=e,this.currentSpeed=0,this.distanceTravelled=0,this.carryOverDistance=0,this.currentWaypointType=HoverLocomotor_WaypointType.None,this.nextWaypointDir=new Vector2}selectNextWaypoint(e,t){var i;return this.currentWaypointType=this.currentWaypointType&&this.currentWaypointType!==HoverLocomotor_WaypointType.End?HoverLocomotor_WaypointType.Normal:HoverLocomotor_WaypointType.Start,this.initialPosition=e.position.getMapPosition(),this.currentWaypointType===HoverLocomotor_WaypointType.Start&&(this.currentSpeed=0),t.length<=1?(this.currentWaypointType=this.currentWaypointType===HoverLocomotor_WaypointType.Start?HoverLocomotor_WaypointType.Single:HoverLocomotor_WaypointType.End,(i=t[t.length-1])&&this.nextWaypointDir.set(i.tile.rx-e.tile.rx,i.tile.ry-e.tile.ry)):(i=t[t.length-1],e=t[t.length-2],this.nextWaypointDir.set(e.tile.rx-i.tile.rx,e.tile.ry-i.tile.ry)),t[t.length-1]}onNewWaypoint(e,t,i){let r=(new Vector2).copy(t).sub(this.initialPosition);this.distanceTravelled=0,this.totalDistanceToTravel=r.length();t=this.maxSpeed=e.moveTrait.baseSpeed,e=60*this.hoverRules.acceleration*GameSpeed.BASE_TICKS_PER_SECOND;this.acceleration=t/e;e=60*this.hoverRules.brake*GameSpeed.BASE_TICKS_PER_SECOND;this.deceleration=t/e}tick(e,t){var i=e.position.getMapPosition();let r=t.clone().sub(i);t=r.length(),i=this.maxSpeed;this.currentWaypointType===HoverLocomotor_WaypointType.Single?this.currentSpeed=i/2:this.currentWaypointType===HoverLocomotor_WaypointType.End?(s=this.computeBrakeDistance(this.currentSpeed,this.deceleration),this.totalDistanceToTravel-this.distanceTravelled<=s&&(this.currentSpeed=Math.max(1,this.currentSpeed-this.deceleration))):this.currentSpeed=Math.min(this.currentSpeed+this.acceleration,i);var s=FacingUtil.fromMapCoords(r),i=FacingUtil.fromMapCoords(this.nextWaypointDir);let a=s,n=e.rules.rot;this.currentWaypointType===HoverLocomotor_WaypointType.Normal&&s!==i&&(s=(o=angleDegBetweenVec2(this.nextWaypointDir,FacingUtil.toMapCoords(e.direction)))/n,s=Math.max(this.currentSpeed*s,this.totalDistanceToTravel),this.totalDistanceToTravel-this.distanceTravelled<=s&&(a=i,n=o/((this.totalDistanceToTravel-this.distanceTravelled)/this.currentSpeed)));var o=FacingUtil.tick(e.direction,a,n)["facing"];e.direction=o;let l=this.currentSpeed;this.carryOverDistance&&(l=this.carryOverDistance);o=Math.min(l,t);let h=r.clone().setLength(o),c=h.clone();return this.carryOverDistance&&c.add(Coords.vecWorldToGround(e.moveTrait.velocity)),e.moveTrait.velocity.set(c.x,0,c.y),this.distanceTravelled+=o,this.carryOverDistance=Math.max(0,l-t),{distance:new Vector3_Vector3(h.x,0,h.y),done:!h.length()||!!this.carryOverDistance}}computeBrakeDistance(e,t){var i=e/t;return Math.max(0,e*i-t*i*i/2)}}class TargetUtil{static computeInterceptPoint(e,t,i,r){let s=e.clone().sub(i);var a=r.length(),e=t*t-a*a,t=2*s.dot(r),a=-s.dot(s);if(t*t-4*e*a<0)return new Vector3_Vector3;e=(-t+GameMath.sqrt(t*t-4*e*a))/(2*e);return r.clone().multiplyScalar(e).add(i)}static computeTurnCircle(e,t,i,r){r/=degToRad(Math.abs(i));let s=rotateVec2(t.clone(),90*-Math.sign(i));return{center:isFinite(r)?s.setLength(r).add(e):e.clone(),radius:r}}}var util_geometry_THREE=__webpack_require__(70);function pointEquals(e,t){return e&&t&&e.x===t.x&&e.y===t.y||!e&&!t}function rectIntersect(e,t){return e.x<=t.x+t.width&&t.x<=e.x+e.width&&e.y<=t.y+t.height&&t.y<=e.y+e.height}function rectEquals(e,t){return e.x===t.x&&e.y===t.y&&e.width===t.width&&e.height===t.height}function circleIntersect(e,t){var i=e.center,r=t.center;return isBetween((i.x-r.x)*(i.x-r.x)+(i.y-r.y)*(i.y-r.y),(e.radius-t.radius)*(e.radius-t.radius),(e.radius+t.radius)*(e.radius+t.radius))}function circleContainsPoint(e,t){var i=e.center;return(i.x-t.x)*(i.x-t.x)+(i.y-t.y)*(i.y-t.y)<=e.radius*e.radius}function rectContainsPoint(e,t){let i=new util_geometry_THREE.Box2(new util_geometry_THREE.Vector2(e.x,e.y),new util_geometry_THREE.Vector2(e.x+e.width,e.y+e.height));return i.containsPoint(new util_geometry_THREE.Vector2(t.x,t.y))}function rectContainsRect(e,t){let i=new util_geometry_THREE.Box2(new util_geometry_THREE.Vector2(e.x,e.y),new util_geometry_THREE.Vector2(e.x+e.width,e.y+e.height));t=new util_geometry_THREE.Box2(new util_geometry_THREE.Vector2(t.x,t.y),new util_geometry_THREE.Vector2(t.x+t.width,t.y+t.height));return i.containsBox(t)}function rectClampPoint(e,t){let i=new util_geometry_THREE.Box2(new util_geometry_THREE.Vector2(e.x,e.y),new util_geometry_THREE.Vector2(e.x+e.width,e.y+e.height));return i.clampPoint(new util_geometry_THREE.Vector2(t.x,t.y),new util_geometry_THREE.Vector2)}function octileDistance(e,t){var i=Math.abs(e.x-t.x),t=Math.abs(e.y-t.y);return i+t+(Math.SQRT2-2)*Math.min(i,t)}class ObjectLiftOffEvent{constructor(e){this.gameObject=e,this.type=EventType.ObjectLiftOff}}class ObjectLandEvent{constructor(e){this.gameObject=e,this.type=EventType.ObjectLand}}const JUMPJET_ACCEL=2;class JumpjetLocomotor{static tickStationary(t,i){if(t.zone===ZoneType.Air){var r=t.tile.onBridgeLandType?i.map.tileOccupation.getBridgeOnTile(t.tile):void 0,s=!t.rules.balloonHover&&(!t.unitOrderTrait.getCurrentTask()?.preventLanding||!t.rules.hoverAttack)&&(i.map.getGroundObjectsOnTile(t.tile).find(e=>e.isBuilding()&&e.dockTrait?.isDocked(t))||i.map.getTileZone(t.tile)!==ZoneType.Water&&0<i.map.terrain.getPassableSpeed(t.tile,SpeedType.Foot,!0,!!t.tile.onBridgeLandType)&&0===i.map.terrain.findObstacles({tile:t.tile,onBridge:r},t).length);let e;e=s?(a=t.tile.z+(r?.tileElevation??0),Coords.tileHeightToWorld(a)):(n=t.tile.z+i.map.getGroundObjectsOnTile(t.tile).filter(e=>!(e.isInfantry()&&e.stance===StanceType.Paradrop)).reduce((e,t)=>Math.max(e,t.tileElevation+t.art.height),0),Coords.tileHeightToWorld(n)+t.rules.jumpjetHeight);var a,n,o=t.position.worldPosition.y;e!==o?(a=t.rules.jumpjetClimb,n=Math.abs(e-o),a=Math.sign(e-o)*Math.min(a,n),n=t.tileElevation,t.position.moveByLeptons3(new Vector3_Vector3(0,a,0)),t.moveTrait.handleElevationChange(n,i)):s&&(t.zone=ZoneType.Ground,t.onBridge=!!r,i.events.dispatch(new ObjectLandEvent(t)),(r=i.map.tileOccupation.getGroundObjectsOnTile(t.tile).find(e=>e.isOverlay()&&e.rules.crate))&&i.crateGeneratorTrait.pickupCrate(t,r,i))}}static tickCrash(e,t,i){var r=2*e.rules.jumpjetCrash;return e.direction=(e.direction-6+360)%360,new Vector3_Vector3(0,-r,0)}constructor(e){this.game=e,this.allowOutOfBounds=!0,this.currentMoveDir=new Vector2,this.currentHorizSpeed=0}onNewWaypoint(e,t,i){this.currentMoveDir=FacingUtil.toMapCoords(e.direction),this.cancelDestLeptons=void 0}tick(t,e,i,r){if(t.zone!==ZoneType.Air&&(t.onBridge=!1,t.zone=ZoneType.Air,this.game.events.dispatch(new ObjectLiftOffEvent(t))),r){if(!this.cancelDestLeptons){let e=t.tile;this.game.map.isWithinBounds(e)||(e=this.game.map.clampWithinBounds(e)),this.cancelDestLeptons=this.computeCancelDest(e,i)}i=this.cancelDestLeptons}var s=t.position.getMapPosition();let a=i.clone().sub(s),n=this.findTilesToCheckForBlockers(t.tile,s,this.currentMoveDir,a.length());var o=n.map(e=>e.z+this.game.map.getGroundObjectsOnTile(e).filter(e=>!(e.isDestroyed||e.isInfantry()&&e.stance===StanceType.Paradrop)).reduce((e,t)=>Math.max(e,t.tileElevation+t.art.height),0)).reduce((e,t)=>Math.max(e,t),0);let l=0;(void 0===this.lastClearZ||2<o-this.lastClearZ)&&(l=4);var h=Coords.tileHeightToWorld(o),c=Coords.tileHeightToWorld(o+l),u=t.position.worldPosition.y,d=FacingUtil.fromMapCoords(a),p=a.length()<t.rules.jumpjetSpeed;let g=0;h<=u&&!p&&({facing:v,delta:r}=FacingUtil.tick(t.direction,d,t.rules.jumpjetTurnRate),g=r,t.direction=v,this.currentMoveDir.copy(FacingUtil.toMapCoords(t.direction))),t.isVehicle()&&(t.spinVelocity=g);let m,y=!1,T=0,f=0;var v=t.rules.jumpjetClimb;u<c?(T=Math.min(v,c-u),m=!1,this.currentHorizSpeed=0):(this.lastClearZ=o,o=h+t.rules.jumpjetHeight,m=!0,o!==u&&(h=Math.abs(o-u),T=Math.sign(o-u)*Math.min(v,h),m=h<=v),v=this.currentHorizSpeed,this.currentHorizSpeed=Math.min(this.currentHorizSpeed+JUMPJET_ACCEL,t.rules.jumpjetSpeed),y=d===t.direction?(f=Math.min(v,a.length()),v>=a.length()):((s=v||g?TargetUtil.computeTurnCircle(s,this.currentMoveDir,Math.sign(g)*t.rules.jumpjetTurnRate,v):void 0)&&circleContainsPoint(s,i)?(f=0,this.currentHorizSpeed=0):f=v,!1));let b;b=p?(y=!0,a):this.currentMoveDir.clone().setLength(f);let w=new Vector3_Vector3(b.x,T,b.y);p=w.clone();return t.moveTrait.velocity.copy(p),{distance:w,done:y&&m}}findTilesToCheckForBlockers(e,t,i,r){r=i.clone().setLength(Math.min(r,Coords.LEPTONS_PER_TILE)).add(t).multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor(),t=this.game.map.tiles.getByMapCoords(r.x,r.y);if(!t||t===e)return[e];r=Math.sign(t.rx-e.rx),t=Math.sign(t.ry-e.ry);let s=[e],a;return r&&(a=this.game.map.tiles.getByMapCoords(e.rx+r,e.ry),a&&s.push(a)),t&&(a=this.game.map.tiles.getByMapCoords(e.rx,e.ry+t),a&&s.push(a)),r&&t&&(a=this.game.map.tiles.getByMapCoords(e.rx+r,e.ry+t),a&&s.push(a)),s}computeCancelDest(e,t){var i=t.clone().multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor().multiplyScalar(Coords.LEPTONS_PER_TILE),i=t.clone().sub(i);return new Vector2(e.rx,e.ry).multiplyScalar(Coords.LEPTONS_PER_TILE).add(i)}}var FlightPhase,NotifyTick_NotifyTick,DockingStatus,ManeuverType,NotifyTeleport,NotifyDestroy,DeathType,NotifyTileChange,NotifyTileChange_NotifyTileChange,NotifyElevationChange,MoveState,MoveResult,CollisionState,NotifyOwnerChange,NotifySpawn,NotifyUnspawn,NotifyAttack,VeteranLevel,NotifyCrash,ParadropState,OverlayBridgeType,NotifyAttack_NotifyAttack,CollisionType,TileDirection,OverlayTibType,TiberiumType,SpecialWarheadType,State,NotifySuperWeaponDeactivate,NotifyDamage,CubicBezierCurve3_THREE=__webpack_require__(70);class CubicBezierCurve3 extends CubicBezierCurve3_THREE.CubicBezierCurve3{constructor(e,t,i,r){super(e||new Vector3_Vector3,t||new Vector3_Vector3,i||new Vector3_Vector3,r||new Vector3_Vector3)}getPoint(e,t){return super.getPoint(e,t||new Vector3_Vector3)}}!function(e){e[e.Boost=0]="Boost",e[e.Midcourse=1]="Midcourse",e[e.Terminal=2]="Terminal"}(FlightPhase=FlightPhase||{});class MissileLocomotor{constructor(e,t){this.game=e,this.missileRules=t,this.flightPhase=FlightPhase.Boost}selectNextWaypoint(e,t){var i=t[t.length-1],t=this.game.map.tileOccupation.getBridgeOnTile(i.tile),t=i.tile.z+(t?.tileElevation??0);return this.targetPosition=Coords.tile3dToWorld(i.tile.rx+.5,i.tile.ry+.5,t),this.cruiseAltitude=Coords.tileHeightToWorld(t)+this.missileRules.altitude,i}onNewWaypoint(e,t,i){}tick(i,e,t){let r=i.position.worldPosition.clone(),s=this.targetPosition.clone().sub(r);i.zone!==ZoneType.Air&&(i.onBridge=!1,i.zone=ZoneType.Air,this.game.events.dispatch(new ObjectLiftOffEvent(i)));let a;var n;a=this.currentVelocity?(n=i.rules.speed,Math.min(this.currentVelocity.length()+this.missileRules.acceleration,n)):(p=this.missileRules.acceleration,this.missileRules.lazyCurve?this.currentVelocity=new Vector3_Vector3(s.x,0,s.z):this.currentVelocity=Coords.vecGroundToWorld(FacingUtil.toMapCoords(i.direction)),rotateVec3Towards(this.currentVelocity,new Vector3_Vector3(this.currentVelocity.x,1e8,this.currentVelocity.z),i.pitch),p),this.currentVelocity.setLength(a);let o=!1;switch(this.flightPhase){case FlightPhase.Boost:if(!(i.position.worldPosition.y>=this.cruiseAltitude)){o=!1;break}this.flightPhase=FlightPhase.Midcourse;case FlightPhase.Midcourse:var l,h=new Vector2(s.x,s.z).length();if(!this.missileRules.lazyCurve){rotateVec3Towards(this.currentVelocity,new Vector3_Vector3(this.currentVelocity.x,0,this.currentVelocity.z),i.rules.rot),this.currentVelocity.y<1&&(l=this.currentVelocity.length(),this.currentVelocity.y=0,this.currentVelocity.setLength(l)),rotateVec3Towards(this.currentVelocity,new Vector3_Vector3(s.x,this.currentVelocity.y,s.z),i.rules.rot),i.direction=FacingUtil.fromMapCoords(Coords.vecWorldToGround(this.currentVelocity)),i.pitch=Math.sign(this.currentVelocity.y)*angleDegBetweenVec3(this.currentVelocity,new Vector3_Vector3(this.currentVelocity.x,0,this.currentVelocity.z)),h/(r.y-this.targetPosition.y)<1&&(this.flightPhase=FlightPhase.Terminal);break}this.flightPhase=FlightPhase.Terminal;var c=r.clone().add(this.currentVelocity.clone().setLength(h/3/GameMath.cos(degToRad(i.pitch)))),u=this.targetPosition.clone().lerp(r,.15).setY(c.y);this.descentCurve=new CubicBezierCurve3(r,c,u,this.targetPosition);case FlightPhase.Terminal:c=this.missileRules.bodyLength;if(this.missileRules.lazyCurve){var d=this.descentCurve.getLength();this.descentTravelled??(this.descentTravelled=0),this.descentTravelled+=Math.min(a,d-c-this.descentTravelled);u=this.descentTravelled/d;let e=this.descentCurve.getPointAt(u),t=this.descentCurve.getTangentAt(u);this.currentVelocity.copy(e.sub(r));u=t.clone().setY(0);i.pitch=Math.sign(t.y-u.y)*angleDegBetweenVec3(u,t),o=1<=(this.descentTravelled+c)/d}else{rotateVec3Towards(this.currentVelocity,s,i.rules.rot),i.direction=FacingUtil.fromMapCoords(Coords.vecWorldToGround(this.currentVelocity)),i.pitch=Math.sign(this.currentVelocity.y)*angleDegBetweenVec3(this.currentVelocity,new Vector3_Vector3(this.currentVelocity.x,0,this.currentVelocity.z));d=s.length()-c;(d<a||d<1)&&(this.currentVelocity.copy(s.clone().addScalar(-c)),o=!0)}break;default:throw new Error(`Unhandled flight phase "${this.flightPhase}"`)}var p=r.clone().add(this.currentVelocity);return this.game.map.isWithinHardBounds(p)?(i.moveTrait.velocity.copy(this.currentVelocity),{distance:this.currentVelocity,done:o}):(this.game.destroyObject(i),{done:!0,distance:new Vector3_Vector3})}}class WaitMinutesTask extends WaitTicksTask{constructor(e){super(Math.floor(GameSpeed.BASE_TICKS_PER_SECOND*e*60))}}class CallbackTask extends Task{constructor(e){super(),this.cb=e}onTick(e){return this.cb(e),!0}}(NotifyTick_NotifyTick=NotifyTick_NotifyTick||{}).onTick=Symbol(),function(e){e[e.Idle=0]="Idle",e[e.MoveToQueueingTile=1]="MoveToQueueingTile",e[e.WaitForTurn=2]="WaitForTurn",e[e.MoveToDock=3]="MoveToDock",e[e.Docking=4]="Docking",e[e.Docked=5]="Docked"}(DockingStatus=DockingStatus||{});class MoveToDockTask extends Task{constructor(e,t){super(),this.game=e,this.target=t,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.dockingStatus=DockingStatus.Idle}onStart(e){if(!this.target.dockTrait)throw new Error(`Target object "${this.target.name}" is not a valid dock`);var t;this.target.dockTrait.hasReservedDockForUnit(e)?this.dockingStatus=DockingStatus.MoveToDock:void 0!==(t=this.target.dockTrait.getFirstAvailableDockNumber())?(this.target.dockTrait.reserveDockAt(e,t),this.dockingStatus=DockingStatus.MoveToDock):this.target.helipadTrait?this.cancel():this.dockingStatus=DockingStatus.MoveToQueueingTile}onEnd(e){this.dockingStatus!==DockingStatus.Docked&&this.target.isSpawned&&(this.target.dockTrait.undockUnit(e),this.target.dockTrait.unreserveDockForUnit(e)),this.dockingStatus=DockingStatus.Idle}onTick(e){if(this.isCancelling())return!0;if(!this.isValidTarget(this.target,e))return!0;if(this.dockingStatus===DockingStatus.MoveToQueueingTile){var t=this.findReachableQueueingTile(e);if(!t)return!0;if(e.tile!==t)return this.children.push(new MoveTask(this.game,t,!1,{closeEnoughTiles:5}),new CallbackTask(()=>{e.moveTrait.lastMoveResult===MoveResult.Fail?this.cancel():e.moveTrait.lastMoveResult===MoveResult.CloseEnough&&(this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)||(this.dockingStatus=DockingStatus.WaitForTurn))})),!1;this.dockingStatus=DockingStatus.WaitForTurn}if(this.dockingStatus===DockingStatus.WaitForTurn){var i=this.target.dockTrait.getFirstAvailableDockNumber();if(void 0===i)return this.children.push(new WaitMinutesTask(1/60)),!1;this.target.dockTrait.reserveDockAt(e,i),this.dockingStatus=DockingStatus.MoveToDock}if(this.dockingStatus===DockingStatus.MoveToDock){var r=this.target.dockTrait.getReservedDockForUnit(e),i=this.target.dockTrait.getDockTile(r),r=Coords.vecWorldToGround(this.target.dockTrait.getDockOffset(r)).add(this.target.position.getMapPosition()).sub(new Vector2(i.rx,i.ry).multiplyScalar(Coords.LEPTONS_PER_TILE));if(e.tile!==i)return this.children.push(new MoveTask(this.game,i,!1,{targetOffset:e.isAircraft()?r:void 0,closeEnoughTiles:0,strictCloseEnough:!0}),new CallbackTask(()=>{e.moveTrait.lastMoveResult===MoveResult.Fail&&this.cancel()})),this.game.afterTick(()=>e.unitOrderTrait[NotifyTick_NotifyTick.onTick](e,this.game)),!1;this.dockingStatus=DockingStatus.Docking}if(this.dockingStatus!==DockingStatus.Docking)return!1;r=this.target.dockTrait.getReservedDockForUnit(e);return this.target.dockTrait.unreserveDockForUnit(e),this.target.dockTrait.dockUnitAt(e,r),e.isAircraft()&&e.airportBoundTrait&&this.target.helipadTrait&&(e.airportBoundTrait.preferredAirport=this.target),this.dockingStatus=DockingStatus.Docked,!0}isValidTarget(e,t){return e.isSpawned&&this.game.areFriendly(e,t)}findReachableQueueingTile(t){var e=this.target.getFoundation(),e=new Vector2(this.target.tile.rx+e.width,this.target.tile.ry+e.height),e=this.game.map.tiles.getByMapCoords(e.x,e.y);return e&&this.isValidQueueingTile(e,t)?e:new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>this.isValidQueueingTile(e,t)).getNextTile()}isValidQueueingTile(e,t){var i=t.rules.movementZone===MovementZone.Fly,r=t.rules.speedType,s=t.isInfantry();let a=!i&&this.game.map.terrain.getPassableSpeed(t.tile,r,s,t.onBridge)?this.game.map.terrain.getIslandIdMap(r,s):void 0;return(i||a?.get(e,!1)===a?.get(t.tile,t.onBridge)&&Math.abs(e.z-this.target.tile.z)<2&&!e.onBridgeLandType&&!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length)&&!this.game.map.tileOccupation.isTileOccupiedBy(e,this.target)}}const WINGED_ACCEL=2,WINGED_DECEL=2,WINGED_CLIMB=30,STATIONARY_FACING=270,STATIONARY_THRESH=5;!function(e){e[e.None=0]="None",e[e.CircleStrafe=1]="CircleStrafe",e[e.HoverStrafe=2]="HoverStrafe"}(ManeuverType=ManeuverType||{});class WingedLocomotor{static tickStationary(s,a){if(s.zone===ZoneType.Air){var n=s.tile.onBridgeLandType?a.map.tileOccupation.getBridgeOnTile(s.tile):void 0;let e=s.rules.landable&&!s.unitOrderTrait.getCurrentTask()?.preventLanding,i=s.spawnLinkTrait?.getParent();e&&i?e=!((!i.isUnit()||!i.onBridge)&&n||i.tile!==s.tile):e&&!s.airportBoundTrait&&(e=a.map.getTileZone(s.tile)!==ZoneType.Water&&0<a.map.terrain.getPassableSpeed(s.tile,SpeedType.Foot,!0,!!s.tile.onBridgeLandType)&&0===a.map.terrain.findObstacles({tile:s.tile,onBridge:n},s).length);let r;if(e){let e=s.airportBoundTrait?.preferredAirport?.dockTrait;var o=e?.isDocked(s)||e?.hasReservedDockForUnit(s);if(!s.airportBoundTrait||o){o=o?0:STATIONARY_FACING;if(s.direction!==o)return void(s.direction=FacingUtil.tick(s.direction,o,s.rules.rot).facing)}if(s.airportBoundTrait){let e=s.airportBoundTrait.preferredAirport;if(!e?.dockTrait?.isDocked(s))return e?.dockTrait?.getAvailableDockCount()||(e=s.airportBoundTrait.findAvailableAirport(s),s.airportBoundTrait.preferredAirport=e,e&&(h=e.dockTrait.getFirstAvailableDockNumber(),e.dockTrait.reserveDockAt(s,h))),void(e?(s.unitOrderTrait.addTask(new MoveToDockTask(a,e)),s.unitOrderTrait[NotifyTick_NotifyTick.onTick](s,a)):s.crashableTrait.crash(void 0))}let t;t=i?i.tile.z+i.tileElevation:s.tile.z+(n?.tileElevation??0),r=Coords.tileHeightToWorld(t)}else{var t=s.tile.z+(n?.tileElevation??0),l=s.rules.flightLevel??a.rules.general.flightLevel;r=Coords.tileHeightToWorld(t)+l}var h=s.position.worldPosition.y;r!==h?(t=WINGED_CLIMB,l=Math.abs(r-h),t=Math.sign(r-h)*Math.min(t,l),l=s.tileElevation,s.position.moveByLeptons3(new Vector3_Vector3(0,t,0)),s.moveTrait.handleElevationChange(l,a)):e&&(s.zone=ZoneType.Ground,i?i.airSpawnTrait.storeAircraft(s,a):s.onBridge=!!n,a.events.dispatch(new ObjectLandEvent(s)),(n=a.map.tileOccupation.getGroundObjectsOnTile(s.tile).find(e=>e.isOverlay()&&e.rules.crate))&&a.crateGeneratorTrait.pickupCrate(s,n,a))}}static tickCrash(e,t,i){var r=WINGED_CLIMB;i.rollDelta??(i.rollDelta=t.generateRandomInt(-15,15)),i.pitchDelta??(i.pitchDelta=t.generateRandomInt(0,15)),e.roll+=i.rollDelta,e.pitch+=i.pitchDelta;e=Coords.vecWorldToGround(e.moveTrait.velocity);return new Vector3_Vector3(e.x,-r,e.y)}constructor(e){this.game=e,this.allowOutOfBounds=!0,this.lastDestLeptons=new Vector2,this.currentMoveDir=new Vector2,this.currentHorizSpeed=0,this.maneuverType=ManeuverType.None,this.deceleratingToTurn=!1}onNewWaypoint(e,t,i){this.currentHorizSpeed=Coords.vecWorldToGround(e.moveTrait.velocity).length(),this.cancelDestLeptons=void 0}tick(t,e,i,r){if(r){if(!this.cancelDestLeptons){let e=t.tile;this.game.map.isWithinBounds(e)||(e=this.game.map.clampWithinBounds(e)),this.cancelDestLeptons=this.computeCancelDest(e,i)}i=this.cancelDestLeptons}var s=t.position.getMapPosition();let a=i.clone().sub(s);var n=a.length();this.lastDestLeptons.equals(i)||(this.lastDestLeptons.copy(i),r?this.maneuverType=ManeuverType.HoverStrafe:t.zone===ZoneType.Air&&this.currentHorizSpeed<STATIONARY_THRESH?this.maneuverType=n>Coords.LEPTONS_PER_TILE?ManeuverType.CircleStrafe:ManeuverType.HoverStrafe:this.maneuverType=ManeuverType.None,this.deceleratingToTurn=!1),t.zone!==ZoneType.Air&&(t.onBridge=!1,t.zone=ZoneType.Air,this.game.events.dispatch(new ObjectLiftOffEvent(t)));var o=t.tile.onBridgeLandType?this.game.map.tileOccupation.getBridgeOnTile(t.tile):void 0,l=t.tile.z+(o?.tileElevation??0),h=t.rules.flightLevel??this.game.rules.general.flightLevel,c=Coords.tileHeightToWorld(l)+h,r=t.position.worldPosition.y,u=FacingUtil.fromMapCoords(a);t.direction===u&&this.maneuverType===ManeuverType.None&&n<=Coords.LEPTONS_PER_TILE?this.maneuverType=ManeuverType.HoverStrafe:t.direction===u&&this.maneuverType===ManeuverType.CircleStrafe&&(this.maneuverType=ManeuverType.None);let d;switch(this.maneuverType){case ManeuverType.HoverStrafe:if(t.attackTrait?.currentTarget){let e=Coords.vecWorldToGround(t.attackTrait.currentTarget.getWorldCoords());d=FacingUtil.fromMapCoords(e.sub(s))}else d=t.airportBoundTrait?.preferredAirport?.dockTrait?.hasReservedDockForUnit(t)?0:STATIONARY_FACING;break;case ManeuverType.CircleStrafe:case ManeuverType.None:d=u;break;default:throw new Error('Unknown maneuver type "'+this.maneuverType)}var{facing:p,delta:g}=FacingUtil.tick(t.direction,d,t.rules.rot);t.direction=p,t.roll=Math.sign(g)*t.rules.pitchAngle;let m;switch(this.maneuverType){case ManeuverType.HoverStrafe:m=u;break;case ManeuverType.CircleStrafe:m=(p-90*Math.sign(g)+360)%360;break;case ManeuverType.None:m=p;break;default:throw new Error('Unknown maneuver type "'+this.maneuverType)}void 0===this.thrustFacing&&(this.thrustFacing=m);var o=this.currentHorizSpeed>STATIONARY_THRESH?t.rules.rot:Number.POSITIVE_INFINITY,{facing:l,delta:h}=FacingUtil.tick(this.thrustFacing,m,o);this.thrustFacing=l,this.currentMoveDir.copy(FacingUtil.toMapCoords(this.thrustFacing));let y=!1,T=0,f=0;o=WINGED_CLIMB;let v=!0;c!==r&&(l=Math.abs(c-r),T=Math.sign(c-r)*Math.min(o,l),v=l<=o);let b=t.rules.speed;n<=Coords.LEPTONS_PER_TILE&&this.maneuverType!==ManeuverType.CircleStrafe&&(b=lerp(1,b/2,GameMath.sqrt(n/Coords.LEPTONS_PER_TILE))),this.deceleratingToTurn?this.currentHorizSpeed=Math.max(0,this.currentHorizSpeed-WINGED_DECEL):this.currentHorizSpeed=Math.min(this.currentHorizSpeed+WINGED_ACCEL,b);o=this.currentHorizSpeed;this.deceleratingToTurn=!1,y=h?(h=o||h?TargetUtil.computeTurnCircle(s,this.currentMoveDir,Math.sign(h)*t.rules.rot,o):void 0,0!==o&&!circleContainsPoint(h,i)||(this.maneuverType===ManeuverType.HoverStrafe||n>Coords.LEPTONS_PER_TILE?this.deceleratingToTurn=!0:this.maneuverType===ManeuverType.None&&(this.maneuverType=ManeuverType.HoverStrafe)),f=o,!1):(f=Math.min(o,n),n<=o);let w;w=n<1?(y=!0,a):y?a:this.currentMoveDir.clone().setLength(f);let S=new Vector3_Vector3(w.x,T,w.y);n=S.clone();return t.moveTrait.velocity.copy(n),{distance:S,done:y&&v}}computeCancelDest(e,t){var i=t.clone().multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor().multiplyScalar(Coords.LEPTONS_PER_TILE),i=t.clone().sub(i);return new Vector2(e.rx,e.ry).multiplyScalar(Coords.LEPTONS_PER_TILE).add(i)}}class LocomotorFactory{constructor(e){this.game=e}create(e){var t=e.rules.locomotor;switch(t){case LocomotorType.Infantry:return new FootLocomotor(this.game);case LocomotorType.Jumpjet:return new JumpjetLocomotor(this.game);case LocomotorType.Vehicle:case LocomotorType.Ship:return new DriveLocomotor(this.game);case LocomotorType.Chrono:return e.isVehicle()&&e.harvesterTrait&&e.rules.teleporter?new DriveLocomotor(this.game):new ChronoLocomotor(this.game);case LocomotorType.Aircraft:return new WingedLocomotor(this.game);case LocomotorType.Missile:return new MissileLocomotor(this.game,this.game.rules.general.getMissileRules(e.name));case LocomotorType.Hover:return new HoverLocomotor(this.game.rules.general.hover);default:throw new Error("Unhandled locomotor type "+t)}}}class RandomTileFinder{constructor(e,t,i,r,s,a,n=!1,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=r,this.rng=s,this.predicate=a,this.includeStartTile=n,this.checkBounds=o,this.pool=[],this.pool=new Array(GameMath.pow(2*this.maxDistance+1,2)).fill(0).map((e,t)=>t),this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){for(var e=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(this.includeStartTile||t!==this.startTile)return t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t)?t:void 0},t=2*this.maxDistance+1;this.pool.length;){var i=1<this.pool.length?this.rng.generateRandomInt(0,this.pool.length):0,r=this.pool.splice(i,1)[0],i=r%t,r=Math.floor(r/t),r=e(this.startTile.rx-this.maxDistance+i,this.startTile.ry-this.maxDistance+r);r&&(yield r)}}}class ObjectTeleportEvent{constructor(e,t,i){this.target=e,this.isChronoshift=t,this.prevTile=i,this.type=EventType.ObjectTeleport}}(NotifyTeleport=NotifyTeleport||{}).onBeforeTeleport=Symbol();class ScatterPositionHelper{constructor(e){this.game=e,this.movePositionHelper=new MovePositionHelper(e.map)}findPositions(e,t){let i=new Set,r=new Map;for(var s of e){var a=this.findFreeMovePosition(s,i,t);a&&(r.set(s,a),i.add(a.tile))}return r}findFreeMovePosition(i,e,{ignoredBlockers:t,excludedTiles:r,noSlopes:s}={}){let a=this.game.map,n=i.onBridge?a.tileOccupation.getBridgeOnTile(i.tile):void 0,o=new RandomTileFinder(a.tiles,a.mapBounds,i.tile,1,this.game,e=>{if(r?.includes(e))return!1;var t=a.tileOccupation.getBridgeOnTile(e);return(t&&this.movePositionHelper.isEligibleTile(e,t,n,i.tile)||this.movePositionHelper.isEligibleTile(e,void 0,n,i.tile))&&(!s||0===e.rampType)}),l,h;for(;;){var c=o.getNextTile();if(!c)break;if(l=c,h=a.tileOccupation.getBridgeOnTile(c),h&&!this.movePositionHelper.isEligibleTile(c,h,n,i.tile)&&(h=void 0),!e.has(c)){let e=a.terrain.findObstacles({tile:c,onBridge:h},i);if(t&&t.length&&(e=e.filter(e=>!t.includes(e.obj))),!e.length)break}}if(l)return{tile:l,onBridge:h}}}class ScatterTask extends Task{constructor(e,t,i){super(),this.game=e,this.target=t,this.options=i}onStart(i){if(!i.moveTrait.isDisabled()&&i.rules.movementZone!==MovementZone.Fly){let e,t;if(this.target)({tile:e,toBridge:t}=this.target);else{i=new ScatterPositionHelper(this.game).findPositions([i],this.options).get(i);if(!i)return;e=i.tile,t=!!i.onBridge}this.children.push(new MoveTask(this.game,e,t,{closeEnoughTiles:0,ignoredBlockers:this.options?.ignoredBlockers}))}}onTick(e){return!0}}const SPEED_MULT=1.5,PLANNING_BAILOUT_TICKS=200,MoveTask_RETRY_TICKS=40,MAX_UNREACH_TILES_BAIL=5;class MoveTask extends Task{constructor(e,t,i,r){super(),this.game=e,this.targetTile=t,this.toBridge=i,this.options=r,this.preventOpportunityFire=!1,this.logger=AppLogger.get("move"),this.destinationLeptons=new Vector2,this.currentWaypointLeptons=new Vector2,this.needsPathUpdate=!1,this.allObstaclesAreBlockers=!1,this.blockedPathNodes=[],this.unreachableTargets=[],this.pushTried=!1,this.cancelProcessed=!1,this.cancelRepositionPending=!1,this.targetLinesConfig={pathNodes:[]}}duplicate(){return new MoveTask(this.game,this.targetTile,this.toBridge,this.options)}setForceMove(e){e?(this.options??(this.options={}),this.options.forceMove=!0):this.options?.forceMove&&(this.options.forceMove=void 0)}onStart(e){if(e.moveTrait.currentWaypoint)throw new Error("Nested move tasks are not supported");void 0===e.moveTrait.locomotor&&(e.moveTrait.locomotor=new LocomotorFactory(this.game).create(e)),e.moveTrait.lastTargetOffset?this.targetOffset=e.moveTrait.lastTargetOffset:this.targetOffset=this.computeTargetOffset(e),e.moveTrait.lastVelocity&&(e.moveTrait.velocity=e.moveTrait.lastVelocity),this.path||(this.groundPathPlan?(this.groundPathPlan.path[this.groundPathPlan.path.length-1].tile===e.tile?this.path=this.applyGroundPathPlan(this.groundPathPlan):this.computePath(e,e.moveTrait.locomotor),this.groundPathPlan=void 0):this.computePath(e,e.moveTrait.locomotor),this.targetLinesConfig.isRecalc=!1),this.updateDestination(this.path,this.targetOffset),e.moveTrait.moveState=MoveState.ReachedNextWaypoint,e.moveTrait.lastMoveResult=void 0,e.moveTrait.lastTargetOffset=void 0,e.moveTrait.lastVelocity=void 0}computeTargetOffset(e){return this.options?.targetOffset??(e.isInfantry()?e.position.getTileOffset():e.position.computeSubCellOffset(0))}computePath(e,t,i=!1){let r;if(this.options?.allowOutOfBoundsTarget||this.game.map.mapBounds.isWithinBounds(this.targetTile))if(e.rules.movementZone===MovementZone.Fly)r=this.computeAirPath(e);else if(t.ignoresTerrain)r=this.computeDirectJumpPath(e);else{t=this.computeGroundPath(e);if(i&&!t.path.length)return!1;r=this.applyGroundPathPlan(t)}else r=[];return e.rules.movementZone===MovementZone.Fly?(this.targetLinesConfig.pathNodes=r.map(({tile:e,onBridge:t})=>({tile:e,onBridge:t})),r.length&&(this.targetLinesConfig.pathNodes[0].onBridge=this.toBridge?this.game.map.tileOccupation.getBridgeOnTile(this.targetTile):void 0)):this.targetLinesConfig.pathNodes=r,this.path=r,!0}computeAirPath(e){return[{tile:this.targetTile,onBridge:void 0},{tile:e.tile,onBridge:void 0}]}computeDirectJumpPath(t){let i=this.game.map;var e=t.onBridge?i.tileOccupation.getBridgeOnTile(t.tile):void 0;let r=this.targetTile,s=this.toBridge?i.tileOccupation.getBridgeOnTile(this.targetTile):void 0,a=this.options?.ignoredBlockers;var n=new RadialTileFinder(i.tiles,i.mapBounds,r,{width:1,height:1},0,5,e=>0<i.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!!e.onBridgeLandType,a)&&!i.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},t).find(e=>!a?.includes(e.obj))).getNextTile();return n?(n!==r&&(r=n,s=i.tileOccupation.getBridgeOnTile(r)),[{tile:r,onBridge:s},{tile:t.tile,onBridge:e}]):[]}computeGroundPath(t){let e=t.tile,i=t.onBridge?this.game.map.tileOccupation.getBridgeOnTile(e):void 0;t.moveTrait.moveState===MoveState.Moving&&t.moveTrait.currentWaypoint&&(e=t.moveTrait.currentWaypoint.tile,i=t.moveTrait.currentWaypoint.onBridge);let r={path:[],ignoredBlockers:[],blockedPathNodes:[]};const s=this.game.map.getObjectsOnTile(e).find(e=>e.isBuilding());if(s&&!this.game.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)){var a=this.options?.ignoredBlockers?.includes(s);if(a||r.ignoredBlockers.push(s),!a&&s.dockTrait){let t=new Set(s.dockTrait?.getAllDockTiles()),e=this.game.map.tileOccupation.calculateTilesForGameObject(s.tile,s);e.filter(e=>!t.has(e)).forEach(e=>r.blockedPathNodes.push({node:{tile:e,onBridge:void 0},obj:s}))}}var n=this.game.map.getGroundObjectsOnTile(this.targetTile).find(e=>(e.isInfantry()||e.isVehicle())&&e.disguiseTrait?.hasTerrainDisguise()&&!(this.game.alliances.haveSharedIntel(t.owner,e.owner)||e.owner.sharedDetectDisguiseTrait?.has(t)));n&&(a=this.toBridge?this.game.map.tileOccupation.getBridgeOnTile(this.targetTile):void 0,r.blockedPathNodes.push({node:{tile:this.targetTile,onBridge:a},obj:n}));let o=[...new Set([...this.options?.ignoredBlockers??[],...r.ignoredBlockers])],l=[...this.blockedPathNodes,...r.blockedPathNodes];n=this.game.map.terrain.computePath(t.rules.speedType,t.isInfantry(),e,!!i,this.targetTile,this.toBridge,{maxExpandedNodes:this.allObstaclesAreBlockers?Math.min(300,this.options?.maxExpandedPathNodes??Number.POSITIVE_INFINITY):this.options?.maxExpandedPathNodes,bestEffort:!this.options?.strictCloseEnough,ignoredBlockers:[...new Set([...o,...this.options?.pathFinderIgnoredBlockers??[]])],excludeTiles:this.allObstaclesAreBlockers||l.length?e=>this.nodeIsBlockedForPathfinding(e,t,o,l):void 0});return r.path=n,r}nodeIsBlockedForPathfinding(t,e,i,r){return this.allObstaclesAreBlockers?!!this.game.map.terrain.findObstacles(t,e).find(e=>!i?.includes(e.obj)):!!r.find(({node:e})=>e.tile===t.tile&&e.onBridge===t.onBridge)}applyGroundPathPlan(e){var t;return this.blockedPathNodes=this.blockedPathNodes.filter(e=>e.obj.isSpawned&&e.node.tile===e.obj.tile),e.ignoredBlockers.length&&(this.options??(this.options={}),(t=this.options).ignoredBlockers??(t.ignoredBlockers=[]),this.options.ignoredBlockers.push(...e.ignoredBlockers)),this.blockedPathNodes.push(...e.blockedPathNodes),e.path}updateDestination(e,t){e=e.length?e[0].tile:this.targetTile;this.destinationLeptons.set(e.rx*Coords.LEPTONS_PER_TILE,e.ry*Coords.LEPTONS_PER_TILE).add(t)}canStopAtTile(t,i,r){if(t.zone===ZoneType.Air){if((!t.isAircraft()||!t.airportBoundTrait)&&!t.rules.spawned&&(!this.options?.forceMove||!t.rules.balloonHover||t.rules.hoverAttack)&&(!this.game.map.terrain.getPassableSpeed(i,SpeedType.Amphibious,!1,r)||this.game.map.getObjectsOnTile(i).filter(e=>e.isBuilding()&&!e.isDestroyed&&!e.dockTrait?.hasReservedDockForUnit(t)&&!t.rules.dock.includes(e.name)||e.isUnit()&&e.tile===i&&e.moveTrait.moveState!==MoveState.Moving&&e!==t).length))return!1}else if(t.isInfantry()){let e=this.game.map.getGroundObjectsOnTile(i).filter(e=>e.isInfantry()&&e.tile===i&&e.onBridge===r&&e.moveTrait.moveState!==MoveState.Moving&&e!==t);if(2<e.length||e.find(e=>e.position.subCell===t.position.subCell))return!1}return!(t.zone!==ZoneType.Air&&t.rules.tooBigToFitUnderBridge&&!r&&i.onBridgeLandType&&this.game.map.tileOccupation.getBridgeOnTile(i)?.isHighBridge())&&!(!this.isCancelling()&&this.options?.strictCloseEnough&&void 0!==this.options?.closeEnoughTiles&&!this.isCloseEnoughToDest(t,i,this.options.closeEnoughTiles))}isCloseEnoughToDest(e,t,i){if(void 0===i)return!0;let r=new RangeHelper(this.game.map.tileOccupation);return!(r.tileDistance(this.targetTile,t)>i)}hasReachedDestination(e){return!this.path.length}updateTarget(e,t,i=!1){this.needsPathUpdate=!0,this.targetChangeRequested={tile:e,toBridge:t,onlyIfPathExists:i}}onEnd(e){e.moveTrait.collisionState=CollisionState.Resolved,e.moveTrait.currentWaypoint=void 0,this.targetOffset.equals(this.computeTargetOffset(e))||(e.moveTrait.lastTargetOffset=this.targetOffset)}forceCancel(e){return!(!this.cancellable||this.children.some(e=>!e.cancellable))&&(!(!this.options?.allowOutOfBoundsTarget&&!this.game.map.isWithinBounds(e.tile))&&(this.status!==TaskStatus.Running&&this.status!==TaskStatus.Cancelling||(e.moveTrait.unreservePathNodes(),e.moveTrait.lastMoveResult=MoveResult.Cancel,this.onEnd(e),e.moveTrait.lastTargetOffset=this.targetOffset,e.moveTrait.lastVelocity=e.moveTrait.velocity.clone()),this.status=TaskStatus.Cancelled,!0))}onTick(s){if(s.moveTrait.isDisabled()&&s.moveTrait.moveState===MoveState.ReachedNextWaypoint)return!!this.isCancelling()&&(s.moveTrait.lastMoveResult=MoveResult.Cancel,!0);var e;this.needsPathUpdate&&(s.moveTrait.moveState===MoveState.PlanMove&&(this.inPlanningForTicks=void 0,s.moveTrait.currentWaypoint=void 0,s.moveTrait.collisionState=CollisionState.Resolved,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,s.moveTrait.velocity.set(0,0,0)),e=this.targetTile,r=this.toBridge,this.targetChangeRequested&&(this.targetTile=this.targetChangeRequested.tile,this.toBridge=this.targetChangeRequested.toBridge),this.computePath(s,s.moveTrait.locomotor,this.targetChangeRequested?.onlyIfPathExists)?(this.path.length||this.unreachableTargets.push({tile:this.targetTile,toBridge:this.toBridge}),this.updateDestination(this.path,this.targetOffset),this.allObstaclesAreBlockers=!1):(this.targetTile=e,this.toBridge=r,this.targetLinesConfig.pathNodes=[...this.targetLinesConfig.pathNodes]),this.targetLinesConfig.isRecalc=!this.targetChangeRequested,this.targetChangeRequested=void 0,this.needsPathUpdate=!1);let i=this.game.map;if(s.moveTrait.moveState===MoveState.ReachedNextWaypoint){s.moveTrait.unreservePathNodes();var r=this.path.findIndex(e=>e===s.moveTrait.currentWaypoint);if(-1!==r?this.path.splice(r):this.path.pop(),s.moveTrait.currentWaypoint=void 0,this.isCancelling()?!this.cancelProcessed:this.hasReachedDestination(s)){var a=!this.isCancelling()&&!this.isCloseEnoughToDest(s,s.tile,this.options?.closeEnoughTiles);if(!a&&this.canStopAtTile(s,s.tile,s.onBridge))return s.moveTrait.lastMoveResult=this.isCancelling()?MoveResult.Cancel:MoveResult.Success,!0;{if(this.unreachableTargets.length>MAX_UNREACH_TILES_BAIL)return s.moveTrait.lastMoveResult=MoveResult.Fail,this.log(s,"bail_max_unreachable_dest"),!0;let e=s.tile,t=s.onBridge?i.tileOccupation.getBridgeOnTile(e):void 0;a&&(e=this.targetTile,t=this.toBridge?i.tileOccupation.getBridgeOnTile(e):void 0);r=this.findRelocationTile(e,t,s);if(!r)return s.moveTrait.lastMoveResult=a?MoveResult.Fail:MoveResult.CloseEnough,this.log(s,"bail_no_free_dest"),!0;a=!t||t.isHighBridge()?i.tileOccupation.getBridgeOnTile(r):void 0;return this.updateTarget(r,!!a),this.isCancelling()&&(this.cancelProcessed=!0,this.cancelRepositionPending=!0),!1}}if(this.cancelProcessed&&!this.path.length)return s.moveTrait.lastMoveResult=MoveResult.Cancel,!0;this.cancelProcessed=!1,s.moveTrait.moveState=MoveState.PlanMove;let e=s.moveTrait.locomotor;s.moveTrait.currentWaypoint=e.selectNextWaypoint?e.selectNextWaypoint(s,this.path):this.path[this.path.length-1],this.currentWaypointLeptons.set(s.moveTrait.currentWaypoint.tile.rx,s.moveTrait.currentWaypoint.tile.ry).multiplyScalar(Coords.LEPTONS_PER_TILE).add(this.targetOffset);a=e.onNewWaypoint(s,this.currentWaypointLeptons,this.destinationLeptons);if(a)return this.children.push(...a),!1}if(s.moveTrait.moveState===MoveState.PlanMove){if(this.isCancelling()&&!this.cancelRepositionPending)return s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s);if(this.inPlanningForTicks=void 0===this.inPlanningForTicks?0:this.inPlanningForTicks+1,this.inPlanningForTicks>PLANNING_BAILOUT_TICKS)return this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,s.moveTrait.velocity.set(0,0,0),this.log(s,"repath_plan_timeout"),!1;if(s.rules.movementZone!==MovementZone.Fly&&!s.moveTrait.locomotor.ignoresTerrain){let t=this.path.slice(this.path.indexOf(s.moveTrait.currentWaypoint)).reverse();var n,o,l,h=s.moveTrait.velocity.length();for(n of t)n.onBridge?.isDestroyed&&(n.onBridge=void 0);for(o of t){if(!i.terrain.getPassableSpeed(o.tile,s.rules.speedType,s.isInfantry(),!!o.onBridge,this.options?.ignoredBlockers))return this.options?.stopOnBlocker&&i.terrain.findObstacles(o,s).some(e=>e.obj===this.options.stopOnBlocker)?(s.moveTrait.lastMoveResult=MoveResult.CloseEnough,!0):(this.needsPathUpdate=!0,s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s));if(!o.onBridge){var c=i.getGroundObjectsOnTile(o.tile).find(e=>e.isOverlay()&&e.rules.crate);if(c)if(this.game.crateGeneratorTrait.peekInsideCrate(c)===PowerupType.Unit){this.game.crateGeneratorTrait.pickupCrate(s,c,this.game);c=this.game.map.getGroundObjectsOnTile(o.tile).find(e=>e.isUnit()&&!e.onBridge);if(c)return this.needsPathUpdate=!0,this.blockedPathNodes.push({node:o,obj:c}),s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s)}}for(l of i.terrain.findObstacles(o,s).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj))){if(l.static)return this.needsPathUpdate=!0,s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s);if(l.obj.rules.crushable){if([SpeedType.Track,SpeedType.Hover].includes(s.rules.speedType)&&s.crusher&&(!l.obj.isTechno()||!this.game.areFriendly(l.obj,s)))continue;if(!l.obj.isTechno())return this.needsPathUpdate=!0,s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s)}if(l.obj.isTerrain()){if(!s.isInfantry())throw new Error(`Obstacle ${l.obj.name} should be a blocker for non infantry`);var u=this.findFreeSubCell(s,o);return void 0!==u?this.relocateToSubCell(s,u):(this.needsPathUpdate=!0,this.blockedPathNodes.push({node:o,obj:l.obj}),s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint),this.onTick(s)}if(!l.obj.isTechno())throw new Error("Unexpected obstacle of type "+l.obj.type);const f=l.obj;var d=f.isUnit()?f.moveTrait.velocity.length():0;if(!f.isAircraft()||f.zone!==ZoneType.Ground||!this.options?.ignoredBlockers?.some(e=>e.isBuilding()&&e.dockTrait?.isDocked(f))){if(1===t.length&&f.isUnit()&&d&&h&&h<=d&&s.direction===f.direction&&f.tile===o.tile&&f.moveTrait.currentWaypoint?.tile!==o.tile)break;if(f.isBuilding()||f.moveTrait.moveState===MoveState.Idle||f.moveTrait.collisionState!==CollisionState.Resolved){if(!h&&s.moveTrait.collisionState!==CollisionState.Resolved&&f.isUnit()&&f.moveTrait.collisionState!==CollisionState.Resolved)return this.inPlanningForTicks+1>PLANNING_BAILOUT_TICKS&&(this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,this.log(s,"repath_waited_too_long_blocker "+f.id),s.moveTrait.velocity.set(0,0,0)),!1;{if(f.isInfantry()&&s.isInfantry()&&f.moveTrait.collisionState===CollisionState.Resolved){var p=this.findFreeSubCell(s,o);if(void 0!==p)return this.relocateToSubCell(s,p),this.onTick(s)}u=findIndexReverse(this.path.slice(0,this.path.indexOf(o)),e=>!i.terrain.findObstacles(e,s).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj)).length);if(-1===u){if(this.canStopAtTile(s,s.tile,s.onBridge)&&this.isCloseEnoughToDest(s,s.tile,this.options?.closeEnoughTiles))return s.moveTrait.lastMoveResult=MoveResult.CloseEnough,this.log(s,"bail_waypoints_blocked_close_enough"),!0;if(!(0===this.options?.closeEnoughTiles||Math.abs(s.tile.rx-this.targetTile.rx)<=1&&Math.abs(s.tile.ry-this.targetTile.ry)<=1))return this.needsPathUpdate=!0,this.blockedPathNodes.push(...this.path.slice(0,this.path.indexOf(o)+1).map(e=>({node:e,obj:i.terrain.findObstacles(e,s)[0].obj}))),s.moveTrait.velocity.set(0,0,0),this.log(s,"repath_waypoints_blocked_too_far"),!1}let e;if(e=-1!==u?(p=this.path[u],i.terrain.computePath(s.rules.speedType,s.isInfantry(),s.tile,s.onBridge,p.tile,!!p.onBridge,{maxExpandedNodes:15,bestEffort:!1,excludeTiles:e=>!!i.terrain.findObstacles(e,s).filter(e=>!this.options?.ignoredBlockers?.includes(e.obj)).length,ignoredBlockers:this.options?.ignoredBlockers})):[],e.length||f.owner!==s.owner||1!==t.length)return e.length?(this.path.splice(u,this.path.length,...e),s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s)):((g=this.selectWeaponVsObstacle(s,f))?(this.children.push(s.attackTrait.createAttackTask(this.game,f,f.tile,g,{passive:!0,holdGround:!0})),s.moveTrait.velocity.set(0,0,0)):this.options?.forceWaitOnPathBlocked?(this.children.push(new WaitTicksTask(MoveTask_RETRY_TICKS)),this.inPlanningForTicks=0,s.moveTrait.velocity.set(0,0,0),s.moveTrait.collisionState=CollisionState.Waiting):(this.needsPathUpdate=!0,this.blockedPathNodes.push({node:o,obj:f}),f.isBuilding()&&(this.allObstaclesAreBlockers=!0),this.log(s,"repath_unavoidable_blocker "+f.id),s.moveTrait.velocity.set(0,0,0)),!1);g=f.unitOrderTrait.hasTasks();if(this.pushTried||f.isBuilding()||f.moveTrait.collisionState===CollisionState.Waiting||g||f.isAircraft()&&f.missileSpawnTrait)return!this.options?.forceWaitOnPathBlocked&&(f.isBuilding()||g&&f.moveTrait.moveState===MoveState.Idle||this.inPlanningForTicks+MoveTask_RETRY_TICKS>PLANNING_BAILOUT_TICKS)?(this.needsPathUpdate=!0,this.allObstaclesAreBlockers=!0,this.log(s,"repath_blocker_busy_wait_timeout "+f.id),s.moveTrait.velocity.set(0,0,0)):(this.children.push(new WaitTicksTask(MoveTask_RETRY_TICKS)),this.options?.forceWaitOnPathBlocked?this.inPlanningForTicks=0:this.inPlanningForTicks+=MoveTask_RETRY_TICKS,s.moveTrait.velocity.set(0,0,0),s.moveTrait.collisionState=CollisionState.Waiting),!1;g=new Vector2(f.tile.rx-s.tile.rx,f.tile.ry-s.tile.ry);return this.pushTried=!0,f.unitOrderTrait.addTask(new MoveAsideTask(this.game,g)),this.children.push(new WaitTicksTask(1)),s.moveTrait.velocity.set(0,0,0),s.moveTrait.collisionState=CollisionState.Waiting,this.log(s,"push "+f.id),!1}}if(f.isInfantry()&&s.isInfantry()){var g=this.findFreeSubCell(s,o);if(void 0!==g)return this.relocateToSubCell(s,g),this.onTick(s)}if(!h)return this.inPlanningForTicks>MoveTask_RETRY_TICKS&&(s.moveTrait.collisionState=CollisionState.Waiting),!1;if(180===Math.abs(s.direction-f.direction))return s.moveTrait.velocity.set(0,0,0),s.moveTrait.collisionState=CollisionState.Waiting,!1;if(Math.abs(s.direction-f.direction)<=45&&h>d*SPEED_MULT){d=this.path.indexOf(o);if(5<=d){let e=findIndexReverse(this.path.slice(0,d-5),e=>!i.terrain.findObstacles(e,s).length);if(-1!==e){d=this.path[e],d=i.terrain.computePath(s.rules.speedType,s.isInfantry(),s.tile,s.onBridge,d.tile,!!d.onBridge,{maxExpandedNodes:15,bestEffort:!1,excludeTiles:t=>!!i.terrain.findObstacles(t,s).length||this.path.findIndex(e=>e.tile===t.tile&&e.onBridge===t.onBridge)>e});if(d.length)return this.path.splice(e,this.path.length,...d),s.moveTrait.currentWaypoint=void 0,s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s)}}return s.moveTrait.collisionState=CollisionState.Waiting,s.moveTrait.velocity.set(0,0,0),!1}return s.moveTrait.velocity.set(0,0,0),s.moveTrait.collisionState=CollisionState.Waiting,!1}}}if(s.rules.speedType===SpeedType.Track&&h){var m,y=this.path.indexOf(s.moveTrait.currentWaypoint);if(0<y){let t=this.path[y-1];for(m of i.getGroundObjectsOnTile(t.tile).filter(e=>e.isUnit()&&e.onBridge===!!t.onBridge&&e.rules.crushable&&e.veteranTrait?.hasVeteranAbility(VeteranAbility.SCATTER)&&!this.game.areFriendly(e,s)))m.unitOrderTrait.hasTasks()||m.unitOrderTrait.addTask(new ScatterTask(this.game))}}s.moveTrait.reservedPathNodes.length||(s.moveTrait.reservedPathNodes.push(...t),t.forEach(e=>{i.tileOccupation.occupySingleTile(e.tile,s)}))}s.moveTrait.moveState=MoveState.Moving,this.inPlanningForTicks=void 0,this.unreachableTargets.length=0,this.pushTried=!1,s.moveTrait.collisionState===CollisionState.Waiting&&(s.moveTrait.collisionState=CollisionState.Resolved)}if(s.moveTrait.moveState===MoveState.Moving){let e=s.moveTrait.locomotor,{distance:t,done:i,isTeleport:r}=e.tick(s,this.currentWaypointLeptons,this.destinationLeptons,(this.isCancelling()||!this.path.length)&&!this.cancelRepositionPending);if(r&&s.traits.filter(NotifyTeleport).forEach(e=>{e[NotifyTeleport.onBeforeTeleport](s,this.game,!0,!0)}),t.length()){a=s.tile,y=e.allowOutOfBounds;if(t.y?(T=s.tileElevation,s.position.moveByLeptons3(t,y),s.moveTrait.handleElevationChange(T,this.game)):s.position.moveByLeptons(t.x,t.z,y),s.tile!==a){var T=s.onBridge?this.game.map.tileOccupation.getBridgeOnTile(a):void 0,y=findReverse(this.path,e=>e.tile===s.tile);let e=y?y.onBridge:T||s.moveTrait.currentWaypoint.onBridge?this.game.map.tileOccupation.getBridgeOnTile(s.tile):void 0;if(e?.isDestroyed&&(e=void 0),s.moveTrait.handleTileChange(a,e,!1,this.game,r),r&&(s.moveTrait.lastTeleportTick=this.game.currentTick,this.game.events.dispatch(new ObjectTeleportEvent(s,!0,a))),s.isDestroyed)return!0}}if(i)return s.moveTrait.moveState=MoveState.ReachedNextWaypoint,this.onTick(s)}return!1}selectWeaponVsObstacle(e,t){let i;if(!this.game.areFriendly(t,e)&&e.attackTrait&&!e.attackTrait.isDisabled()&&e.attackTrait.isIdle()&&(i=e.attackTrait.selectWeaponVersus(e,t,this.game,!1,!0))&&i.name!==e.armedTrait?.deathWeapon?.name&&(!i.rules.limboLaunch||!i.warhead.rules.parasite)&&!i.warhead.rules.mindControl)return i}findRelocationTile(a,n,o){let l=this.game.map,i;if(o.rules.movementZone===MovementZone.Fly){var t=e=>!l.tileOccupation.getGroundObjectsOnTile(e).some(e=>e.isBuilding()&&!e.isDestroyed||e.isTerrain()||e.isOverlay()&&e.rules.isARock);let e=new RandomTileFinder(l.tiles,l.mapBounds,a,1,this.game,t);if(i=e.getNextTile(),!i){let e=new RadialTileFinder(l.tiles,l.mapBounds,a,o.getFoundation(),2,15,t);i=e.getNextTile()}}else{let e=!this.options?.ignoredBlockers?.length&&l.terrain.getPassableSpeed(o.tile,o.rules.speedType,o.isInfantry(),o.onBridge)?this.game.map.terrain.getIslandIdMap(o.rules.speedType,o.isInfantry()):void 0,r=e?.get(o.tile,o.onBridge),s=new MovePositionHelper(l),t=new RadialTileFinder(l.tiles,l.mapBounds,a,{width:1,height:1},0,5,t=>{let i=!n||n.isHighBridge()?l.tileOccupation.getBridgeOnTile(t):void 0;return!this.unreachableTargets.find(e=>e.tile===t&&e.toBridge===!!i)&&(o.zone===ZoneType.Air||e?.get(t,!!i)===r&&!l.terrain.findObstacles({tile:t,onBridge:i},o).length&&s.isEligibleTile(t,i,n,a))&&this.canStopAtTile(o,t,!!i)});i=t.getNextTile()}return i}findFreeSubCell(t,i){let e=this.game.map.getGroundObjectsOnTile(i.tile);var r=e.filter(e=>e.isInfantry()&&e.onBridge===!!i.onBridge&&e!==t).map(e=>e.position.desiredSubCell),s=e.filter(e=>e.isTerrain()).map(e=>e.rules.getOccupiedSubCells(this.game.map.getTheaterType())).flat();let a=[...r,...s];return Infantry_Infantry.SUB_CELLS.find(e=>-1===a.indexOf(e))}relocateToSubCell(e,t){e.position.desiredSubCell=t;t=e.position.computeSubCellOffset(t);this.targetOffset=t,this.currentWaypointLeptons.set(e.moveTrait.currentWaypoint.tile.rx,e.moveTrait.currentWaypoint.tile.ry).multiplyScalar(Coords.LEPTONS_PER_TILE).add(this.targetOffset),this.updateDestination(this.path,this.targetOffset),e.moveTrait.locomotor.onWaypointUpdate?.(e,this.currentWaypointLeptons,this.destinationLeptons)}getTargetLinesConfig(e){var t,i;return this.path||(t=new LocomotorFactory(this.game).create(e),(this.options?.allowOutOfBoundsTarget||this.game.map.mapBounds.isWithinBounds(this.targetTile))&&e.rules.movementZone!==MovementZone.Fly&&!t.ignoresTerrain&&e.unitOrderTrait.getCurrentTask()?.isCancelling()?this.groundPathPlan||(i=this.computeGroundPath(e),this.targetLinesConfig.pathNodes=i.path,i.path.length&&(this.groundPathPlan=i)):((i=e.moveTrait).locomotor??(i.locomotor=t),this.computePath(e,e.moveTrait.locomotor)),this.targetLinesConfig.isRecalc=!1),this.targetLinesConfig}log(e,t){this.logger.debug(`<${e.id}>: `+t)}}(NotifyDestroy=NotifyDestroy||{}).onDestroy=Symbol(),function(e){e[e.None=0]="None",e[e.Normal=1]="Normal",e[e.Demolish=2]="Demolish",e[e.Crush=3]="Crush",e[e.Temporal=4]="Temporal",e[e.Sink=5]="Sink"}(DeathType=DeathType||{}),(NotifyTileChange=NotifyTileChange||{}).onTileChange=Symbol(),(NotifyTileChange_NotifyTileChange=NotifyTileChange_NotifyTileChange||{}).onTileChange=Symbol();class EnterTileEvent{constructor(e,t){this.target=e,this.source=t,this.type=EventType.EnterTile}}(NotifyElevationChange=NotifyElevationChange||{}).onElevationChange=Symbol(),function(e){e[e.Idle=0]="Idle",e[e.ReachedNextWaypoint=1]="ReachedNextWaypoint",e[e.PlanMove=2]="PlanMove",e[e.Moving=3]="Moving"}(MoveState=MoveState||{}),function(e){e[e.Success=0]="Success",e[e.Cancel=1]="Cancel",e[e.CloseEnough=2]="CloseEnough",e[e.Fail=3]="Fail"}(MoveResult=MoveResult||{}),function(e){e[e.Waiting=0]="Waiting",e[e.Resolved=1]="Resolved"}(CollisionState=CollisionState||{});const findMoveTaskDeep=e=>e instanceof MoveTask||e.children[0]&&findMoveTaskDeep(e.children[0]);class MoveTrait{get baseSpeed(){return this.gameObject.rules.speed*(this.gameObject.veteranTrait?.getVeteranSpeedMultiplier()??1)*this.gameObject.crateBonuses.speed*(this.gameObject.isVehicle()&&this.gameObject.healthTrait.health<=50&&this.gameObject.rules.locomotor!==LocomotorType.Hover?.75:1)*(1-this.speedPenalty)}constructor(e,t){this.gameObject=e,this.tileOccupation=t,this.disabled=!1,this.speedPenalty=0,this.velocity=new Vector3_Vector3,this.reservedPathNodes=[],this.moveState=MoveState.Idle,this.collisionState=CollisionState.Resolved}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}isMoving(){return this.moveState===MoveState.Moving}isIdle(){return this.moveState===MoveState.Idle}isWaiting(){return this.collisionState===CollisionState.Waiting}[NotifyTick_NotifyTick.onTick](e,t){var i;this.moveState!==MoveState.Idle&&this.collisionState===CollisionState.Resolved&&((i=e.unitOrderTrait.getCurrentTask())&&findMoveTaskDeep(i)||(this.velocity.set(0,0,0),this.moveState=MoveState.Idle,this.locomotor=void 0,!i&&!e.attackTrait?.currentTarget&&e.isVehicle()&&e.turretTrait&&(e.turretTrait.desiredFacing=e.direction))),this.moveState===MoveState.Idle&&(e.rules.locomotor===LocomotorType.Jumpjet?JumpjetLocomotor.tickStationary(e,t):e.isAircraft()&&e.rules.locomotor===LocomotorType.Aircraft&&WingedLocomotor.tickStationary(e,t))}[NotifyDestroy.onDestroy](e,t){this.unreservePathNodes()}teleportUnitToTile(e,t,i,r,s){let a=this.gameObject;var n=a.tile;a.traits.filter(NotifyTeleport).forEach(e=>{e[NotifyTeleport.onBeforeTeleport](a,s,i,r)}),a.position.tileElevation=a.tileElevation,a.position.tile=e,a.position.subCell=a.position.desiredSubCell,this.handleTileChange(n,t,!0,s,!0),r||(this.unreservePathNodes(),this.speedPenalty=0,this.velocity.set(0,0,0),this.moveState=MoveState.Idle,this.collisionState=CollisionState.Resolved,this.locomotor=void 0,this.currentWaypoint=void 0,this.lastTargetOffset=void 0,this.lastVelocity=void 0,this.lastMoveResult=MoveResult.Cancel,a.isVehicle()&&(a.spinVelocity=0,a.turretTrait&&(a.turretTrait.desiredFacing=a.direction))),this.lastTeleportTick=s.currentTick,s.events.dispatch(new ObjectTeleportEvent(a,i,n))}handleTileChange(t,e,i,r,s=!1){const a=this.gameObject;if(r.map.tileOccupation.unoccupyTileRange(t,a),r.map.tileOccupation.occupyTileRange(a.tile,a),r.map.technosByTile.updateObject(a),a.zone!==ZoneType.Air){var n=a.onBridge?r.map.tileOccupation.getBridgeOnTile(t):void 0,o=a.onBridge?t.onBridgeLandType:t.landType,l=e?a.tile.onBridgeLandType:a.tile.landType;o!==l&&(0<r.rules.getLandRules(l).getSpeedModifier(a.rules.speedType)||a.rules.speedType===SpeedType.Amphibious||s)&&(a.zone=getZoneType(l)),e!==n&&(a.position.tileElevation+=-(n?.tileElevation??0)+(e?.tileElevation??0),a.onBridge=!!e);var h,e=a.moveTrait.reservedPathNodes.findIndex(e=>e.tile===a.tile);if(-1!==e&&a.moveTrait.reservedPathNodes.splice(e,1),a.crusher)for(h of r.map.getGroundObjectsOnTile(a.tile).filter(e=>(!e.isUnit()||e.onBridge===a.onBridge)&&e.rules.crushable&&!(e.isInfantry()&&e.stance===StanceType.Paradrop)&&(!(e.isTechno()&&!i)||!r.areFriendly(e,a))))h.isDestroyed||(h.isInfantry()&&(h.infDeathType=InfDeathType.None),a.isVehicle()&&h.isOverlay()&&h.rules.wall&&a.applyRocking(0,.5),h.deathType=DeathType.Crush,r.destroyObject(h,{player:a.owner,obj:a}));a.onBridge||(e=r.map.tileOccupation.getGroundObjectsOnTile(a.tile).find(e=>e.isOverlay()&&e.rules.crate))&&r.crateGeneratorTrait.pickupCrate(a,e,r)}r.traits.filter(NotifyTileChange).forEach(e=>{e[NotifyTileChange.onTileChange](a,r,t,s)}),a.traits.filter(NotifyTileChange_NotifyTileChange).forEach(e=>{e[NotifyTileChange_NotifyTileChange.onTileChange](a,r,t,s)}),r.events.dispatch(new EnterTileEvent(a.tile,a))}handleElevationChange(t,i){i.traits.filter(NotifyElevationChange).forEach(e=>{e[NotifyElevationChange.onElevationChange](this.gameObject,i,t)})}unreservePathNodes(){this.reservedPathNodes.forEach(e=>{e.tile!==this.gameObject.tile&&this.tileOccupation.unoccupySingleTile(e.tile,this.gameObject)}),this.reservedPathNodes.length=0}dispose(){this.gameObject=void 0}}class SuppressionTrait{constructor(){this.suppressionTicks=0,this.enabled=!0}disable(){this.enabled=!1}isSuppressed(){return this.enabled&&0<this.suppressionTicks}suppress(){this.enabled&&(this.suppressionTicks=30)}[NotifyTick_NotifyTick.onTick](){0<this.suppressionTicks&&this.suppressionTicks--}}class Traits{constructor(){this.allTraits=[],this.traitsByTypeCache=new Map}add(e){this.allTraits.push(e),this.traitsByTypeCache.clear()}addToFront(e){this.allTraits.unshift(e),this.traitsByTypeCache.clear()}remove(e){e=this.allTraits.indexOf(e);-1!==e&&(this.allTraits.splice(e,1),this.traitsByTypeCache.clear())}filter(t){let e=this.traitsByTypeCache.get(t);return e||(e="function"==typeof t?this.allTraits.filter(e=>e instanceof t):this.allTraits.filter(e=>this.traitImplements(e,t)),this.traitsByTypeCache.set(t,e)),e}get(e){e=this.find(e);if(!e)throw new Error("No matching trait found");return e}find(e){return this.filter(e)[0]}getAll(){return this.allTraits}traitImplements(e,t){for(var i of Object.getOwnPropertyNames(t))if(void 0===e[t[i]])return!1;return!0}clear(){this.allTraits.length=0,this.traitsByTypeCache.clear()}dispose(){this.getAll().forEach(e=>e.dispose?.()),this.clear()}}(NotifyOwnerChange=NotifyOwnerChange||{}).onChange=Symbol(),(NotifySpawn=NotifySpawn||{}).onSpawn=Symbol(),(NotifyUnspawn=NotifyUnspawn||{}).onUnspawn=Symbol(),(NotifyAttack=NotifyAttack||{}).onAttack=Symbol();class GameObject{get tile(){return this.position.tile}get tileElevation(){return this.position.tileElevation}constructor(e,t,i,r){this.traits=new Traits,this.cachedTraits={tick:[]},this.isCrashing=!1,this.isDestroyed=!1,this.deathType=DeathType.Normal,this.isDisposed=!1,this.isSpawned=!1,this.type=e,this.name=t,this.rules=i,this.art=r}getFoundation(){return{width:1,height:1}}isSmudge(){return this.type===ObjectType.Smudge}isOverlay(){return this.type===ObjectType.Overlay}isTerrain(){return this.type===ObjectType.Terrain}isProjectile(){return this.type===ObjectType.Projectile}isDebris(){return this.type===ObjectType.Debris}isBuilding(){return!1}isInfantry(){return!1}isVehicle(){return!1}isAircraft(){return!1}isUnit(){return!1}isTechno(){return!1}update(e){for(var t of this.cachedTraits.tick)t[NotifyTick_NotifyTick.onTick](this,e)}onSpawn(t){this.isSpawned=!0,this.traits.filter(NotifySpawn).forEach(e=>{e[NotifySpawn.onSpawn](this,t)})}onUnspawn(t){this.isSpawned=!1,this.traits.filter(NotifyUnspawn).forEach(e=>{e[NotifyUnspawn.onUnspawn](this,t)})}onDestroy(t,i,r){this.traits.filter(NotifyDestroy).forEach(e=>{e[NotifyDestroy.onDestroy](this,t,i,r)})}onOwnerChange(t,i){this.traits.filter(NotifyOwnerChange).forEach(e=>{e[NotifyOwnerChange.onChange](this,t,i)})}onAttack(t,i){this.traits.filter(NotifyAttack).forEach(e=>{e[NotifyAttack.onAttack](this,i,t)})}addTrait(e){this.traits.add(e),e[NotifyTick_NotifyTick.onTick]&&this.cachedTraits.tick.push(e)}getUiName(){return this.rules.uiName}getHash(){var e=this.position.worldPosition;return fnv32a([this.id,...new Uint8Array(new Float64Array([e.x,e.y,e.z]).buffer),...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{id:this.id,position:this.position.worldPosition.toArray(),traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.isDisposed=!0,this.traits.dispose(),this.cachedTraits.tick.length=0}}!function(e){e[e.None=0]="None",e[e.Veteran=1]="Veteran",e[e.Elite=2]="Elite"}(VeteranLevel=VeteranLevel||{});class Techno_Techno extends GameObject{get primaryWeapon(){return this.armedTrait?.primaryWeapon}get secondaryWeapon(){return this.armedTrait?.secondaryWeapon}get ammo(){return this.ammoTrait?.ammo}get sight(){return Math.min(TechnoRules.MAX_SIGHT,this.rules.sight*(this.veteranTrait?.getVeteranSightMultiplier()??1))}get veteranLevel(){return this.veteranTrait?.veteranLevel??VeteranLevel.None}constructor(e,t,i,r){super(e,t,i,r),this.explodes=this.rules.explodes,this.radarInvisible=this.rules.radarInvisible,this.c4=this.rules.c4,this.crusher=this.rules.crusher,this.defaultToGuardArea=this.rules.defaultToGuardArea,this.guardMode=this.rules.defaultToGuardArea,this.purchaseValue=this.rules.cost}resetGuardModeToIdle(){this.guardMode=this.defaultToGuardArea,this.guardArea=void 0}update(e){if(this.warpedOutTrait.isActive())for(var t of this.cachedTraits.tick)t.ticksWhenWarpedOut&&t[NotifyTick_NotifyTick.onTick](this,e);else super.update(e)}isTechno(){return!0}}class IdleActionTrait{constructor(){this.cooldownTicks=Number.POSITIVE_INFINITY,this._actionDueThisTick=!1}[NotifyTick_NotifyTick.onTick](e,t){this._actionDueThisTick=!1;var i=!e.unitOrderTrait.hasTasks();i&&!this.idle?this.resetCooldown(t):i?0===this.cooldownTicks?(this.doIdleAction(e,t),this.resetCooldown(t)):this.cooldownTicks--:this.cooldownTicks=Number.POSITIVE_INFINITY,this.idle=i}doIdleAction(e,t){if(e.isInfantry()){if(e.rules.fraidycat)if(.5<t.generateRandom())return void e.unitOrderTrait.addTask(new ScatterTask(t,void 0,{noSlopes:!0}));this._actionDueThisTick=!0}}actionDueThisTick(){return this._actionDueThisTick}resetCooldown(e){var t=e.rules.audioVisual.idleActionFrequency,e=e.generateRandom()*t*.5,e=Math.max(0,t-e);this.cooldownTicks=Math.floor(e*GameSpeed.BASE_TICKS_PER_SECOND)}}class ObjectCrashingEvent{constructor(e){this.gameObject=e,this.type=EventType.ObjectCrashing}}(NotifyCrash=NotifyCrash||{}).onCrash=Symbol();class CrashableTrait{constructor(e){this.gameObject=e,this.crashingEvtSent=!1,this.crashState={}}[NotifyTick_NotifyTick.onTick](i,r){if(i.isCrashing){if(this.crashingEvtSent||(this.crashingEvtSent=!0,i.traits.filter(NotifyCrash).forEach(e=>e[NotifyCrash.onCrash](i,r)),r.events.dispatch(new ObjectCrashingEvent(i))),i.rules.locomotor!==LocomotorType.Jumpjet&&i.rules.locomotor!==LocomotorType.Aircraft)throw new Error("Crashing logic not implemented for locomotor "+LocomotorType[i.rules.locomotor]);{let e;if(i.rules.locomotor===LocomotorType.Jumpjet)e=JumpjetLocomotor.tickCrash(i,r,this.crashState);else{if(i.rules.locomotor!==LocomotorType.Aircraft)throw new Error(`Unhandled locomotor type "${i.rules.locomotor}"`);if(!i.isAircraft())throw new Error(`Obj "${i.name}#${i.id} is not an aircraft`);e=WingedLocomotor.tickCrash(i,r,this.crashState)}let t=!1;var s,a,n=e.clone().add(i.position.worldPosition);r.map.isWithinHardBounds(n)?(a=i.tile,s=i.tileElevation,i.position.moveByLeptons3(e),i.tile!==a&&i.moveTrait.handleTileChange(a,void 0,!1,r),a=(n=i.tile.onBridgeLandType?r.map.tileOccupation.getBridgeOnTile(i.tile):void 0)?.tileElevation??0,i.position.tileElevation=Math.max(i.position.tileElevation,a),i.position.tileElevation===a&&(i.zone=r.map.getTileZone(i.tile),i.onBridge=!!n,t=!0),i.tileElevation!==s&&i.moveTrait.handleElevationChange(s,r)):t=!0,t&&r.destroyObject(i,this.attackerInfo)}}}crash(e){this.attackerInfo=e,this.gameObject.isCrashing=!0,this.gameObject.cachedTraits.tick.length=0,this.gameObject.cachedTraits.tick=[this]}dispose(){this.gameObject=void 0}}class AgentTrait{infiltrate(e,t,i){var r;t.rules.radar&&![...t.owner.buildings].some(e=>e.rules.spySat)&&i.mapShroudTrait.resetShroud(t.owner,i),0<t.rules.power&&(r=i.rules.general.spyPowerBlackout,t.owner.powerTrait?.setBlackoutFor(r,i)),t.superWeaponTrait&&t.superWeaponTrait.getSuperWeapon(t)?.resetTimer(),0<t.rules.storage&&(r=clamp(i.rules.general.spyMoneyStealPercent,0,1),r=Math.floor(t.owner.credits*r),t.owner.credits-=r,e.owner.credits+=r),!i.rules.ai.buildTech.includes(t.name)||void 0!==(i=t.rules.aiBasePlanningSide)&&e.owner.production.addStolenTech(i),t.factoryTrait&&[FactoryType.InfantryType,FactoryType.UnitType].includes(t.factoryTrait.type)&&e.owner.production?.addVeteranType(t.factoryTrait.type)}}class CrateBonuses{constructor(){this.firepower=1,this.armor=1,this.speed=1}}class Infantry_Infantry extends Techno_Techno{get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,r){let s=new this(e,t,i);return s.moveTrait=new MoveTrait(s,r),s.traits.add(s.moveTrait),s.rules.crashable&&(s.crashableTrait=new CrashableTrait(s),s.traits.add(s.crashableTrait)),s.rules.fearless||(s.suppressionTrait=new SuppressionTrait,s.traits.add(s.suppressionTrait)),s.rules.agent&&(s.agentTrait=new AgentTrait,s.traits.add(s.agentTrait)),s.idleActionTrait=new IdleActionTrait,s.traits.add(s.idleActionTrait),s}constructor(e,t,i){super(ObjectType.Infantry,e,t,i),this.direction=0,this.onBridge=!1,this.zone=ZoneType.Ground,this._stance=StanceType.None,this.isFiring=!1,this.isPanicked=!1,this.infDeathType=InfDeathType.Gunfire,this.crateBonuses=new CrateBonuses}get stance(){return this._stance===StanceType.None&&this.suppressionTrait?.isSuppressed()?StanceType.Prone:this._stance}set stance(e){this._stance=e,this.moveTrait.setDisabled([StanceType.Deployed,StanceType.Cheer].includes(e)),this.attackTrait?.setDisabled([StanceType.Paradrop,StanceType.Cheer].includes(e))}isUnit(){return!0}isInfantry(){return!0}}Infantry_Infantry.SUB_CELLS=[2,4,3];class ParadropTask extends Task{constructor(e){super(),this.game=e}onTick(e){var t=Math.abs(this.game.rules.general.parachuteMaxFallRate),i=e.tile.onBridgeLandType?this.game.map.tileOccupation.getBridgeOnTile(e.tile).tileElevation:0,r=Coords.tileHeightToWorld(i),s=e.tileElevation,a=Coords.tileHeightToWorld(s);return r<Math.max(r,a-t)?(e.position.moveByLeptons3(new Vector3_Vector3(0,-t,0)),e.moveTrait.handleElevationChange(s,this.game),!1):(e.position.tileElevation=i,e.stance=StanceType.None,this.game.map.terrain.getPassableSpeed(e.tile,e.rules.speedType,e.isInfantry(),e.onBridge)||(e.infDeathType=InfDeathType.None,this.game.destroyObject(e,void 0,!0)),!0)}}function bresenham(i,r,s,a,n){let o=[];n=n||((e,t)=>{o.push({x:e,y:t})});var e=s-i,t=a-r,l=Math.abs(e),h=Math.abs(t);let c=0;var u=0<e?1:-1,d=0<t?1:-1;if(h<l)for(let e=i,t=r;u<0?e>=s:e<=s;e+=u)n(e,t),c+=h,c<<1>=l&&(t+=d,c-=l);else for(let e=i,t=r;d<0?t>=a:t<=a;t+=d)n(e,t),c+=l,c<<1>=h&&(e+=u,c-=h);return o}function isNotNullOrUndefined(e){return null!=e}class TaskGroup extends Task{constructor(...e){super(),this.children.push(...e)}onTick(e){return!0}}class UnlandableTrait{constructor(){this.enabled=!0}setEnabled(e){this.enabled=e}[NotifyTick_NotifyTick.onTick](e,t){var i;this.enabled&&(e.owner.isNeutral||e.name===t.rules.general.paradrop.paradropPlane)&&e.unitOrderTrait.isIdle()&&(i=this.chooseExitTile(e.tile,t),e.unitOrderTrait.addTask(new TaskGroup(new MoveTask(t,i,!1,{allowOutOfBoundsTarget:!0}),new CallbackTask(e=>t.unspawnObject(e))).setCancellable(!1)))}chooseExitTile(e,t){var i=t.map.tiles.getMapSize(),i=.5<t.generateRandom()?new Vector2(Math.floor(i.width/2),0):new Vector2(0,Math.floor(i.height/2)),e=new Vector2(e.rx,e.ry),i=bresenham(e.x,e.y,i.x,i.y).map(e=>t.map.tiles.getByMapCoords(e.x,e.y)).filter(isNotNullOrUndefined);if(!i.length)throw new Error("No valid exit tile found");return i[i.length-1]}}!function(e){e[e.Spawning=0]="Spawning",e[e.EnRoute=1]="EnRoute",e[e.Dropping=2]="Dropping",e[e.TurningAround=3]="TurningAround"}(ParadropState=ParadropState||{});const PLANE_SPAWN_DELAY_FRAMES=5*GameSpeed.BASE_TICKS_PER_SECOND,MAX_FAILED_ATTEMPTS=5;class ParadropEffect extends SuperWeaponEffect{constructor(e,t,i,r,s){super(e,t,i),this.paradropSquad=r,this.state=ParadropState.Spawning,this.failedAttempts=0,this.spawnDelay=s*PLANE_SPAWN_DELAY_FRAMES}onStart(e){this.passengerRules=e.rules.getObject(this.paradropSquad.inf,ObjectType.Infantry),this.passengerCount=this.paradropSquad.num}computeFlightPath(e,t,i){if(t.equals(e))throw new Error("Source and destination must be different");let r=e.clone().sub(t);e=i.rules.general.paradrop.paradropRadius/Coords.LEPTONS_PER_TILE,e=t.clone().add(r.clone().setLength(r.length()+2*e)).floor();let s=bresenham(t.x,t.y,e.x,e.y).map(e=>i.map.tiles.getByMapCoords(e.x,e.y)??i.map.tiles.getPlaceholderTile(e.x,e.y));for(;s.length;){var a=s[0],a=Coords.tileToWorld(a.rx+.5,a.ry+.5);if(i.map.isWithinHardBounds(new Vector2(a.x,a.y)))break;s.shift()}if(!s.length)throw new Error("No valid paradrop path found");return{fromTile:s[0],toTile:s[s.length-1]}}onTick(s){if(this.state===ParadropState.Spawning){if(0<this.spawnDelay)return this.spawnDelay--,!1;var a=s.map.tiles.getMapSize(),n=[new Vector2(0,0),new Vector2(Math.floor(a.width/2),0),new Vector2(0,Math.floor(a.height/2))][s.generateRandomInt(0,2)];let t=this.passengerRules.speedType,e=new RadialTileFinder(s.map.tiles,s.map.mapBounds,this.tile,{width:1,height:1},0,50,e=>0<s.map.terrain.getPassableSpeed(e,t,!0,!!e.onBridgeLandType));var o=this.targetTile=e.getNextTile();if(!o)return!0;let i=new Vector2(o.rx,o.ry);var{fromTile:l,toTile:a}=this.computeFlightPath(i,n,s),o=s.rules.general.paradrop.paradropPlane,n=s.rules.getObject(o,ObjectType.Aircraft);let r=this.pdPlane=s.createUnitForPlayer(n,this.owner);s.spawnObject(r,l),r.direction=FacingUtil.fromMapCoords(i.clone().sub(new Vector2(l.rx,l.ry))),r.position.tileElevation=Coords.worldToTileHeight(r.rules.flightLevel??s.rules.general.flightLevel),r.zone=ZoneType.Air,r.onBridge=!1,r.unitOrderTrait.addTask(new MoveTask(s,a,!1,{allowOutOfBoundsTarget:!0})),r.traits.get(UnlandableTrait).setEnabled(!1),this.state=ParadropState.EnRoute}if(!this.pdPlane||this.pdPlane.isDestroyed||this.pdPlane.isCrashing)return!0;o=this.targetTile;if(!this.pdPlane.unitOrderTrait.hasTasks())return this.state=ParadropState.TurningAround,this.pdPlane.unitOrderTrait.addTask(new MoveTask(s,o,!1,{allowOutOfBoundsTarget:!0})),!1;n=s.rules.general.paradrop.paradropRadius/Coords.LEPTONS_PER_TILE;let e=new RangeHelper(s.map.tileOccupation);l=e.isInTileRange(this.pdPlane.tile,o,0,n);if(this.state===ParadropState.EnRoute&&l&&(this.state=ParadropState.Dropping),this.state===ParadropState.Dropping)if(l&&0<this.passengerCount){a=this.pdPlane.tile;let t=!!a.onBridgeLandType;if(this.failedAttempts>MAX_FAILED_ATTEMPTS&&s.map.mapBounds.isWithinBounds(a))return this.passengerCount=0,!1;if(!s.map.terrain.getPassableSpeed(a,this.passengerRules.speedType,!0,t))return!1;let e=s.map.getGroundObjectsOnTile(a);if(e.some(e=>e.isVehicle()&&e.onBridge===t||e.isBuilding()&&!e.isDestroyed||e.isInfantry()&&e.stance===StanceType.Paradrop))return!1;n=this.findFreeSubCell(s,a);if(!n)return!1;this.passengerCount--;let i=s.createUnitForPlayer(this.passengerRules,this.owner);i.stance=StanceType.Paradrop,i.position.tileElevation=this.pdPlane.tileElevation,i.position.subCell=n,i.onBridge=t,i.rules.trainable&&this.owner.canProduceVeteran(i.rules)&&i.veteranTrait?.setVeteranLevel(VeteranLevel.Veteran),s.spawnObject(i,a),i.unitOrderTrait.addTask(new ParadropTask(s).setCancellable(!1))}else{if(!(0<this.passengerCount))return this.pdPlane.unitOrderTrait.getCurrentTask().forceCancel(this.pdPlane),this.pdPlane.traits.get(UnlandableTrait).setEnabled(!0),!0;this.failedAttempts++,this.state=ParadropState.TurningAround,this.pdPlane.unitOrderTrait.getCurrentTask().updateTarget(o,!!o.onBridgeLandType)}return this.state===ParadropState.TurningAround&&l&&(o=this.computeFlightPath(new Vector2(o.rx,o.ry),new Vector2(this.pdPlane.tile.rx,this.pdPlane.tile.ry),s)["toTile"],this.pdPlane.unitOrderTrait.getCurrentTask().updateTarget(o,!1),this.state=ParadropState.EnRoute),!1}findFreeSubCell(t,e){let i=t.map.getGroundObjectsOnTile(e).filter(e=>e.isTerrain()).map(e=>e.rules.getOccupiedSubCells(t.map.getTheaterType())).flat();e=Infantry_Infantry.SUB_CELLS.filter(e=>-1===i.indexOf(e));if(e.length)return 1<e.length?e[t.generateRandomInt(0,e.length-1)]:e[0]}}!function(e){e[e.NotBridge=0]="NotBridge",e[e.Concrete=1]="Concrete",e[e.Wood=2]="Wood"}(OverlayBridgeType=OverlayBridgeType||{});class BridgeOverlayTypes{static getOverlayBridgeType(e){return isBetween(e,this.minHighBridgeConcreteId,this.maxHighBridgeConcreteId)||isBetween(e,this.minLowBridgeConcreteId,this.maxLowBridgeConcreteId)?OverlayBridgeType.Concrete:isBetween(e,this.minHighBridgeWoodId,this.maxHighBridgeWoodId)||isBetween(e,this.minLowBridgeWoodId,this.maxLowBridgeWoodId)?OverlayBridgeType.Wood:OverlayBridgeType.NotBridge}static isBridge(e){return this.isHighBridge(e)||this.isLowBridge(e)}static isBridgePlaceholder(e){return this.bridgePlaceholderIds.includes(e)}static isHighBridge(e){return isBetween(e,this.minHighBridgeWoodId,this.maxHighBridgeWoodId)||isBetween(e,this.minHighBridgeConcreteId,this.maxHighBridgeConcreteId)}static isLowBridge(e){return isBetween(e,this.minLowBridgeWoodId,this.maxLowBridgeWoodId)||isBetween(e,this.minLowBridgeConcreteId,this.maxLowBridgeConcreteId)}static isXBridge(e){return e===this.minHighBridgeWoodId||e===this.minHighBridgeConcreteId||isBetween(e,this.minLowBridgeWoodId,this.minLowBridgeWoodId+8)||isBetween(e,this.minLowBridgeWoodId+18,this.minLowBridgeWoodId+21)||isBetween(e,this.minLowBridgeConcreteId,this.minLowBridgeConcreteId+8)||isBetween(e,this.minLowBridgeConcreteId+18,this.minLowBridgeConcreteId+21)}static isLowBridgeHead(e){return isBetween(e,this.minLowBridgeWoodId+18,this.minLowBridgeWoodId+25)||isBetween(e,this.minLowBridgeConcreteId+18,this.minLowBridgeConcreteId+25)}static isLowBridgeHeadStart(e){return isBetween(e,this.minLowBridgeWoodId+20,this.minLowBridgeWoodId+23)||isBetween(e,this.minLowBridgeConcreteId+20,this.minLowBridgeConcreteId+23)}static calculateLowBridgeOverlayId(e,t){let i;if(e===OverlayBridgeType.Concrete)i=this.minLowBridgeConcreteId;else{if(e!==OverlayBridgeType.Wood)throw new Error("Not implemented");i=this.minLowBridgeWoodId}return i+(t?0:9)}static calculateHighBridgeOverlayId(e,t){let i;if(e===OverlayBridgeType.Concrete)i=this.minHighBridgeConcreteId;else{if(e!==OverlayBridgeType.Wood)throw new Error("Not implemented");i=this.minHighBridgeWoodId}return i+(t?0:1)}}BridgeOverlayTypes.minLowBridgeWoodId=74,BridgeOverlayTypes.maxLowBridgeWoodId=99,BridgeOverlayTypes.minLowBridgeConcreteId=205,BridgeOverlayTypes.maxLowBridgeConcreteId=230,BridgeOverlayTypes.minHighBridgeConcreteId=24,BridgeOverlayTypes.maxHighBridgeConcreteId=25,BridgeOverlayTypes.minHighBridgeWoodId=237,BridgeOverlayTypes.maxHighBridgeWoodId=238,BridgeOverlayTypes.bridgePlaceholderIds=[100,101,231,232],(NotifyAttack_NotifyAttack=NotifyAttack_NotifyAttack||{}).onAttack=Symbol(),function(e){e[e.None=0]="None",e[e.Ground=1]="Ground",e[e.Wall=2]="Wall",e[e.Cliff=3]="Cliff",e[e.OnBridge=4]="OnBridge",e[e.UnderBridge=5]="UnderBridge",e[e.Shore=6]="Shore"}(CollisionType=CollisionType||{});class WarheadDetonateEvent{constructor(e,t,i,r){this.target=e,this.position=t,this.explodeAnim=i,this.isLightningStrike=r,this.type=EventType.WarheadDetonate}}!function(e){e[e.Top=0]="Top",e[e.TopLeft=1]="TopLeft",e[e.TopRight=2]="TopRight",e[e.Left=3]="Left",e[e.Right=4]="Right",e[e.BottomLeft=5]="BottomLeft",e[e.Bottom=6]="Bottom",e[e.BottomRight=7]="BottomRight"}(TileDirection=TileDirection||{});class TileCollection{constructor(i,r,e,s){this.tileSets=r,this.generalRules=e;let a=this.rSize={width:0,height:0},n=this.dSize={width:0,height:0};for(let e=0,t=i.length;e<t;++e)a.width=Math.max(a.width,i[e].rx),a.height=Math.max(a.height,i[e].ry),n.width=Math.max(n.width,i[e].dx),n.height=Math.max(n.height,i[e].dy);a.width++,a.height++,n.width++,n.height++;let o=this.tilesByRxy=new Array(a.width*a.height);o.fill(void 0);let l=this.tilesByDxy=new Array(n.width*n.height);l.fill(void 0);let h=this.tiles=new Array(i.length),c=[],u=this.bridgeSetTiles=[],d=new Set(Object.values(TerrainType));this.minTileHeight=Number.POSITIVE_INFINITY;for(let e=this.maxTileHeight=0,t=i.length;e<t;++e){var p=i[e],g=r.getTileImage(p.tileNum,p.subTile,s),m=g.terrainType;if(!d.has(m))throw new Error(`Tile (${p.rx}, ${p.ry}) has unknown terrain type "${m}"`);var y={...p,terrainType:m,landType:getLandType(m),onBridgeLandType:void 0,rampType:g.rampType,id:p.rx+"_"+p.ry,occluded:!1},T=y.rx,f=y.ry,v=y.dx,m=y.dy;h[e]=y,o[T+f*a.width]=y,l[v+m*n.width]=y,this.minTileHeight=Math.min(this.minTileHeight,y.z),this.maxTileHeight=Math.max(this.maxTileHeight,y.z),4!==g.height||y.terrainType!==TerrainType.Cliff&&!r.isCliffTile(y.tileNum)||c.push(y),r.isHighBridgeBoundaryTile(p.tileNum)&&u.push(y)}this.computeLandBehindCliffTiles(c),this.cutoffTileHeight=this.computeCutoffTileHeight()}computeLandBehindCliffTiles(t){if(!(this.generalRules.cliffBackImpassability<2)){let e=[[-2,-2],[-1,-1],[-1,1],[1,-1],[0,1],[1,0]];t.forEach(t=>{for(var[i,r]of e){let e=this.getByMapCoords(t.rx+i,t.ry+r);e&&e.z<t.z&&e.terrainType!==TerrainType.Cliff&&e.terrainType!==TerrainType.Rough&&0===e.rampType&&(e.landType=LandType.Rock)}})}}getTileRadarColor(e){let t=this.tileSets.getTileImage(e.tileNum,e.subTile,()=>0);return t.radarLeft.clone().multiplyScalar(.5)}getAll(){return[...this.tiles]}forEach(i){for(let e=0,t=this.tiles.length;e<t;++e)i(this.tiles[e],e)}reduce(t,e){let i=e;return this.forEach(e=>{i=t(i,e)}),i}getMinTileHeight(){return this.minTileHeight}getMaxTileHeight(){return this.maxTileHeight}getCutoffTileHeight(){return this.cutoffTileHeight}computeCutoffTileHeight(){var t=this.dSize.width-1;let i=this.dSize.height-1,r=0,s=!0;for(;s&&0<i;){for(let e=1;e<t-3;e++){var a=this.getByDisplayCoords(e,i);a&&(s=!1,a.z>r&&(r=a.z))}s&&i--}return r}getAllBridgeSetTiles(){return this.bridgeSetTiles}getAllNeighbourTiles(e){var t=e.rx,e=e.ry;return[this.getByMapCoords(t+1,e+1),this.getByMapCoords(t-1,e-1),this.getByMapCoords(t-1,e+1),this.getByMapCoords(t+1,e-1),this.getByMapCoords(t,e+1),this.getByMapCoords(t+1,e),this.getByMapCoords(t-1,e),this.getByMapCoords(t,e-1)].filter(isNotNullOrUndefined)}getNeighbourTile(e,t){var i=e.rx,r=e.ry;switch(t){case TileDirection.Bottom:return this.getByMapCoords(i+1,r+1);case TileDirection.Top:return this.getByMapCoords(i-1,r-1);case TileDirection.Left:return this.getByMapCoords(i-1,r+1);case TileDirection.Right:return this.getByMapCoords(i+1,r-1);case TileDirection.BottomLeft:return this.getByMapCoords(i,r+1);case TileDirection.BottomRight:return this.getByMapCoords(i+1,r);case TileDirection.TopLeft:return this.getByMapCoords(i-1,r);case TileDirection.TopRight:return this.getByMapCoords(i,r-1);default:throw new Error("Invalid direction")}}getByDisplayCoords(e,t){if(!(e>=this.dSize.width||t>=this.dSize.height))return this.tilesByDxy[e+t*this.dSize.width]}getByMapCoords(e,t){if(!(e>=this.rSize.width||t>=this.rSize.height))return this.tilesByRxy[e+t*this.rSize.width]}getMapSize(){return this.rSize}getDisplaySize(){return this.dSize}getInRectangle(e,t){let i,r,s,a;a=t?(i=e.rx,r=e.ry,s=t.width,t.height):(i=e.x,r=e.y,s=e.width,e.height);let n=[];for(let t=0;t<s;t++)for(let e=0;e<a;e++){var o=i+t,l=r+e,l=this.getByMapCoords(o,l);l&&n.push(l)}return n}getPlaceholderTile(e,t){var i=this.tiles[0],i=i.dx-i.rx+i.ry+1;return{rx:e,ry:t,dx:e-t+i-1,dy:e+t-i-1,z:0,id:e+"_"+t,landType:LandType.Rock,terrainType:TerrainType.Rock1,rampType:0,subTile:0,tileNum:0,occluded:!1,onBridgeLandType:void 0}}}!function(e){e[e.NotSpecial=0]="NotSpecial",e[e.Riparius=1]="Riparius",e[e.Cruentus=2]="Cruentus",e[e.Vinifera=4]="Vinifera",e[e.Aboreus=8]="Aboreus",e[e.Ore=1]="Ore",e[e.Gems=2]="Gems",e[e.All=15]="All"}(OverlayTibType=OverlayTibType||{});class OreOverlayTypes{static getOverlayTibType(e){return this.isRiparius(e)?OverlayTibType.Riparius:this.isCruentus(e)?OverlayTibType.Cruentus:this.isVinifera(e)?OverlayTibType.Vinifera:this.isAboreus(e)?OverlayTibType.Aboreus:OverlayTibType.NotSpecial}static isRiparius(e){return e>=this.minIdRiparius&&e<=this.maxIdRiparius}static isCruentus(e){return e>=this.minIdCruentus&&e<=this.maxIdCruentus}static isVinifera(e){return e>=this.minIdVinifera&&e<=this.maxIdVinifera}static isAboreus(e){return e>=this.minIdAboreus&&e<=this.maxIdAboreus}}OreOverlayTypes.minIdRiparius=102,OreOverlayTypes.maxIdRiparius=127,OreOverlayTypes.minIdCruentus=27,OreOverlayTypes.maxIdCruentus=38,OreOverlayTypes.minIdVinifera=127,OreOverlayTypes.maxIdVinifera=146,OreOverlayTypes.minIdAboreus=147,OreOverlayTypes.maxIdAboreus=166,function(e){e[e.Riparius=0]="Riparius",e[e.Cruentus=1]="Cruentus",e[e.Vinifera=2]="Vinifera",e[e.Aboreus=3]="Aboreus",e[e.Ore=0]="Ore",e[e.Gems=1]="Gems"}(TiberiumType=TiberiumType||{});class TiberiumTrait{static canBePlacedOn(e,t){return[LandType.Clear,LandType.Road,LandType.Rough].includes(e.landType)&&!t.getGroundObjectsOnTile(e).find(e=>!e.isSmudge()&&!e.isUnit())}constructor(e){this.gameObject=e}getTiberiumType(){var e=OreOverlayTypes.getOverlayTibType(this.gameObject.overlayId);switch(e){case OverlayTibType.Ore:return TiberiumType.Ore;case OverlayTibType.Gems:return TiberiumType.Gems;case OverlayTibType.Vinifera:return TiberiumType.Ore;default:throw new Error("Unsupported tiberium type "+e)}}collectBail(){var e=this.getBailCount();if(e<=0)throw new Error("Attempted to collect an ore bail, but there are none left");return this.gameObject.value--,1<e?this.getTiberiumType():void 0}spawnBails(e){this.gameObject.value=Math.min(TiberiumTrait.maxBails,this.gameObject.value+e)}removeBails(e){this.gameObject.value=Math.max(-1,this.gameObject.value-e)}getBailCount(){return this.gameObject.value+1}dispose(){this.gameObject=void 0}}TiberiumTrait.maxBails=11;class AnimTerrainEffect{destroyOre(i,r,s){if(r.landType===LandType.Tiberium&&(s.art.hasObject(i,ObjectType.Animation)?s.art.getAnimation(i):void 0)?.crater){let t=s.map.getObjectsOnTile(r).find(e=>e.isOverlay()&&e.isTiberium());if(t){r=Math.ceil(TiberiumTrait.maxBails/2),r=i.startsWith("S_CLSN")?r:s.generateRandomInt(1,r);let e=t.traits.get(TiberiumTrait);e.removeBails(r),e.getBailCount()||s.unspawnObject(t)}}}spawnSmudges(e,s,a){if(s.landType===LandType.Clear&&0===s.rampType&&a.map.mapBounds.isWithinBounds(s)&&!a.map.getObjectsOnTile(s).find(e=>!e.isUnit())){e=a.art.hasObject(e,ObjectType.Animation)?a.art.getAnimation(e):void 0;if(e?.crater){let t=e?.forceBigCraters?2:1,i=e?.scorch,r=[TileDirection.Bottom,TileDirection.BottomLeft,TileDirection.BottomRight].every(e=>a.map.tiles.getNeighbourTile(s,e));e=[...a.rules.smudgeRules.values()].filter(e=>(e.crater&&e.width===t&&e.height===t||i&&e.burn)&&!((1<e.width||1<e.height)&&!r));e.length&&(e=e[a.generateRandomInt(0,e.length-1)].name,e=a.createObject(ObjectType.Smudge,e),a.spawnObject(e,s))}}}}class ObjectAttackedEvent{constructor(e,t,i){this.target=e,this.attacker=t,this.incidental=i,this.type=EventType.ObjectAttacked}}!function(e){e[e.None=0]="None",e[e.Shrapnel=1]="Shrapnel",e[e.LightningStrike=2]="LightningStrike",e[e.TntCharge=3]="TntCharge"}(SpecialWarheadType=SpecialWarheadType||{});const ROCKING_MAX_DMG=300;class Warhead{constructor(e){this.rules=e}canDamage(e,t,i){return!(!e.isSpawned||e.isDisposed||e.isDestroyed||e.isCrashing)&&(!(e.isTechno()&&e.warpedOutTrait.isInvulnerable()&&!this.rules.temporal)&&((!e.isUnit()||!e.moveTrait.reservedPathNodes.find(e=>e.tile===t))&&(!!e.healthTrait&&((!e.isUnit()||e.zone!==ZoneType.Air||i===ZoneType.Air)&&(!(!e.isUnit()&&i===ZoneType.Air)&&((!e.isBuilding()||!e.rules.invisibleInGame)&&(!((e.isTechno()||e.isTerrain())&&e.rules.immune&&!this.rules.temporal)&&(!(e.isTechno()&&!e.rules.warpable&&this.rules.temporal)&&(!(this.rules.radiation&&(!e.isUnit()||e.rules.immuneToRadiation))&&(!(this.rules.psychicDamage&&(!e.isUnit()||e.rules.immuneToPsionics))&&(!e.isOverlay()||!BridgeOverlayTypes.isLowBridgeHead(e.overlayId))))))))))))}computeDamage(e,t,i,r=!1){let s=e;if(0<e&&t.isTechno()&&t.invulnerableTrait.isActive())return 0;if(t.isAircraft()&&t.missileSpawnTrait&&t.zone!==ZoneType.Air)return 0;if(!i.gameOpts.destroyableBridges&&t.isOverlay()&&t.bridgeTrait)return 0;if(this.rules.radiation||this.rules.temporal||!t.isInfantry()||t.stance!==StanceType.Prone||(s*=this.rules.proneDamage),t.isTechno()||t.isOverlay()||t.isTerrain()){let e=t.isTerrain()?ArmorType.Wood:t.rules.armor;t.isOverlay()&&t.isBridge()&&((i=BridgeOverlayTypes.getOverlayBridgeType(t.overlayId))===OverlayBridgeType.Wood?e=ArmorType.Wood:i===OverlayBridgeType.Concrete&&(e=ArmorType.Concrete)),r&&t.isOverlay()&&(t.isBridge()||t.rules.wall)||(s*=this.rules.verses.get(e)),0<s&&t.isTechno()&&t.veteranTrait&&(s/=t.veteranTrait.getVeteranArmorMultiplier()),0<s&&t.isUnit()&&(s/=t.crateBonuses.armor)}return(t.isOverlay()||t.isBuilding())&&t.rules.wall&&(this.rules.wallAbsoluteDestroyer?s=Number.POSITIVE_INFINITY:this.rules.wall||this.rules.wood&&t.rules.armor===ArmorType.Wood||(s=0)),t.isOverlay()&&t.isBridge()&&(this.rules.wall||(s=0)),s=0<s?Math.floor(s):Math.ceil(s),s}inflictDamage(e,t,i,r,s=!1){let a=t.healthTrait;return e===Number.POSITIVE_INFINITY&&(e=a.getHitPoints()),a.inflictDamage(e,i,r),r.traits.filter(NotifyAttack_NotifyAttack).forEach(e=>{e[NotifyAttack_NotifyAttack.onAttack](t,i?.obj,r)}),t.onAttack(r,i),r.events.dispatch(new ObjectAttackedEvent(t,i,s)),t.isTechno()&&!this.rules.temporal&&this.supressOrScatterTarget(t,r),!a.health&&(t.isInfantry()&&(t.infDeathType=this.rules.infDeath),this.rules.temporal&&(t.deathType=DeathType.Temporal),t.isUnit()&&t.crashableTrait&&t.zone===ZoneType.Air&&!this.rules.temporal?t.crashableTrait.crash(i):r.destroyObject(t,i,void 0,s),!0)}supressOrScatterTarget(e,t){e.rules.fraidycat||e.isVehicle()&&!e.owner.isCombatant()&&e.rules.insignificant?e.unitOrderTrait.hasTasks()||(e.isInfantry()&&(e.isPanicked=!0),e.unitOrderTrait.addTask(new ScatterTask(t)),e.isInfantry()&&e.unitOrderTrait.addTask(new CallbackTask(()=>e.isPanicked=!1).setCancellable(!1))):e.isInfantry()&&(e.moveTrait.isIdle()||e.suppressionTrait?.isSuppressed())&&e.suppressionTrait?.suppress()}createDummyWeaponInfo(){return{minRange:0,range:0,speed:Number.POSITIVE_INFINITY,type:WeaponType.Primary,rules:new WeaponRules(new IniSection("Dummy")),projectileRules:new ProjectileRules(ObjectType.Projectile,new IniSection("Dummy")),warhead:this}}detonate(r,e,t,i,s,a,n,o,l,h=SpecialWarheadType.None,c,u,d=!1){var p,g,m,y,T,f=l?.weapon??this.createDummyWeaponInfo(),v=l?.obj,b=l?.player,w=h===SpecialWarheadType.Shrapnel,S=h===SpecialWarheadType.LightningStrike,A=h===SpecialWarheadType.TntCharge,_=u?u/Coords.LEPTONS_PER_TILE:this.rules.cellSpread,O=this.rules.percentAtMax;let E=new Set,C=new Map,k=new RangeHelper(r.map.tileOccupation),P=new RadialTileFinder(r.map.tiles,r.map.mapBounds,t,{width:1,height:1},0,Math.ceil(_),()=>!0);for(;p=P.getNextTile();)for(g of r.map.getObjectsOnTile(p))if((!E.has(g)||g.isBuilding())&&(n!==CollisionType.UnderBridge||!g.isUnit()||!g.onBridge)&&!(v&&g.isTechno()&&g.rules.typeImmune&&g.owner===b&&g.name===v.name)&&(!A||g!==v)&&this.canDamage(g,p,a)&&(!g.isOverlay()||!(!n&&.1<Math.abs(g.tileElevation-i)||n===CollisionType.OnBridge&&!g.isBridge()))){let e=g.isBuilding()?p===t?0:k.distance3(p,s)/Coords.LEPTONS_PER_TILE:g.isTerrain()||g.isOverlay()?k.distance3(p,t)/Coords.LEPTONS_PER_TILE:k.distance3(g,s)/Coords.LEPTONS_PER_TILE;if(e<.001&&(e=0),!(w&&g.isInfantry()&&b)||g.owner!==b&&!r.alliances.areAllied(g.owner,b)){if(!_)if(g.isTerrain()){if(p!==t||!this.rules.wall)continue}else if(!w&&(p!==t||!g.isBuilding()&&g!==(o.obj||o.getBridge())))continue;_&&e>_||(E.add(g),C.set(g,g.isBuilding()?(C.get(g)||[]).concat(e):[e]))}}let I=!1,B;for(m of E)if(!m.isDestroyed&&!m.isCrashing){let i=this.computeDamage(e,m,r,S);if(0<e&&!this.rules.affectsAllies&&m.isTechno()&&b&&(r.alliances.areAllied(m.owner,b)||m.owner===b)&&(i=0),i)for(var N of C.get(m)){let t=i;if(0<_&&Number.isFinite(t)&&(t=lerp(t,O*t,N/_)),Math.abs(t)<1&&(!_||.25<=t/i)&&(t=+Math.sign(t)),t=0<t?Math.floor(t):Math.ceil(t),t){let e=m.healthTrait;if(t<0){if(!v)throw new Error("Expected healer object to be set");if(e.healBy(-t,v,r),100===e.health)break}else{if(m===o.obj&&N<1&&(B=m),this.rules.causesDelayKill&&m.isBuilding()&&m.delayedKillTrait&&(y=m.healthTrait.getHitPoints(),t>=y&&(t=y-1,m.delayedKillTrait.isActive()||(y=this.rules.delayKillAtMax,T=lerp(T=this.rules.delayKillFrames,y*T,N/_),m.delayedKillTrait.activate(T,l)))),this.inflictDamage(t,m,l,r,!B))break;m.isVehicle()&&this.rules.rocker&&(0<(N=clamp(i/ROCKING_MAX_DMG,0,1))&&(T=FacingUtil.fromMapCoords(m.position.getMapPosition().clone().sub(Coords.vecWorldToGround(s)))-m.direction,m.applyRocking(T,N)))}}}else m.isTechno()&&m.invulnerableTrait.isActive()&&(I=!0)}f=f.rules.radLevel;f&&_&&r.mapRadiationTrait.createRadSite(t,f,_+1);d=d?void 0:I?r.rules.audioVisual.weaponNullifyAnim:this.pickExplodeAnim(e,B,a,r,S);if(!I&&a===ZoneType.Ground){let e=new AnimTerrainEffect;d&&e.destroyOre(d,t,r),c&&e.spawnSmudges(c,t,r),d&&e.spawnSmudges(d,t,r)}r.events.dispatch(new WarheadDetonateEvent(this,s,d,S))}pickExplodeAnim(t,i,r,s,a){if(t){if(a)return s.rules.audioVisual.weatherConBoltExplosion;if(this.rules.conventional&&r===ZoneType.Water&&(!i||i.isBuilding()||i.isVehicle()&&i.submergibleTrait)){var n=s.rules.combatDamage.splashList;return n[clamp(Math.floor(t/50),0,n.length-1)]}n=this.rules.animList.length;let e;return n?(e=s.rules.combatDamage.c4Warhead===this.rules.name?n-1:this.rules.emEffect?s.generateRandomInt(0,n-1):clamp(Math.floor(t/25),0,n-1),this.rules.animList[e]):void 0}}}Warhead.SPECIAL_WARHEAD_NAME="Special",Warhead.HE_WARHEAD_NAME="HE";class FlhCoords{constructor(e){this.forward=0,this.lateral=0,this.vertical=0,e&&3===e.length&&this.fromArray(e)}fromArray(e){return this.forward=e[0],this.lateral=e[1],this.vertical=e[2],this}clone(){return new FlhCoords([this.forward,this.lateral,this.vertical])}}class WeaponFireEvent{constructor(e,t){this.weapon=e,this.gameObject=t,this.type=EventType.WeaponFire}}class WeaponTargeting{constructor(e,t,i,r,s,a){this.weaponType=e,this.projectileRules=t,this.weaponRules=i,this.warheadRules=r,this.gameObject=s,this.generalRules=a,this.targetChecks=[],this.initConditions()}initConditions(){this.projectileRules.isAntiGround||this.targetChecks.push(e=>!!e);const a=this.generalRules.prism.type;this.gameObject.name===a&&this.weaponType===WeaponType.Secondary?this.targetChecks.push((e,t,i,r,s)=>!(!s||!e?.isBuilding()||e.name!==a||e.owner!==this.gameObject.owner)):this.warheadRules.electricAssault?this.targetChecks.push((e,t,i,r,s)=>!(!r&&!s||!e?.isBuilding()||!e.overpoweredTrait||e.owner!==this.gameObject.owner)):this.weaponRules.damage<0?this.targetChecks.push((e,t,i)=>!!(e!==this.gameObject&&e?.isUnit()&&i.areFriendly(e,this.gameObject)&&e.healthTrait.health<100&&this.gameObject.isAircraft()===e.isAircraft())):(this.gameObject.rules.attackCursorOnFriendlies||this.warheadRules.bombDisarm?this.targetChecks.push((e,t,i,r,s)=>!s&&!!(!this.warheadRules.bombDisarm||e?.isTechno()&&e.tntChargeTrait?.hasCharge())):this.targetChecks.push((e,t,i,r)=>!((!r||this.warheadRules.mindControl)&&e?.isTechno()&&i.areFriendly(e,this.gameObject))),this.targetChecks.push((e,t,i)=>!(e?.isTechno()&&e.cloakableTrait?.isCloaked()&&!i.alliances.haveSharedIntel(this.gameObject.owner,e.owner))),this.weaponRules.limboLaunch&&this.targetChecks.push((e,t,i,r,s)=>!(s&&e&&(e.isVehicle()||e.isAircraft())&&e.parasiteableTrait?.isInfested())),this.warheadRules.ivanBomb&&this.targetChecks.push(e=>!(!e?.isTechno()||!e.tntChargeTrait||e.tntChargeTrait.hasCharge())),this.warheadRules.parasite&&this.targetChecks.push((e,t,i,r)=>!!(!e&&r||e?.isInfantry()||(e?.isVehicle()||e?.isAircraft())&&e.parasiteableTrait)),this.warheadRules.mindControl&&this.targetChecks.push(e=>!(!e?.isTechno()||!e.mindControllableTrait)),this.warheadRules.temporal||this.targetChecks.push((e,t,i,r,s)=>!(s&&e?.isTechno()&&e.warpedOutTrait.isInvulnerable())),this.gameObject.rules.natural&&this.targetChecks.push(e=>!e?.isTechno()||!e.rules.unnatural)),this.targetChecks.push((e,t)=>this.canTargetZone(e,t))}canTarget(t,i,r,s,a){return this.targetChecks.every(e=>e(t,i,r,s,a))}canTargetZone(e,t){let i;if(e?.isUnit()){if(e?.isInfantry()&&e.stance===StanceType.Paradrop&&2<e.tileElevation)return this.projectileRules.isAntiAir&&(this.projectileRules.isAntiGround||this.weaponType===WeaponType.Secondary);if(e.zone===ZoneType.Air)return this.projectileRules.isAntiAir;if(this.weaponType===WeaponType.Secondary&&this.projectileRules.isAntiAir&&!this.projectileRules.isAntiGround)return!1;i=e.zone}else i=t.landType===LandType.Water?ZoneType.Water:ZoneType.Ground;return i===ZoneType.Water?this.canTargetNaval(this.gameObject.rules.navalTargeting,this.gameObject,e,this.weaponType):this.canTargetLand(this.gameObject.rules.landTargeting,this.weaponType)}canTargetLand(e,t){switch(e){case LandTargeting.LandOk:return!0;case LandTargeting.LandNotOk:return!1;case LandTargeting.LandSecondary:return t===WeaponType.Secondary;default:throw new Error(`Unhandled LandTargeting value "${e}"`)}}canTargetNaval(e,t,i,r){switch(e){case NavalTargeting.UnderwaterNever:return!i||!(i.isVehicle()&&i.submergibleTrait?.isSubmerged());case NavalTargeting.UnderwaterSecondary:return i&&i.isVehicle()&&i.submergibleTrait&&!t.rules.spawned?r===WeaponType.Secondary:r===WeaponType.Primary;case NavalTargeting.UnderwaterOnly:return!!(i&&i.isVehicle()&&i.submergibleTrait);case NavalTargeting.OrganicSecondary:return i?.isTechno()&&i.rules.organic?r===WeaponType.Secondary:r===WeaponType.Primary;case NavalTargeting.SealSpecial:return i?.isTechno()&&i.rules.naval&&!i.rules.organic&&(i.isBuilding()||i.rules.speedType===SpeedType.Float)?r===WeaponType.Secondary:r===WeaponType.Primary;case NavalTargeting.NavalAll:return!0;case NavalTargeting.NavalNone:return!1;default:throw new Error(`Unhandled NavalTargeting value "${e}"`)}}}const ARCING_PROJECTILE_SPEED=50,BOMBER_BURST=5,NON_FIGHTER_BURST=2,FIGHTER_BURST=1;class Weapon{static factory(e,t,i,r,s){var a=r.getWeapon(e);let n=a.warhead;n===Warhead.SPECIAL_WARHEAD_NAME&&(n=Weapon.findSpecialWarheadName(a,i,r));var o=new Warhead(r.getWarhead(n)),e=r.getProjectile(a.projectile),r=new WeaponTargeting(t,e,a,o.rules,i,r.general);return new this(t,i,a,o,e,s||new FlhCoords,r)}static findSpecialWarheadName(e,t,i){let r;if(!e.spawner)throw new Error(`Weapon "${e.name} can't use "Special" warhead without Spawner=yes`);if(t.rules.spawns===i.general.v3Rocket.type)r=i.combatDamage.v3Warhead;else if(t.rules.spawns===i.general.dMisl.type)r=i.combatDamage.dMislWarhead;else{if(!t.rules.spawns)throw new Error(`Can't use "Special" warhead on unit type "${t.name}" without "Spawns"`);t=i.getObject(t.rules.spawns,ObjectType.Aircraft);if(!t.primary)throw new Error(`Spawned unit "${t.name}" doesn't have a primary weapon`);r=i.getWeapon(t.primary).warhead}return r}static computeSpeed(e,t){return t.arcing?.75*ObjectRules.iniSpeedToLeptonsPerTick(ARCING_PROJECTILE_SPEED,100):!t.rot||t.inviso||e.isLaser||e.isElectricBolt?Number.POSITIVE_INFINITY:e.speed}constructor(e,t,i,r,s,a,n){this.type=e,this.gameObject=t,this.rules=i,this.warhead=r,this.projectileRules=s,this.flh=a,this.targeting=n,this.cooldownTicks=0,this.burstsLeft=0,this.burstIndex=0,this.useBurstDelay=!1,this.lateralMuzzleMult=1,this.distributedFireAngle=t.rules.distributedFire&&t.rules.radialFireSegments?-90:0}get name(){return this.rules.name}get minRange(){return this.rules.minimumRange}get range(){return this.gameObject.isBuilding()&&!this.gameObject.overpoweredTrait&&this.type===WeaponType.Secondary&&this.gameObject.primaryWeapon?Math.min(this.gameObject.primaryWeapon.rules.range,this.rules.range):this.rules.range}get speed(){return Weapon.computeSpeed(this.rules,this.projectileRules)}get rof(){let e=this.rules.rof;return this.gameObject.isBuilding()&&this.gameObject.garrisonTrait?.isOccupied()&&(e/=this.gameObject.garrisonTrait.units.length),this.gameObject.veteranTrait&&(e*=this.gameObject.veteranTrait.getVeteranRofMultiplier()),Math.floor(e)}getCooldownTicks(){return this.cooldownTicks}expireCooldown(){this.cooldownTicks=0}resetCooldown(){this.cooldownTicks=this.rof}hasBurstsLeft(){return 0<this.burstsLeft}resetBursts(){this.burstsLeft=0,this.burstIndex=0,this.resetCooldown(),this.gameObject.ammoTrait&&0<this.gameObject.ammoTrait.ammo&&this.gameObject.ammoTrait.ammo--}tick(){0<this.cooldownTicks&&this.cooldownTicks--}getBurstsFired(){return this.burstIndex}fire(s,a,n=1){let o=this.gameObject,e,t=0;if(!o.airSpawnTrait||!this.rules.spawner||(e=o.airSpawnTrait.prepareLaunch(o,s,a),t=o.airSpawnTrait.availableSpawns,e)){this.burstsLeft?(this.burstsLeft--,this.burstIndex++,this.lateralMuzzleMult*=-1):(this.useBurstDelay=!1,this.burstIndex=0,e?this.burstsLeft=t:this.gameObject.isAircraft()?this.burstsLeft=this.projectileRules.iniRot<=1?BOMBER_BURST-1:this.gameObject.rules.fighter?FIGHTER_BURST-1:NON_FIGHTER_BURST-1:(this.burstsLeft=this.rules.burst-1,this.useBurstDelay=!0),this.lateralMuzzleMult=1),0<this.burstsLeft&&(e&&0<t?this.cooldownTicks=this.rules.iniSpeed:this.gameObject.isAircraft()?this.cooldownTicks=this.rules.rof:this.cooldownTicks=this.useBurstDelay&&void 0!==this.gameObject.rules.burstDelay[this.burstIndex]?this.gameObject.rules.burstDelay[this.burstIndex]:a.generateRandomInt(3,5)),this.burstsLeft||this.resetBursts(),this.rules.limboLaunch&&(a.limboObject(this.gameObject,{selected:a.getUnitSelection().isSelected(this.gameObject),controlGroup:a.getUnitSelection().getOrCreateSelectionModel(this.gameObject).getControlGroupNumber()}),this.warhead.rules.parasite&&(s.obj?.isVehicle()||s.obj?.isAircraft())&&s.obj.parasiteableTrait&&(s.obj.parasiteableTrait.beingBoarded=!0));let i=e??a.createProjectile(this.projectileRules.name,this.gameObject,this,s,!1);i.isAircraft()||(i.baseDamageMultiplier=n*(this.gameObject.isUnit()?this.gameObject.crateBonuses.firepower:1));let r=this.flh.clone();r.lateral*=this.lateralMuzzleMult;var l=o.position.getMapPosition();if(a.map.isWithinHardBounds(l)){i.position.moveToLeptons(l),i.position.tileElevation=o.position.tileElevation;let e=new Vector2(r.lateral,r.forward);n=this.getMuzzleFacing()+this.distributedFireAngle;e=rotateVec2(e,n);var l=rotateVec2(l=new Vector2(0,o.art.turretOffset),o.direction);e.add(l),o.rules.radialFireSegments&&o.rules.distributedFire&&(l=Math.floor(180/o.rules.radialFireSegments),this.distributedFireAngle=(this.distributedFireAngle+l+90)%180-90),i.direction=n,o.isBuilding()&&o.rules.turretAnim&&(h=Coords.screenDistanceToWorld(o.rules.turretAnimX,o.rules.turretAnimY),n=o.getFoundationCenterOffset(),i.position.moveByLeptons(-n.x+h.x,-n.y+h.y));let t=new Vector3_Vector3(e.x,r.vertical,-e.y);var h=t.clone().add(i.position.worldPosition);if(a.map.isWithinHardBounds(h)&&i.position.moveByLeptons3(t),i.tileElevation<0&&(i.position.tileElevation=0),i.isAircraft()?a.unlimboObject(i,i.position.tile):a.spawnObject(i,i.position.tile),this.rules.revealOnFire&&s.obj?.isTechno()){let e=a.mapShroudTrait.getPlayerShroud(s.obj.owner);e?.isShrouded(o.tile,o.tileElevation)&&e.revealTemporarily(o)}this.rules.decloakToFire&&this.gameObject.cloakableTrait?.uncloak(a),a.events.dispatch(new WeaponFireEvent(this,this.gameObject))}else e&&(e.owner.removeOwnedObject(e),e.dispose())}}getMuzzleFacing(){let e=this.gameObject,t;return t=!e.isInfantry()&&!e.isAircraft()&&(e.isBuilding()||e.isVehicle())&&e.turretTrait?e.turretTrait.facing:e.direction,t}}Weapon.NUKE_PAYLOAD_NAME="NukePayload";class NukeEffect extends SuperWeaponEffect{constructor(e,t,i,r){super(e,t,i),this.weaponType=r}onStart(t){var i=t.rules.getWeapon(this.weaponType),r=t.createTarget(void 0,this.tile),s=this.owner.getOwnedObjectsByType(ObjectType.Building).find(e=>e.rules.nukeSilo);if(s){let e=Weapon.factory(i.name,WeaponType.Primary,s,t.rules);e.fire(r,t)}else this.fireLooseNuke(i,r,t)}fireLooseNuke(t,i,r){var s=new Vector2(this.tile.rx+.5,this.tile.ry+.5).multiplyScalar(Coords.LEPTONS_PER_TILE);if(r.map.isWithinHardBounds(s)){let e=r.createLooseProjectile(t.name,this.owner,i);e.position.moveToLeptons(s),e.position.tileElevation=Coords.worldToTileHeight(e.rules.detonationAltitude),r.spawnObject(e,e.position.tile)}}onTick(e){return!0}}class LightningStormCloudEvent{constructor(e){this.position=e,this.type=EventType.LightningStormCloud}}class LightningStormManifestEvent{constructor(e){this.target=e,this.type=EventType.LightningStormManifest}}!function(e){e[e.Approaching=0]="Approaching",e[e.Manifesting=1]="Manifesting"}(State=State||{});class LightningStormEffect extends SuperWeaponEffect{constructor(){super(...arguments),this.state=State.Approaching,this.clouds=[]}onStart(e){e=e.rules.general.lightningStorm;this.manifestStartTimer=e.deferment,this.manifestEndTimer=e.duration,this.nextDirectHitTimer=0,this.nextRandomHitTimer=0}onTick(t){if(this.state===State.Approaching&&(0<this.manifestStartTimer?this.manifestStartTimer--:(this.state=State.Manifesting,t.events.dispatch(new LightningStormManifestEvent(this.tile)))),this.state===State.Manifesting){var i,s=t.rules.general.lightningStorm;if(0<this.manifestEndTimer&&(this.manifestEndTimer--,0<this.nextDirectHitTimer&&this.nextDirectHitTimer--,this.nextDirectHitTimer<=0&&(this.nextDirectHitTimer=s.hitDelay,this.spawnCloudAt(this.tile,t)),0<this.nextRandomHitTimer&&this.nextRandomHitTimer--,this.nextRandomHitTimer<=0)){this.nextRandomHitTimer=s.scatterDelay;var a=Math.floor(s.cellSpread/2);let i=s.separation,r=new RangeHelper(t.map.tileOccupation),e=new RandomTileFinder(t.map.tiles,t.map.mapBounds,this.tile,a,t,t=>!this.clouds.some(e=>r.tileDistance(t,e.tile)<i),!1);a=e.getNextTile();a&&this.spawnCloudAt(a,t)}for(i of this.clouds.slice())if(0<i.ticksLeft){if(i.ticksLeft--,i.ticksLeft===Math.floor(i.durationTicks/2)){var r=s.warhead;let e=new Warhead(t.rules.getWarhead(r));var n=i.tile,o=t.map.tileOccupation.getBridgeOnTile(n),l=o?.tileElevation??0,r=t.map.getTileZone(n);e.detonate(t,s.damage,n,l,Coords.tile3dToWorld(n.rx+.5,n.ry+.5,n.z+l),r,o?CollisionType.OnBridge:CollisionType.None,t.createTarget(o,n),{player:this.owner,weapon:void 0},SpecialWarheadType.LightningStrike)}}else this.clouds.splice(this.clouds.indexOf(i),1);if(!this.clouds.length&&this.manifestEndTimer<=0)return!0}return!1}spawnCloudAt(e,t){var i=t.rules.audioVisual.weatherConClouds,i=t.generateRandomInt(0,i.length-1);let r=t.art.getAnimation(t.rules.audioVisual.weatherConClouds[i]);i=r.art.getNumber("Rate",60*GameSpeed.BASE_TICKS_PER_SECOND)/60,i=Math.floor(GameSpeed.BASE_TICKS_PER_SECOND/i*60);this.clouds.push({tile:e,durationTicks:i,ticksLeft:i});i=(t.map.tileOccupation.getBridgeOnTile(e)?.tileElevation??0)+Coords.worldToTileHeight(t.rules.general.flightLevel),i=Coords.tile3dToWorld(e.rx+.5,e.ry+.5,e.z+i);t.events.dispatch(new LightningStormCloudEvent(i))}}class IronCurtainEffect extends SuperWeaponEffect{onStart(e){var t,i,r=e.rules.combatDamage.ironCurtainDuration,s={player:this.owner};let a=new RadialTileFinder(e.map.tiles,e.map.mapBounds,this.tile,{width:1,height:1},0,1,()=>!0);for(;t=a.getNextTile();)for(i of e.map.getGroundObjectsOnTile(t))!i.isTechno()||i.isUnit()&&i.tile!==t||i.rules.missileSpawn||(i.rules.organic?i.isDestroyed||e.destroyObject(i,s):(i.invulnerableTrait.setActiveFor(r,e.currentTick),(i.isVehicle()||i.isAircraft())&&i.parasiteableTrait?.isInfested()&&i.parasiteableTrait.destroyParasite(s,e)))}onTick(e){return!0}}class ChronoSphereEffect extends SuperWeaponEffect{constructor(e,t,i,r){super(e,t,i),this.tile2=r,this.objectsToTeleport=[]}onStart(i){this.delayTicks=i.rules.general.chronoDelay;let r=i.map.tiles;for(let t=-1;t<=1;t++)for(let e=-1;e<=1;e++){var s=r.getByMapCoords(this.tile.rx+t,this.tile.ry+e);if(s){var a,n=!!s.onBridgeLandType,o=r.getByMapCoords(this.tile2.rx+t,this.tile2.ry+e);for(a of i.map.getGroundObjectsOnTile(s))!a.isUnit()||a.tile!==s||a.onBridge!==n||a.isInfantry()&&a.stance===StanceType.Paradrop&&2<a.tileElevation||a.isDisposed||a.invulnerableTrait.isActive()||(a.rules.organic&&!a.rules.teleporter||!o?i.destroyObject(a,{player:this.owner}):a.warpedOutTrait.isActive()||(a.warpedOutTrait.setActive(!0,!0,i),this.objectsToTeleport.push({obj:a,destTile:o})))}}}onTick(c){if(0<this.delayTicks&&this.delayTicks--,this.delayTicks)return!1;for(let{obj:l,destTile:h}of this.objectsToTeleport)if(l.isSpawned){let i=!1,r=h?c.map.tileOccupation.getBridgeOnTile(h):void 0,s=c.map.getGroundObjectsOnTile(h),a=s.find(e=>e.isBuilding());var u=s.some(e=>c.rules.general.padAircraft.includes(e.name)),t=c.rules.general.padAircraft.includes(l.name)&&!!a?.helipadTrait&&!!a.dockTrait?.getAllDockTiles().includes(h)&&!a.dockTrait.hasReservedDockAt(a.dockTrait.getDockNumberByTile(h))&&a.owner===l.owner;let e=!1,n=l.rules.speedType,o=l.isInfantry();l.rules.movementZone===MovementZone.Fly&&(n=SpeedType.Wheel);var d=c.map.mapBounds.isWithinBounds(h);if(!(t||c.map.terrain.getPassableSpeed(h,n,o,!!r)&&d)){let t=!1;if(!u&&(0<c.map.terrain.getPassableSpeed(h,n,o,!!r,void 0,!0)||!d)){a&&(i=!0);let e=new RadialTileFinder(c.map.tiles,c.map.mapBounds,h,{width:1,height:1},1,15,e=>0<c.map.terrain.getPassableSpeed(e,n,o,!!e.onBridgeLandType)&&!c.map.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},l).length);d=e.getNextTile();d&&(h=d,r=c.map.tileOccupation.getBridgeOnTile(h),s=c.map.getGroundObjectsOnTile(h),t=!0)}t||(l.moveTrait.teleportUnitToTile(h,r,!0,!1,c),l.warpedOutTrait.setActive(!1,!0,c),c.map.getTileZone(h)===ZoneType.Water&&(l.deathType=DeathType.Sink),c.destroyObject(l,{player:this.owner}),e=!0)}for(let t of s)t.isDisposed||t.isUnit()&&(this.objectsToTeleport.some(({obj:e})=>e===t)||t.onBridge!==!!r&&t.tile===h||2<Math.abs(t.tileElevation-l.tileElevation)||(t.isInfantry()&&t.stance!==StanceType.Paradrop&&(t.deathType=DeathType.Crush),c.destroyObject(t,{player:this.owner,obj:l})));if(!e){if(l.moveTrait.teleportUnitToTile(h,r,!0,!1,c),t&&a?.dockTrait){t=a.dockTrait.getAllDockTiles().indexOf(h);if(a.dockTrait.undockUnitAt(t),a.dockTrait.hasReservedDockAt(t))throw new Error("Target building dock is already reserved by another unit");a.dockTrait.dockUnitAt(l,t)}i?l.warpedOutTrait.setTimed(c.rules.general.chronoDelay,!1,c):l.warpedOutTrait.setActive(!1,!0,c)}}return!0}}(NotifySuperWeaponDeactivate=NotifySuperWeaponDeactivate||{}).onDeactivate=Symbol();class SuperWeaponsTrait{constructor(){this.effects=[]}[NotifyTick.onTick](i){for(var e of i.getCombatants()){var t;for(t of e.superWeaponsTrait.getAll())t.update(i)}for(let t of this.effects)t.status===EffectStatus.NotStarted&&(t.onStart(i),t.status=EffectStatus.Running),t.onTick(i)&&(t.status=EffectStatus.Finished,i.traits.filter(NotifySuperWeaponDeactivate).forEach(e=>{e[NotifySuperWeaponDeactivate.onDeactivate](t.type,t.owner,i)}));this.effects=this.effects.filter(e=>e.status!==EffectStatus.Finished)}[NotifyPower.onPowerLow](e,t){e.superWeaponsTrait?.getAll()?.filter(e=>e.rules.isPowered).forEach(e=>{this.updateTimer(e,!1)})}[NotifyPower.onPowerRestore](e,t){e.superWeaponsTrait?.getAll()?.filter(e=>e.rules.isPowered).forEach(e=>{this.updateTimer(e,!0)})}[NotifyPower.onPowerChange](e,t){}[NotifyWarpChange.onChange](e,t){var i;e.owner.powerTrait&&e.isBuilding()&&e.superWeaponTrait&&((i=e.superWeaponTrait.getSuperWeapon(e))&&this.updateTimer(i,!e.owner.powerTrait.isLowPower()))}updateTimer(e,t){var i=this.superWeaponHasValidBuilding(e);t&&i?e.resumeTimer():e.pauseTimer()}superWeaponHasValidBuilding(t){return[...t.owner.buildings].find(e=>!(e.superWeaponTrait?.getSuperWeapon(e)!==t||e.warpedOutTrait.isActive()&&t.rules.isPowered))}addEffect(e){this.effects.push(e)}activateSuperWeapon(t,e,i,r,s){let a=e.superWeaponsTrait?.getAll().find(e=>e.rules.type===t);if(a&&a.status===SuperWeaponStatus.Ready){if(a.oneTimeOnly){e.superWeaponsTrait.remove(a.name);for(var n of e.buildings)n.rules.superWeapon===a.name&&n.superWeaponTrait&&n.superWeaponTrait.addSuperWeaponToPlayerIfNeeded(e,i)}else a.resetTimer();this.activateEffect(a.rules,e,i,r,s)}}activateEffect(e,i,r,s,a,n=!1){const o=e.type;if(void 0!==o){let t=[];switch(o){case SuperWeaponType.AmerParaDrop:for(var[l,h]of r.rules.general.paradrop.amerParaDrop.entries())r.rules.hasObject(h.inf,ObjectType.Infantry)?t.push(new ParadropEffect(o,i,s,h,l)):console.warn(`Can't paradrop unknown infantry type "${h.inf}"`);break;case SuperWeaponType.ParaDrop:{let e=r.rules.general.paradrop.getParadropSquads(i.country.side);for(var[c,u]of e.entries())r.rules.hasObject(u.inf,ObjectType.Infantry)?t.push(new ParadropEffect(o,i,s,u,c)):console.warn(`Can't paradrop unknown infantry type "${u.inf}"`);break}case SuperWeaponType.MultiMissile:if(!e.weaponType)throw new Error("Missing WeaponType in super weapon rules");t.push(new NukeEffect(o,i,s,e.weaponType));break;case SuperWeaponType.LightningStorm:t.push(new LightningStormEffect(o,i,s));break;case SuperWeaponType.IronCurtain:t.push(new IronCurtainEffect(o,i,s));break;case SuperWeaponType.ChronoSphere:if(!a)throw new Error("Missing tile2 action param");t.push(new ChronoSphereEffect(o,i,s,a))}for(var d of t)this.addEffect(d);r.traits.filter(NotifySuperWeaponActivate).forEach(e=>{e[NotifySuperWeaponActivate.onActivate](o,i,r,s,a)}),r.events.dispatch(new SuperWeaponActivateEvent(o,i,s,a,n))}}}class ObjectCloakChangeEvent{constructor(e){this.target=e,this.type=EventType.ObjectCloakChange}}(NotifyDamage=NotifyDamage||{}).onDamage=Symbol();class CloakableTrait{constructor(e,t){this.gameObject=e,this.cloakDelayMinutes=t,this.isActive=!1,this.resetCloakCooldown()}isCloaked(){return this.isActive}uncloak(e){var t=this.isActive;this.resetCloakCooldown(),t&&(this.isActive=!1,e.events.dispatch(new ObjectCloakChangeEvent(this.gameObject)))}resetCloakCooldown(){this.cooldownTicks=Math.floor(60*this.cloakDelayMinutes*GameSpeed.BASE_TICKS_PER_SECOND)}[NotifySpawn.onSpawn](e,t){this.resetCloakCooldown()}[NotifyTick_NotifyTick.onTick](e,t){0<this.cooldownTicks&&this.cooldownTicks--,!(this.cooldownTicks<=0)||this.isActive||e.isVehicle()&&e.submergibleTrait&&!e.submergibleTrait.isSubmerged()||e.temporalTrait.getTarget()||(this.isActive=!0,t.events.dispatch(new ObjectCloakChangeEvent(this.gameObject)))}[NotifyDamage.onDamage](e,t){this.uncloak(t)}dispose(){this.gameObject=void 0}}class OreSpread{static calculateOverlayId(e,t){if(e!==OverlayTibType.NotSpecial){var i=t.dx,t=t.dy,i=Math.floor((t-9)/2%12*((t-8)/2%12)%12-(i-13)/2%12*((i-12)/2%12)%12+12e4);return i%=12,e===OverlayTibType.Ore?OreOverlayTypes.minIdRiparius+i:e===OverlayTibType.Gems?OreOverlayTypes.minIdCruentus+i:e===OverlayTibType.Vinifera?OreOverlayTypes.minIdVinifera+i:e===OverlayTibType.Aboreus?OreOverlayTypes.minIdAboreus+i:void 0}}}var SequenceType,LightingType,PowerLevel,QueueType,QueueStatus,AttackState,NotifySell,LayerType,NotifyWarpChange_NotifyWarpChange,NotifyProduceUnit,FactoryStatus,NotifyBuildStatus,RepairStatus,ShroudType,ShroudFlag,BuildStatus,NotifyOrder,OrderType,HarvesterStatus,NotifyHeal,ProjectileState,DeployFireState,NotifyHealthChange,NotifyHealthChange_NotifyHealthChange,HealthLevel,SpawnStatus,NotifyTargetDestroy,BridgeHeadType,Box2_THREE=__webpack_require__(70);class Box2 extends Box2_THREE.Box2{}const EDGE_SPAWN_CHANCE=2/3,WATER_MAP_EDGE_SPAWN_CHANCE=1/3,UNSUPPORTED_POWERUP_TYPES=[PowerupType.IonStorm,PowerupType.Gas,PowerupType.Pod,PowerupType.Squad];class CrateGeneratorTrait{constructor(e){this.randomCrateSpawn=e,this.crates=[],this.availEdgeTiles=[],this.allTiles=[]}init(n){var o=n.map.tiles.getMapSize();let l=n.map.tiles,e=[],h=0;for(let a=0;a<o.width;++a){let t,i,r=!1,s=!1;for(let e=0;e<o.height;++e){var c=l.getByMapCoords(a,e);if(c&&this.canPlaceCrateOnTile(n,c)){var u=n.map.getTileZone(c)===ZoneType.Water;t?(u||(i=c),s=u):u?r=s=!0:t=i=c}else if(t&&!c)break}t&&(e.push(t),i&&i!==t&&e.push(i),r||s||h++)}this.availEdgeTiles=e,this.allTiles=l.getAll(),this.mapEdgeIsWater=0===h,this.minCrates=n.rules.crateRules.crateMinimum*n.gameOpts.humanPlayers.filter(e=>e.countryId!==OBS_COUNTRY_ID).length}[NotifyTick.onTick](t){for(var e of this.crates)e.ticksLeft--,e.ticksLeft<=0&&(t.unspawnObject(e.obj),e.obj.dispose());if(this.crates=this.crates.filter(e=>0<e.ticksLeft),this.randomCrateSpawn)for(let e=0;e<this.minCrates-this.crates.length&&this.spawnCrateAtRandom(this.allTiles,t);e++);}spawnCrateAtRandom(e,t){e=this.chooseSpawnTile(e,t);if(e)return this.spawnRandomCrateAt(e,t)}spawnRandomCrateAt(e,t){if(this.canPlaceCrateOnTile(t,e)){var i=t.map.getTileZone(e,!0)===ZoneType.Water,i=this.choosePowerup(i,t.rules.powerups.powerups,t);if(i)return this.spawnCrateAt(e,i,t)}}spawnCrateAt(t,i,r){if(this.canPlaceCrateOnTile(r,t)){var s=r.map.getTileZone(t,!0)===ZoneType.Water,a=r.rules.crateRules,s=s?a.waterCrateImg:a.crateImg;let e=r.createObject(ObjectType.Overlay,s);e.overlayId=r.rules.getOverlayId(s),e.value=0,r.spawnObject(e,t);r=60*a.crateRegen*GameSpeed.BASE_TICKS_PER_SECOND*(.5+1.5*r.generateRandom());return this.crates.push({obj:e,powerup:i,ticksLeft:r}),e}}chooseSpawnTile(e,t){return t.generateRandom()<(this.mapEdgeIsWater?WATER_MAP_EDGE_SPAWN_CHANCE:EDGE_SPAWN_CHANCE)&&this.availEdgeTiles.length&&(e=this.availEdgeTiles),this.chooseRandomTile(e,t)}chooseRandomTile(e,t){let i;let r=0;for(;i=e[t.generateRandomInt(0,e.length-1)],r++,r<100&&!this.canPlaceCrateOnTile(t,i););if(100<=r){var s=t.map.tileOccupation.getEmptyTiles();if(!s.length)return;i=s[t.generateRandomInt(0,s.length-1)]}return i}canPlaceCrateOnTile(e,t){return e.map.mapBounds.isWithinBounds(t)&&!e.map.getGroundObjectsOnTile(t).length&&0<e.map.terrain.getPassableSpeed(t,SpeedType.Amphibious,!1,!1)&&t.terrainType!==TerrainType.Shore&&0===t.rampType}choosePowerup(t,i,r){if((i=t?i.filter(e=>e.waterAllowed):i).length){var s,t=i.reduce((e,t)=>e+t.probShares,0),a=r.generateRandomInt(0,t);let e=0;for(s of i)if(e+=s.probShares,a<e)return s}}peekInsideCrate(t){return this.crates.find(e=>e.obj===t)?.powerup.type}pickupCrate(e,t,i){let r=this.crates.find(e=>e.obj===t);if(r){this.crates.splice(this.crates.indexOf(r),1),i.unspawnObject(r.obj),r.obj.dispose();let t=this.grantPowerup(e,r.powerup,r.obj.tile,i);var s;return void 0!==t&&(e.owner.cratesPickedUp++,s=i.rules.powerups.powerups.find(e=>e.type===t),i.events.dispatch(new CratePickupEvent(s,e.owner,e,r.obj.tile))),this.randomCrateSpawn&&this.spawnCrateAtRandom(this.allTiles,i),t}}grantPowerup(t,i,r,s){let a=t.owner,n=!1;if(a.isCombatant()){if(i.type===PowerupType.Unit){let e;if(![...a.buildings].some(e=>e.rules.constructionYard)&&s.rules.crateRules.freeMCV){let t=s.rules.general.baseUnit;if(!a.getOwnedObjects(!0).some(e=>t.includes(e.name))&&a.credits>=[...s.rules.ai.buildPower,...s.rules.ai.buildRefinery].map(e=>s.rules.getBuilding(e)).filter(e=>e.aiBasePlanningSide===a.country.side).reduce((e,t)=>e+t.cost,0)){var o=t.find(e=>{let t=s.rules.getObject(e,ObjectType.Vehicle);return t.isAvailableTo(a.country)&&t.hasOwner(a.country)});if(!o)throw new Error("No suitable MCV found for player country "+a.country?.name);e=s.rules.getObject(o,ObjectType.Vehicle)}}if(e||(o=(o=s.rules.crateRules.unitCrateType)?s.rules.hasObject(o,ObjectType.Vehicle)?[s.rules.getObject(o,ObjectType.Vehicle)]:[]:[...s.rules.vehicleRules.values()].filter(e=>e.crateGoodie&&0<s.map.terrain.getPassableSpeed(r,e.speedType,!1,!1))).length&&(e=o[s.generateRandomInt(0,o.length-1)]),e){let t=s.createUnitForPlayer(e,a);var l=new RadialTileFinder(s.map.tiles,s.map.mapBounds,r,{width:1,height:1},0,3,e=>0<s.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)&&!s.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length).getNextTile();l?(s.spawnObject(t,l),n=!0):(a.removeOwnedObject(t),t.dispose())}}else if(i.type===PowerupType.Money){if(!i.data)throw new Error("Money powerup missing data field");l=Math.floor(Number(i.data)*(.55+2*s.generateRandom()*.45));a.credits=Math.max(0,a.credits+l),0<l&&(a.creditsGained+=l),n=!0}else if(i.type===PowerupType.HealBase){var e;for(e of a.getOwnedObjects(!0))e.isDestroyed||e.healthTrait.healToFull(void 0,s);n=!0}else if(i.type===PowerupType.Reveal)s.mapShroudTrait.revealMap(a,s),n=!0;else if(i.type===PowerupType.Darkness)s.mapShroudTrait.resetShroud(a,s),n=!0;else if(i.type===PowerupType.Veteran){if(t.veteranTrait&&!t.veteranTrait.isMaxLevel()){n=!0;var h,c=Number(i.data);for(h of this.getUnitsInCrateRadius(s,r,a))h.veteranTrait?.promote(c,s)}}else if(i.type===PowerupType.Armor){if(1===t.crateBonuses.armor){n=!0;var u,d=Number(i.data);for(u of this.getUnitsInCrateRadius(s,r,a))1===u.crateBonuses.armor&&(u.crateBonuses.armor=d)}}else if(i.type===PowerupType.Firepower){if(1===t.crateBonuses.firepower){n=!0;var p,g=Number(i.data);for(p of this.getUnitsInCrateRadius(s,r,a))1===p.crateBonuses.firepower&&(p.crateBonuses.firepower=g)}}else if(i.type===PowerupType.Speed){if(1===t.crateBonuses.speed){n=!0;var m,y=Number(i.data);for(m of this.getUnitsInCrateRadius(s,r,a))1===m.crateBonuses.speed&&(m.crateBonuses.speed=y)}}else if(i.type===PowerupType.Cloak){if(!t.cloakableTrait){n=!0;for(var T of this.getUnitsInCrateRadius(s,r,a))T.cloakableTrait||(T.cloakableTrait=new CloakableTrait(T,s.rules.general.cloakDelay),s.addObjectTrait(T,T.cloakableTrait))}}else if(i.type===PowerupType.ICBM){var f=[...s.rules.superWeaponRules.values()].find(e=>e.type===SuperWeaponType.MultiMissile);if(f&&a.superWeaponsTrait&&!a.superWeaponsTrait.has(f.name)){let e=s.createSuperWeapon(f.name,a,!0);e.isGift=!0,a.superWeaponsTrait.add(e),n=!0}}else if(i.type===PowerupType.Invulnerability){var v=[...s.rules.superWeaponRules.values()].find(e=>e.type===SuperWeaponType.IronCurtain);v&&(s.traits.get(SuperWeaponsTrait).activateEffect(v,a,s,r,void 0,!0),n=!0)}else if(i.type===PowerupType.Explosion||i.type===PowerupType.Napalm){n=!0;f=Number(i.data),v=i.type===PowerupType.Napalm?s.rules.combatDamage.flameDamage:s.rules.combatDamage.c4Warhead;let e=new Warhead(s.rules.getWarhead(v));e.detonate(s,f,t.tile,t.tileElevation,t.position.worldPosition,t.zone,CollisionType.None,s.createTarget(t,t.tile),{player:t.owner,weapon:void 0},SpecialWarheadType.None,void 0,0)}else{if(i.type!==PowerupType.Tiberium)return void console.warn(`Unhandled powerup type "${PowerupType[i.type]}"`);{let e=new RandomTileFinder(s.map.tiles,s.map.mapBounds,r,2,s,e=>TiberiumTrait.canBePlacedOn(e,s.map)),t,i=0;for(;i++<6&&(t=e.getNextTile());){var b=OreSpread.calculateOverlayId(OverlayTibType.Ore,t);if(void 0===b)throw new Error("Expected an overlayId");let e=s.createObject(ObjectType.Overlay,s.rules.getOverlayName(b));e.overlayId=b,e.value=3,s.spawnObject(e,t),n=!0}}}if(n)return i.type;i=s.rules.powerups.powerups.find(e=>e.type===PowerupType.Money&&0<e.probShares);return i?this.grantPowerup(t,i,r,s):void 0}}getUnitsInCrateRadius(e,t,i){let r=e.rules.crateRules.crateRadius,s=new RangeHelper(e.map.tileOccupation);return e.map.technosByTile.queryRange((new Box2).setFromCenterAndSize(new Vector2(t.rx,t.ry),new Vector2(r,r))).filter(e=>e.owner===i&&e.isUnit()&&s.tileDistance(e,t)<=r)}}class PowerupsRules{constructor(){this.powerups=[]}readIni(e){for(var[s,a]of e.entries){let[e,t,i,r]=a.split(",");var n=Number(e),a=PowerupType[s];void 0!==a?UNSUPPORTED_POWERUP_TYPES.includes(a)||this.powerups.push({type:a,probShares:n,animName:"<none>"!==t.toLowerCase()?t:void 0,waterAllowed:"yes"===i,data:r}):console.warn(`Unknown powerup "${s}". Skipping.`)}return this}}const mpAllowedColors=["Gold","DarkRed","DarkBlue","DarkGreen","Orange","DarkSky","Purple","Magenta"];class Rules{constructor(e,t){this.ini=e,this.logger=t,this.buildingTypes=new Map,this.vehicleTypes=new Map,this.infantryTypes=new Map,this.aircraftTypes=new Map,this.terrainTypes=new Map,this.overlayTypes=new Map,this.overlayIdsByType=new Map,this.animationTypes=new Map,this.animationNames=new Set,this.voxelAnimTypes=new Map,this.smudgeTypes=new Map,this.warheadTypes=new Map,this.tiberiumTypes=new Map,this.superWeaponTypes=new Map,this.countryTypes=new Map,this.weaponTypes=new Map,this.allObjectRules=new Map,this.buildingRules=new Map,this.infantryRules=new Map,this.vehicleRules=new Map,this.aircraftRules=new Map,this.terrainRules=new Map,this.overlayRules=new Map,this.smudgeRules=new Map,this.voxelAnimRules=new Map,this.countryRules=new Map,this.warheadRules=new Map,this.powerups=new PowerupsRules,this.colors=new Map,this.general=new GeneralRules,this.ai=new AiRules,this.crateRules=new CrateRules,this.elevationModel=new ElevationModelRules,this.mpDialogSettings=new MpDialogSettings,this.audioVisual=new AudioVisualRules,this.combatDamage=new CombatDamageRules,this.radiation=new RadiationRules,this.landRules=new Map,this.tiberiumRules=new Map,this.superWeaponRules=new Map,this.cachedWeaponRules=new Map,this.cachedProjectileRules=new Map,this.init()}hasObject(e,t){return this.allObjectRules.get(t)?.has(e)}getObject(e,t){t=this.allObjectRules.get(t)?.get(e);if(!t)throw new Error(`Missing rules for object "${e}"`);return t}getTechnoByInternalId(e,t){let i;if(t===ObjectType.Building)i=this.buildingTypes.get(e);else if(t===ObjectType.Infantry)i=this.infantryTypes.get(e);else if(t===ObjectType.Vehicle)i=this.vehicleTypes.get(e);else{if(t!==ObjectType.Aircraft)throw new Error(`Type ${ObjectType[t]} is not a techno type`);i=this.aircraftTypes.get(e)}if(void 0===i)throw new Error(`Object type "${ObjectType[t]}" with ID "${e}" not found`);return this.getObject(i,t)}getBuilding(e){var t=this.buildingRules.get(e);if(!t)throw new Error(`Missing rules for building "${e}"`);return t}getWeapon(e){let t=this.cachedWeaponRules.get(e);if(!t){var i=this.ini.getSection(e);if(!i)throw new Error(`Weapon ${e} is missing ini section`);t=new WeaponRules(i),this.cachedWeaponRules.set(e,t)}return t}getWeaponByInternalId(e){var t=this.weaponTypes.get(e);if(!t)throw new RangeError(`Weapon with internal ID "${e}" not found`);return this.getWeapon(t)}getWarhead(t){let i=t.toLowerCase(),r=this.warheadRules.get(i);if(!r){let e=this.ini.getSection(t);if(!e&&(e=this.ini.getOrderedSections().find(e=>e.name.toLowerCase()===i),!e))throw new Error("Unknown warhead "+t);r=new WarheadRules(e),this.warheadRules.set(i,r)}return r}getProjectile(t){let i=t.toLowerCase(),r=this.cachedProjectileRules.get(i);if(!r){let e=this.ini.getSection(t);if(!e&&(e=this.ini.getOrderedSections().find(e=>e.name.toLowerCase()===i),!e))throw new Error(`Projectile ${t} is missing ini section`);r=new ProjectileRules(ObjectType.Projectile,e),this.cachedProjectileRules.set(i,r)}return r}getOverlayName(e){var t=this.overlayTypes.get(e);if(!t)throw new Error("Invalid overlay id "+e);return t}hasOverlayId(e){return this.overlayTypes.has(e)}getOverlayId(e){var t=this.overlayIdsByType.get(e);if(void 0===t)throw new Error("Invalid overlay name "+e);return t}getOverlay(e){var t=this.overlayRules.get(e);if(!t)throw new Error(`Missing rules for overlay "${e}"`);return t}getAnimationName(e){return this.animationTypes.get(e)}getCountry(e){if(!this.countryRules.has(e))throw new Error("Unknown country "+e);return this.countryRules.get(e)}getMultiplayerCountries(){return[...this.countryRules.values()].filter(e=>e.multiplay)}getMultiplayerColors(){let t=new Map;return mpAllowedColors.forEach(e=>{if(!this.colors.has(e))throw new Error(`Multiplayer color "${e}" does not exist in the rules [Colors] section.`);t.set(e,this.colors.get(e))}),t}getLandRules(e){let t=this.landRules.get(e);var i;return t||(i=e===LandType.Cliff?"Rock":LandType[e],t=(new LandRules).readIni(this.ini.getOrCreateSection(i)),this.landRules.set(e,t)),t}getTiberium(e){var t=this.tiberiumTypes.get(e);if(!t)throw new Error("Unknown tiberium type "+e);return this.tiberiumRules.get(t)}getSuperWeapon(e){if(!this.superWeaponRules.has(e))throw new Error(`Unknown superweapon type "${e}"`);return this.superWeaponRules.get(e)}getIni(){return this.ini}applySpecialFlags(e){e.initialVeteran&&(this.general.veteran.initialVeteran=!0)}init(){this.readAudioVisual(),this.readCombatDamage(),this.readRadiation(),this.readGeneral(),this.readAi(),this.readCrateRules(),this.readElevationModel(),this.readMpDialogSettings(),this.readObjectTypes("BuildingTypes",this.buildingTypes),this.readObjectTypes("InfantryTypes",this.infantryTypes),this.readObjectTypes("VehicleTypes",this.vehicleTypes),this.readObjectTypes("AircraftTypes",this.aircraftTypes),this.readObjectTypes("TerrainTypes",this.terrainTypes),this.readObjectTypes("SmudgeTypes",this.smudgeTypes),this.readObjectTypes("Animations",this.animationTypes),this.animationNames=new Set(this.animationTypes.values()),this.readObjectTypes("VoxelAnims",this.voxelAnimTypes),this.readObjectTypes("OverlayTypes",this.overlayTypes),this.overlayTypes.forEach((e,t)=>this.overlayIdsByType.set(e,t)),this.readColors(),this.readObjectTypes("Countries",this.countryTypes),this.readObjectTypes("Warheads",this.warheadTypes),this.readObjectTypes("Tiberiums",this.tiberiumTypes),this.readObjectTypes("SuperWeaponTypes",this.superWeaponTypes),this.allObjectRules.set(ObjectType.Building,this.buildingRules).set(ObjectType.Infantry,this.infantryRules).set(ObjectType.Vehicle,this.vehicleRules).set(ObjectType.Aircraft,this.aircraftRules).set(ObjectType.Terrain,this.terrainRules).set(ObjectType.Overlay,this.overlayRules).set(ObjectType.Smudge,this.smudgeRules).set(ObjectType.VoxelAnim,this.voxelAnimRules),this.readObjects(ObjectType.Building,this.buildingTypes,this.buildingRules),this.readObjects(ObjectType.Infantry,this.infantryTypes,this.infantryRules),this.readObjects(ObjectType.Vehicle,this.vehicleTypes,this.vehicleRules),this.readObjects(ObjectType.Aircraft,this.aircraftTypes,this.aircraftRules),this.readObjects(ObjectType.Terrain,this.terrainTypes,this.terrainRules),this.readObjects(ObjectType.Overlay,this.overlayTypes,this.overlayRules),this.readObjects(ObjectType.Smudge,this.smudgeTypes,this.smudgeRules),this.readObjects(ObjectType.VoxelAnim,this.voxelAnimTypes,this.voxelAnimRules),this.readCountries(),this.readWarheads(),this.readPowerups(),this.readTiberiums(),this.readSuperWeapons(),this.buildWeaponsList()}readAudioVisual(){var e=this.ini.getSection("AudioVisual");if(!e)throw new Error("Missing [AudioVisual] section");this.audioVisual.readIni(e)}readCombatDamage(){var e=this.ini.getSection("CombatDamage");if(!e)throw new Error("Missing [CombatDamage] section");this.combatDamage.readIni(e)}readRadiation(){var e=this.ini.getSection("Radiation");if(!e)throw new Error("Missing [Radiation] section");this.radiation.readIni(e)}readGeneral(){var e=this.ini.getSection("General");if(!e)throw new Error("Missing [General] section");this.general.readIni(e)}readAi(){var e=this.ini.getSection("AI");if(!e)throw new Error("Missing [AI] section");this.ai.readIni(e)}readCrateRules(){var e=this.ini.getSection("CrateRules");if(!e)throw new Error("Missing [CrateRules] section");this.crateRules.readIni(e)}readElevationModel(){var e=this.ini.getSection("ElevationModel");if(!e)throw new Error("Missing [ElevationModel] section");this.elevationModel.readIni(e)}readMpDialogSettings(){var e=this.ini.getSection("MultiplayerDialogSettings");if(!e)throw new Error("Missing [MultiplayerDialogSettings] section");this.mpDialogSettings.readIni(e)}readObjectTypes(i,r){let e=this.ini.getSection(i);if(!e)throw new Error(`Missing [${i}] section`);let s=0,a=new Set;e.entries.forEach((e,t)=>{"string"==typeof e?Number.isNaN(Number(t))?this.logger?.debug(`Non-numeric id "${t}" found in rules section [${i}]. Skipping.`):a.has(e)?this.logger?.debug(`Duplicate type "${e}" in rules section [${i}]. Skipping.`):(r.set(s++,e),a.add(e)):this.logger?.debug(`Non-string type found in rules section [${i}]. Skipping.`)})}readColors(){let e=this.ini.getSection("Colors");if(!e)throw new Error("Missing [Colors] section");e.entries.forEach((e,t)=>{var[i,r,e]=e.split(","),e=Color.fromHsv(parseInt(i,10),parseInt(r,10),parseInt(e,10));this.colors.set(t,e)})}readObjects(r,e,s){e.forEach((e,t)=>{var i=this.ini.getSection(e);i?(t=(new ObjectRulesFactory).create(r,i,this.general,t),s.set(e,t)):this.logger?.debug(ObjectType[r]+` type "${e}" has no rules section`)})}readCountries(){this.countryTypes.forEach((e,t)=>{var i=this.ini.getSection(e);if(!i)throw new Error("Missing ini section for country "+e);let r=new CountryRules(t);r.readIni(i),this.countryRules.set(e,r)})}readWarheads(){this.warheadTypes.forEach(e=>{var t=this.ini.getSection(e);t?(t=new WarheadRules(t),this.warheadRules.set(e.toLowerCase(),t)):this.logger?.debug(`Warhead "${e}" has no rules section`)})}readPowerups(){var e=this.ini.getSection("Powerups");if(!e)throw new Error("Missing [Powerups] section");this.powerups.readIni(e)}readTiberiums(){this.tiberiumTypes.forEach(e=>{var t=this.ini.getSection(e);if(!t)throw new Error("Missing rules section for tiberium type "+e);this.tiberiumRules.set(e,(new TiberiumRules).readIni(t))})}readSuperWeapons(){this.superWeaponTypes.forEach((e,t)=>{var i=this.ini.getSection(e);if(!i)throw new Error("Missing rules section for superweapon type "+e);this.superWeaponRules.set(e,new SuperWeaponRules(t).readIni(i))})}buildWeaponsList(){let e=new Set;e.add(this.general.dropPodWeapon);for(var t of this.superWeaponRules.values())t.weaponType&&e.add(t.weaponType);var r,i;e.add(Weapon.NUKE_PAYLOAD_NAME);for(let i of[...this.buildingRules.values(),...this.aircraftRules.values(),...this.vehicleRules.values(),...this.infantryRules.values()])for(r of[i.deathWeapon,i.primary,i.secondary,i.elitePrimary,i.eliteSecondary,i.occupyWeapon,i.eliteOccupyWeapon,...i.weaponCount?new Array(i.weaponCount).fill(0).map((e,t)=>[i.getWeaponAtIndex(t),i.getEliteWeaponAtIndex(t)]).flat():[]].filter(isNotNullOrUndefined).filter(e=>""!==e))e.add(r);let s=0;for(i of e)this.weaponTypes.set(s++,i)}}!function(e){e[e.Ready=0]="Ready",e[e.Guard=1]="Guard",e[e.Prone=2]="Prone",e[e.Walk=3]="Walk",e[e.FireUp=4]="FireUp",e[e.Down=5]="Down",e[e.Crawl=6]="Crawl",e[e.Up=7]="Up",e[e.FireProne=8]="FireProne",e[e.Idle1=9]="Idle1",e[e.Idle2=10]="Idle2",e[e.Die1=11]="Die1",e[e.Die2=12]="Die2",e[e.Hover=13]="Hover",e[e.Fly=14]="Fly",e[e.FireFly=15]="FireFly",e[e.Tumble=16]="Tumble",e[e.AirDeathStart=17]="AirDeathStart",e[e.AirDeathFalling=18]="AirDeathFalling",e[e.AirDeathFinish=19]="AirDeathFinish",e[e.Tread=20]="Tread",e[e.Swim=21]="Swim",e[e.WetAttack=22]="WetAttack",e[e.WetIdle1=23]="WetIdle1",e[e.WetIdle2=24]="WetIdle2",e[e.WetDie1=25]="WetDie1",e[e.WetDie2=26]="WetDie2",e[e.Deploy=27]="Deploy",e[e.Deployed=28]="Deployed",e[e.DeployedFire=29]="DeployedFire",e[e.DeployedIdle=30]="DeployedIdle",e[e.Undeploy=31]="Undeploy",e[e.Paradrop=32]="Paradrop",e[e.Cheer=33]="Cheer",e[e.Panic=34]="Panic"}(SequenceType=SequenceType||{});const facingByCardinal=new Map([["E",5],["S",3],["W",1],["N",7]]);class SequenceReader{readIni(e){let t=new Map;for(var[i,r]of e.entries){i=SequenceType[i];void 0!==i&&(r=r.split(","),r={type:i,startFrame:Number(r[0]),frameCount:Number(r[1]),facingMult:Number(r[2]),onlyFacing:r[3]?facingByCardinal.get(r[3]):void 0},t.set(i,r))}return t}}!function(e){e[e.None=0]="None",e[e.Global=1]="Global",e[e.Level=2]="Level",e[e.Ambient=3]="Ambient",e[e.Full=4]="Full",e[e.Default=5]="Default"}(LightingType=LightingType||{});class ObjectArt{static getDefaultPalette(e){switch(e){case ObjectType.Building:case ObjectType.Aircraft:case ObjectType.Infantry:case ObjectType.Vehicle:case ObjectType.Projectile:case ObjectType.VoxelAnim:return PaletteType.Unit;case ObjectType.Overlay:return PaletteType.Overlay;case ObjectType.Smudge:case ObjectType.Terrain:return PaletteType.Iso;default:ObjectType.Animation;return PaletteType.Anim}}static getDefaultLighting(e){switch(e){case ObjectType.Animation:return LightingType.None;case ObjectType.Aircraft:case ObjectType.Building:case ObjectType.Infantry:case ObjectType.Vehicle:return LightingType.Ambient;case ObjectType.Projectile:case ObjectType.VoxelAnim:return LightingType.Global;case ObjectType.Overlay:case ObjectType.Smudge:case ObjectType.Terrain:default:return LightingType.Full}}static getDefaultRemapability(e){switch(e){case ObjectType.Aircraft:case ObjectType.Building:case ObjectType.Infantry:case ObjectType.Vehicle:return!0;case ObjectType.Overlay:case ObjectType.Smudge:case ObjectType.Terrain:case ObjectType.Animation:case ObjectType.Projectile:case ObjectType.VoxelAnim:return!1;default:throw new Error("Unknown object type "+e)}}static getDefaultDrawOffset(e){switch(e){case ObjectType.Animation:case ObjectType.Building:case ObjectType.Vehicle:case ObjectType.Infantry:case ObjectType.Overlay:case ObjectType.Smudge:case ObjectType.Projectile:case ObjectType.VoxelAnim:return new Vector2(0,0);case ObjectType.Terrain:case ObjectType.Aircraft:return new Vector2(0,(Coords.ISO_TILE_SIZE+1)/2);default:throw new Error("Unknown object type "+e)}}static getDefaultShadow(e){switch(e){case ObjectType.Overlay:case ObjectType.Building:case ObjectType.Infantry:case ObjectType.Terrain:case ObjectType.Vehicle:case ObjectType.Aircraft:return!0;default:case ObjectType.Smudge:case ObjectType.Animation:case ObjectType.Projectile:case ObjectType.VoxelAnim:return!1}}static getDefaultHeight(e){switch(e){case ObjectType.Building:return 2;case ObjectType.Infantry:case ObjectType.Vehicle:case ObjectType.Aircraft:return 1;default:return 0}}static factory(e,t,i,r){let s=new this(e,t,r);return e===ObjectType.Infantry&&(!(r=r.getString("Sequence"))||(r=i.getSection(r))&&(s.sequences=(new SequenceReader).readIni(r))),s}constructor(e,t,i){this.sequences=new Map,this.dockingOffsets=[],this.type=e,this.rules=t,this.art=i,this.init()}init(){this.image=[ObjectType.Infantry,ObjectType.Vehicle,ObjectType.Aircraft].includes(this.type)?"":this.art.getString("Image"),this.report=this.art.getString("Report")||void 0,this.readRotors(),this.noHva=this.art.getBool("NoHVA"),this.startSound=this.art.getString("StartSound")||void 0,this.readMuzzleFlash(),this.readPaletteAndLightingTypes(),this.readRemapability(),this.readFlatness(),this.readDockingOffsets();var e=this.art.getNumberArray("QueueingCell");this.queueingCell=e.length?new Vector2(e[0],e[1]):void 0,this.demandLoad=this.art.getBool("DemandLoad");var t=this.art.getBool("UseLineTrail"),i=this.art.getNumberArray("LineTrailColor"),e=this.art.getNumber("LineTrailColorDecrement",ObjectArt.DEFAULT_LINE_TRAIL_DEC);t&&i.length?(this.useLineTrail=!0,this.lineTrailColor=i,this.lineTrailColorDecrement=e):this.useLineTrail=!1,this.crater=this.art.getBool("Crater"),this.forceBigCraters=this.art.getBool("ForceBigCraters"),this.scorch=this.art.getBool("Scorch"),this.height=this.art.getNumber("Height",ObjectArt.getDefaultHeight(this.type)),this.isVoxel=this.art.getBool("Voxel"),this.occupyHeight=this.art.getNumber("OccupyHeight",this.height),this.type===ObjectType.Building?this.canHideThings=this.art.getBool("CanHideThings",!0):this.canHideThings=!1,this.canBeHidden=this.art.getBool("CanBeHidden",!0),this.addOccupy=this.readAddRemoveOccupy("AddOccupy"),this.removeOccupy=this.readAddRemoveOccupy("RemoveOccupy"),this.rotates=this.art.getBool("Rotates")}get imageName(){return(this.image||this.rules.imageName)+(this.rules.alternateArcticArt?"A":"")}get cameo(){let e=this.art.getString("Cameo")||ObjectArt.MISSING_CAMEO;return e.toLowerCase()}get altCameo(){let e=this.art.getString("AltCameo")||this.cameo;return e.toLowerCase()}get useTheaterExtension(){return this.art.getBool("Theater")}readPaletteAndLightingTypes(){this.paletteType=PaletteType.Default,this.lightingType=LightingType.Default,(this.rules instanceof OverlayRules?this.rules.noUseTileLandType:void 0)&&(this.paletteType=PaletteType.Iso,this.lightingType=LightingType.Full),this.art.getBool("TerrainPalette")||this.art.getBool("ShouldUseCellDrawer")?this.paletteType=PaletteType.Iso:this.art.getBool("AnimPalette")?(this.paletteType=PaletteType.Anim,this.lightingType=LightingType.None):this.art.getString("Palette")&&(this.paletteType=PaletteType.Custom,this.customPaletteName=this.art.getString("Palette")),this.art.getBool("AltPalette")&&(this.paletteType=PaletteType.Unit),(this.rules instanceof OverlayRules||this.rules instanceof TechnoRules)&&this.rules.wall&&(this.paletteType=PaletteType.Unit,this.lightingType=LightingType.Ambient),(this.rules instanceof TerrainRules||this.rules instanceof TechnoRules)&&this.rules.gate&&(this.paletteType=PaletteType.Unit),this.rules instanceof TerrainRules&&this.rules.spawnsTiberium&&(this.paletteType=PaletteType.Unit,this.lightingType=LightingType.None),this.rules instanceof OverlayRules&&(this.rules.isVeins&&(this.paletteType=PaletteType.Unit,this.lightingType=LightingType.None),this.rules.isVeinholeMonster&&(this.paletteType=PaletteType.Unit,this.lightingType=LightingType.None),this.rules.tiberium&&(this.lightingType=LightingType.None),this.rules.land===LandType.Railroad&&(this.paletteType=PaletteType.Iso,this.lightingType=LightingType.Full),this.rules.crate&&(this.paletteType=PaletteType.Iso,this.lightingType=LightingType.Full)),this.paletteType===PaletteType.Default&&(this.paletteType=ObjectArt.getDefaultPalette(this.type)),this.lightingType===LightingType.Default&&(this.lightingType=ObjectArt.getDefaultLighting(this.type))}readRemapability(){this.remapable=ObjectArt.getDefaultRemapability(this.type),this.art.getBool("TerrainPalette")||this.art.getBool("AnimPalette")?this.remapable=!1:this.rules instanceof ProjectileRules&&this.rules.firersPalette&&(this.remapable=!0)}readFlatness(){let e=!1;this.type===ObjectType.Building||this.type===ObjectType.Animation?e=this.art.getBool("Flat"):this.type===ObjectType.Smudge&&(e=!0),this.rules instanceof OverlayRules&&(this.rules.wall||this.rules.crate||this.rules.isARock||(e=!0)),this.flat=e}readRotors(){var i=this.art.getArray("Rotors");if(i.length){let t=[];for(let e=0;e<i.length;++e){var r=this.art.getNumberArray(`Rotor${e+1}Axis`,void 0,[0,1,0]),r=new Vector3_Vector3(-r[2],-r[0],r[1]).normalize();t.push({name:i[e],axis:r,speed:this.art.getNumber(`Rotor${e+1}Rate`)||void 0,idleSpeed:this.art.getNumber(`Rotor${e+1}IdleRate`)||void 0})}t.length&&(this.rotors=t)}}readMuzzleFlash(){let e=0,t="MuzzleFlash"+e,i=[];for(;this.art.has(t);){var[r,s]=this.art.getNumberArray(t);i.push({x:r,y:s}),e++,t="MuzzleFlash"+e}this.muzzleFlash=i.length?i:void 0}readDockingOffsets(){if(this.type===ObjectType.Building){var t=this.rules.numberOfDocks;for(let e=0;e<t;e++){var[i,r,s]=this.art.getNumberArray("DockingOffset"+e,/,\s*/,[0,0,0]);this.dockingOffsets.push(new Vector3_Vector3(i,s,r))}}}readAddRemoveOccupy(e){let t=0,i=[];for(;;){var r=this.art.getNumberArray(e+ ++t);if(!r.length)break;i.push(new Vector2(r[0],r[1]))}return i}get bibShape(){return this.art.getString("BibShape")}get foundation(){let e=this.art.getString("Foundation","1x1");var[t,i]=e.split(/x/i);return{width:parseInt(t,10),height:parseInt(i,10)}}get foundationCenter(){return new Vector2(Math.floor(this.foundation.width/2-.5),Math.floor(this.foundation.height/2-.5))}getDrawOffset(){if(this.rules instanceof TerrainRules&&this.rules.spawnsTiberium)return new Vector2(0,0);let e=ObjectArt.getDefaultDrawOffset(this.type);return this.rules instanceof OverlayRules&&this.rules.isARock&&(e.y+=(Coords.ISO_TILE_SIZE+1)/2),e}get hasShadow(){return this.art.getBool("Shadow",ObjectArt.getDefaultShadow(this.type))&&!this.rules.noShadow}get turretOffset(){return this.art.getNumber("TurretOffset")}get facings(){return this.art.getNumber("Facings",8)}get walkFrames(){return this.art.getNumber("WalkFrames")}get firingFrames(){return this.art.getNumber("FiringFrames")}get standingFrames(){return this.art.getNumber("StandingFrames",1)}get startWalkFrame(){return this.art.getNumber("StartWalkFrame",0)}get startStandFrame(){return this.art.getNumber("StartStandFrame",this.walkFrames*this.facings)}get startFiringFrame(){return this.art.getNumber("StartFiringFrame",(this.walkFrames+this.standingFrames)*this.facings)}get isFlamingGuy(){return this.art.getBool("IsFlamingGuy")}get runningFrames(){return this.art.getNumber("RunningFrames")}get crawls(){return this.art.getBool("Crawls",!0)}get primaryFireFlh(){return new FlhCoords(this.art.getNumberArray("PrimaryFireFLH"))}get elitePrimaryFireFlh(){var e=this.art.getNumberArray("ElitePrimaryFireFLH");return e.length?new FlhCoords(e):this.primaryFireFlh}get primaryFirePixelOffset(){return this.art.getNumberArray("PrimaryFirePixelOffset")}get secondaryFirePixelOffset(){return this.art.getNumberArray("SecondaryFirePixelOffset")}get secondaryFireFlh(){return new FlhCoords(this.art.getNumberArray("SecondaryFireFLH"))}get eliteSecondaryFireFlh(){var e=this.art.getNumberArray("EliteSecondaryFireFLH");return e.length?new FlhCoords(e):this.secondaryFireFlh}getSpecialWeaponFlh(e){return new FlhCoords(this.art.getNumberArray(`Weapon${e+1}FLH`))}get fireUp(){return this.art.getNumber("FireUp")||this.art.getNumber("DelayedFireDelay")}get isAnimDelayedFire(){return this.art.getBool("IsAnimDelayedFire")}get zShapePointMove(){return this.art.getNumberArray("ZShapePointMove")}get zAdjust(){return this.art.getNumber("ZAdjust")}get trailer(){return this.art.getString("Trailer")}get spawnDelay(){return this.art.getNumber("SpawnDelay",1)}get translucent(){return this.art.getBool("Translucent")}get translucency(){var e=(e=this.art.getNumber("Translucency",0))/25*25;return e/=100}}ObjectArt.DEFAULT_LINE_TRAIL_DEC=16,ObjectArt.MISSING_CAMEO="xxicon";class Art{constructor(e,t,i,r){this.rules=e,this.artIni=t,this.mapFile=i,this.logger=r,this.objectArt=new Map,this.parse()}hasObject(e,t){return this.objectArt.get(t)?.has(e)}getObject(e,t){if(!e)throw new Error(`Must specify an art name for type "${ObjectType[t]}"`);var i=this.objectArt.get(t)?.get(e);return i||(this.logger?.debug(`Missing art for object "${e}"`),new ObjectArt(t,this.rules.hasObject(e,t)?this.rules.getObject(e,t):new ObjectRules(t,new IniSection(e)),new IniSection(e)))}getAnimation(e){return this.getObject(e,ObjectType.Animation)}getProjectile(e){var t=this.rules.getProjectile(e),i=t.imageName;let r=this.artIni.getSection(i);return r||(this.logger?.debug(`Image ${i} (Projectile: ${e}) has no section in art.ini`),r=new IniSection(i)),ObjectArt.factory(t.type,t,this.artIni,r)}getIni(){return this.artIni}parse(){this.rules.allObjectRules.forEach((e,t)=>{let r=new Map;this.objectArt.set(t,r),e.forEach(e=>{var t=this.artIni.getSection(e.imageName),i=this.artIni.getSection(e.name);(t=this.applyUnitMapOverrides(e,this.mapFile,i,t))?(t=ObjectArt.factory(e.type,e,this.artIni,t),r.set(e.name,t)):this.logger?.debug(`${ObjectType[e.type]} "${e.name}" has no art section "${e.imageName}"`)})});let e=[[ObjectType.Animation,this.rules.animationNames]];e.forEach(([r,e])=>{let s=new Map;this.objectArt.set(r,s),e.forEach(e=>{var t,i=this.artIni.getSection(e);i?(t=new ObjectRules(r,new IniSection(e)),i=new ObjectArt(r,t,i),s.set(e,i)):this.logger?.debug(ObjectType[r]+` "${e}" has no art section`)})})}applyUnitMapOverrides(e,t,r,s){if([ObjectType.Infantry,ObjectType.Vehicle,ObjectType.Aircraft].includes(e.type)&&!!t?.getSection(e.name)?.getString("Image")&&r){let i=r.clone();s?.entries.forEach((e,t)=>{i.set(t,e)}),s=i,this.logger?.debug(`${ObjectType[e.type]} "${e.name}": `+`Using merged art sections ${e.name} and `+e.imageName)}return s}}class Country{static factory(e,t){return new this(t.getCountry(e))}constructor(e){this.rules=e}get id(){return this.rules.id}get side(){return this.rules.side}get name(){return this.rules.name}isPlayable(){return this.rules.multiplay&&!this.rules.multiplayPassive}hasVeteranUnit(e,t){let i=[];switch(e){case ObjectType.Aircraft:i=this.rules.veteranAircraft;break;case ObjectType.Infantry:i=this.rules.veteranInfantry;break;case ObjectType.Vehicle:i=this.rules.veteranUnits;break;default:throw new Error(`Unsupported object type "${ObjectType[e]}"`)}return i.includes(t)}}class BuildingEvacuateEvent{constructor(e,t){this.target=e,this.player=t,this.type=EventType.BuildingEvacuate}}class GarrisonTrait{constructor(e,t,i){this.building=e,this.evacThreshold=t,this.maxOccupants=i,this.units=[]}isOccupied(){return!!this.units.length}canBeOccupied(){return this.building.healthTrait.health>100*this.evacThreshold}[NotifyDamage.onDamage](e,t){e.healthTrait.health<=100*this.evacThreshold&&this.evacuate(t)}[NotifyDestroy.onDestroy](e,t,i,r){if(r){for(var s of this.units)s.deathType=e.deathType,t.destroyObject(s,i,!0);this.units=[]}else this.evacuate(t)}getHash(){return fnv32a(this.units.map(e=>e.getHash()))}debugGetState(){return{units:this.units.map(e=>e.debugGetState())}}dispose(){this.building=void 0}evacuate(r,s=!1){let a=this.building,n=this.units;if(n.length){let e=new Map;for(var t of n)e.set(t.rules.speedType,(e.get(t.rules.speedType)||[]).concat(t));for(let[t,i]of e){var o,l=new RadialTileFinder(r.map.tiles,r.map.mapBounds,a.tile,a.art.foundation,1,1,e=>0<r.map.terrain.getPassableSpeed(e,t,!0,!1)&&Math.abs(e.z-a.tile.z)<2&&!r.map.terrain.findObstacles({tile:e,onBridge:void 0},i[0]).length).getNextTile();for(o of i){var h=n.indexOf(o);l?(n.splice(h,1),r.unlimboObject(o,l),o.onBridge=r.map.tileOccupation.getBridgeOnTile(l)?.isLowBridge()??!1,o.position.tileElevation=0,o.unitOrderTrait.addTask(new ScatterTask(r))):s||(r.destroyObject(o,{player:o.owner}),n.splice(h,1))}}var i=a.owner;n.length||a.isDestroyed||r.changeObjectOwner(a,r.getCivilianPlayer()),r.events.dispatch(new BuildingEvacuateEvent(a,i))}}}class TurretTrait{constructor(){this.facing=0,this.desiredFacing=0}isRotating(){return this.facing!==this.desiredFacing}[NotifySpawn.onSpawn](e){e.isUnit()&&(this.facing=this.desiredFacing=e.direction)}[NotifyTick_NotifyTick.onTick](e){this.desiredFacing!==this.facing&&(e=e.rules.rot,this.facing=FacingUtil.tick(this.facing,this.desiredFacing,e||Number.POSITIVE_INFINITY).facing)}}class BuildStatusChangeEvent{constructor(e,t){this.target=e,this.status=t,this.type=EventType.BuildStatusChange}}class PowerLowEvent{constructor(e){this.target=e,this.type=EventType.PowerLow}}class PowerRestoreEvent{constructor(e){this.target=e,this.type=EventType.PowerRestore}}class PowerChangeEvent{constructor(e,t,i){this.target=e,this.power=t,this.drain=i,this.type=EventType.PowerChange}}!function(e){e[e.Low=0]="Low",e[e.Normal=1]="Normal"}(PowerLevel=PowerLevel||{});class PowerTrait{constructor(e){this.player=e,this.power=0,this.drain=0,this.level=PowerLevel.Normal,this.blackoutFrames=0,this.powerByObject=new Map}isLowPower(){return this.level===PowerLevel.Low}setBlackoutFor(e,t){var i=0<this.blackoutFrames;this.blackoutFrames=e,i||this.updateLevel(t)}updateBlackout(e){0<this.blackoutFrames&&(this.blackoutFrames--,this.blackoutFrames<=0&&this.updateLevel(e))}getBlackoutDuration(){return this.blackoutFrames}updateFrom(t,i,r){var s=t.rules.power;if(s){if(s<0)"add"!==i&&"remove"!==i||(this.drain+="add"===i?-s:s);else{let e=0;if("add"===i){var a=Math.ceil(s*t.healthTrait.health/100);this.powerByObject.set(t,a),e=a}else if("update"===i||"remove"===i){a=this.powerByObject.get(t);if(void 0===a)throw new Error("Cannot update power before add.");e="update"===i?(s=Math.ceil(s*t.healthTrait.health/100),this.powerByObject.set(t,s),s-a):(this.powerByObject.delete(t),-a)}this.power+=e}this.updateLevel(r),r.traits.filter(NotifyPower).forEach(e=>{e[NotifyPower.onPowerChange](this.player,r)}),r.events.dispatch(new PowerChangeEvent(this.player,this.power,this.drain))}}updateLevel(t){var e=this.level;this.level=this.power>=this.drain&&!this.blackoutFrames?PowerLevel.Normal:PowerLevel.Low,this.level!==e&&(e===PowerLevel.Normal&&this.level===PowerLevel.Low&&(t.traits.filter(NotifyPower).forEach(e=>{e[NotifyPower.onPowerLow](this.player,t)}),t.events.dispatch(new PowerLowEvent(this.player))),e===PowerLevel.Low&&this.level===PowerLevel.Normal&&(t.traits.filter(NotifyPower).forEach(e=>{e[NotifyPower.onPowerRestore](this.player,t)}),t.events.dispatch(new PowerRestoreEvent(this.player))))}getHash(){return fnv32a([this.power,this.drain])}debugGetState(){return{power:this.power,drain:this.drain}}dispose(){this.player=void 0,this.powerByObject.clear()}}class PoweredTrait{constructor(e){this.obj=e,this.turnedOn=!0}setTurnedOn(e){this.turnedOn=e}isCharged(){return!!this.obj.isBuilding()&&!!this.obj.overpoweredTrait?.hasChargersToPowerOn()}isPoweredOn(e=!1){return!(!this.obj||!this.turnedOn)&&(!(e||!this.isCharged())||(!this.obj.rules.power&&this.obj.rules.needsEngineer?!this.obj.owner.isNeutral:!!this.obj.owner.powerTrait&&this.obj.owner.powerTrait?.level!==PowerLevel.Low))}dispose(){this.obj=void 0}}class EventDispatcher{constructor(){this.listeners=new Set}subscribe(e){this.listeners.add(e)}subscribeOnce(i){let r=(e,t)=>{i(e,t),this.unsubscribe(r),r=void 0};this.subscribe(r)}unsubscribe(e){this.listeners.delete(e)}dispatch(t,i){this.listeners.forEach(e=>e(i,t))}asEvent(){return this}}!function(e){e[e.Structures=0]="Structures",e[e.Armory=1]="Armory",e[e.Infantry=2]="Infantry",e[e.Vehicles=3]="Vehicles",e[e.Aircrafts=4]="Aircrafts",e[e.Ships=5]="Ships"}(QueueType=QueueType||{}),function(e){e[e.Idle=0]="Idle",e[e.Active=1]="Active",e[e.OnHold=2]="OnHold",e[e.Ready=3]="Ready"}(QueueStatus=QueueStatus||{});class ProductionQueue{get onUpdate(){return this._onUpdate.asEvent()}constructor(e,t,i){this.type=e,this._maxSize=t,this.maxItemQuantity=i,this.items=[],this.size=0,this._status=QueueStatus.Idle,this._onUpdate=new EventDispatcher}get status(){return this._status}set status(e){var t=this._status;(this._status=e)!==t&&this._onUpdate.dispatch(this)}get maxSize(){return this._maxSize}set maxSize(e){var t=this.size;this.size=Math.min(e,this.size);let i=0,r=0;for(;i<=this.size&&r<this.items.length;){let e=this.items[r];i+=e.quantity,i>this.size&&(e.quantity-=i-this.size),0<e.quantity&&r++}this._maxSize=e,this.items[r]&&this.items.splice(r),t!==this.size&&(this.size||(this._status=QueueStatus.Idle),this._onUpdate.dispatch(this))}get currentSize(){return this.size}find(t){return this.items.filter(e=>e.rules===t)}getFirst(){return this.items[0]}getAll(){return[...this.items]}push(e,t,i){t=Math.min(this.maxSize-this.size,t);var r=this.find(e).reduce((e,t)=>e+t.quantity,0);(t=Math.min(this.maxItemQuantity-r,t))&&(this.items[this.items.length-1]?.rules===e?this.items[this.items.length-1].quantity+=t:this.items.push({rules:e,quantity:t,creditsEach:i,creditsSpent:0,creditsSpentLeftover:0,progress:0}),this.size+=t,this._status===QueueStatus.Idle&&(this._status=QueueStatus.Active),this._onUpdate.dispatch(this))}insertAfterFirst(t,i,r){i=Math.min(this.maxSize-this.size,i);var s=this.find(t).reduce((e,t)=>e+t.quantity,0);if(i=Math.min(this.maxItemQuantity-s,i))if(this.items.length){let e=this.items[0];var a=e.quantity,s=Math.max(0,a-1);e.quantity=1;const n=[e];a=this.items.slice(1);n.push({rules:t,quantity:i,creditsEach:r,creditsSpent:0,creditsSpentLeftover:0,progress:0}),0<s&&n.push({rules:e.rules,quantity:s,creditsEach:e.creditsEach,creditsSpent:0,creditsSpentLeftover:0,progress:0}),n.push(...a),this.items=n,this.size+=i,this._status===QueueStatus.Idle&&(this._status=QueueStatus.Active),this._onUpdate.dispatch(this)}else this.push(t,i,r)}pop(e,t){this.remove(e,t,!1)}shift(e,t){this.remove(e,t,!0)}remove(e,t,i){let r=this.find(e);if(!r.length)throw new Error(`Can't remove non-existent item ${e.name} from queue `+QueueType[this.type]);var s;if(r.reduce((e,t)=>e+t.quantity,0)<t)throw new Error(`Attempted to remove a quantity larger than the one in queue (${e.name})`);let a=t;for(;0<a;){let e=i?r.shift():r.pop();e.quantity<=a?(s=this.getFirst()===e,this.items.splice(this.items.indexOf(e),1),s&&(this._status=QueueStatus.Active),a-=e.quantity):(e.quantity-=a,a=0)}this.size-=t,t&&(this.size||(this._status=QueueStatus.Idle),this._onUpdate.dispatch(this))}notifyUpdated(){this._onUpdate.dispatch(this)}}const LosHelper_isGameObject=e=>void 0!==e.position;class LosHelper{constructor(e,t){this.tiles=e,this.tileOccupation=t}hasLineOfSight(t,i,r){var s=r.warhead.rules.wall||!r.projectileRules.subjectToWalls,a=r.projectileRules.subjectToCliffs,n=r.rules.spawner;let o=0,l=!1;if(!s||a||n){var h,c,r=LosHelper_isGameObject(t)?t.tile:t,i=LosHelper_isGameObject(i)?i.isBuilding()?i.centerTile:i.tile:i;let e=r.z;a&&LosHelper_isGameObject(t)&&t.isUnit()&&t.onBridge&&(e+=this.tileOccupation.getBridgeOnTile(r)?.tileElevation??0);for({x:h,y:c}of bresenham(r.rx,r.ry,i.rx,i.ry)){var u=this.tiles.getByMapCoords(h,c);if(!u)return!1;if(!s&&u.landType===LandType.Wall)return!1;if(a)if(u.landType===LandType.Cliff){if(u.z>e)return!1;l=!0}else{if(u.z>e&&l)return!1;l=!1}if(n&&o<2&&this.tileOccupation.getBridgeOnTile(u)?.isHighBridge())return!1;o++}}return!0}}const STRAFE_CLOSE_ENOUGH=2,BOMBER_RETURN_TILES=7;class MoveInWeaponRangeTask extends MoveTask{constructor(e,t,i,r){super(e,t instanceof GameObject?t.isBuilding()?t.centerTile:t.tile:t,i,{pathFinderIgnoredBlockers:t instanceof GameObject&&0<r.range?[t]:void 0}),this.target=t,this.weapon=r,this.recalcMinRange=!0,this.cancelRequested=!1,this.bomberInitialLock=!1,this.rangeHelper=new RangeHelper(e.map.tileOccupation),this.losHelper=new LosHelper(e.map.tiles,e.map.tileOccupation)}onStart(i){let e=this.target,r=this.game.map;if(e instanceof GameObject&&e.isBuilding()&&i.rules.movementZone!==MovementZone.Fly){let t=e.tile;var s=e instanceof GameObject?e.getFoundation():{width:1,height:1},s=new RadialTileFinder(r.tiles,r.mapBounds,t,s,1,5,e=>0<r.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-t.z)<2).getNextTile();s&&this.rangeHelper.tileDistance(e,s)>Math.SQRT2&&this.updateTarget(s,!1)}this.bomberInitialLock=this.isCloseEnoughToDest(i,i.tile),super.onStart(i)}cancel(){this.bomberManeuverTile?this.cancelRequested=!0:super.cancel()}shouldAirStrafe(e){return e.rules.movementZone===MovementZone.Fly&&e.rules.locomotor===LocomotorType.Aircraft&&e.rules.fighter&&1<this.weapon.projectileRules.iniRot}isBombingRun(e){return e.rules.movementZone===MovementZone.Fly&&e.rules.locomotor===LocomotorType.Aircraft&&this.weapon.projectileRules.iniRot<=1}isAirStrafeCloseEnough(e){return this.rangeHelper.tileDistance(e,this.targetTile)<Math.min(this.weapon.range,STRAFE_CLOSE_ENOUGH)}bomberCanReturn(e){return!this.bomberManeuverTile||this.rangeHelper.tileDistance(e,this.bomberManeuverTile)<=1}findStrafeDestination(t,i){let e=new RandomTileFinder(this.game.map.tiles,this.game.map.mapBounds,i,this.weapon.range,this.game,e=>this.rangeHelper.isInWeaponRange(t,i,this.weapon,this.game.rules,e));return e.getNextTile()}hasReachedDestination(e){return super.hasReachedDestination(e)||this.canStopAtTile(e,e.tile,e.onBridge)}canStopAtTile(t,e,i){if(t.zone!==ZoneType.Air&&this.target instanceof GameObject&&this.game.map.tileOccupation.isTileOccupiedBy(e,this.target)&&(!this.target.isUnit()||this.target.tile===e&&this.target.moveTrait.moveState!==MoveState.Moving))return!1;if(t.zone!==ZoneType.Air){if(!super.canStopAtTile(t,e,i))return!1}else if(this.game.map.tileOccupation.getAirObjectsOnTile(e).filter(e=>e.isUnit()&&e.moveTrait.moveState!==MoveState.Moving&&e!==t).length)return!1;return!(this.isBombingRun(t)&&!this.bomberCanReturn(e))&&(!!this.isCancelling()||this.isCloseEnoughToDest(t,e))}isCloseEnoughToDest(e,t){if(e.rules.balloonHover&&!e.rules.hoverAttack)return this.rangeHelper.isInTileRange(t,this.target,0,0);if(this.weapon.rules.cellRangefinding||!e.isInfantry())return this.rangeHelper.isInWeaponRange(e,this.target,this.weapon,this.game.rules,t)&&this.losHelper.hasLineOfSight(t,this.target,this.weapon);var i=e.zone===ZoneType.Air?e.position.computeSubCellOffset(e.position.desiredSubCell):e.position.getTileOffset(),{minRange:r,range:s}=this.rangeHelper.computeWeaponRangeVsTarget(t,this.target,this.weapon,this.game.rules),i=Coords.tile3dToWorld(t.rx+i.x/Coords.LEPTONS_PER_TILE,t.ry+i.y/Coords.LEPTONS_PER_TILE,t.z+e.position.tileElevation);return(e.isUnit()&&e.rules.movementZone===MovementZone.Fly?this.rangeHelper.isInRange2(i,this.target,r,s):this.rangeHelper.isInRange3(i,this.target,r,s))&&this.losHelper.hasLineOfSight(t,this.target,this.weapon)}findRelocationTile(t,i,r){if(r.rules.movementZone!==MovementZone.Fly)return super.findRelocationTile(t,i,r);{i=this.game.map;let e=new RandomTileFinder(i.tiles,i.mapBounds,t,1,this.game,e=>this.isCancelling()||this.isCloseEnoughToDest(r,e));return e.getNextTile()}}retarget(e,t){var i=e instanceof GameObject?e.isBuilding()?e.centerTile:e.tile:e;this.bomberManeuverTile?this.bomberQueuedTargetTile=i:(this.updateTarget(i,t),this.recalcMinRange=!0),this.target=e,this.options?.ignoredBlockers&&(this.options.ignoredBlockers=e instanceof GameObject?[e]:void 0),this.options??(this.options={}),this.options.pathFinderIgnoredBlockers=e instanceof GameObject?[e]:void 0}onTick(s){if(this.recalcMinRange){this.recalcMinRange=!1;var e=this.findMinRangeRelocationTile(s,this.targetTile);if(e!==this.targetTile){if(!e)return this.cancel(),!1;this.updateTarget(e,!!e.onBridgeLandType)}}if(this.shouldAirStrafe(s)&&!this.isCancelling()&&(this.updateTarget(this.target instanceof GameObject?this.target.isBuilding()?this.target.centerTile:this.target.tile:this.target,!1),!this.isAirStrafeCloseEnough(s)||(a=this.findStrafeDestination(s,this.targetTile))&&this.updateTarget(a,!1)),this.isBombingRun(s)&&!this.isCancelling()&&(!s.ammo||this.weapon.getBurstsFired()||this.bomberInitialLock)&&!this.bomberManeuverTile){this.bomberInitialLock=!1;let e=s.position.getMapPosition();var a=this.target instanceof GameObject?this.target.isBuilding()?this.target.centerTile:this.target.tile:this.target;let t=new Vector2(a.rx+.5,a.ry+.5).clone().multiplyScalar(Coords.LEPTONS_PER_TILE).sub(e),i=t.length();i||(t.copy(FacingUtil.toMapCoords(s.direction)),i=Number.EPSILON);let r=e.clone().add(t.setLength(i+BOMBER_RETURN_TILES*Coords.LEPTONS_PER_TILE));a=r.multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor(),a=bresenham(a.x,a.y,s.tile.rx,s.tile.ry);if(!a.length)throw new Error("Bresenham returned no tiles");a=a[0];this.bomberManeuverTile=this.game.map.tiles.getByMapCoords(a.x,a.y)??this.game.map.tiles.getPlaceholderTile(a.x,a.y),this.options.allowOutOfBoundsTarget=!0,this.updateTarget(this.bomberManeuverTile,!1)}return this.bomberManeuverTile&&this.bomberCanReturn(s.tile)&&(this.bomberManeuverTile=void 0,this.bomberQueuedTargetTile&&(this.updateTarget(this.bomberQueuedTargetTile,!1),this.recalcMinRange=!0,this.bomberQueuedTargetTile=void 0)),this.cancelRequested&&(this.bomberManeuverTile||(this.cancelRequested=!1,this.cancel())),!!(this.isBombingRun(s)&&this.isCancelling()&&this.forceCancel(s))||super.onTick(s)}forceCancel(e){return!this.bomberManeuverTile&&super.forceCancel(e)}findMinRangeRelocationTile(e,t){var{minRange:i,range:r}=this.rangeHelper.computeWeaponRangeVsTarget(e,this.target,this.weapon,this.game.rules);return e.rules.locomotor===LocomotorType.Chrono?this.rangeHelper.isInRange(e,this.target,r-1,r,this.weapon.rules.cellRangefinding)?t:this.findTileInRange(e,t,r-1,2*r)??t:this.rangeHelper.isInRange(e,this.target,i,Number.POSITIVE_INFINITY,this.weapon.rules.cellRangefinding)?t:this.findTileInRange(e,t,2*i,r-i)}findTileInRange(t,e,i,r){let s=this.game.map;var a,i=new Vector2(t.tile.rx-e.rx,t.tile.ry-e.ry).setLength(i).floor().add(new Vector2(e.rx,e.ry));let n;for(a of bresenham(i.x,i.y,e.rx,e.ry))if(n=s.tiles.getByMapCoords(a.x,a.y),n)break;if(n){let e=new RadialTileFinder(s.tiles,s.mapBounds,n,{width:1,height:1},0,r,e=>this.rangeHelper.isInWeaponRange(t,this.target,this.weapon,this.game.rules,e)&&this.losHelper.hasLineOfSight(e,this.target,this.weapon)&&0<s.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!!e.onBridgeLandType)&&!s.terrain.findObstacles({tile:e,onBridge:!!e.onBridgeLandType},t).length);return e.getNextTile()}}}class TaskRunner{tick(e,t){this.tickChildren(e,t)}startTask(e,t){if(e.status!==TaskStatus.NotStarted)throw new Error("Attempted to start a task with status "+e.status);e.status=TaskStatus.Running,e.onStart(t)}tickTask(e,t){let i=this.tickChildren(e.children,t);var r=e.children.find(e=>e.blocking);if(!i&&r)return!1;if(!t.isSpawned)return!1;if(e.status===TaskStatus.NotStarted)throw new Error("Attempted tick on a non-started task");if(e.isRunning()||e.isCancelling()){var s=e.isCancelling(),a=!!e.waitingForChildrenToFinish||e.onTick(t);e.children.length&&!r&&a&&(i=e.children.every(e=>e.status===TaskStatus.Cancelled||e.status===TaskStatus.Finished),e.waitingForChildrenToFinish=!i);a=a&&i;return a&&(e.onEnd(t),e.status=s?TaskStatus.Cancelled:TaskStatus.Finished),a}return!0}tickChildren(r,s){let a=!0;if(r.length){let t=new Set,i;for(;s.isSpawned&&(i=r.find(e=>!t.has(e)));){let e;if(i.status===TaskStatus.NotStarted&&this.startTask(i,s),i.status===TaskStatus.Running||i.status===TaskStatus.Cancelling)e=!0===this.tickTask(i,s);else{if(i.status!==TaskStatus.Cancelled)throw new Error("Unhandled task status "+TaskStatus[i.status]);e=!0}if(e){var n=r.indexOf(i);-1!==n&&r.splice(n,1)}else{if(a=!1,i.blocking)break;t.add(i)}}}return a}}class Target{constructor(e,t,i){this.tileOccupation=i,this.isOre=!1,e?e.isOverlay()&&e.isBridge()?(this.bridge=e,this.tile=t):e.isOverlay()&&e.isTiberium()?(this.isOre=!0,this.tile=e.tile):(this.obj=e,this.tile=e.isBuilding()?e.centerTile:e.tile):(t.landType===LandType.Tiberium&&(this.isOre=!0),this.tile=t)}equals(e){return this.obj===e.obj&&this.tile===e.tile&&this.bridge===e.bridge&&this.isOre===e.isOre}getWorldCoords(){return this.obj?this.obj.position.worldPosition:Coords.tile3dToWorld(this.tile.rx+.5,this.tile.ry+.5,this.tile.z+(this.bridge?.tileElevation??0))}isBridge(){return!this.obj&&!!this.bridge}getBridge(){return this.bridge||(this.obj?.isUnit()&&this.obj.onBridge?this.tileOccupation.getBridgeOnTile(this.obj.tile):void 0)}}const SCAN_TARGET_FOUNDATION_ADJUST=3;!function(e){e[e.Idle=0]="Idle",e[e.CheckRange=1]="CheckRange",e[e.PrepareToFire=2]="PrepareToFire",e[e.FireUp=3]="FireUp",e[e.Firing=4]="Firing",e[e.JustFired=5]="JustFired"}(AttackState=AttackState||{});class AttackTrait{constructor(e,t){this.disabled=!1,this.attackState=AttackState.Idle,this.passiveScanCooldownTicks=0,this.taskRunner=new TaskRunner,this.distributedFireHistory=new Map,this.rangeHelper=new RangeHelper(t),this.losHelper=new LosHelper(e,t)}isIdle(){return this.attackState===AttackState.Idle}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}isOnCooldown(e){let t=[e.primaryWeapon,e.secondaryWeapon],i=e.armedTrait?.getDeployFireWeapon();return i?.rules.areaFire&&!i.rules.fireOnce&&(t=t.filter(e=>e!==i)),t.some(e=>0<(e?.getCooldownTicks()??0))}expirePassiveScanCooldown(){this.passiveScanCooldownTicks=0}increasePassiveScanCooldown(e){this.passiveScanCooldownTicks+=e}cancelOpportunityFire(){this.opportunityFireTask?.cancel()}getOpportunityFireTask(){return this.opportunityFireTask}selectDefaultWeapon(e){let i;if((e.isInfantry()||e.isVehicle())&&e.rules.deployFire){let t=e.armedTrait?.getDeployFireWeapon();i=e.deployerTrait?.isDeployed()?t&&!t.rules.areaFire?t:void 0:[e.primaryWeapon,e.secondaryWeapon].find(e=>e!==t)}else i=e.isBuilding()&&e.garrisonTrait?e.garrisonTrait.isOccupied()?e.owner.country.side===SideType.GDI?e.primaryWeapon:e.secondaryWeapon??e.primaryWeapon:void 0:e.isBuilding()&&e.overpoweredTrait?e.overpoweredTrait.getWeapon():e.primaryWeapon;return i}selectWeaponVersus(e,t,i,r=!1,s=!1){var a=t.tile;const n=t instanceof Target?t.obj:t;t=this.getAvailableWeapons(e,s,n?.isOverlay()||r&&!n);return this.selectWeaponFromList(e,n,a,t,i,r,s,!1)}selectWeaponFromList(e,t,i,r,s,a,n,o){if((!t?.isInfantry()&&!t?.isVehicle()||!t.disguiseTrait||this.canAttackThroughDisguise(e,t,t.disguiseTrait,s,a,n,o))&&(t?.isBuilding()&&t.overpoweredTrait&&t.owner===e.owner&&r.find(e=>e.warhead.rules.electricAssault)&&(r=r.filter(e=>e.warhead.rules.electricAssault)),!(n&&t?.isAircraft()&&t.missileSpawnTrait&&t.zone!==ZoneType.Air))){var l=t?.isTechno()?t.rules.armor:void 0;for(const h of r)if(h.targeting.canTarget(t,i,s,a,n)&&(void 0===l||this.checkArmor(h.warhead.rules,l,n)))return h}}getAvailableWeapons(e,t,i){let r;var s;return r=(e.isInfantry()||e.isVehicle())&&e.rules.deployFire&&e.armedTrait?(s=e.armedTrait.getDeployFireWeapon(),[e.deployerTrait?.isDeployed()?s.rules.areaFire?void 0:s:s===e.secondaryWeapon?e.primaryWeapon:e.secondaryWeapon]):e.isBuilding()&&e.garrisonTrait?e.garrisonTrait.isOccupied()?[e.owner.country.side===SideType.GDI?e.primaryWeapon:e.secondaryWeapon??e.primaryWeapon]:[]:e.isBuilding()&&e.overpoweredTrait?[e.overpoweredTrait.getWeapon()]:i||t?[e.primaryWeapon,!i&&t&&e.secondaryWeapon?e.secondaryWeapon:void 0]:[e.primaryWeapon,e.secondaryWeapon],r.filter(e=>e&&!e.rules.neverUse)}canAttackThroughDisguise(e,t,i,r,s,a,n){if(!s&&i.hasTerrainDisguise()&&!r.areFriendly(e,t)&&!e.owner.sharedDetectDisguiseTrait?.has(t))return!1;if(a){if(n&&t.moveTrait.isIdle()&&!e.rules.detectDisguise&&!e.owner.sharedDetectDisguiseTrait?.has(t)&&!r.areFriendly(t,e))return!1;i=i.getDisguise();if(i?.owner&&!e.rules.detectDisguise&&!e.owner.sharedDetectDisguiseTrait?.has(t)&&(i.owner===e.owner||r.alliances.areAllied(e.owner,i.owner)))return!1}return!0}checkArmor(e,t,i){var r=e.ivanBomb||e.bombDisarm||e.nukeMaker?1:e.verses.get(t);return void 0===r?(console.warn(`Unhandled ArmorType ${ArmorType[t]} in warhead ${e.name} verses`),!1):!(100*r<=(i?1:0))}createAttackTask(e,t,i,r,s){return new AttackTask(e,e.createTarget(t,i),r,s)}[NotifyTick_NotifyTick.onTick](a,n){if(!this.isDisabled()){if(this.opportunityFireTask&&(!a.unitOrderTrait.hasTasks()||a.isUnit()&&!a.unitOrderTrait.getTasks()[0].preventOpportunityFire||(a.unitOrderTrait.getTasks()[0]instanceof AttackTask?this.opportunityFireTask=void 0:this.opportunityFireTask.cancel()),this.opportunityFireTask&&(c=[this.opportunityFireTask],this.taskRunner.tick(c,a),c.length||(this.opportunityFireTask=void 0))),!this.opportunityFireTask&&this.retaliateTarget){var o=this.retaliateTarget;this.retaliateTarget=void 0;let e;!a.unitOrderTrait.hasTasks()&&n.isValidTarget(o)&&(e=this.selectWeaponVersus(a,o,n,!1))&&a.unitOrderTrait.addTask(this.createAttackTask(n,o,o.tile,e,{holdGround:a.rules.movementZone===MovementZone.Fly}))}if(!this.opportunityFireTask&&this.shouldPassiveAcquire(a))if(0<this.passiveScanCooldownTicks)this.passiveScanCooldownTicks--;else{this.passiveScanCooldownTicks=a.guardMode?n.rules.general.guardAreaTargetingDelay:n.rules.general.normalTargetingDelay;let e=this.selectDefaultWeapon(a);var l,h,c=a.unitOrderTrait.hasTasks();let t=void 0,i,r;!c&&a.guardMode&&e&&a.owner.isCombatant()&&(t=a.armedTrait?.computeGuardScanRange(e),i=a.guardArea?.tile,r=50);let s=!1;!e||(o=this.scanForTarget(a,e,n,t,i)).target&&({target:l,weapon:h}=o,l=this.createAttackTask(n,l,l.tile,h,{holdGround:c||!a.guardMode,disallowTurning:c,leashTiles:r,passive:!0}),c?this.opportunityFireTask=l:a.unitOrderTrait.addTask(l),s=!0,c||!a.guardMode||a.guardArea||(a.guardArea={tile:a.tile,onBridge:!!a.isUnit()&&a.onBridge}),s&&!c&&a.unitOrderTrait[NotifyTick_NotifyTick.onTick](a,n)),s||c||!a.secondaryWeapon?.warhead.rules.electricAssault||(e=a.secondaryWeapon,(h=this.scanForTarget(a,e,n,void 0,void 0,!0)).target&&({target:l,weapon:h}=h,h=this.createAttackTask(n,l,l.tile,h,{passive:!0}),a.unitOrderTrait.addTask(h),s=!0)),!s&&!c&&a.guardArea&&a.isUnit()&&a.moveTrait&&!a.moveTrait.isDisabled()&&a.guardArea.tile!==a.tile&&a.unitOrderTrait.addTasks(new MoveTask(n,a.guardArea.tile,a.guardArea.onBridge),new CallbackTask(()=>{[MoveResult.Success,MoveResult.CloseEnough].includes(a.moveTrait.lastMoveResult)||a.resetGuardModeToIdle(),a.guardArea=void 0}))}}}[NotifyDamage.onDamage](e,t,i,r){this.isDisabled()||!this.retaliateTarget&&!this.opportunityFireTask&&r&&r.obj&&r.weapon&&this.shouldRetaliate(e,t,i,r.obj,r.weapon.warhead)&&(this.retaliateTarget=r.obj)}[NotifyTeleport.onBeforeTeleport](e,t,i,r){r||(this.attackState=AttackState.Idle,this.currentTarget=void 0,this.retaliateTarget=void 0,this.opportunityFireTask=void 0)}shouldPassiveAcquire(e){if(!e.owner.isCombatant()&&e.rules.needsEngineer||!e.rules.canPassiveAquire||!e.primaryWeapon||e.ammoTrait&&!e.ammoTrait.ammo&&e.rules.manualReload)return!1;if(e.mindControllerTrait?.isAtCapacity())return!1;var t=e.rules.opportunityFire||e.rules.balloonHover&&e.unitOrderTrait.getCurrentTask()?.isAttackMove;if(e.isUnit()&&t){if(e.unitOrderTrait.hasTasks()&&e.unitOrderTrait.getTasks()[0].preventOpportunityFire)return!1}else if(e.unitOrderTrait.hasTasks())return!1;return!0}shouldRetaliate(e,t,i,r,s){if(i<1||t.areFriendly(e,r)||!e.rules.canRetaliate||!e.primaryWeapon||e.ammoTrait&&!e.ammoTrait.ammo&&e.rules.manualReload||s.rules.temporal||r.rules.missileSpawn||e.unitOrderTrait.hasTasks()||!t.isValidTarget(r)||(r.isInfantry()||r.isVehicle())&&r.disguiseTrait&&!e.rules.detectDisguise||e.mindControllerTrait?.isAtCapacity())return!1;t=this.selectWeaponVersus(e,r,t,!1);return!(!t||(e.isBuilding()||r.isBuilding()?this.rangeHelper.tileDistance(e,r):this.rangeHelper.distance2(e,r)/Coords.LEPTONS_PER_TILE)>Math.max(t.range,e.sight))}scanForTarget(e,t,i,r,s,a=!1){let n={},o=Number.NEGATIVE_INFINITY;var l=this.getAvailableWeapons(e,!0,!1),t=r??(e.rules.guardRange||t.range)+1+SCAN_TARGET_FOUNDATION_ADJUST+i.rules.elevationModel.bonusCap+(t.projectileRules.isAntiAir?e.rules.airRangeBonus:0);for(const u of this.scanTechnosAround(e,t,i)){var h,c=this.selectWeaponFromList(e,u,u.tile,l,i,!1,!0,!0);c&&this.canPassiveAcquire(u,i)&&i.isValidTarget(u)&&(r?this.rangeHelper.isInRange(e,u,c.minRange,r,c.rules.cellRangefinding)&&(!s||this.rangeHelper.isInRange2(s,u,0,r)):this.rangeHelper.isInWeaponRange(e,u,c,i.rules))&&(a||this.losHelper.hasLineOfSight(e,u,c))&&(h=this.rangeHelper.distance3(e,u)/Coords.LEPTONS_PER_TILE,(h=this.computeThreat(u,e,c,h,i.rules.general.threat))>o&&(n={target:u,weapon:c},o=h))}return n.target&&e.rules.distributedFire&&this.updateDistributedFireHistory(n),n}scanTechnosAround(e,t,i){var r=e.getFoundation();const s=new Vector2(e.tile.rx,e.tile.ry),a=new Vector2(e.tile.rx+r.width-1,e.tile.ry+r.height-1);s.addScalar(-t),a.addScalar(t);t=new Box2(s,a);return i.map.technosByTile.queryRange(t)}canPassiveAcquire(e,t){return!e.owner.isNeutral&&!e.rules.civilian&&!e.rules.insignificant&&(1<e.rules.threatPosed||0<e.rules.specialThreatValue&&!e.isBuilding()||e.rules.harvester||e.name===t.rules.general.paradrop.paradropPlane)}computeThreat(e,t,i,r,s){let a=[e.primaryWeapon,e.secondaryWeapon].filter(isNotNullOrUndefined).map(e=>e.warhead.rules.verses.get(t.rules.armor)??0).reduce((e,t)=>Math.max(e,t),0)*s.targetEffectivenessCoefficientDefault;return e.attackTrait?.currentTarget?.obj===t&&(a*=-1),a+=e.rules.specialThreatValue*s.targetSpecialThreatCoefficientDefault,a+=(i.warhead.rules.verses.get(e.rules.armor)??0)*s.myEffectivenessCoefficientDefault,a+=e.healthTrait.health/100*s.targetStrengthCoefficientDefault,a+=r*s.targetDistanceCoefficientDefault,a+=1e5,t.rules.vhpScan!==VhpScan.None&&(s=e.healthTrait.getProjectedHitPoints(),t.rules.vhpScan===VhpScan.Strong?s<=0&&(a=Number.NEGATIVE_INFINITY):t.rules.vhpScan===VhpScan.Normal&&(s<=0?a/=2:s<=e.healthTrait.maxHitPoints/2&&(a*=2))),t.rules.distributedFire&&(a-=1e6*(this.distributedFireHistory.get(e)??0)),a}updateDistributedFireHistory(e){if(50!==this.distributedFireHistory.get(e.target)){for(var[t,i]of this.distributedFireHistory)i--,i<=0?this.distributedFireHistory.delete(t):this.distributedFireHistory.set(t,i);this.distributedFireHistory.set(e.target,50)}}dispose(){this.distributedFireHistory.clear()}}const MAX_MOVE_ATTEMPTS=3,FACING_DELTA_NONHOMING_THRESH_DEG=11.25,FACING_DELTA_HOMING_THRESH_DEG=4*FACING_DELTA_NONHOMING_THRESH_DEG;class AttackTask extends Task{constructor(e,t,i,r={}){super(),this.game=e,this.target=t,this.weapon=i,this.options=r,this.moveExecuted=!1,this.moveAttempts=0,this.rangeCheckCooldown=0,this.lastInRangeTargetPosition=new Vector3_Vector3,this.lastInRangeSelfPosition=new Vector3_Vector3,this.initialIndirectTarget=!1,this.forceDropTarget=!1,this.rangeHelper=new RangeHelper(e.map.tileOccupation),this.losHelper=new LosHelper(e.map.tiles,e.map.tileOccupation),this.targetLinesConfig={pathNodes:[]},this.updateTargetLines(this.target,!0)}duplicate(){return new AttackTask(this.game,this.target,this.weapon,this.options)}getWeapon(){return this.weapon}setWeapon(e){this.weapon=e}setForceAttack(e){this.options.force=e}requestTargetUpdate(e){this.target.equals(e)||(this.needsTargetUpdate=e)}onTargetChange(e){let t=e.attackTrait,i=this.target;t.currentTarget=i,this.lastValidTargetPosition=i.obj?{tile:i.tile,onBridge:i.getBridge()}:void 0,this.initialTargetOwner=i.obj?.isTechno()?i.obj.owner:void 0,this.initialIndirectTarget=!i.obj&&this.game.map.tileOccupation.getObjectsOnTile(i.tile).some(e=>e.isOverlay()&&!e.isBridgePlaceholder()||e.isTerrain()),this.updateTargetLines(i,!0)}updateTargetLines(e,t){this.targetLinesConfig.target=e.obj,this.targetLinesConfig.pathNodes=e.obj?[]:[{tile:e.tile,onBridge:e.getBridge()}],this.targetLinesConfig.isAttack=t}onStart(t){if(!t.attackTrait)throw new Error(`Object ${t.name} has no attack trait`);if(0!==t.ammo){let e=this.game.map.tileOccupation;var i,r;t.attackTrait.attackState=AttackState.CheckRange,this.onTargetChange(t),this.initialSelfPosition={tile:t.tile,onBridge:t.isUnit()&&t.onBridge?e.getBridgeOnTile(t.tile):void 0},this.weapon.rules.limboLaunch&&t.isUnit()&&!this.target.obj&&(this.forceDropTarget=!0,{reachable:i,fallback:r}=this.findReachableMeleePosition(this.target.tile,!!this.target.getBridge(),{width:1,height:1},t),!i&&r&&(this.lastValidTargetPosition=r,this.updateTargetLines(this.game.createTarget(r.onBridge,r.tile),!1))),this.weapon.rules.limboLaunch&&this.target.obj?.isTechno()&&t.isUnit()&&!this.rangeHelper.isInWeaponRange(t,this.target.obj,this.weapon,this.game.rules)&&({reachable:i,fallback:r}=this.findReachableMeleePosition(this.target.obj.tile,this.target.obj.isUnit()&&this.target.obj.onBridge,this.target.obj.getFoundation(),t),i||(1<(t.unitOrderTrait.waypointPath?.waypoints?.length??0)?this.cancel():(this.forceDropTarget=!0,r&&(this.lastValidTargetPosition=r,this.updateTargetLines(this.game.createTarget(r.onBridge,r.tile),!1))))),this.rangeHelper.isInWeaponRange(t,this.target.obj??this.target.tile,this.weapon,this.game.rules)&&t.isUnit()&&t.rules.movementZone===MovementZone.Fly&&t.zone!==ZoneType.Air&&(t.rules.hoverAttack||t.isAircraft())&&this.children.push(new MoveTask(this.game,t.tile,!1).setCancellable(!1))}else this.cancel()}findReachableMeleePosition(r,e,t,s){let i=this.game.map,a=i.tileOccupation,n=e?a.getBridgeOnTile(r):void 0,o=new MovePositionHelper(i),l=s.rules.movementZone===MovementZone.Fly,h=(e,t)=>l||0<i.terrain.getPassableSpeed(e,s.rules.speedType,s.isInfantry(),!!t)&&o.isEligibleTile(e,t,n,r)&&!i.terrain.findObstacles({tile:e,onBridge:t},s).length,c,u=new RadialTileFinder(i.tiles,i.mapBounds,r,t,1,Math.ceil(this.weapon.rules.range),e=>{let t=!1;var i;return h(e,void 0)&&(c=c??{tile:e,onBridge:void 0},t=!0),void 0!==e.onBridgeLandType&&(i=a.getBridgeOnTile(e),h(e,i)&&(c=c??{tile:e,onBridge:i},t=!0)),!!t&&this.rangeHelper.isInWeaponRange(s,r,this.weapon,this.game.rules,e)});return{reachable:u.getNextTile(),fallback:c}}onEnd(e){e.isVehicle()&&e.turretTrait&&(e.turretTrait.desiredFacing=e.direction),e.attackTrait.attackState=AttackState.Idle,e.attackTrait.currentTarget=void 0;var t=this.game.rules.general.prism.type;e.isBuilding()&&e.name===t&&this.weapon.type!==WeaponType.Secondary&&this.countSupportBeamsAndFireDownTowers(e,t),this.weapon.rules.limboLaunch&&e.attackTrait.expirePassiveScanCooldown(),(e.isInfantry()||e.isVehicle())&&(e.isFiring=!1),this.weapon.hasBurstsLeft()&&this.weapon.resetBursts()}forceCancel(t){if(t.rules.movementZone!==MovementZone.Fly)return!1;if(!this.cancellable||this.children.some(e=>!e.cancellable))return!1;if(this.status===TaskStatus.Running||this.status===TaskStatus.Cancelling){if(this.children.filter(e=>e instanceof MoveTask).some(e=>!e.forceCancel(t)))return!1;this.onEnd(t),(t.isInfantry()||t.isVehicle())&&(t.isFiring=!1)}return this.status=TaskStatus.Cancelled,!0}onTick(r){let s=r.attackTrait;(r.isInfantry()||r.isVehicle())&&s.attackState!==AttackState.Firing&&(r.isFiring=!1);let t=this.target.obj,a=this.children.find(e=>e instanceof MoveInWeaponRangeTask);if(this.isCancelling()&&s.attackState!==AttackState.FireUp)return!r.airSpawnTrait?.isLaunchingMissiles()&&(a?.cancel(),!0);let n=!1;if(s.attackState===AttackState.FireUp){if(s.isDisabled())return!0;s.attackState=AttackState.Firing,n=!0}if(s.attackState===AttackState.Firing){if(this.initialIndirectTarget&&!this.game.map.getObjectsOnTile(this.target.tile).find(e=>e.isOverlay()&&!e.isBridgePlaceholder()||e.isTerrain()))return this.cancel(),this.onTick(r);if(n){var o=this.target.obj||this.target.tile;if(!this.game.isValidTarget(this.target.obj)||this.shouldDropTarget(this.target.obj)||!this.weapon.targeting.canTarget(this.target.obj,this.target.tile,this.game,!!this.options.force,!!this.options.passive)||!this.rangeHelper.isInWeaponRange(r,o,this.weapon,this.game.rules)||!this.losHelper.hasLineOfSight(r,o,this.weapon))return s.attackState=AttackState.CheckRange,this.onTick(r)}if(this.weapon.rules.limboLaunch){if((t?.isVehicle()||t?.isAircraft())&&t.parasiteableTrait?.isInfested())return!0;if(r.rules.movementZone!==MovementZone.Fly&&t?.isUnit()&&t.zone===ZoneType.Air)return!0}if(this.target.tile.onBridgeLandType&&r.tile.onBridgeLandType&&r.isUnit()&&(this.game.map.tileOccupation.getBridgeOnTile(this.target.tile)?.isHighBridge()||this.game.map.tileOccupation.getBridgeOnTile(r.tile)?.isHighBridge()))if((t?t.isUnit()&&(t.zone===ZoneType.Air||t.onBridge):this.target.isBridge())!==(r.zone===ZoneType.Air||r.onBridge))return!0;let e=1;o=this.game.rules.general.prism.type;if(r.isBuilding()&&r.name===o&&this.weapon.type!==WeaponType.Secondary&&(o=this.countSupportBeamsAndFireDownTowers(r,o),e=1+o*this.game.rules.general.prism.supportModifier),this.weapon.rules.spawner&&(r.isVehicle()||r.isAircraft())&&r.parasiteableTrait?.isParalyzed())return!0;if(0===r.ammo)return r.isAircraft()&&(r.rules.fighter||r.rules.spawned)&&a?.cancel(),!0;let i=!1;if(this.weapon.rules.limboLaunch){let t=a;if(!t){let e=r.unitOrderTrait.getCurrentTask();if(e&&e!==this&&s.getOpportunityFireTask()===this){if(!(e instanceof MoveTask))return e.cancel(),!1;t=e}}if(t){if(!t.forceCancel(r))return!1;r.moveTrait.lastTargetOffset=void 0,r.moveTrait.lastVelocity=void 0}i=!0}return(this.weapon.fire(this.target,this.game,e),i)?!0:!!this.weapon.rules.fireOnce||(!(!this.options.passive||!r.rules.distributedFire)||(s.attackState=AttackState.JustFired,!1))}if(s.attackState===AttackState.JustFired)return s.attackState=AttackState.PrepareToFire,this.onTick(r);this.needsTargetUpdate&&(this.target=this.needsTargetUpdate,t=this.target.obj,this.needsTargetUpdate=void 0,this.onTargetChange(r),t||a?.retarget(this.target.tile,!!this.target.getBridge())),t?.isTechno()&&t.replacedBy&&(l=this.game.createTarget(t.replacedBy,t.replacedBy.tile),this.target=l,t=t.replacedBy,this.onTargetChange(r));let i=this.game.isValidTarget(t)&&!this.shouldDropTarget(t);if(i){let e=this.weapon.targeting.canTarget(t,this.target.tile,this.game,!!this.options.force,!!this.options.passive);if(!e||!r.armedTrait.isEquippedWithWeapon(this.weapon)){var l=s.selectWeaponVersus(r,this.target,this.game,this.options.force,this.options.passive);if(l){if(this.setWeapon(l),s.attackState!==AttackState.CheckRange)return s.attackState=AttackState.CheckRange,this.onTick(r);e=!0}else e=!1}i=e}if(i&&(h=this.lastTargetTpCheck,t?.isUnit()&&h&&t.moveTrait.lastTeleportTick>=h?(i=!1,this.rangeCheckCooldown=0):this.lastTargetTpCheck=this.game.currentTick),i&&t&&(this.lastValidTargetPosition={tile:t.tile,onBridge:this.target.getBridge()}),i||(this.targetLinesConfig.isAttack=!1),s.attackState===AttackState.CheckRange){if(0<this.rangeCheckCooldown)return this.rangeCheckCooldown--,!1;let e=this.target.obj?i?this.target.obj:this.lastValidTargetPosition.tile:this.target.tile;var h=this.target.obj?i?this.target.obj.isBuilding()?this.target.obj.centerTile:this.target.obj.tile:this.lastValidTargetPosition.tile:this.target.tile;if(!this.rangeHelper.isInWeaponRange(r,e,this.weapon,this.game.rules)||!this.losHelper.hasLineOfSight(r,e,this.weapon)||r.isUnit()&&r.rules.balloonHover&&!r.rules.hoverAttack&&!a&&r.tile!==h&&!this.options.holdGround||r.isAircraft()&&this.weapon.projectileRules.iniRot<=1&&!a){if(r.isUnit()&&!this.options.holdGround&&this.game.map.isWithinBounds(h)){if(a){if(a.target!==this.target.obj||i)if(i&&this.target.obj&&this.rangeHelper.tileDistance(this.target.obj,this.lastSelfMoveTargetTile)>this.weapon.range)a.retarget(this.target.obj,!!this.target.getBridge()),this.lastSelfTileBeforeMove=r.tile,this.lastSelfMoveTargetTile=this.target.obj?.tile??this.target.tile;else{if(void 0!==this.options.leashTiles&&this.rangeHelper.tileDistance(this.initialSelfPosition.tile,r.tile)>this.options.leashTiles)return a.cancel(),!0;var c=e instanceof GameObject&&e.isUnit()?e.moveTrait.baseSpeed:0,u=Math.ceil((this.rangeHelper.tileDistance(r,e)-(this.weapon.range+1))/((r.moveTrait.baseSpeed+c)/Coords.LEPTONS_PER_TILE));0<u&&(this.rangeCheckCooldown=Math.min(GameSpeed.BASE_TICKS_PER_SECOND,u))}else{let e;e=void 0!==this.options.leashTiles?this.game.createTarget(this.initialSelfPosition.onBridge,this.initialSelfPosition.tile):this.game.createTarget(this.lastValidTargetPosition.onBridge,this.lastValidTargetPosition.tile),s.currentTarget=e,a.retarget(e.tile,e.isBridge()),this.updateTargetLines(e,!1)}return!1}if(!r.moveTrait||r.moveTrait.isDisabled())return!0;if(this.isCancelling())return!0;if(r.tile===this.lastSelfTileBeforeMove||this.moveExecuted&&r.moveTrait.lastMoveResult===MoveResult.Fail?this.moveAttempts++:this.moveAttempts=0,this.weapon.rules.limboLaunch&&r.defaultToGuardArea&&t&&this.moveExecuted&&r.moveTrait.lastMoveResult===MoveResult.Fail&&this.rangeHelper.isInRange(r,t,0,r.armedTrait.computeGuardScanRange(this.weapon),!0))return!0;if(this.moveAttempts>MAX_MOVE_ATTEMPTS)return!0;0<this.moveAttempts&&this.children.push(new WaitMinutesTask(1/60));c=e,u=t&&!i?this.lastValidTargetPosition.onBridge:this.target.getBridge();return a=new MoveInWeaponRangeTask(this.game,c,!!u,this.weapon),a.blocking=!1,this.children.push(a),this.moveExecuted=!0,this.lastSelfTileBeforeMove=r.tile,this.lastSelfMoveTargetTile=c instanceof GameObject?c.tile:c,this.onTick(r)}return!0}if(this.moveExecuted=!1,this.moveAttempts=0,a&&(r.rules.balloonHover&&!r.rules.hoverAttack||r.rules.fighter||r.rules.spawned||r.rules.movementZone===MovementZone.Fly&&!this.rangeHelper.isInRange2(r,this.target.obj??this.target.tile,this.weapon.minRange,this.weapon.range-1)||a.cancel()),a&&(r.isInfantry()||this.weapon.rules.spawner))return!1;if(a?.children.some(e=>!e.cancellable)&&this.weapon.rules.limboLaunch)return!1;if(a&&a.shouldAirStrafe(r)&&this.target.obj?.isUnit()&&this.target.obj.moveTrait.isMoving()&&1<this.weapon.range&&!this.rangeHelper.isInRange2(r,this.target.obj,this.weapon.minRange,this.weapon.range-1))return!1;s.attackState=AttackState.PrepareToFire}if(s.attackState!==AttackState.PrepareToFire)return!1;if(!i||s.isDisabled())return a?.cancel(),!0;u=this.target.getWorldCoords(),c=r.position.worldPosition;if(!(this.lastInRangeTargetPosition.length()&&this.lastInRangeTargetPosition.equals(u)&&this.lastInRangeSelfPosition.length()&&this.lastInRangeSelfPosition.equals(c)))return this.lastInRangeTargetPosition.copy(u),this.lastInRangeSelfPosition.copy(c),s.attackState=AttackState.CheckRange,this.onTick(r);if(!(this.weapon.rules.omniFire||r.rules.omniFire&&r.rules.fighter)){var c=(new Vector3_Vector3).copy(u).sub(c),e=FacingUtil.fromMapCoords(new Vector2(c.x,c.z)),c=this.weapon.projectileRules.rot?FACING_DELTA_HOMING_THRESH_DEG:FACING_DELTA_NONHOMING_THRESH_DEG;if((r.isVehicle()||r.isBuilding())&&r.turretTrait){if(r.turretTrait.desiredFacing=e,Math.abs(e-r.turretTrait.facing)>=c)return!1}else if(Math.abs(e-r.direction)>=c){if(r.isAircraft())return r.direction=FacingUtil.tick(r.direction,e,r.rules.rot).facing,!1;if(a)return!1;if(this.options.disallowTurning)return!0;if(r.isVehicle())return this.children.push(new TurnTask(e)),!1;r.direction=e}}if(!this.losHelper.hasLineOfSight(r,this.target.obj||this.target.tile,this.weapon))return s.attackState=AttackState.CheckRange,this.onTick(r);if(s.isOnCooldown(r))return!1;if(this.weapon.warhead.rules.temporal&&r.temporalTrait.getTarget()===this.target.obj)return!1;if(this.weapon.rules.suicide&&this.weapon.type!==WeaponType.DeathWeapon)return this.game.destroyObject(r,{player:r.owner,obj:r,weapon:this.weapon}),!0;e=this.game.rules.general.prism.type;return r.isBuilding()&&r.name===e&&this.weapon.type!==WeaponType.Secondary&&this.fireUpPrismSupportTowers(r,e),(r.isInfantry()||r.isVehicle())&&(r.isFiring=!0),r.art.fireUp?(this.children.push(new WaitTicksTask(r.art.fireUp).setCancellable(!1)),s.attackState=AttackState.FireUp,!1):(s.attackState=AttackState.Firing,this.onTick(r))}shouldDropTarget(e){return this.forceDropTarget||e?.isTechno()&&(this.weapon.rules.limboLaunch&&((e.isVehicle()||e.isAircraft())&&e.parasiteableTrait?.isInfested()||e.invulnerableTrait.isActive())||e.warpedOutTrait.isInvulnerable()&&!this.weapon.warhead.rules.temporal||this.initialTargetOwner!==e.owner)}fireUpPrismSupportTowers(t,i){var e;for(e of t.owner.getOwnedObjectsByType(ObjectType.Building).filter(e=>e.name===i&&e.secondaryWeapon&&!e.unitOrderTrait.hasTasks()&&e.attackTrait&&!e.attackTrait.isDisabled()&&!e.attackTrait.isOnCooldown(e)).filter(e=>this.rangeHelper.isInWeaponRange(e,t,e.secondaryWeapon,this.game.rules)).slice(0,this.game.rules.general.prism.supportMax))e.unitOrderTrait.addTask(e.attackTrait.createAttackTask(this.game,t,t.centerTile,e.secondaryWeapon,{passive:!0}))}countSupportBeamsAndFireDownTowers(t,i){var e,r=t.owner.getOwnedObjectsByType(ObjectType.Building).filter(e=>e.name===i&&e.attackTrait?.currentTarget?.obj===t);for(e of r)e.unitOrderTrait.getCurrentTask()?.cancel();return Math.min(this.game.rules.general.prism.supportMax,r.length)}getTargetLinesConfig(){return this.targetLinesConfig}}class AttackMoveTargetTask extends AttackTask{constructor(e,t,i){if(super(e,t,i),this.isAttackMove=!0,this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.internalTargetUpdateRequested=!1,this.scanCooldownTicks=0,!t.obj?.isTechno())throw new Error("Target must be a techno object");this.initialTarget=t,this.initialWeapon=i,this.requestedTarget=t}duplicate(){return new AttackMoveTargetTask(this.game,this.initialTarget,this.initialWeapon)}requestTargetUpdate(e){this.internalTargetUpdateRequested?(this.requestedTarget=e,this.internalTargetUpdateRequested=!1):(this.requestedTarget===this.initialTarget?this.requestedTarget=e:this.attackPerformed=!0,this.initialTarget=e),super.requestTargetUpdate(e)}onTargetChange(e){super.onTargetChange(e);e=e.attackTrait.currentTarget;e&&e.obj!==this.initialTarget.obj&&e.obj!==this.requestedTarget.obj&&(this.requestedTarget===this.initialTarget&&(this.requestedTarget=e),this.initialTarget=e)}onTick(t){if(t.moveTrait.moveState===MoveState.Moving&&(this.passedFirstWaypoint=!0),this.scanCooldownTicks=Math.max(0,this.scanCooldownTicks-1),t.attackTrait&&!t.attackTrait.isDisabled()&&!this.isCancelling()&&(this.requestedTarget===this.initialTarget||this.attackPerformed)){if(!(t.moveTrait.isIdle()||t.tile===this.lastScanTile&&this.scanCooldownTicks)){this.lastScanTile=t.tile,this.scanCooldownTicks=this.game.rules.general.normalTargetingDelay;let e=t.attackTrait.selectDefaultWeapon(t);if(e&&(this.passedFirstWaypoint||!e.getCooldownTicks())){var i=t.attackTrait.scanForTarget(t,e,this.game);if(i.target){let{target:e,weapon:t}=i;if(!t.getCooldownTicks()){this.options.holdGround=!0,this.options.passive=!0,this.setWeapon(t);var r=this.game.createTarget(e,e.tile);return this.internalTargetUpdateRequested=!0,this.requestTargetUpdate(r),this.attackPerformed=!1}}}}if(this.attackPerformed){if(!t.isSpawned){if(!this.forceCancel(t))throw new Error("Force cancel failed");return!0}this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.options.holdGround=!1,this.options.passive=!1,this.setWeapon(this.initialWeapon),this.internalTargetUpdateRequested=!0,this.requestTargetUpdate(this.initialTarget)}}r=super.onTick(t);return r&&this.requestedTarget!==this.initialTarget?(this.attackPerformed=!0,this.isCancelling()||t.attackTrait.isDisabled()):r}}class AttackMoveTask extends MoveTask{constructor(){super(...arguments),this.isAttackMove=!0,this.attackPerformed=!1,this.passedFirstWaypoint=!1}duplicate(){return new AttackMoveTask(this.game,this.targetTile,this.toBridge,this.options)}onTick(i){if(i.moveTrait.moveState===MoveState.Moving&&(this.passedFirstWaypoint=!0),i.moveTrait.moveState===MoveState.ReachedNextWaypoint&&i.attackTrait&&!i.attackTrait.isDisabled()&&(i.rules.movementZone!==MovementZone.Fly||!i.rules.balloonHover)&&(!i.ammoTrait||i.ammoTrait.ammo||!i.rules.manualReload)&&!this.isCancelling()){let e=i.attackTrait.selectDefaultWeapon(i);if(e&&(this.passedFirstWaypoint||e&&!e.getCooldownTicks())){var r=i.attackTrait.scanForTarget(i,e,this.game);if(r.target){let{target:e,weapon:t}=r;if(!t.getCooldownTicks()){r=i.attackTrait.createAttackTask(this.game,e,e.tile,t,{holdGround:!0,passive:!0});return this.children.push(r),this.useChildTargetLines=!0,this.attackPerformed=!0,i.moveTrait.velocity.set(0,0,0),i.moveTrait.currentWaypoint=void 0,i.moveTrait.collisionState=CollisionState.Waiting,!1}}}if(this.attackPerformed){if(!i.isSpawned){if(!this.forceCancel(i))throw new Error("Force cancel failed");return!0}this.attackPerformed=!1,this.passedFirstWaypoint=!1,this.useChildTargetLines=!1,i.moveTrait.collisionState=CollisionState.Resolved,this.updateTarget(this.targetTile,this.toBridge)}}return super.onTick(i)}}class ExitFactoryTask extends MoveTask{constructor(e,t,i,r){super(e,i,!1,{ignoredBlockers:[t],closeEnoughTiles:0,strictCloseEnough:!0,forceWaitOnPathBlocked:t.factoryTrait?.type!==FactoryType.InfantryType}),this.factory=t,this.rallyPoint=r,this.preventOpportunityFire=!0,this.rampBlockersPushed=!1,this.cancellable=!1}onStart(t){super.onStart(t),this.factory.factoryTrait?.type===FactoryType.UnitType&&(this.checkRampTiles=this.game.map.tileOccupation.calculateTilesForGameObject(this.factory.tile,this.factory).filter(e=>0<this.game.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)))}canStopAtTile(e,t,i){return!this.game.map.tileOccupation.isTileOccupiedBy(t,this.factory)&&super.canStopAtTile(e,t,i)}onTick(e){if(this.checkRampTiles){for(var t of this.checkRampTiles){var i,r;for(i of this.game.map.tileOccupation.getGroundObjectsOnTile(t))if(i.isUnit()){if(this.rampBlockersPushed)return!1;let e=new ScatterTask(this.game,void 0,{excludedTiles:this.checkRampTiles});e.setCancellable(!1);let t=i.unitOrderTrait.getCurrentTask();t?t.constructor!==MoveTask&&t.constructor!==AttackTask&&t.constructor!==AttackMoveTask&&t.constructor!==AttackMoveTargetTask||(r=t.duplicate(),t.cancel(),i.unitOrderTrait.addTaskNext(r),i.unitOrderTrait.addTaskNext(e)):i.unitOrderTrait.addTask(e)}}if(!this.rampBlockersPushed)return!(this.rampBlockersPushed=!0);this.checkRampTiles=void 0}return e.moveTrait.moveState===MoveState.ReachedNextWaypoint&&this.options?.ignoredBlockers&&!this.game.map.terrain.isBlockerObject(this.factory,e.tile,!1,e.rules.speedType,e.isInfantry())&&(this.options.ignoredBlockers=void 0,this.preventOpportunityFire=!1,this.rallyPoint&&(this.updateTarget(this.rallyPoint.tile,!!this.rallyPoint.onBridge),this.cancellable=!0,this.options.closeEnoughTiles=this.game.rules.general.closeEnough,this.options.strictCloseEnough=!1,this.options.forceWaitOnPathBlocked=!1)),super.onTick(e)}}class CardinalTileFinder{constructor(e,t,i,r,s,a=()=>!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=s,this.predicate=a,this.dirVec=new Vector2(10,0),this.finished=!1,this.diagonal=!0,this.distance=r}getNextTile(){if(!this.finished){let t;do{let e={x:this.startTile.rx,y:this.startTile.ry};e.x+=this.distance*Math.sign(this.dirVec.x),e.y+=this.distance*Math.sign(this.dirVec.y),this.dirVec.rotateAround(new Vector2,Math.PI/4*(this.diagonal?1:2)).round();var i=this.tiles.getByMapCoords(e.x,e.y);if(i&&this.mapBounds.isWithinBounds(i)&&this.predicate(i)&&(t=i),!this.dirVec.angle()){if(this.maxDistance&&this.distance>=this.maxDistance)return this.finished=!0,t;this.distance++}}while(!t);return t}}}(NotifySell=NotifySell||{}).onSell=Symbol();class DockableTrait{[NotifyUnspawn.onUnspawn](e){this.undock(e),this.reservedDock?.dockTrait.unreserveDockForUnit(e)}[NotifyOwnerChange.onChange](e){e.owner!==this.dock?.owner&&this.undock(e),e.owner!==this.reservedDock?.owner&&this.reservedDock?.dockTrait.unreserveDockForUnit(e)}[NotifyTeleport.onBeforeTeleport](e,t,i,r){r||this.undock(e)}undock(e){this.dock&&!this.dock.isDisposed&&this.dock.dockTrait.undockUnit(e)}dispose(){this.dock=void 0,this.reservedDock=void 0}}class DockTrait{constructor(e,t,i,r){this.building=e,this.tiles=t,this.numberOfDocks=i,this.dockingOffsets=r,this.ticksWhenWarpedOut=!0,this.unitsByDockNumber=new Array(i).fill(void 0),this.reservedDocks=new Array(i).fill(void 0)}[NotifySpawn.onSpawn](){this.dockTiles=[];for(let e=0;e<this.numberOfDocks;e++){var t=this.findDockTile(e);if(!t)throw new Error(`Docking tile ${e} not found for object "${this.building.name}"`);this.dockTiles[e]=t}}[NotifyUnspawn.onUnspawn](){for(let e=0;e<this.numberOfDocks;e++)this.unreserveDockAt(e)}[NotifyTick_NotifyTick.onTick](){for(let e=0;e<this.numberOfDocks;e++){var t=this.unitsByDockNumber[e];t&&t.tile!==this.getDockTile(e)&&this.undockUnit(t)}}[NotifyDestroy.onDestroy](e,t,i,r){var s=(e.rules.unitRepair||e.helipadTrait)&&!e.rules.naval&&!i?.weapon?.warhead.rules.temporal;if(s)for(var a of this.unitsByDockNumber)a&&!a.isDestroyed&&(s?t.destroyObject(a,i,r):this.undockUnit(a))}[NotifySell.onSell](r,s){if(r.helipadTrait&&this.hasDockedUnits()){var a,e,n;let t=[],i=0;for(a of[...r.owner.buildings].filter(e=>e.helipadTrait&&(e.dockTrait?.getAvailableDockCount()??!1)&&e!==r)){let e=a.dockTrait?.getAvailableDockCount()??0;for(;0<e&&i<this.unitsByDockNumber.length;)t.push(a),e--,i++;if(i===this.unitsByDockNumber.length)break}i=0;for(e of this.unitsByDockNumber)e&&((n=t[i])?e.unitOrderTrait.addTask(new MoveToDockTask(s,n)):e.unitOrderTrait.addTask(new TaskGroup(new MoveTask(s,e.tile,!1),new CallbackTask(e=>{e.crashableTrait?e.crashableTrait.crash({player:r.owner}):s.destroyObject(e,{player:r.owner})})).setCancellable(!1))),i++}else{var t,i=r.rules.unitRepair&&!r.rules.naval;for(t of this.unitsByDockNumber)t&&(i?s.sellTrait.sell(t):this.undockUnit(t))}}[NotifyOwnerChange.onChange](e,t,i){for(var r of this.unitsByDockNumber)r&&i.changeObjectOwner(r,e.owner)}getFirstAvailableDockNumber(){if(!this.building?.warpedOutTrait.isActive()){var e=this.unitsByDockNumber.findIndex((e,t)=>!e&&!this.reservedDocks[t]);if(-1!==e)return e}}getAvailableDockCount(){return this.building?.warpedOutTrait.isActive()?0:this.unitsByDockNumber.filter((e,t)=>!e&&!this.reservedDocks[t]).length}getFirstEmptyDockNumber(){if(!this.building?.warpedOutTrait.isActive()){var e=this.unitsByDockNumber.findIndex(e=>!e);if(-1!==e)return e}}getDockOffset(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);return this.dockingOffsets[e]}getDockTile(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);return this.dockTiles[e]}getDockNumberByTile(e){e=this.dockTiles.indexOf(e);if(-1!==e)return e}getAllDockTiles(){return[...this.dockTiles]}findDockTile(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);var t=this.building.position.getMapPosition(),e=this.getDockOffset(e);return this.tiles.getByMapCoords(Math.floor((t.x+e.x)/Coords.LEPTONS_PER_TILE),Math.floor((t.y+e.z)/Coords.LEPTONS_PER_TILE))}isValidUnitForDock(e){return(this.building.unitRepairTrait&&e.isVehicle()&&!this.building.helipadTrait&&(!e.rules.consideredAircraft||e.rules.landable)||e.rules.dock.includes(this.building.name)&&!(e.isAircraft()&&!this.building.helipadTrait))&&this.building.rules.naval===e.rules.naval}dockUnitAt(e,t){if(t>this.numberOfDocks-1)throw new RangeError(`Index ${t} exceeds available docks (${this.numberOfDocks})`);if(this.unitsByDockNumber[t])throw new Error("Another unit is already docked at dock #"+t);let i=e.traits.find(DockableTrait);if(!i)throw new Error(`Unit "${e.name}" cannot be docked to `+this.building.name);this.unitsByDockNumber[t]=e,i.dock=this.building}undockUnitAt(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);let t=this.unitsByDockNumber[e];t&&(this.unitsByDockNumber[e]=void 0,t.traits.get(DockableTrait).dock=void 0)}undockUnit(e){e=this.unitsByDockNumber.indexOf(e);-1!==e&&this.undockUnitAt(e)}isDocked(e){return this.unitsByDockNumber.includes(e)}hasDockedUnits(){return!!this.unitsByDockNumber.find(e=>e)}getDockedUnits(){return this.unitsByDockNumber.filter(isNotNullOrUndefined)}reserveDockAt(e,t){if(t>this.numberOfDocks-1)throw new RangeError(`Index ${t} exceeds available docks (${this.numberOfDocks})`);if(this.reservedDocks[t])throw new Error(`Dock #${t} is already reserved by `+this.reservedDocks[t].name);(this.reservedDocks[t]=e).traits.get(DockableTrait).reservedDock?.dockTrait.unreserveDockForUnit(e),e.traits.get(DockableTrait).reservedDock=this.building}unreserveDockAt(e){if(e>this.numberOfDocks-1)throw new RangeError(`Index ${e} exceeds available docks (${this.numberOfDocks})`);let t=this.reservedDocks[e];t&&(this.reservedDocks[e]=void 0,t.traits.get(DockableTrait).reservedDock=void 0)}unreserveDockForUnit(e){e=this.reservedDocks.indexOf(e);-1!==e&&this.unreserveDockAt(e)}hasReservedDockForUnit(e){return!!this.reservedDocks.includes(e)}hasReservedDockAt(e){return!!this.reservedDocks[e]}getReservedDockForUnit(e){e=this.reservedDocks.indexOf(e);if(-1!==e)return e}dispose(){this.building=void 0}}class FactoryProduceUnitEvent{constructor(e){this.target=e,this.type=EventType.FactoryProduceUnit}}!function(e){e[e.All=0]="All",e[e.Ground=1]="Ground",e[e.Air=2]="Air"}(LayerType=LayerType||{});class TileOccupation{get onChange(){return this._onChange.asEvent()}constructor(e){this.tiles=e,this.tileOccupation=[],this.emptyTiles=new Set,this._onChange=new EventDispatcher;let t=this.tileOccupation;for(var i of e.getAll())t[i.rx]=t[i.rx]||[],t[i.rx][i.ry]=new Set,this.emptyTiles.add(i)}occupyTileRange(e,t){let i=this.calculateTilesForGameObject(e,t);i.forEach(e=>this.occupyTile(e,t)),this._onChange.dispatch(this,{tiles:i,object:t,type:"added"})}unoccupyTileRange(e,t){let i=this.calculateTilesForGameObject(e,t);i.forEach(e=>this.unoccupyTile(e,t)),this._onChange.dispatch(this,{tiles:i,object:t,type:"removed"})}occupySingleTile(e,t){this.occupyTile(e,t),this._onChange.dispatch(this,{tiles:[e],object:t,type:"added"})}unoccupySingleTile(e,t){this.unoccupyTile(e,t),this._onChange.dispatch(this,{tiles:[e],object:t,type:"removed"})}calculateTilesForGameObject(e,t){return this.tiles.getInRectangle(e,t.getFoundation())}occupyTile(e,t){let i=this.tileOccupation[e.rx]?.[e.ry];i&&(i.add(t),this.emptyTiles.delete(e),e.landType=this.computeTileLandType(e),e.onBridgeLandType=this.computeOnBridgeLandType(e))}unoccupyTile(e,t){let i=this.tileOccupation[e.rx]?.[e.ry];i&&(i.delete(t),i.size||this.emptyTiles.add(e),e.landType=this.computeTileLandType(e),e.onBridgeLandType=this.computeOnBridgeLandType(e))}isTileOccupiedBy(e,t){return!!this.tileOccupation[e.rx]?.[e.ry]?.has(t)}computeTileLandType(e){if(e.landType===LandType.Rock)return LandType.Rock;var t,i=getLandType(e.terrainType);for(t of this.tileOccupation[e.rx]?.[e.ry]??[]){if((t.isOverlay()||t.isBuilding())&&t.rules.wall)return LandType.Wall;if(t.isOverlay()&&t.isTiberium())return LandType.Tiberium;if(t.isOverlay()&&t.rules.land!==LandType.Clear&&!t.isBridge()&&!t.isBridgePlaceholder())return t.rules.land}return i}computeOnBridgeLandType(e){for(var t of this.tileOccupation[e.rx]?.[e.ry]??[])if(t.isOverlay()&&t.isBridge())return t.isHighBridge()?LandType.Road:t.rules.land}getTileZone(e,t=!1){return getZoneType(t?e.landType:e.onBridgeLandType??e.landType)}getBridgeOnTile(e){for(var t of this.tileOccupation[e.rx]?.[e.ry]??[])if(t.isOverlay()&&t.isBridge())return t}getObjectsOnTile(e){return[...this.tileOccupation[e.rx]?.[e.ry]??[]]}getGroundObjectsOnTile(e){let t=[];for(var i of this.tileOccupation[e.rx]?.[e.ry]??[])i.isTechno()&&!i.isBuilding()&&i.zone===ZoneType.Air||t.push(i);return t}getAirObjectsOnTile(e){let t=[];for(var i of this.tileOccupation[e.rx]?.[e.ry]??[])i.isUnit()&&i.zone===ZoneType.Air&&t.push(i);return t}getObjectsOnTileByLayer(e,t){if(t===LayerType.Ground)return this.getGroundObjectsOnTile(e);if(t===LayerType.Air)return this.getAirObjectsOnTile(e);if(t===LayerType.All)return this.getObjectsOnTile(e);throw new Error(`Unhandled layer type "${t}"`)}getEmptyTiles(){return[...this.emptyTiles]}}(NotifyWarpChange_NotifyWarpChange=NotifyWarpChange_NotifyWarpChange||{}).onChange=Symbol(),(NotifyProduceUnit=NotifyProduceUnit||{}).onProduce=Symbol(),function(e){e[e.Idle=0]="Idle",e[e.Delivering=1]="Delivering"}(FactoryStatus=FactoryStatus||{});class FactoryTrait{constructor(e,t=!1){this.type=e,this.isCloningVats=t,this.status=FactoryStatus.Idle}[NotifySpawn.onSpawn](e,t){this.resetRallyPoint(e,t)}resetRallyPoint(e,t){var i;[FactoryType.BuildingType,FactoryType.AircraftType].includes(this.type)||(i=this.computeDefaultRallyPoint(e,this.type,t.map),e.rallyTrait?.changeRallyPoint(i,e,t))}[NotifyWarpChange_NotifyWarpChange.onChange](t,e,i){if(t.owner.production){let e=[];e=this.type===FactoryType.BuildingType?[QueueType.Structures,QueueType.Armory]:[t.owner.production.getQueueTypeForFactory(this.type)];for(var r of e)t.owner.production.getQueue(r).notifyUpdated()}}[NotifyOwnerChange.onChange](e,t,i){this.status===FactoryStatus.Delivering&&e.rules.deployTime&&this.deliveringUnit&&!this.deliveringUnit.isDestroyed&&this.unitIsInsideFactory(this.deliveringUnit,e,i)&&i.changeObjectOwner(this.deliveringUnit,e.owner)}[NotifyDestroy.onDestroy](e,t,i,r){this.status===FactoryStatus.Delivering&&e.rules.deployTime&&this.deliveringUnit&&!this.deliveringUnit.isDestroyed&&e.deathType!==DeathType.Temporal&&this.unitIsInsideFactory(this.deliveringUnit,e,t)&&t.destroyObject(this.deliveringUnit,i,r)}[NotifyTick_NotifyTick.onTick](i,r){if(this.status===FactoryStatus.Delivering){if(!this.deliveringUnit||this.deliveringUnit.isDestroyed){if(this.buildingProductionTicks=this.buildingProductionTicks??1,0<this.buildingProductionTicks--)return;this.buildingProductionTicks=void 0}else if(!this.unitHasClearedFactory(this.deliveringUnit,i,r))return;return this.status=FactoryStatus.Idle,void(this.deliveringUnit=void 0)}if(i.owner.production&&!i.warpedOutTrait.isActive()){let e=i.owner.production.getPrimaryFactory(this.type);if((e?.warpedOutTrait.isActive()||e===i||e?.factoryTrait?.deliveringUnit&&e.factoryTrait.type===FactoryType.UnitType)&&this.type!==FactoryType.BuildingType){let e=i.owner.production.getQueueForFactory(this.type);if(e&&e.status===QueueStatus.Ready){let t=e.getFirst();if(this.type===FactoryType.AircraftType){let e=this.produceAircraftAt(i,t,r);var s;if(!e)for(s of[...i.owner.buildings].filter(e=>e.factoryTrait?.type===FactoryType.AircraftType&&e.helipadTrait)){if(e)break;e=this.produceAircraftAt(s,t,r)}if(!e)return}else{var a;if(this.produceGroundUnitAt(i,t,r),!this.isCloningVats&&this.type===FactoryType.InfantryType)for(a of[...i.owner.buildings].filter(e=>e.factoryTrait&&e.rules.cloning))a.factoryTrait.status===FactoryStatus.Idle&&a.factoryTrait.produceGroundUnitAt(a,t,r)}i.owner.addUnitsBuilt(t.rules,1),t.creditsSpent=0,t.progress=0,e.shift(t.rules,1),e.currentSize&&(e.status=QueueStatus.Active)}}}}unitIsInsideFactory(e,t,i){return i.map.tileOccupation.isTileOccupiedBy(e.tile,t)&&e.zone!==ZoneType.Air}unitHasClearedFactory(e,t,i){return!i.map.tileOccupation.isTileOccupiedBy(e.tile,t)||e.rules.consideredAircraft&&e.position.tileElevation>=t.art.height}produceGroundUnitAt(t,e,i){let r=i.createUnitForPlayer(e.rules,t.owner);e.rules.trainable&&t.owner.canProduceVeteran(r.rules)&&r.veteranTrait?.setVeteranLevel(VeteranLevel.Veteran),r.isInfantry()&&(r.position.subCell=Infantry_Infantry.SUB_CELLS[0]);let s=this.computeInternalRallyPoint(t,this.type,t.rallyTrait.getRallyPoint(),i.map);this.type!==FactoryType.UnitType&&(s=t.rallyTrait.findRallyPointforUnit(r,s,i.map,!1,t.tile.z));let a;a=this.type===FactoryType.NavalUnitType?s:(e=this.computeExitCoords(t,this.type),i.map.tiles.getByMapCoords(Math.floor(e.rx),Math.floor(e.ry))),r.rules.consideredAircraft&&(s=a);let n;if(t.rallyTrait.getRallyPoint()!==s&&(n=t.rallyTrait.findRallyNodeForUnit(r,i.map)),r.isInfantry()){let t=i.map.tileOccupation.getObjectsOnTileByLayer(n?.tile??s,r.rules.consideredAircraft?LayerType.Air:LayerType.Ground).filter(e=>e.isInfantry()&&e.moveTrait.moveState!==MoveState.Moving).map(e=>e.position.subCell);r.position.subCell=Infantry_Infantry.SUB_CELLS.find(e=>!t.includes(e))??Infantry_Infantry.SUB_CELLS[0]}function o(){var e;r.rules.consideredAircraft?(e=n??{tile:s,onBridge:void 0},r.unitOrderTrait.addTaskNext(new MoveTask(i,e.tile,!!e.onBridge,{closeEnoughTiles:i.rules.general.closeEnough}))):r.unitOrderTrait.addTaskNext(new ExitFactoryTask(i,t,s,n))}r.direction=270,i.spawnObject(r,a),i.traits.filter(NotifyProduceUnit).forEach(e=>{e[NotifyProduceUnit.onProduce](r,i)}),i.events.dispatch(new FactoryProduceUnitEvent(r)),t.rules.deployTime?r.unitOrderTrait.addTask(new TaskGroup(new WaitMinutesTask(t.rules.deployTime),new CallbackTask(()=>{t.isSpawned&&t.buildStatus!==BuildStatus.BuildDown&&o()})).setCancellable(!1)):o(),this.status=FactoryStatus.Delivering,this.deliveringUnit=r}produceAircraftAt(e,t,i){let r=e.traits.find(DockTrait);if(!r)return!1;var s=r.getFirstAvailableDockNumber();if(void 0===s)return!1;let a=i.createUnitForPlayer(t.rules,e.owner);t.rules.trainable&&e.owner.canProduceVeteran(a.rules)&&a.veteranTrait?.setVeteranLevel(VeteranLevel.Veteran);t=r.getDockOffset(s);return a.position.moveToLeptons(e.position.getMapPosition()),a.position.moveByLeptons3(t),i.spawnObject(a,a.position.tile),r.dockUnitAt(a,s),a.isAircraft()&&a.airportBoundTrait&&(a.airportBoundTrait.preferredAirport=e),i.traits.filter(NotifyProduceUnit).forEach(e=>{e[NotifyProduceUnit.onProduce](a,i)}),i.events.dispatch(new FactoryProduceUnitEvent(a)),!0}computeExitCoords(e,t){if(t===FactoryType.InfantryType)return this.computeBarracksDefaultExitCoords(e);if(t===FactoryType.UnitType)return this.computeWarFactoryExitCoords(e);throw new Error("Unsupported factory type "+FactoryType[t])}computeInternalRallyPoint(e,t,i,r){let s,a;if(t===FactoryType.NavalUnitType)a=this.computeNavalInternalRallyPoint(e,i,r);else{if(t===FactoryType.InfantryType)s=this.computeBarracksInternalRallyCoords(e);else{if(t!==FactoryType.UnitType)throw new Error("Unsupported factory type "+FactoryType[t]);s=this.computeWarFactoryInternalRallyCoords(e)}a=r.tiles.getByMapCoords(s.rx,s.ry)}return a??this.findTileAdjacentToBuilding(e,r)}computeDefaultRallyPoint(e,t,i){let r,s;if(t===FactoryType.NavalUnitType)s=this.computeNavalDefaultRallyPoint(e,i);else{if(t===FactoryType.InfantryType)r=this.computeBarracksInternalRallyCoords(e);else{if(t!==FactoryType.UnitType)throw new Error("Unsupported factory type "+FactoryType[t]);r=this.computeWarFactoryDefaultRallyCoords(e)}s=i.tiles.getByMapCoords(r.rx,r.ry)}return s??this.findTileAdjacentToBuilding(e,i)}findTileAdjacentToBuilding(e,t){return new RadialTileFinder(t.tiles,t.mapBounds,e.tile,e.getFoundation(),1,1,()=>!0).getNextTile()}computeBarracksDefaultExitCoords(e){var t=e.getFoundation();let i,r;return t.width<=2||t.height<=2?(i=t.width-1,r=t.height-1,e.rules.gdiBarracks&&2<t.width&&(i=Math.floor(t.width/2))):(i=0,r=t.height-1),{rx:e.tile.rx+i,ry:e.tile.ry+r}}computeBarracksInternalRallyCoords(e){var t=e.getFoundation();let{rx:i,ry:r}=this.computeBarracksDefaultExitCoords(e);return!(t.width<=2||t.height<=2)||e.rules.gdiBarracks?r+=1:e.rules.nodBarracks&&(i+=t.width<=2?1:0,r+=t.height<=2?1:0),{rx:i,ry:r}}computeWarFactoryExitCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+Math.floor(t.width/2),ry:e.tile.ry+Math.floor(t.height/2)}}computeWarFactoryInternalRallyCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+t.width-1,ry:e.tile.ry+Math.floor(t.height/2)}}computeWarFactoryDefaultRallyCoords(e){var t=e.getFoundation();return{rx:e.tile.rx+t.width,ry:e.tile.ry+Math.floor(t.height/2)}}computeNavalDefaultRallyPoint(e,t){let i=new CardinalTileFinder(t.tiles,t.mapBounds,e.centerTile,5,5,e=>e.terrainType===TerrainType.Water&&!t.getObjectsOnTile(e).find(e=>e.isBuilding()||e.isOverlay()&&e.isBridge()));return i.diagonal=!1,i.getNextTile()??t.tiles.getByMapCoords(e.tile.rx+e.getFoundation().width,e.tile.ry+e.getFoundation().height)}computeNavalInternalRallyPoint(e,t,i){t=new Vector2(t.rx,t.ry).sub(new Vector2(e.centerTile.rx,e.centerTile.ry));return i.tiles.getByMapCoords(e.centerTile.rx+Math.sign(t.x)*(Math.floor(e.getFoundation().width/2)+1),e.centerTile.ry+Math.sign(t.y)*(Math.floor(e.getFoundation().height/2)+1))}}(NotifyBuildStatus=NotifyBuildStatus||{}).onStatusChange=Symbol();class RadialBackFirstTileFinder{constructor(e,t,i,r,s,a,n,o=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.foundation=r,this.maxDistance=a,this.predicate=n,this.checkBounds=o,this.distance=s,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){var r=(e,t)=>{t=this.tiles.getByMapCoords(e,t);if(t&&(!this.checkBounds||this.mapBounds.isWithinBounds(t))&&this.predicate(t))return t};do{var s=this.startTile.rx-this.distance,a=this.startTile.ry-this.distance,n=this.startTile.rx+this.foundation.width-1+this.distance,o=this.startTile.ry+this.foundation.height-1+this.distance;let e,t,i;if(0<this.distance){for(t=1+a;t<o;t++)i=r(s,t),i&&(yield i);for(e=s;e<n;e++)i=r(e,a),i&&(yield i);for(t=o-1;t>=a;t--)i=r(n,t),i&&(yield i);for(e=n;e>=s;e--)i=r(e,o),i&&(yield i)}else this.predicate(this.startTile)&&(yield this.startTile)}while(this.distance++,this.distance<=this.maxDistance)}}class FreeUnitTrait{[NotifyBuildStatus.onStatusChange](t,s,a){if(s.buildStatus===BuildStatus.Ready&&t===BuildStatus.BuildUp&&!s.owner.isNeutral){let e;if(a.rules.hasObject(s.rules.freeUnit,ObjectType.Vehicle))e=a.rules.getObject(s.rules.freeUnit,ObjectType.Vehicle);else{if(!a.rules.hasObject(s.rules.freeUnit,ObjectType.Infantry))return void console.warn(`Free unit "${s.rules.freeUnit}" is not a vehicle or infantry type.`);e=a.rules.getObject(s.rules.freeUnit,ObjectType.Infantry)}let i=a.createUnitForPlayer(e,s.owner),r;t=new RadialBackFirstTileFinder(a.map.tiles,a.map.mapBounds,s.tile,s.getFoundation(),1,1,e=>{var t=0<a.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-s.tile.z)<2&&!a.map.terrain.findObstacles({tile:e,onBridge:void 0},i).length;return!r&&t&&(r=e),t&&!a.map.getObjectsOnTile(e).find(e=>e.isOverlay())}).getNextTile()??r;if(!t)return s.owner.removeOwnedObject(i),i.dispose(),void(s.owner.credits+=i.purchaseValue);a.spawnObject(i,t)}}}class CrewedTrait{[NotifySell.onSell](e,t){this.spawnSurvivors(e,t)}[NotifyDestroy.onDestroy](e,t,i,r){r||i?.obj===e&&i.weapon?.rules.suicide||e.isVehicle()&&e.moveTrait.isMoving()||e.crashableTrait||this.spawnSurvivors(e,t)}spawnSurvivors(r,s){var e=s.rules.general.crew,t=r.owner.country.side;let i,a;if(t===SideType.GDI)i=e.alliedSurvivorDivisor,a=e.alliedCrew;else if(t===SideType.Nod)i=e.sovietSurvivorDivisor,a=e.sovietCrew;else{if(t!==SideType.ThirdSide)return;i=e.thirdSurvivorDivisor,a=e.thirdCrew}let n=s.sellTrait.computeRefundValue(r)/i;n=0<n&&n<1?1:Math.floor(n),n=r.isVehicle()?Math.min(1,n):Math.min(5,n);let o=[];for(let e=0;e<n;e++)o.push(a);if(0<o.length){r.rules.constructionYard&&(o[o.length-1]=s.rules.general.engineer);var l,h=s.map.tiles.getInRectangle(r.tile,r.getFoundation()).filter(e=>s.map.isWithinBounds(e));let i=[...h];for(l of o){var c=s.rules.getObject(l,ObjectType.Infantry);if(s.map.terrain.getPassableSpeed(r.tile,c.speedType,!0,!r.isBuilding()&&r.onBridge,void 0,!0)){let e=s.createUnitForPlayer(c,r.owner),t=i.length?i.splice(s.generateRandomInt(0,i.length-1),1)[0]:void 0;t=t||h[s.generateRandomInt(0,h.length-1)],e.isInfantry()&&(e.position.subCell=Infantry_Infantry.SUB_CELLS[0]),e.veteranTrait&&r.owner.canProduceVeteran(e.rules)&&e.veteranTrait.setVeteranLevel(VeteranLevel.Veteran),s.spawnObject(e,t),r.isBuilding()&&e.unitOrderTrait.addTask(new ScatterTask(s,void 0,{ignoredBlockers:r.isDestroyed?void 0:[r]}))}}}}}class CabHutTrait{constructor(e,t){this.gameObject=e,this.bridges=t,this.checkedClosestBridge=!1}canRepairBridge(){var e=this.findClosestBridgeBounds();return e?this.bridges.canBeRepaired(e):(console.warn(`No bridge associated with hut at ${this.gameObject.tile.rx}, ${this.gameObject.tile.ry}.`),!1)}repairBridge(t,i){var r=this.findClosestBridgeBounds();if(!r)throw new Error("No bridge bounds found");var e=this.bridges.findDestroyedPieceTiles(r),s=r.start.rx!==r.end.rx;let a;a=r.isHigh?BridgeOverlayTypes.calculateHighBridgeOverlayId(r.type,s):BridgeOverlayTypes.calculateLowBridgeOverlayId(r.type,s);var n,o,l=t.rules.getOverlayName(a);for(n of e){let e=t.createObject(ObjectType.Overlay,l);e.overlayId=a,e.value=0,e.position.tileElevation=r.isHigh?4:0,t.spawnObject(e,n),this.updateUnitsUnderBridgePiece(n,r,t,i)}for(o of this.bridges.findBridgePieces(r))o.obj.bridgeTrait.bridgeSpec=r}updateUnitsUnderBridgePiece(e,i,r,s){var a;for(let t of this.bridges.getPieceTiles(this.bridges.getPieceAtTile(e)))if(i.isHigh){let e=r.map.getGroundObjectsOnTile(t).filter(e=>e.tile===t&&e.isUnit()&&!e.unitOrderTrait.hasTasks()&&e.rules.tooBigToFitUnderBridge);e.forEach(e=>e.unitOrderTrait.addTask(new ScatterTask(r)))}else for(a of r.map.getGroundObjectsOnTile(t))a.isUnit()&&(r.map.terrain.getPassableSpeed(t,a.rules.speedType,a.isInfantry(),!0)?(a.zone=ZoneType.Ground,a.onBridge=!0):a.isDestroyed||r.destroyObject(a,{player:s}))}demolishBridge(e,t){var i=this.getBridgePieces();if(i)for(var r of i)r.obj.isLowBridge()&&e.map.getTileZone(r.obj.tile,!0)!==ZoneType.Water||r.obj.isDestroyed||(r.obj.deathType=DeathType.Demolish,e.destroyObject(r.obj,t,!0))}getBridgePieces(){var e=this.findClosestBridgeBounds();if(e)return this.bridges.findBridgePieces(e)}findClosestBridgeBounds(){return this.checkedClosestBridge||(this.checkedClosestBridge=!0,this.closestBridge=this.bridges.findClosestBridgeSpec(this.gameObject.tile)),this.closestBridge}dispose(){this.gameObject=void 0}}class OilDerrickTrait{constructor(){this.isActive=!1,this.produceCashCooldown=0}[NotifySpawn.onSpawn](e){e.owner.isNeutral||(this.isActive=!0)}[NotifyOwnerChange.onChange](e,t){t.isNeutral&&!e.owner.isNeutral&&(e.owner.credits=Math.max(0,e.owner.credits+e.rules.produceCashStartup),0<e.rules.produceCashStartup&&(e.owner.creditsGained+=e.rules.produceCashStartup),this.isActive=!0,this.produceCashCooldown=e.rules.produceCashDelay)}[NotifyTick_NotifyTick.onTick](e){this.isActive&&(this.produceCashCooldown--,this.produceCashCooldown<=0&&(this.produceCashCooldown=e.rules.produceCashDelay,e.owner.credits=Math.max(0,e.owner.credits+e.rules.produceCashAmount),0<e.rules.produceCashAmount&&(e.owner.creditsGained+=e.rules.produceCashAmount)))}}const wallTypes=[[0,0,0,0],[1,0,0,0],[0,1,0,0],[1,1,0,0],[0,0,1,0],[1,0,1,0],[0,1,1,0],[1,1,1,0],[0,0,0,1],[1,0,0,1],[0,1,0,1],[1,1,0,1],[0,0,1,1],[1,0,1,1],[0,1,1,1],[1,1,1,1]];class WallTrait{constructor(){this.linkedDamageHandled=!1,this.wallType=0}[NotifySpawn.onSpawn](e,t){e.isBuilding()?this.connectWall(e,t.map):this.wallType=e.value}[NotifyUnspawn.onUnspawn](e,t){this.updateAdjacentWalls(e,t.map)}[NotifyDamage.onDamage](e,t,i,r){if(!this.linkedDamageHandled){var s=Math.floor(i/2);if(s)for(var a of t.map.tiles.getAllNeighbourTiles(e.tile))if(a.landType===LandType.Wall){let e=t.map.getObjectsOnTile(a).find(e=>(e.isBuilding()||e.isOverlay())&&e.wallTrait);e.wallTrait.linkedDamageHandled=!0,e.healthTrait.inflictDamage(s,r,t),e.wallTrait.linkedDamageHandled=!1,e.healthTrait.health||t.destroyObject(e,r)}}}updateAdjacentWalls(t,e){let i=new CardinalTileFinder(e.tiles,e.mapBounds,t.tile,1,1);for(i.diagonal=!1;r=i.getNextTile();){var r=e.getObjectsOnTile(r).find(e=>(e.isBuilding()||e.isOverlay())&&e.name===t.rules.name);r&&this.connectWall(r,e)}}connectWall(e,i){let t=this.getAdjacentWallData(e.tile,e.name,i);this.updateWallType(e,t.map(e=>e.direction)),t.forEach(e=>{let t=this.getAdjacentWallData(e.tile,e.wall.name,i);this.updateWallType(e.wall,t.map(e=>e.direction))})}updateWallType(e,t){let i=[0,0,0,0];for(var r of t)0===r[0]&&-1===r[1]&&(i[0]=1),1===r[0]&&0===r[1]&&(i[1]=1),0===r[0]&&1===r[1]&&(i[2]=1),-1===r[0]&&0===r[1]&&(i[3]=1);t=this.findWallType(i);e.wallTrait.wallType=t,e.isOverlay()&&(e.value=t)}findWallType(t){for(let e=0;e<wallTypes.length;++e){var i=wallTypes[e];if(i[0]===t[0]&&i[1]===t[1]&&i[2]===t[2]&&i[3]===t[3])return e}return console.warn("Invalid wall directions",t),0}getAdjacentWallData(e,t,i){var r;let s=[];for(r of[[0,1],[0,-1],[1,0],[-1,0]]){var a={x:e.rx+r[0],y:e.ry+r[1]},n=i.tiles.getByMapCoords(a.x,a.y);n&&((a=i.getObjectsOnTile(n).find(e=>(e.isBuilding()||e.isOverlay())&&e.name===t))&&s.push({direction:r,tile:n,wall:a}))}return s}}const CHARGERS_TO_POWER_ON=2,CHARGERS_TO_OVERPOWER=1;class OverpoweredTrait{constructor(e){this.obj=e,this.chargers=new Set}isOverpowered(){let e=CHARGERS_TO_OVERPOWER;return this.obj?.poweredTrait?.isPoweredOn(!0)||(e+=CHARGERS_TO_POWER_ON),this.chargers.size>=e}hasChargersToPowerOn(){return this.chargers.size>=CHARGERS_TO_POWER_ON}chargeFrom(e){this.chargers.add(e),this.swapAttackTaskWeapon()}[NotifyTick_NotifyTick.onTick](i){if(0<this.chargers.size){let t=!1;this.chargers.forEach(e=>{(e.isDestroyed||e.isCrashing||e.owner!==i.owner||e.attackTrait?.currentTarget?.obj!==i)&&(this.chargers.delete(e),t=!0)}),t&&this.swapAttackTaskWeapon()}}swapAttackTaskWeapon(){let e=this.obj?.unitOrderTrait.getCurrentTask();var t;e instanceof AttackTask&&((t=this.getWeapon())?e.setWeapon(t):e.cancel())}getWeapon(){return this.isOverpowered()?this.obj?.secondaryWeapon:this.obj?.primaryWeapon}dispose(){this.obj=void 0,this.chargers.clear()}}class UnitRepairFinishEvent{constructor(e,t){this.target=e,this.from=t,this.type=EventType.UnitRepairFinish}}class UnitRepairStartEvent{constructor(e){this.target=e,this.type=EventType.UnitRepairStart}}!function(e){e[e.Idle=0]="Idle",e[e.Repairing=1]="Repairing"}(RepairStatus=RepairStatus||{});class UnitRepairTrait{constructor(){this.status=RepairStatus.Idle,this.cooldownTicks=0,this.lastRepairTickSuccessful=!1}[NotifySpawn.onSpawn](e,t){this.resetRallyPoint(e,t)}resetRallyPoint(e,t){var i;e.factoryTrait||(i=this.computeDefaultRallyPoint(e,t.map),e.rallyTrait.changeRallyPoint(i,e,t))}[NotifyTick_NotifyTick.onTick](t,i){if(t.dockTrait&&(!t.rules.needsEngineer||!t.owner.isNeutral))if(!t.dockTrait.hasDockedUnits()||t.dockTrait.getDockedUnits().some(e=>e.zone===ZoneType.Air)||t.poweredTrait&&!t.poweredTrait.isPoweredOn())this.status=RepairStatus.Idle;else if(this.cooldownTicks<=0){var r,s,a=i.rules.general.repair,a=t.rules.unitReload?a.reloadRate:a.uRepairRate;this.cooldownTicks+=GameSpeed.BASE_TICKS_PER_SECOND*a*60;let e=!1;for(r of t.dockTrait.getDockedUnits())r.zone!==ZoneType.Air&&(r.healthTrait.health<100&&i.areFriendly(r,t)?(this.tickRepair(r,i,t)&&(e=!0),!e||this.status!==RepairStatus.Idle&&this.lastRepairTickSuccessful||t.helipadTrait||i.events.dispatch(new UnitRepairStartEvent(r))):((s=t.rallyTrait.findRallyNodeForUnit(r,i.map))&&(t.dockTrait.undockUnit(r),r.unitOrderTrait.addTask(new MoveTask(i,s.tile,!!s.onBridge,{closeEnoughTiles:i.rules.general.closeEnough}))),t.helipadTrait||i.events.dispatch(new UnitRepairFinishEvent(r,t))));this.lastRepairTickSuccessful=e,this.status=e?RepairStatus.Repairing:RepairStatus.Idle}else this.cooldownTicks--}tickRepair(e,t,i){var r=t.rules.general.repair,s=Math.floor(r.repairStep),a=r.repairPercent;let n;if(a){r=a*e.purchaseValue/e.healthTrait.maxHitPoints,a=Math.min(i.owner.credits,Math.max(1,Math.floor(r*s)));if(n=r&&a?Math.floor(a/r):s,!a)return!1;i.owner.credits-=a}else n=s;return n=Math.min(n,e.healthTrait.maxHitPoints-e.healthTrait.getHitPoints()),!!n&&(e.healthTrait.healBy(n,i,t),!0)}computeDefaultRallyPoint(e,t){var i=e.getFoundation(),i=new Vector2(e.tile.rx,e.tile.ry+i.height);return t.tiles.getByMapCoords(i.x,i.y)??e.tile}}class RallyTrait{getRallyPoint(){return this.rallyPoint}changeRallyPoint(e,t,i){i=this.findValidRallyPoint(t,e,i.map);i&&(this.rallyPoint=i)}findValidRallyPoint(i,e,r){let t=new RadialTileFinder(r.tiles,r.mapBounds,e,{width:1,height:1},0,20,e=>i.rules.naval===(e.terrainType===TerrainType.Water)&&!r.tileOccupation.isTileOccupiedBy(e,i)),s=t.getNextTile();if(!s&&i.factoryTrait?.type===FactoryType.NavalUnitType){var{width:a,height:n}=i.getFoundation();for(let t=0;t<a;t++)for(let e=0;e<n;e++){var o=r.tiles.getByMapCoords(i.tile.rx+t,i.tile.ry+e);if(!o)break;if(0<r.terrain.getPassableSpeed(o,SpeedType.Float,!1,!1)){s=o;break}}}return s}findRallyNodeForUnit(e,t){if(this.rallyPoint){var i=this.findRallyPointforUnit(e,this.rallyPoint,t,!0);return{tile:i,onBridge:e.rules.naval?void 0:t.tileOccupation.getBridgeOnTile(i)}}}findRallyPointforUnit(i,e,r,s,a){let n=i.rules.naval?void 0:r.tileOccupation.getBridgeOnTile(e),o=i.rules.movementZone===MovementZone.Fly,t=new RadialTileFinder(r.tiles,r.mapBounds,e,{width:1,height:1},0,5,e=>{var t=!n||n.isHighBridge()?r.tileOccupation.getBridgeOnTile(e):void 0;return!(o?[]:r.terrain.findObstacles({tile:e,onBridge:t},i)).length&&(void 0===a||Math.abs(a-(e.z+(t?.tileElevation??0)))<4)&&(!s||!r.getObjectsOnTile(e).find(e=>e.isBuilding()&&!e.isDestroyed))&&(o||0<r.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!!t))});return t.getNextTile()??e}}class Timer{constructor(){this.activeTicks=0}isActive(){return 0<this.activeTicks}setActiveFor(e,t){this.activeTicks=e,this.activeFor=e,this.activeSince=t}reset(){this.activeTicks=0,this.activeSince=void 0,this.activeFor=void 0}getTicksLeft(){return this.activeTicks}getInitialTicks(){return this.activeFor??0}tick(e){return 0<this.activeTicks&&(this.activeTicks--,this.activeTicks<=0||void 0!==this.activeSince&&e-this.activeSince>this.activeFor)&&(this.reset(),!0)}}class C4ChargeTrait{constructor(){this.timer=new Timer}hasCharge(){return this.timer.isActive()}setCharge(e,t){this.hasCharge()||(this.timer.setActiveFor(e),this.attackerInfo=t)}[NotifyTick_NotifyTick.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.invulnerableTrait.isActive()||(e.isBuilding()&&e.cabHutTrait?e.cabHutTrait.demolishBridge(t,this.attackerInfo):(e.deathType=DeathType.Demolish,t.destroyObject(e,this.attackerInfo,!0))))}}class HelipadTrait{[NotifyOwnerChange.onChange](e,t,i){this.checkAircraftsForPlayer(t,i)}[NotifyUnspawn.onUnspawn](e,t){this.checkAircraftsForPlayer(e.owner,t)}checkAircraftsForPlayer(e,t){let i=t.rules.general.padAircraft;var r;for(r of e.getOwnedObjectsByType(ObjectType.Aircraft).filter(e=>i.includes(e.name)))r.airportBoundTrait&&(r.airportBoundTrait.preferredAirport=void 0)}}class UnitReloadTrait{[NotifyTick_NotifyTick.onTick](t,i){if(t.dockTrait&&t.dockTrait.hasDockedUnits()&&!t.dockTrait.getDockedUnits().every(e=>!this.canReloadUnit(e)))if(void 0===this.cooldownTicks&&(this.cooldownTicks=GameSpeed.BASE_TICKS_PER_SECOND*i.rules.general.repair.reloadRate*60),this.cooldownTicks<=0){this.cooldownTicks=GameSpeed.BASE_TICKS_PER_SECOND*i.rules.general.repair.reloadRate*60;let e=t.dockTrait.getDockedUnits();var r;for(r of 0===e[0].ammo?e.slice(0,1):e)this.canReloadUnit(r)&&r.ammoTrait.ammo++}else this.cooldownTicks--}canReloadUnit(e){return!(!e.ammoTrait||!e.rules.manualReload||e.ammoTrait.isFull()||e.zone===ZoneType.Air)}}class WaitForBuildUpTask extends TaskGroup{constructor(e,t){super(new WaitMinutesTask(e),new CallbackTask(e=>e.setBuildStatus(BuildStatus.Ready,t))),this.cancellable=!1}}class SuperWeaponTrait{constructor(e){this.name=e}getSuperWeapon(e){return e.owner.superWeaponsTrait?.get(this.name)}[NotifySpawn.onSpawn](e,t){this.addSuperWeaponToPlayerIfNeeded(e.owner,t)}[NotifyUnspawn.onUnspawn](e,t){this.removeSuperWeaponFromPlayerIfNeeded(e.owner)}[NotifyOwnerChange.onChange](e,t,i){this.removeSuperWeaponFromPlayerIfNeeded(t),this.addSuperWeaponToPlayerIfNeeded(e.owner,i)}addSuperWeaponToPlayerIfNeeded(t,i){if(t.superWeaponsTrait&&!t.superWeaponsTrait.has(this.name)){let e=i.createSuperWeapon(this.name,t);t.superWeaponsTrait.add(e),e.rules.isPowered&&t.powerTrait?.isLowPower()&&e.pauseTimer()}}removeSuperWeaponFromPlayerIfNeeded(e){let t=e.superWeaponsTrait;t&&(e.getOwnedObjectsByType(ObjectType.Building).some(e=>e.superWeaponTrait?.name===this.name)||(e=t.get(this.name))&&!e.isGift&&t.remove(this.name))}}const TEMPORARY_REVEAL_SECONDS=5,TEMPORARY_REVEAL_RADIUS=3,OBJECT_REVEAL_RADIUS=4.25,SHROUD_TYPE_BITS=3,SHROUD_TYPE_MASK=(1<<SHROUD_TYPE_BITS)-1;!function(e){e[e.Unexplored=0]="Unexplored",e[e.TemporaryReveal=1]="TemporaryReveal",e[e.Explored=2]="Explored"}(ShroudType=ShroudType||{}),function(e){e[e.Darken=8]="Darken"}(ShroudFlag=ShroudFlag||{});class MapShroud{constructor(){this.invalidations=new Map,this.temporaryReveals=new Map,this.fullInvalidation=!1,this._onChange=new EventDispatcher}get onChange(){return this._onChange.asEvent()}fromTiles(e){var t,i=e.getMapSize(),r=e.getMaxTileHeight(),r=this.padding=(r+r%2)/2;this.size={width:i.width+r,height:i.height+r},this.tiles=new Uint8Array(this.size.width*this.size.height),this.tiles.fill(ShroudType.Unexplored),this.tileElevation=new Uint8Array(this.size.width*this.size.height);for(t of e.getAll()){var s=this.getTileIndex(t);this.tileElevation[s]=Math.max(this.tileElevation[s],t.terrainType===TerrainType.Cliff&&0<t.z?t.z-1:t.z)}return this}getSize(){return this.size}getTileIndex(e){var{sx:t,sy:e}=this.rxyzToSxy(e.rx,e.ry,e.z);return t+e*this.size.width}rxyzToSxy(e,t,i){i=(i|=0)+i%2;return{sx:e-i/2+this.padding,sy:t-i/2+this.padding}}sxyzToRxy(e,t,i){return{rx:e+Math.ceil(i/2)-this.padding,ry:t+Math.ceil(i/2)-this.padding}}shroudCoordsToWorld({sx:e,sy:t}){return this.sxyzToRxy(e,t,0)}findTilesAtShroudCoords({sx:t,sy:i},r){var e=r.getMaxTileHeight(),s=e+e%2;let a=[];for(let e=0;e<=s;e+=2){var n=e+e%2,{rx:o,ry:n}=this.sxyzToRxy(t,i,n),n=r.getByMapCoords(o,n);n?.z===e&&a.push(n)}return a}clone(){let e=new MapShroud;return e.tiles=this.tiles.slice(),e.size=this.size,e.padding=this.padding,e.tileElevation=this.tileElevation,e}copy(e){this.tiles=e.tiles.slice(),this.size=e.size,this.padding=e.padding,this.tileElevation=e.tileElevation}merge(e){if(this.size.width!==e.size.width||this.size.height!==e.size.height)throw new Error("Size mismatch");var i=e.tiles;for(let e=0,t=this.tiles.length;e<t;e++)this.tiles[e]=Math.max(i[e]&SHROUD_TYPE_MASK,this.tiles[e]&SHROUD_TYPE_MASK)|(i[e]|this.tiles[e])>>SHROUD_TYPE_BITS<<SHROUD_TYPE_BITS}isShrouded(e,t=0){t=this.rxyzToSxy(e.rx,e.ry,e.z+t);return this.getShroudTypeByShroudCoords(t)===ShroudType.Unexplored}getShroudType(e){return this.tiles[this.getTileIndex(e)]&SHROUD_TYPE_MASK}isFlagged(e,t){return 0!=(this.tiles[this.getTileIndex(e)]&t)}getShroudTypeByTileCoords(e,t,i){return this.getShroudTypeByShroudCoords(this.rxyzToSxy(e,t,i))}getShroudTypeByShroudCoords({sx:e,sy:t}){return e<0||t<0||e>=this.size.width||t>=this.size.height?ShroudType.Unexplored:this.tiles[e+t*this.size.width]&SHROUD_TYPE_MASK}invalidateFull(){this.fullInvalidation=!0}invalidate(e,t,i){var r=e.sx+e.sy*this.size.width;let s=this.invalidations.get(r);s||(s={center:e,elevation:0,radius:0},this.invalidations.set(r,s)),s.elevation=Math.max(s.elevation,t),s.radius=Math.max(s.radius,i)}revealFrom(e){var t,i;e.isBuilding()&&e.wallTrait||(t=e.sight)&&(i=e.tile.z+e.tileElevation,e=this.rxyzToSxy(e.tile.rx,e.tile.ry,i),this.invalidate(e,i,t))}revealAround(e,t){e=this.rxyzToSxy(e.rx,e.ry,e.z);this.invalidate(e,Number.POSITIVE_INFINITY,t)}unrevealAround(e,t){var i=[],e=this.rxyzToSxy(e.rx,e.ry,e.z);this.setValueAround(e,t,Number.POSITIVE_INFINITY,i,ShroudType.Unexplored,ShroudType.Explored),this._onChange.dispatch(this,{type:"incremental",coords:i})}revealTemporarily(e){e=this.rxyzToSxy(e.tile.rx,e.tile.ry,e.tile.z+e.tileElevation);this.temporaryReveals.set(e,TEMPORARY_REVEAL_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND)}revealObject(e){e=this.rxyzToSxy(e.tile.rx,e.tile.ry,e.tile.z+e.tileElevation);this.invalidate(e,Number.POSITIVE_INFINITY,OBJECT_REVEAL_RADIUS)}toggleFlagsAround(e,t,i,r){var s=[],e=this.rxyzToSxy(e.rx,e.ry,e.z);this.setValueAround(e,t,Number.POSITIVE_INFINITY,s,void 0,void 0,r?{setFlags:i}:{clearFlags:i}),this._onChange.dispatch(this,{type:"incremental",coords:s})}update(){let i=[];if(this.invalidations.size){for(var e of this.invalidations.values())this.setValueAround(e.center,e.radius,e.elevation,i,ShroudType.Explored,[ShroudType.Unexplored,ShroudType.TemporaryReveal]);this.invalidations.clear()}this.temporaryReveals.size&&this.temporaryReveals.forEach((e,t)=>{e<=0?(this.setValueAround(t,TEMPORARY_REVEAL_RADIUS,Number.POSITIVE_INFINITY,i,ShroudType.Unexplored,ShroudType.TemporaryReveal),this.temporaryReveals.delete(t)):(e===TEMPORARY_REVEAL_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND&&this.setValueAround(t,TEMPORARY_REVEAL_RADIUS,Number.POSITIVE_INFINITY,i,ShroudType.TemporaryReveal,ShroudType.Unexplored),this.temporaryReveals.set(t,e-1))}),this.fullInvalidation?(this.fullInvalidation=!1,this._onChange.dispatch(this,{type:"full"})):i.length&&this._onChange.dispatch(this,{type:"incremental",coords:i})}setValueAround(r,s,a,n,o,l=void 0,{setFlags:h,clearFlags:c}={}){var e=Math.ceil(s),t=clamp(r.sx-e,0,this.size.width-1),u=clamp(r.sx+e,0,this.size.width-1),d=clamp(r.sy-e,0,this.size.height-1),p=clamp(r.sy+e,0,this.size.height-1),g=this.size.width;for(let i=t;i<=u;i++)for(let t=d;t<=p;t++){var m=i+t*g,y=this.tiles[m]&SHROUD_TYPE_MASK,T=this.tiles[m]>>SHROUD_TYPE_BITS<<SHROUD_TYPE_BITS;let e=T;void 0!==h&&(e|=h),void 0!==c&&(e&=~c),void 0!==l&&("number"!=typeof l?!l.includes(y):l!==y)||((i-r.sx)*(i-r.sx)+(t-r.sy)*(t-r.sy)>s*s+1||this.tileElevation[m]>=a+4||(this.tiles[m]=(o??y)|e,y===o&&T===e||n.push({sx:i,sy:t})))}}revealAll(){this.tiles.fill(ShroudType.Explored),this._onChange.dispatch(this,{type:"clear"})}reset(){this.tiles.fill(ShroudType.Unexplored),this._onChange.dispatch(this,{type:"cover"})}}const GAP_REFRESH_SECONDS=5;class GapGeneratorTrait{constructor(e){this.radiusTiles=e,this.refreshTicks=0}[NotifyTick_NotifyTick.onTick](e,t){0<this.refreshTicks&&this.refreshTicks--,this.refreshTicks<=0&&this.update(e,t)}[NotifySpawn.onSpawn](e,t){this.markGapTilesForFriendlies(e,e.owner,t,!0)}[NotifyUnspawn.onUnspawn](e,t){this.markGapTilesForFriendlies(e,e.owner,t,!1),this.update(e,t)}[NotifyOwnerChange.onChange](e,t,i){this.markGapTilesForFriendlies(e,t,i,!1),this.markGapTilesForFriendlies(e,e.owner,i,!0),this.update(e,i)}[NotifyWarpChange_NotifyWarpChange.onChange](e,t,i){this.markGapTilesForFriendlies(e,e.owner,t,!i),i&&this.update(e,t)}markGapTilesForFriendlies(i,e,r,t){let s=[e,...r.alliances.getAllies(e)],a;for(var n of s){let e=r.mapShroudTrait.getPlayerShroud(n);if(e&&(e.toggleFlagsAround(i.tile,this.radiusTiles,ShroudFlag.Darken,t),!t)){if(!a){let t=new RangeHelper(r.map.tileOccupation);a=s.map(e=>[...e.buildings]).flat().filter(e=>e.gapGeneratorTrait&&e!==i&&t.tileDistance(e,i)<=e.gapGeneratorTrait.radiusTiles+this.radiusTiles)}for(var o of a)e.toggleFlagsAround(o.tile,o.gapGeneratorTrait.radiusTiles,ShroudFlag.Darken,!0)}}}update(t,i){this.refreshTicks=GAP_REFRESH_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND;let r;var s,a,n,o,l=t.owner.buildings.has(t)&&t.poweredTrait?.isPoweredOn();for(s of i.getCombatants())if(s!==t.owner&&!i.alliances.areAllied(t.owner,s)){let e=i.mapShroudTrait.getPlayerShroud(s);if(e)if(l){e.unrevealAround(t.tile,this.radiusTiles),r||(n=this.radiusTiles+TechnoRules.MAX_SIGHT,a=new Vector2(t.tile.rx,t.tile.ry).addScalar(-n),n=new Vector2(t.tile.rx,t.tile.ry).addScalar(n),r=i.map.technosByTile.queryRange(new Box2(a,n)));for(o of r)o.owner===s||i.alliances.areAllied(o.owner,s)?e.revealFrom(o):o.rules.revealToAll&&e.revealObject(o)}else[...s.buildings].some(e=>e.rules.spySat)&&e.revealAround(t.tile,this.radiusTiles)}}}const SCAN_FRAMES=GameSpeed.BASE_TICKS_PER_SECOND;class PsychicDetectorTrait{constructor(e){this.radiusTiles=e,this.detectionLines=[],this.nextScan=SCAN_FRAMES}[NotifyTick_NotifyTick.onTick](e,t){e.owner.powerTrait?.isLowPower()?this.disable():(0<this.nextScan&&this.nextScan--,this.nextScan<=0&&(this.nextScan=SCAN_FRAMES,this.detectionLines=this.scan(e,t)))}[NotifyWarpChange_NotifyWarpChange.onChange](e,t,i){i&&this.disable()}disable(){this.detectionLines.length&&(this.detectionLines=[],this.nextScan=0)}scan(t,i){var e=i.getCombatants().filter(e=>e!==t.owner&&!i.alliances.areAllied(e,t.owner));let r=[],s=new RangeHelper(i.map.tileOccupation);var a,n,o,l=e=>s.distance2(e,t)/Coords.LEPTONS_PER_TILE<=this.radiusTiles;for(a of e)for(var h of a.getOwnedObjects())h.attackTrait?.currentTarget?l((n=h.attackTrait.currentTarget).obj??n.tile)&&r.push({source:h,target:n}):h.isUnit()&&h.unitOrderTrait.targetLinesConfig&&((o=h.unitOrderTrait.targetLinesConfig).target?l(o.target)&&(n=i.createTarget(o.target,o.target.tile),r.push({source:h,target:n})):(o=o.pathNodes[0])&&l(o.tile)&&(o=i.createTarget(o.onBridge,o.tile),r.push({source:h,target:o})));return r}}const HEALING_SECONDS=5;class HospitalTrait{constructor(){this.healQueue=[]}addToHealQueue(e){return this.healQueue.push(e),this.healQueue.length-1}unitIsFirstInHealQueue(e){return this.healQueue[0]===e}removeFromHealQueue(e){e=this.healQueue.indexOf(e);-1!==e&&this.healQueue.splice(e,1)}startHealing(e){if(this.unit)throw new Error(`Already busy healing unit ${ObjectType[this.unit.type]}#${this.unit.id}}`);this.unit=e,this.healTicks=HEALING_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND}[NotifyTick_NotifyTick.onTick](e,t){var i;this.healQueue=this.healQueue.filter(e=>!e.isDestroyed&&!e.isCrashing),this.unit&&void 0!==this.healTicks&&(0<this.healTicks&&this.healTicks--,this.healTicks<=0&&(this.healTicks=void 0,this.removeFromHealQueue(this.unit),this.unit.healthTrait.healToFull(e,t),e.ammoTrait&&e.ammoTrait.ammo--,this.evacuate(this.unit,e,t),i=this.unit,this.unit=void 0,t.events.dispatch(new UnitRepairFinishEvent(i,e))))}[NotifyDestroy.onDestroy](e,t,i){this.unit&&(this.unit.deathType=e.deathType,t.destroyObject(this.unit,i,!0),this.unit=void 0)}evacuate(t,i,r){let e;var s={x:i.tile.rx,y:i.tile.ry+i.art.foundation.height},s=r.map.tiles.getByMapCoords(s.x,s.y);s&&r.map.isWithinBounds(s)&&this.canEvacuateTo(s,t,i,r)&&(e=s),e=e||new RadialTileFinder(r.map.tiles,r.map.mapBounds,i.tile,i.art.foundation,1,1,e=>this.canEvacuateTo(e,t,i,r)).getNextTile(),e?(r.unlimboObject(t,e),t.unitOrderTrait.addTask(new ScatterTask(r))):r.destroyObject(t,{player:t.owner})}canEvacuateTo(e,t,i,r){return 0<r.map.terrain.getPassableSpeed(e,t.rules.speedType,t.isInfantry(),!1)&&Math.abs(e.z-i.tile.z)<2&&!r.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length}}class DelayedKillTrait{constructor(){this.timer=new Timer}isActive(){return this.timer.isActive()}activate(e,t){this.isActive()||(this.timer.setActiveFor(e),this.attackerInfo=t)}[NotifyTick_NotifyTick.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.invulnerableTrait.isActive()||e.isBuilding()&&e.cabHutTrait||t.destroyObject(e,this.attackerInfo,!0,!0))}}!function(e){e[e.BuildUp=0]="BuildUp",e[e.Ready=1]="Ready",e[e.BuildDown=2]="BuildDown"}(BuildStatus=BuildStatus||{});class Building extends Techno_Techno{get buildStatus(){return this._buildStatus}static factory(e,t,i,r,s,a){let n=new this(e,t,r);return t.canBeOccupied&&(n.garrisonTrait=new GarrisonTrait(n,i.audioVisual.conditionRed,t.maxNumberOccupants),n.traits.add(n.garrisonTrait)),t.canC4&&!t.wall&&(n.c4ChargeTrait=new C4ChargeTrait,n.traits.add(n.c4ChargeTrait)),t.eligibleForDelayKill&&(n.delayedKillTrait=new DelayedKillTrait,n.traits.add(n.delayedKillTrait)),t.bridgeRepairHut&&(n.cabHutTrait=new CabHutTrait(n,a),n.traits.add(n.cabHutTrait)),t.crewed&&(n.crewedTrait=new CrewedTrait,n.traits.add(n.crewedTrait)),t.turret&&(n.turretTrait=new TurretTrait,n.traits.add(n.turretTrait)),t.overpowerable&&(n.overpoweredTrait=new OverpoweredTrait(n),n.traits.add(n.overpoweredTrait)),(t.powered&&0!==t.power||t.needsEngineer)&&(n.poweredTrait=new PoweredTrait(n),n.traits.add(n.poweredTrait)),(t.factory||t.cloning)&&(n.factoryTrait=new FactoryTrait(t.cloning?FactoryType.InfantryType:t.factory,t.cloning),n.traits.add(n.factoryTrait)),t.superWeapon&&(n.superWeaponTrait=new SuperWeaponTrait(t.superWeapon),n.traits.add(n.superWeaponTrait)),t.numberOfDocks&&(n.dockTrait=new DockTrait(n,s,t.numberOfDocks,r.dockingOffsets),n.traits.add(n.dockTrait),t.helipad&&(n.helipadTrait=new HelipadTrait,n.traits.add(n.helipadTrait)),(t.unitRepair||t.unitReload)&&(n.unitRepairTrait=new UnitRepairTrait,n.traits.add(n.unitRepairTrait)),t.unitReload&&(n.unitReloadTrait=new UnitReloadTrait,n.traits.add(n.unitReloadTrait))),t.hospital&&(n.hospitalTrait=new HospitalTrait,n.traits.add(n.hospitalTrait)),(t.factory||t.cloning||t.numberOfDocks)&&(n.rallyTrait=new RallyTrait,n.traits.add(n.rallyTrait)),t.freeUnit&&n.traits.add(new FreeUnitTrait),t.produceCashStartup&&n.traits.add(new OilDerrickTrait),t.wall&&(n.wallTrait=new WallTrait,n.traits.add(n.wallTrait)),t.gapGenerator&&(n.gapGeneratorTrait=new GapGeneratorTrait(t.gapRadiusInCells),n.traits.add(n.gapGeneratorTrait)),t.psychicDetectionRadius&&(n.psychicDetectorTrait=new PsychicDetectorTrait(t.psychicDetectionRadius),n.traits.add(n.psychicDetectorTrait)),n}constructor(e,t,i){super(ObjectType.Building,e,t,i),this.showWeaponRange=!1,this.direction=0,this._buildStatus=BuildStatus.BuildUp,this.lastBuildStatus=this.buildStatus}isBuilding(){return!0}getFoundation(){return this.art.foundation}getFoundationCenterOffset(){var e=this.getFoundation();return new Vector2(e.width/2*Coords.LEPTONS_PER_TILE,e.height/2*Coords.LEPTONS_PER_TILE)}update(e){this.buildStatus!==BuildStatus.BuildUp||this.unitOrderTrait.hasTasks()||this.unitOrderTrait.addTask(new WaitForBuildUpTask(e.rules.general.buildupTime,e)),this.attackTrait?.setDisabled(this.buildStatus!==BuildStatus.Ready||!!this.poweredTrait&&!this.poweredTrait.isPoweredOn()),super.update(e)}setBuildStatus(e,t){this._buildStatus=e;let i=this.lastBuildStatus;this.buildStatus!==i&&(this.lastBuildStatus=this.buildStatus,this.traits.filter(NotifyBuildStatus).forEach(e=>{e[NotifyBuildStatus.onStatusChange](i,this,t)}),t.events.dispatch(new BuildStatusChangeEvent(this,this.buildStatus)))}}class Terrain_Terrain extends GameObject{static factory(e,t,i){return new this(e,t,i)}constructor(e,t,i){super(ObjectType.Terrain,e,t,i),this.radarInvisible=this.rules.radarInvisible}}class Overlay_Overlay extends GameObject{static factory(e,t,i){let r=new this(e,t,i);return t.wall&&(r.wallTrait=new WallTrait,r.traits.add(r.wallTrait)),r}constructor(e,t,i){super(ObjectType.Overlay,e,t,i),this.radarInvisible=this.rules.radarInvisible}isTiberium(){return OreOverlayTypes.getOverlayTibType(this.overlayId)!==OverlayTibType.NotSpecial}isBridge(){return BridgeOverlayTypes.isBridge(this.overlayId)}isXBridge(){return BridgeOverlayTypes.isXBridge(this.overlayId)}isHighBridge(){return BridgeOverlayTypes.isHighBridge(this.overlayId)}isLowBridge(){return BridgeOverlayTypes.isLowBridge(this.overlayId)}isBridgePlaceholder(){return BridgeOverlayTypes.isBridgePlaceholder(this.overlayId)}getFoundation(){let e={width:1,height:1};return this.isBridge()&&(this.isXBridge()?e.height+=2:e.width+=2),e}}class Smudge_Smudge extends GameObject{static factory(e,t,i){return new this(e,t,i)}constructor(e,t,i){super(ObjectType.Smudge,e,t,i)}getFoundation(){return{width:this.rules.width,height:this.rules.height}}}class TeleportMoveToRefineryTask extends MoveTask{constructor(e,t,i,r){super(e,i??t,!1,{closeEnoughTiles:i?void 0:0,strictCloseEnough:!i}),this.teleportTile=t,this.teleportCondition=r}onStart(e){if(super.onStart(e),!e.harvesterTrait||e.rules.locomotor!==LocomotorType.Chrono)throw new Error(`Vehicle ${e.name} is not a chrono miner`)}onTick(e){return!e.moveTrait.isDisabled()&&(!(this.isCancelling()||e.moveTrait.moveState!==MoveState.ReachedNextWaypoint||e.tile===this.teleportTile||!this.tryTeleportToRefinery(e))||!0===super.onTick(e)&&(this.isCancelling()||e.tile===this.teleportTile||this.tryTeleportToRefinery(e),!0))}tryTeleportToRefinery(e){return(!this.teleportCondition||!1!==this.teleportCondition(e,this.teleportTile))&&(!this.game.map.terrain.findObstacles({tile:this.teleportTile,onBridge:void 0},e).length&&(e.moveTrait.teleportUnitToTile(this.teleportTile,void 0,!0,!0,this.game),e.zone===ZoneType.Air&&(e.zone=ZoneType.Ground,e.position.tileElevation=0),!0))}}const RETRY_MOVE_SECONDS=5,LOAD_RATE_SECONDS=1,ADJACENT_SCAN_PRIORITIES=[[8,5,6],[3,0,2],[7,4,1]];class GatherOreTask extends Task{constructor(e,t,i=!1){super(),this.game=e,this.initialTarget=t,this.explicitOrder=i,this.forceMoveTried=!1,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.rangeHelper=new RangeHelper(e.map.tileOccupation),this.scanNearRadius=e.rules.ai.tiberiumNearScan,this.scanFarRadius=e.rules.ai.tiberiumFarScan}onStart(e){if(!e.isVehicle()||!e.harvesterTrait)throw new Error(`Unit ${e.name} is not a harvester.`);e.harvesterTrait.status=HarvesterStatus.MovingToOreSite,e.harvesterTrait.lastGatherExplicit=this.explicitOrder}onEnd(e){e.harvesterTrait.status!==HarvesterStatus.LookingForOreSite&&(e.harvesterTrait.status=HarvesterStatus.Idle)}onTick(i){if(this.isCancelling())return!0;let r=i.harvesterTrait;if(r.status===HarvesterStatus.MovingToOreSite){var e=this.target;if(this.target=this.findClosestReachableOreSite(i,this.target||this.initialTarget?.landType!==LandType.Tiberium?r.lastOreSite??i.tile:this.initialTarget,!0),r.lastOreSite=this.target,!this.target){r.status=HarvesterStatus.LookingForOreSite;let e=this.getRefineryOnTile(i.tile);if(e&&1===i.unitOrderTrait.getTasks().length){let t=i.rules.movementZone===MovementZone.Fly;var s=new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,e.tile,e.getFoundation(),1,5,e=>t||0<this.game.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&Math.abs(e.z-i.tile.z)<2&&!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},i).length).getNextTile();s&&i.unitOrderTrait.addTasks(new MoveTask(this.game,s,!1),new CallbackTask(()=>{[MoveResult.Success,MoveResult.CloseEnough,MoveResult.Cancel].includes(i.moveTrait.lastMoveResult)||this.children.push(new WaitMinutesTask(1/60))}))}return!0}s=this.game.rules.general.closeEnough,e=e&&this.rangeHelper.tileDistance(i.tile,this.target)<=s;if(!(i.tile===this.target||i.tile.landType===LandType.Tiberium&&e)){if(i.tile!==this.target&&e&&i.tile.landType!==LandType.Tiberium){e=this.findClosestReachableOreSite(i,i.tile,!1,!0);if(e)this.target=e,r.lastOreSite=this.target;else{if(!this.forceMoveTried)return this.forceMoveTried=!0,this.children.push(new MoveTask(this.game,this.target,!1,{closeEnoughTiles:0,strictCloseEnough:!0})),!1;if(this.forceMoveTried=!1,!r.isEmpty())return this.returnOreIfPossible(i),!0;e=this.findClosestReachableOreSite(i,i.tile,!0,!0);if(!e)return r.status=HarvesterStatus.LookingForOreSite,!0;this.target=e,r.lastOreSite=this.target}}return this.children.push(new MoveTask(this.game,this.target,!1,{closeEnoughTiles:s}),new CallbackTask(()=>{[MoveResult.Success,MoveResult.CloseEnough,MoveResult.Cancel].includes(i.moveTrait.lastMoveResult)||this.children.push(new WaitMinutesTask(RETRY_MOVE_SECONDS/60))})),!1}this.target=i.tile,r.lastOreSite=this.target,r.status=HarvesterStatus.Harvesting,this.forceMoveTried=!1}if(r.status!==HarvesterStatus.Harvesting)return!1;{if(r.isFull())return this.returnOreIfPossible(i),!0;let e=this.game.map.getObjectsOnTile(i.tile).find(e=>e.isOverlay()&&e.isTiberium());if(!e)return this.findClosestReachableOreSite(i,r.lastOreSite??i.tile,!1)||r.isEmpty()?(r.status=HarvesterStatus.MovingToOreSite,this.onTick(i)):(this.returnOreIfPossible(i),!0);let t=e.traits.get(TiberiumTrait);s=t.collectBail();if(t.getBailCount()||this.game.unspawnObject(e),void 0!==s)if(s===TiberiumType.Ore)r.ore++;else{if(s!==TiberiumType.Gems)throw new Error("Unsupported tiberium type "+s);r.gems++}return[...i.owner.buildings].some(e=>e.rules.refinery)||this.explicitOrder?(this.children.push(new WaitMinutesTask(LOAD_RATE_SECONDS/60)),!1):!0}}findClosestReachableOreSite(t,i,e,r=!1){let s=t.rules.movementZone===MovementZone.Fly;var a=t.rules.speedType,n=t.isInfantry();let o=!s&&this.game.map.terrain.getPassableSpeed(t.tile,a,n,t.onBridge)?this.game.map.terrain.getIslandIdMap(a,n):void 0,l=o?.get(t.tile,t.onBridge);var h,n=e=>e.landType===LandType.Tiberium&&o?.get(e,!1)===l&&(!r||(s||!this.game.map.terrain.findObstacles({tile:e,onBridge:void 0},t).length));if(n(i))return i;let c=1;if(!e){let e=new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,i,{width:1,height:1},c,c,n),t=[];for(;h=e.getNextTile();)t.push(h);if(t.length){let e=t.map(e=>{var t=this.game.map.getObjectsOnTile(e).find(e=>e.isOverlay()&&e.isTiberium());if(!t)throw new Error(`Ore should exist on tile ${e.rx},${e.ry} b/c of landType`);return{tile:e,ore:t}});return e.sort((e,t)=>1e3*(t.ore.value-e.ore.value)+(ADJACENT_SCAN_PRIORITIES[1+t.tile.ry-i.ry][1+t.tile.rx-i.rx]-ADJACENT_SCAN_PRIORITIES[1+e.tile.ry-i.ry][1+e.tile.rx-i.rx])),e[0].tile}c=2}e=e?this.scanFarRadius:this.scanNearRadius;let u=new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,i,{width:1,height:1},c,e,n);return u.getNextTile()}getRefineryOnTile(e){return this.game.map.getObjectsOnTile(e).find(e=>e.isBuilding()&&e.rules.refinery)}returnOreIfPossible(e){1===e.unitOrderTrait.getTasks().length&&e.unitOrderTrait.addTask(new ReturnOreTask(this.game))}getTargetLinesConfig(e){return{pathNodes:this.initialTarget?[{tile:this.initialTarget,onBridge:void 0}]:[]}}}class ReturnOreTask extends Task{constructor(e,t,i=!1,r=!1){super(),this.game=e,this.forceTarget=t,this.resetLastOreSite=i,this.explicitOrder=r,this.useChildTargetLines=!0,this.preventOpportunityFire=!1,this.rangeHelper=new RangeHelper(e.map.tileOccupation)}onStart(e){if(!e.isVehicle()||!e.harvesterTrait)throw new Error(`Unit ${e.name} is not a harvester.`);e.harvesterTrait.status=HarvesterStatus.MovingToRefinery,this.resetLastOreSite&&(e.harvesterTrait.lastOreSite=void 0)}onEnd(e){this.target?.isSpawned&&(this.target.dockTrait.undockUnit(e),this.target.dockTrait.unreserveDockForUnit(e)),e.harvesterTrait.status!==HarvesterStatus.LookingForRefinery&&(e.harvesterTrait.status=HarvesterStatus.Idle)}onTick(r){if(this.isCancelling())return!0;let s=r.harvesterTrait;if(s.status===HarvesterStatus.LookingForRefinery)return!0;if(s.status===HarvesterStatus.MovingToRefinery){if(!this.target||!this.isValidTargetRefinery(this.target,r)||r.tile!==this.findRefineryDockingTile(this.target)){var a=this.forceTarget??this.findClosestReachableRefinery(r);if(!a)return s.status=HarvesterStatus.LookingForRefinery,!0;this.target&&this.target!==a&&this.target.dockTrait.hasReservedDockForUnit(r)&&this.target.dockTrait.unreserveDockForUnit(r),this.target=a}let e=this.target.dockTrait.getFirstAvailableDockNumber(),t=!1;void 0===e&&(e=this.target.dockTrait.getFirstEmptyDockNumber(),void 0!==e&&(t=!this.target.dockTrait.hasReservedDockForUnit(r)));let i=this.findRefineryDockingTile(this.target);var n=this.rangeHelper.tileDistance(r,i);if(void 0===e||t||n>this.game.rules.general.harvesterTooFarDistance&&!this.explicitOrder){var o=this.findReachableQueueingTile(r);return o?(r.tile!==o&&this.children.push(r.rules.teleporter?new TeleportMoveToRefineryTask(this.game,i,o,()=>this.chronoMinerCanTeleport(r,i,this.target)):new MoveTask(this.game,o,!1),new CallbackTask(()=>{r.moveTrait.lastMoveResult===MoveResult.Fail?s.status=HarvesterStatus.LookingForRefinery:r.moveTrait.lastMoveResult===MoveResult.CloseEnough?this.children.push(new WaitMinutesTask(5/60)):r.moveTrait.lastMoveResult===MoveResult.Success&&this.children.push(new WaitMinutesTask(2/60))})),!1):!0}if(this.target.dockTrait.hasReservedDockForUnit(r)||this.target.dockTrait.reserveDockAt(r,e),void 0===this.reservedDockNumber&&(this.reservedDockNumber=this.target.dockTrait.getReservedDockForUnit(r)),r.tile!==i)return this.children.push(r.rules.teleporter?new TeleportMoveToRefineryTask(this.game,i,void 0,()=>this.chronoMinerCanTeleport(r,i,this.target)):new MoveTask(this.game,i,!1,{closeEnoughTiles:0,strictCloseEnough:!0}),new CallbackTask(()=>{r.moveTrait.lastMoveResult===MoveResult.Fail&&(s.status=HarvesterStatus.LookingForRefinery)})),!1;s.status=HarvesterStatus.Docking}if(!this.isValidTargetRefinery(this.target,r))return s.status=HarvesterStatus.MovingToRefinery,this.forceTarget=void 0,this.onTick(r);if(s.status===HarvesterStatus.Docking){if(270!==r.direction)return this.children.push(new TurnTask(270)),!1;this.target.dockTrait.dockUnitAt(r,this.reservedDockNumber),this.reservedDockNumber=void 0,s.status=HarvesterStatus.PreparingToUnload}if(s.status===HarvesterStatus.PreparingToUnload)return this.preventOpportunityFire=!0,this.children.push(new WaitMinutesTask(2/60)),s.status=HarvesterStatus.Unloading,!1;if(s.status!==HarvesterStatus.Unloading)return!1;var e=s.ore*this.game.rules.getTiberium(TiberiumType.Ore).value+s.gems*this.game.rules.getTiberium(TiberiumType.Gems).value,a=e,n=[...this.target.owner.buildings].filter(e=>e.rules.orePurifier&&(!e.poweredTrait||!this.target.owner.powerTrait?.isLowPower())).length,o=this.game.rules.general.purifierBonus;return a+=n*Math.floor(e*o),this.target.owner.credits+=a,this.target.owner.creditsGained+=a,s.ore=0,s.gems=0,1===r.unitOrderTrait.getTasks().length&&r.unitOrderTrait.addTask(new GatherOreTask(this.game)),!0}isValidTargetRefinery(e,t){return e.isSpawned&&this.game.areFriendly(e,t)&&!e.warpedOutTrait.isActive()}findClosestReachableRefinery(i){let r=this.rangeHelper;var e=i.zone===ZoneType.Air,t=i.rules.speedType,s=i.isInfantry();let a=!e&&this.game.map.terrain.getPassableSpeed(i.tile,t,s,i.onBridge)?this.game.map.terrain.getIslandIdMap(t,s):void 0,n=[...i.owner.buildings].filter(e=>e.rules.refinery&&e.dockTrait&&!e.warpedOutTrait.isActive()&&(e=>i.rules.teleporter||a?.get(e,!1)===a?.get(i.tile,i.onBridge))(this.findRefineryDockingTile(e))).sort((e,t)=>r.distance2(i,e)-r.distance2(i,t));t=n[0],s=n.find(e=>0<e.dockTrait.getAvailableDockCount());return!s||t&&r.tileDistance(i,s.centerTile)-r.tileDistance(i,t.centerTile)>this.game.rules.general.harvesterTooFarDistance?t:s}findReachableQueueingTile(t){if(this.target.art.queueingCell){var e=new Vector2(this.target.tile.rx,this.target.tile.ry).add(this.target.art.queueingCell),e=this.game.map.tiles.getByMapCoords(e.x,e.y);if(e&&this.isValidQueueingTile(e,t))return e}return new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>this.isValidQueueingTile(e,t)).getNextTile()}isValidQueueingTile(e,t){var i=t.zone===ZoneType.Air,r=t.rules.speedType,s=t.isInfantry();let a=!i&&this.game.map.terrain.getPassableSpeed(t.tile,r,s,t.onBridge)?this.game.map.terrain.getIslandIdMap(r,s):void 0;return i||a?.get(e,!1)===a?.get(t.tile,t.onBridge)&&Math.abs(e.z-this.target.tile.z)<2&&!e.onBridgeLandType}findRefineryDockingTile(e){e={x:e.tile.rx+e.getFoundation().width-1,y:e.tile.ry+Math.floor(e.getFoundation().height/2)};return this.game.map.tiles.getByMapCoords(e.x,e.y)}chronoMinerCanTeleport(e,t,i){let r=this.rangeHelper;t=r.tileDistance(e,t);return!(!this.forceTarget&&t>this.game.rules.general.chronoHarvTooFarDistance)&&(!(t<=1)&&(!!this.isValidTargetRefinery(i,e)&&!(0===i.dockTrait.getAvailableDockCount()&&!i.dockTrait.hasReservedDockForUnit(e))))}}(NotifyOrder=NotifyOrder||{}).onPush=Symbol(),function(e){e[e.Move=0]="Move",e[e.ForceMove=1]="ForceMove",e[e.Attack=2]="Attack",e[e.ForceAttack=3]="ForceAttack",e[e.AttackMove=4]="AttackMove",e[e.Guard=5]="Guard",e[e.GuardArea=6]="GuardArea",e[e.Capture=7]="Capture",e[e.Occupy=8]="Occupy",e[e.Deploy=9]="Deploy",e[e.DeploySelected=10]="DeploySelected",e[e.Stop=11]="Stop",e[e.Cheer=12]="Cheer",e[e.Dock=13]="Dock",e[e.Gather=14]="Gather",e[e.Repair=15]="Repair",e[e.Scatter=16]="Scatter",e[e.EnterTransport=17]="EnterTransport",e[e.PlaceBomb=18]="PlaceBomb"}(OrderType=OrderType||{}),function(e){e[e.Idle=0]="Idle",e[e.LookingForOreSite=1]="LookingForOreSite",e[e.MovingToOreSite=2]="MovingToOreSite",e[e.Harvesting=3]="Harvesting",e[e.LookingForRefinery=4]="LookingForRefinery",e[e.MovingToRefinery=5]="MovingToRefinery",e[e.Docking=6]="Docking",e[e.PreparingToUnload=7]="PreparingToUnload",e[e.Unloading=8]="Unloading"}(HarvesterStatus=HarvesterStatus||{});const CHECK_REFINERY_SECONDS=5,CHECK_EXTRA_REFINERY_SECONDS=25,CHECK_ORE_SITE_SECONDS=20;class HarvesterTrait{constructor(e){this.storage=e,this.ore=0,this.gems=0,this.status=HarvesterStatus.Idle,this.lastGatherExplicit=!1,this.autoGatherOnNextIdle=!1,this.ticksSinceLastRefineryCheck=0,this.ticksSinceLastOreCheck=0}[NotifySpawn.onSpawn](e,t){e.owner.isCombatant()&&(t.afterTick(()=>{e.unitOrderTrait.addTask(new GatherOreTask(t))}),e.attackTrait?.increasePassiveScanCooldown(1))}[NotifyOwnerChange.onChange](e,t,i){(!t.isCombatant()&&e.owner.isCombatant()||i.alliances.areAllied(e.owner,t))&&i.afterTick(()=>{e.unitOrderTrait.addTask(new GatherOreTask(i))})}[NotifyTick_NotifyTick.onTick](e,t){this.status===HarvesterStatus.LookingForRefinery?this.ticksSinceLastRefineryCheck++>CHECK_REFINERY_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND&&(this.ticksSinceLastRefineryCheck=0,e.unitOrderTrait.hasTasks()?this.ticksSinceLastRefineryCheck=-CHECK_EXTRA_REFINERY_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND:[...e.owner.buildings].some(e=>e.rules.refinery)||this.lastGatherExplicit?e.unitOrderTrait.addTask(new ReturnOreTask(t)):this.status=HarvesterStatus.Idle):this.status===HarvesterStatus.LookingForOreSite?this.ticksSinceLastOreCheck++>CHECK_ORE_SITE_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND&&(this.ticksSinceLastOreCheck=0,e.unitOrderTrait.hasTasks()||e.unitOrderTrait.addTask(new GatherOreTask(t))):this.status===HarvesterStatus.Idle&&this.autoGatherOnNextIdle&&e.unitOrderTrait.isIdle()&&e.tile.landType===LandType.Tiberium&&(this.autoGatherOnNextIdle=!1,e.unitOrderTrait.addTask(new GatherOreTask(t,e.tile,!0)))}[NotifyTeleport.onBeforeTeleport](e,t,i,r){!r&&e.owner.isCombatant()&&(this.status=HarvesterStatus.Idle,this.lastOreSite=void 0,i&&e.rules.teleporter&&t.afterTick(()=>{e.unitOrderTrait.addTask(new(this.isFull()?ReturnOreTask:GatherOreTask)(t))}))}[NotifyOrder.onPush](e,t){this.autoGatherOnNextIdle=[OrderType.AttackMove,OrderType.Move,OrderType.ForceMove,OrderType.Scatter].includes(t),[HarvesterStatus.LookingForRefinery,HarvesterStatus.LookingForOreSite].includes(this.status)&&(this.status=HarvesterStatus.Idle)}isFull(){return this.ore+this.gems>=this.storage}isEmpty(){return!this.ore&&!this.gems}getHash(){return 100*this.ore+this.gems}debugGetState(){return{ore:this.ore,gems:this.gems}}}class LeaveTransportEvent{constructor(e){this.target=e,this.type=EventType.LeaveTransport}}class TransportTrait{constructor(e){this.obj=e,this.units=[],this.loadQueue=[]}unitFitsInside(e){return e.rules.size<=this.obj.rules.sizeLimit&&e.rules.size<=this.getAvailableCapacity()}getOccupiedCapacity(){return this.units.reduce((e,t)=>e+t.rules.size,0)}getMaxCapacity(){return this.obj.rules.passengers}getAvailableCapacity(){return this.getMaxCapacity()-this.getOccupiedCapacity()}addToLoadQueue(e){return this.loadQueue.push(e),this.loadQueue.length-1}unitIsFirstInLoadQueue(e){return this.loadQueue[0]===e}removeFromLoadQueue(e){e=this.loadQueue.indexOf(e);-1!==e&&this.loadQueue.splice(e,1)}[NotifyTick_NotifyTick.onTick](e,t){this.loadQueue=this.loadQueue.filter(e=>!e.isDestroyed&&!e.isCrashing)}[NotifyDestroy.onDestroy](e,t,i,r){var s=!!e.armedTrait?.deathWeapon,a=i?.weapon?.warhead.rules.parasite;if(r||s||e.zone===ZoneType.Air||a)for(var n of this.units)s&&n.armedTrait&&(n.armedTrait.deathWeapon=void 0),n.position.tileElevation=e.position.tileElevation,n.zone=e.zone,n.onBridge=e.onBridge,n.position.tile=e.tile,n.deathType=e.deathType,t.destroyObject(n,i,!0);else this.spawnSurvivors(t);this.units=[]}spawnSurvivors(e){var t=this.obj;if(this.units.length){for(var i of this.units)0<e.map.terrain.getPassableSpeed(t.tile,i.rules.speedType,i.isInfantry(),t.onBridge)?(i.owner.addOwnedObject(i),i.position.tileElevation=t.onBridge?e.map.tileOccupation.getBridgeOnTile(t.tile).tileElevation:0,i.onBridge=t.onBridge,i.zone=e.map.getTileZone(t.tile,!t.onBridge),e.unlimboObject(i,t.tile),i.unitOrderTrait.addTask(new ScatterTask(e))):(i.position.tileElevation=t.position.tileElevation,i.zone=t.zone,i.onBridge=t.onBridge,i.position.tile=t.tile,i.zone===ZoneType.Water&&(i.deathType=DeathType.Sink),i.armedTrait?.deathWeapon&&(i.armedTrait.deathWeapon=void 0),e.destroyObject(i,{player:i.owner}));e.events.dispatch(new LeaveTransportEvent(t))}}getHash(){return fnv32a(this.units.map(e=>e.getHash()))}debugGetState(){return this.units.map(e=>e.debugGetState())}dispose(){this.obj=void 0}}class GunnerTrait{[NotifyTick_NotifyTick.onTick](e){var t,i;!!e.transportTrait.units.length!==this.lastHadGunner&&(this.lastHadGunner=!!e.transportTrait.units.length,i=t=e.transportTrait.units[0]?.rules.ifvMode??0,(t=e.rules.turretIndexesByIfvMode.get(t)??0)<e.rules.turretCount&&(e.turretNo=t,e.armedTrait?.selectSpecialWeapon(i,e.veteranLevel===VeteranLevel.Elite)))}getUiNameForIfvMode(e,t){switch(e){case 0:return"tip:rocket";case 1:return"tip:repair";case 2:case 4:case 5:return"tip:machinegun";default:return t?"name:"+t.toLowerCase():void 0}}}(NotifyHeal=NotifyHeal||{}).onHeal=Symbol();const getSquidDamageTicks=()=>ROCKING_TICKS+2;class ParasiteableTrait{constructor(e){this.gameObject=e,this.beingBoarded=!1}infest(e,t){this.beingBoarded=!1,this.parasite=e,this.parasiteWeapon=t,e.rules.organic?this.damageTickCooldown=getSquidDamageTicks():this.damageTickCooldown=0,this.lastExternalDamageInflicted=void 0,this.lastExternalDamageTick=void 0,t.warhead.rules.paralyzes&&this.gameObject.moveTrait.setDisabled(!0)}isInfested(){return!(!this.parasite||this.parasite.isDestroyed)||this.beingBoarded}isParalyzed(){return!!this.parasiteWeapon?.warhead.rules.paralyzes}uninfest(){this.parasite&&(this.parasiteWeapon.warhead.rules.paralyzes&&this.gameObject.moveTrait.setDisabled(!1),this.parasite=void 0,this.parasiteWeapon=void 0)}getParasite(){return this.parasite}[NotifyTick_NotifyTick.onTick](r,s){if(this.parasite)if(this.parasite.isDestroyed)this.uninfest();else if(0<this.damageTickCooldown)this.damageTickCooldown--;else{let e=this.parasiteWeapon;this.damageTickCooldown=this.parasite.rules.organic?getSquidDamageTicks():e.getCooldownTicks();let t=e.rules.damage;this.parasite.veteranTrait&&(t*=this.parasite.veteranTrait.getVeteranDamageMultiplier());let i=e.warhead.computeDamage(t,r,s);this.canBeCulled(r,this.parasite,e,s)&&(i=r.healthTrait.getHitPoints()),e.warhead.inflictDamage(i,r,{player:this.parasite.owner,obj:this.parasite,weapon:e},s),r.isCrashing?(this.parasiteWeapon.expireCooldown(),this.evictOrDestroyParasite(r,s)):!r.isDestroyed&&r.isVehicle()&&r.zone!==ZoneType.Air&&e.warhead.rules.rocker&&r.applyRocking(90*(.5<=s.generateRandom()?1:-1),1)}}canBeCulled(e,t,i,r){if(!i.warhead.rules.culling)return!1;r=r.rules.audioVisual,r=t.veteranTrait?.isElite()?r.conditionYellow:r.conditionRed;return e.healthTrait.health<=100*r}[NotifyHeal.onHeal](e,t,i,r){var s;!this.parasite||this.parasite.isDestroyed||r===e||e.isAircraft()&&r?.rules.unitReload||(this.parasite.rules.organic?(s=this.parasite,this.evictOrDestroyParasite(e,t),this.stunParasite(s,t)):(this.parasite.deathType=DeathType.None,t.destroyObject(this.parasite,r?{player:r.owner,obj:r}:void 0),this.uninfest()))}[NotifyDamage.onDamage](e,t,i,r){r?.obj!==this.parasite&&(this.lastExternalDamageInflicted=i,this.lastExternalDamageTick=t.currentTick)}[NotifyAttack.onAttack](i,r,s){if(this.parasite&&!this.parasite.isDestroyed&&r?.weapon?.warhead.rules.sonic){var a=this.parasite;this.evictOrDestroyParasite(i,s),this.stunParasite(a,s);let e=r.weapon.warhead;e.canDamage(a,a.tile,a.zone)&&(i=e.computeDamage(r.weapon.rules.damage,a,s),e.inflictDamage(i,a,r,s));let t=r.obj?.unitOrderTrait.getCurrentTask();t instanceof AttackTask&&t.getWeapon().warhead.rules.sonic&&t.cancel()}}[NotifyDestroy.onDestroy](e,t,i,r){this.parasite&&!this.parasite.isDestroyed&&(r||!this.parasite.invulnerableTrait.isActive()&&this.shouldSupressParasite(t,this.parasite,i)?(this.parasite.deathType=DeathType.None,t.destroyObject(this.parasite,i,r),this.uninfest()):(this.parasiteWeapon.expireCooldown(),this.evictOrDestroyParasite(e,t)))}shouldSupressParasite(e,t,i){return i?.obj!==t||this.lastExternalDamageInflicted&&this.lastExternalDamageInflicted>t.rules.suppressionThreshold&&e.currentTick-this.lastExternalDamageTick<2*this.lastExternalDamageInflicted}[NotifyTeleport.onBeforeTeleport](e,t,i,r){i&&r&&this.parasite&&!this.parasite.isDestroyed&&(this.parasiteWeapon.expireCooldown(),r=this.parasite,this.evictOrDestroyParasite(e,t,!0),r.isDestroyed||this.stunParasite(r,t))}stunParasite(e,t){e.unitOrderTrait.addTaskToFront(new WaitMinutesTask(10/60).setCancellable(!1)),e.isVehicle()&&e.submergibleTrait&&(e.submergibleTrait.emerge(e,t),e.cloakableTrait?.uncloak(t),e.submergibleTrait.setCooldown(10*GameSpeed.BASE_TICKS_PER_SECOND))}evictOrDestroyParasite(r,s,a=!1){if(this.parasite&&!this.parasite.isDestroyed){if(s.map.terrain.getPassableSpeed(r.tile,this.parasite.rules.speedType,this.parasite.isInfantry(),r.onBridge)||s.map.getObjectsOnTile(r.tile).find(e=>e.isBuilding())){let t=r.tile,i=r.onBridge;if(!a&&!r.isDestroyed||this.parasite.rules.organic){let e=new RadialTileFinder(s.map.tiles,s.map.mapBounds,t,{width:1,height:1},1,1,e=>0<s.map.terrain.getPassableSpeed(e,this.parasite.rules.speedType,this.parasite.isInfantry(),i)&&!s.map.terrain.findObstacles({tile:e,onBridge:i},this.parasite).length);a=e.getNextTile();if(!a)return this.parasite.deathType=DeathType.None,s.destroyObject(this.parasite,{player:r.owner,obj:r}),void this.uninfest();t=a}this.parasite.onBridge=i,this.parasite.position.subCell=this.parasite.isInfantry()?r.position.subCell:0,this.parasite.zone=s.map.getTileZone(t,!i),this.parasite.position.tileElevation=i?s.map.tileOccupation.getBridgeOnTile(t).tileElevation:0,this.parasite.resetGuardModeToIdle(),s.unlimboObject(this.parasite,t,!0)}else this.parasite.deathType=DeathType.None,s.destroyObject(this.parasite,{player:r.owner,obj:r});this.uninfest()}}destroyParasite(e,t){this.parasite&&(this.parasite.deathType=DeathType.None,t.destroyObject(this.parasite,e),this.uninfest())}dispose(){this.gameObject=void 0}}class ShipSubmergeChangeEvent{constructor(e){this.target=e,this.type=EventType.ShipSubmergeChange}}const SUBMERGE_PENALTY_SECONDS=5;class SubmergibleTrait{constructor(){this.isActive=!1}isSubmerged(){return this.isActive}setCooldown(e){this.cooldownTicks=e}[NotifyTick_NotifyTick.onTick](e,t){this.isActive||e.parasiteableTrait?.isInfested()||(e.attackTrait&&e.attackTrait.attackState!==AttackState.Idle&&!e.moveTrait.isMoving()?this.cooldownTicks=Math.max(this.cooldownTicks??0,SUBMERGE_PENALTY_SECONDS*GameSpeed.BASE_TICKS_PER_SECOND):this.cooldownTicks??(this.cooldownTicks=Math.floor(60*t.rules.general.cloakDelay*GameSpeed.BASE_TICKS_PER_SECOND)),0<this.cooldownTicks&&this.cooldownTicks--,this.cooldownTicks<=0&&(this.isActive=!0,t.events.dispatch(new ShipSubmergeChangeEvent(e))))}[NotifyDamage.onDamage](e,t){this.emerge(e,t)}emerge(e,t){this.isActive&&(this.isActive=!1,this.cooldownTicks=void 0,t.events.dispatch(new ShipSubmergeChangeEvent(e)))}}class HoverBobTrait{constructor(){this.prevHoverBobLeptons=0,this.spawnTick=0}[NotifySpawn.onSpawn](e,t){this.setBaseElevation(e,t),this.spawnTick=t.currentTick}[NotifyTileChange_NotifyTileChange.onTileChange](e,t,i,r){r&&(this.prevHoverBobLeptons=0,this.setBaseElevation(e,t))}setBaseElevation(e,t){e.position.tileElevation=(e.onBridge?t.map.tileOccupation.getBridgeOnTile(e.tile)?.tileElevation??0:0)+Coords.worldToTileHeight(t.rules.general.hover.height)}[NotifyTick_NotifyTick.onTick](e,t){var i=this.computeHoverBobLeptons(t.currentTick,t.rules.general.hover),t=i-this.prevHoverBobLeptons;this.prevHoverBobLeptons=i;i=Coords.tileHeightToWorld(e.position.tileElevation);e.position.tileElevation=Coords.worldToTileHeight(i+t)}computeHoverBobLeptons(e,t){e=(e-this.spawnTick)/GameSpeed.BASE_TICKS_PER_SECOND/(60*t.bob);return.1*t.height*GameMath.sin(2*e*Math.PI)}}class TilterTrait{constructor(){this.tilt={pitch:0,yaw:0}}[NotifySpawn.onSpawn](e){this.tilt=this.computeTilt(e.tile.rampType)}[NotifyTileChange_NotifyTileChange.onTileChange](e){this.tilt=this.computeTilt(e.tile.rampType)}computeTilt(e){let t,i;return 0===e||17<=e?t=i=0:i=e<=4?(t=25,-90*e):(t=25,225-(e-1)%4*90),{pitch:t,yaw:i}}}const ROCKING_TICKS=34;class Vehicle_Vehicle extends Techno_Techno{get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,r,s){let a=new this(e,t,i);return a.isSinker=!t.underwater&&(t.weight>=r.general.shipSinkingWeight||!t.naval),a.moveTrait=new MoveTrait(a,s),a.traits.add(a.moveTrait),t.crashable&&(a.crashableTrait=new CrashableTrait(a),a.traits.add(a.crashableTrait)),t.crewed&&(a.crewedTrait=new CrewedTrait,a.traits.add(a.crewedTrait)),t.harvester&&(a.harvesterTrait=new HarvesterTrait(t.storage),a.traits.add(a.harvesterTrait)),t.passengers&&(a.transportTrait=new TransportTrait(a),a.traits.add(a.transportTrait),t.gunner&&(a.gunnerTrait=new GunnerTrait,a.traits.add(a.gunnerTrait))),t.turret&&(a.turretTrait=new TurretTrait,a.traits.add(a.turretTrait)),t.consideredAircraft&&!t.landable||a.traits.add(new DockableTrait),t.parasiteable&&(a.parasiteableTrait=new ParasiteableTrait(a),a.traits.add(a.parasiteableTrait)),t.naval&&t.underwater&&(a.submergibleTrait=new SubmergibleTrait,a.traits.add(a.submergibleTrait)),t.locomotor===LocomotorType.Hover&&a.traits.add(new HoverBobTrait),[LocomotorType.Vehicle,LocomotorType.Chrono].includes(t.locomotor)&&i.isVoxel&&(a.tilterTrait=new TilterTrait,a.traits.add(a.tilterTrait)),a}constructor(e,t,i){super(ObjectType.Vehicle,e,t,i),this.direction=0,this.spinVelocity=0,this.crateBonuses=new CrateBonuses,this.turretNo=0,this.onBridge=!1,this.isSinker=!1,this.isFiring=!1,this.zone=t.naval?ZoneType.Water:ZoneType.Ground}isUnit(){return!0}isVehicle(){return!0}getUiName(){if(this.gunnerTrait){var e=this.armedTrait.getSpecialWeaponIndex(),t=this.gunnerTrait.getUiNameForIfvMode(e,this.transportTrait?.units[0]?.name),e="name:"+this.name;return t?`{${t}} {${e}}`:e}return super.getUiName()}update(e){this.rocking&&(this.rocking.ticksLeft--,this.rocking.ticksLeft||(this.rocking=void 0)),super.update(e)}applyRocking(e,t){this.rules.consideredAircraft||(this.rocking={ticksLeft:this.rocking?.ticksLeft??ROCKING_TICKS,facing:e,factor:t})}}class AirportBoundTrait{constructor(e){this.airportNames=e}findAvailableAirport(e){return[...e.owner.buildings].find(e=>e.dockTrait&&this.airportNames.includes(e.name)&&0<e.dockTrait.getAvailableDockCount())}}class SpawnLinkTrait{setParent(e){this.parent=e}getParent(){return this.parent}[NotifyTick_NotifyTick.onTick](r,s){if(this.parent&&r.attackTrait&&r.primaryWeapon){let e=this.parent.attackTrait?.currentTarget,t=r.unitOrderTrait.getCurrentTask(),i=new RangeHelper(s.map.tileOccupation);var a=this.parent.armedTrait?.getWeapons().find(e=>e.rules.spawner);r.ammo&&!(e&&r.attackTrait.currentTarget?e.equals(r.attackTrait.currentTarget):e===r.attackTrait.currentTarget||!e&&this.parent.isUnit()&&(this.parent.unitOrderTrait.getCurrentTask()instanceof MoveTask||this.parent.unitOrderTrait.getCurrentTask()instanceof AttackTask))&&(!e||a&&i.isInWeaponRange(this.parent,e.obj??e.tile,a,s.rules))?e&&r.primaryWeapon.targeting.canTarget(e.obj,e.tile,s,!0,!1)?!t||t instanceof MoveTask?(r.unitOrderTrait.cancelAllTasks(),r.unitOrderTrait.addTask(r.attackTrait.createAttackTask(s,e.obj,e.tile,r.primaryWeapon,{force:!0}))):r.attackTrait.attackState!==AttackState.Idle&&t.requestTargetUpdate(e):t?t instanceof MoveTask||t.cancel():this.tryMoveToParent(r,this.parent,s):this.tryMoveToParent(r,this.parent,s)}}tryMoveToParent(t,i,r){if(t.tile!==i.tile){let e=t.unitOrderTrait.getCurrentTask();e?e instanceof MoveTask&&e.updateTarget(i.tile,!!i.isUnit()&&i.onBridge):t.unitOrderTrait.addTask(new MoveTask(r,i.tile,!!i.isUnit()&&i.onBridge,{closeEnoughTiles:0,strictCloseEnough:!0}))}}}class MissileSpawnTrait{setWarhead(e){return this.warhead=e,this}setDamage(e){return this.damage=e,this}setLauncher(e){return this.launcher=e,this}[NotifyDestroy.onDestroy](e,t){this.warhead&&this.damage&&this.launcher&&this.warhead.detonate(t,this.damage,e.tile,e.tileElevation,e.position.worldPosition,e.zone,CollisionType.None,t.createTarget(void 0,e.tile),{player:e.owner,obj:this.launcher,weapon:void 0})}dispose(){this.launcher=void 0}}class Aircraft_Aircraft extends Techno_Techno{get direction(){return this.yaw}set direction(e){this.yaw=e}get isMoving(){return this.moveTrait.isMoving()}static factory(e,t,i,r,s){let a=new this(e,t,i);return a.rules.airportBound&&a.rules.dock.length&&(a.airportBoundTrait=new AirportBoundTrait(a.rules.dock),a.traits.add(a.airportBoundTrait)),a.rules.missileSpawn||(a.crashableTrait=new CrashableTrait(a),a.traits.add(a.crashableTrait)),a.rules.spawned&&(a.rules.missileSpawn?(a.missileSpawnTrait=new MissileSpawnTrait,a.traits.add(a.missileSpawnTrait)):(a.spawnLinkTrait=new SpawnLinkTrait,a.traits.add(a.spawnLinkTrait))),a.moveTrait=new MoveTrait(a,s),a.traits.add(a.moveTrait),t.dock.length&&a.traits.add(new DockableTrait),t.landable&&e!==r.general.paradrop.paradropPlane||a.traits.add(new UnlandableTrait),t.parasiteable&&(a.parasiteableTrait=new ParasiteableTrait(a),a.traits.add(a.parasiteableTrait)),a}constructor(e,t,i){super(ObjectType.Aircraft,e,t,i),this.pitch=0,this.yaw=0,this.roll=0,this.onBridge=!1,this.zone=ZoneType.Ground,this.crateBonuses=new CrateBonuses}isUnit(){return!0}isAircraft(){return!0}}class UnitOrderTrait{constructor(e){this.gameObject=e,this.orders=[],this.queuedOrders=new Set,this.tasks=[],this.taskRunner=new TaskRunner}[NotifyTick_NotifyTick.onTick](i,e){if(i.isSpawned){var r=this.hasTasks(),t=this.tasks.find(e=>!e.isCancelling());if(r&&this.taskRunner.tick(this.tasks,i),i.isSpawned){var s,a=this.orders.length;if(a&&(!r||!t)){let e,t=!1;for(;e=this.orders[0];){if(e.isValid()&&e.isAllowed()&&((s=e.process())&&(this.queuedOrders.has(e)&&(this.tasks.push(new WaitTicksTask(5)),this.tasks.push(new CallbackTask(()=>{i.resetGuardModeToIdle()}))),this.tasks.push(...s),r||this.taskRunner.tick(this.tasks,i)),t=!0),this.orders.shift(),this.queuedOrders.delete(e),!i.isSpawned)return;if(this.waypointPath&&(this.currentWaypoint?(this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.currentWaypoint=this.currentWaypoint?.next):this.currentWaypoint=this.waypointPath.waypoints[0],this.currentWaypoint||this.cleanupWaypointPath()),t)break}}!a&&!r&&this.waypointPath&&this.currentWaypoint&&(this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.cleanupWaypointPath());let e=t;for(;e?.useChildTargetLines;){var n=e.children.find(e=>!e.isCancelling());if(!n)break;e=n}this.targetLinesTask!==e&&(this.targetLinesTask=e,this.targetLinesConfig=e?.getTargetLinesConfig(this.gameObject))}}}[NotifyOwnerChange.onChange](){this.clearOrders(),this.cancelAllTasks()}[NotifyTeleport.onBeforeTeleport](e,t,i,r){i&&!r&&(this.clearOrders(),this.tasks.length=0)}addOrder(t,e=!1){!1!==t.onAdd(this.tasks,e)?(e||(this.clearOrders(),this.tasks=this.tasks.filter(e=>e.status!==TaskStatus.NotStarted),this.tasks.forEach(e=>e.cancel())),this.orders.push(t),e&&this.queuedOrders.add(t),this.gameObject.traits.filter(NotifyOrder).forEach(e=>{e[NotifyOrder.onPush](this.gameObject,t.orderType)})):this.targetLinesTask=void 0}clearOrders(){this.orders.length=0,this.queuedOrders.clear(),this.currentWaypoint&&this.waypointPath&&this.cleanupWaypoint(this.currentWaypoint,this.waypointPath),this.cleanupWaypointPath(),this.gameObject.resetGuardModeToIdle()}unmarkNextQueuedOrder(){this.orders.length&&this.queuedOrders.delete(this.orders[0])}hasTasks(){return!!this.tasks.length}isIdle(){return!this.orders.length&&!this.tasks.length}getCurrentTask(){return this.tasks[0]}cancelAllTasks(){this.tasks.forEach(e=>e.cancel())}addTask(e){this.tasks.push(e)}addTasks(...e){e.forEach(e=>this.addTask(e))}addTaskToFront(e){this.tasks.unshift(e)}addTaskNext(e){this.tasks.splice(1,0,e)}getTasks(){return[...this.tasks]}dispose(){this.clearOrders(),this.tasks.length=0,this.gameObject=void 0}cleanupWaypointPath(){this.waypointPath&&(this.waypointPath.units.splice(this.waypointPath.units.indexOf(this.gameObject),1),this.waypointPath.units.length||(this.waypointPath.waypoints.forEach(e=>e.next=void 0),this.waypointPath.waypoints.length=0),this.waypointPath=void 0),this.currentWaypoint=void 0}cleanupWaypoint(t,e){if(!e.units.find(e=>e!==this.gameObject&&(e.unitOrderTrait.currentWaypoint??e.unitOrderTrait.waypointPath?.waypoints[0])===t)&&!e.waypoints.find(e=>e.next===t)){var i=e.waypoints.indexOf(t);if(-1===i)throw new Error("Given waypoint not found in waypoint path");e.waypoints.splice(i,1)}}}const rampHeights=[[0,0,0,0],[0,0,1,1],[1,0,0,1],[1,1,0,0],[0,1,1,0],[0,0,0,1],[1,0,0,0],[0,1,0,0],[0,0,1,0],[1,0,1,1],[1,1,0,1],[1,1,1,0],[0,1,1,1],[1,0,1,2],[2,1,0,1],[1,2,1,0],[0,1,2,1],[1,0,1,0],[0,1,0,1],[1,0,1,0],[0,1,0,1]];class ObjectPosition{get onPositionChange(){return this._onPositionChange.asEvent()}get worldPosition(){return this._worldPosition}get tile(){return this._tile}set tile(e){var t=!!this._tile&&e!==this._tile;(this._tile=e)&&(this.updateWorldPosition(e,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:t}))}get tileElevation(){return void 0===this._tileElevation?(void 0===this._computedTileElevation&&(this._computedTileElevation=this.computeTileElevationFromWorldPos()),this._computedTileElevation):this._tileElevation}set tileElevation(e){this._absoluteElevation=void 0,this._tileElevation=e,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}get subCell(){if(!this._tileOffset.x&&!this._tileOffset.y)return 0;var e=Math.sign(this._tileOffset.x/Coords.LEPTONS_PER_TILE-.5),t=Math.sign(this._tileOffset.y/Coords.LEPTONS_PER_TILE-.5);return e&&t?t+1+(e+1)/2+1:0}set subCell(e){this._tileOffset=this.computeSubCellOffset(e),this.desiredSubCell=e,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}constructor(e,t){this.tiles=e,this.tileOccupation=t,this._worldPosition=new Vector3_Vector3,this._tileOffset=new Vector2,this._centerOffset=new Vector2,this.desiredSubCell=0,this._tileElevation=0,this._onPositionChange=new EventDispatcher}getTileOffset(){return this._tileOffset.clone()}setTileOffset(e){this._tileOffset.copy(e),this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}setCenterOffset(e){this._centerOffset.copy(e),this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}getMapPosition(){if(this._tile)return new Vector2(this._tile.rx*Coords.LEPTONS_PER_TILE+this._tileOffset.x+this._centerOffset.x,this._tile.ry*Coords.LEPTONS_PER_TILE+this._tileOffset.y+this._centerOffset.y)}getBridgeBelow(){return this._tile?.onBridgeLandType?this.tileOccupation.getBridgeOnTile(this._tile):void 0}moveToTileCell(e,t=0){if(!this._tile)throw new Error("Tile is not set");var i=e!==this._tile;this._tile=e,this._tileOffset=this.computeSubCellOffset(t),this.desiredSubCell=t,this.updateWorldPosition(e,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:i})}moveToTileCoords(e,t,i=!1){var r=Math.floor(e),s=Math.floor(t),a=!this._tile||this._tile.rx!==r||this._tile.ry!==s;if(a){let e=this.tiles.getByMapCoords(r,s);if(!e){if(!i)throw new RangeError(`Attempted move to a non-existent tile: [${r},${s}]`);e=this.tiles.getPlaceholderTile(r,s)}this._tile=e}this._tileOffset.set((e-r)*Coords.LEPTONS_PER_TILE,(t-s)*Coords.LEPTONS_PER_TILE),this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:a})}moveToLeptons(e,t=!1){this.moveToTileCoords(e.x/Coords.LEPTONS_PER_TILE,e.y/Coords.LEPTONS_PER_TILE,t)}moveByLeptons(e,t,i=!1){if(!this._tile)throw new Error("Tile is not set");this.moveToTileCoords(this._tile.rx+(this._tileOffset.x+e)/Coords.LEPTONS_PER_TILE,this._tile.ry+(this._tileOffset.y+t)/Coords.LEPTONS_PER_TILE,i)}moveByLeptons3(e,t=!1){var i=this._worldPosition.y;this.moveByLeptons(e.x,e.z,t),this.setAbsoluteElevationWorld(i+e.y)}setAbsoluteElevationWorld(e){this._absoluteElevation=e,this._tileElevation=void 0,this._tile&&(this.updateWorldPosition(this._tile,this._tileOffset),this._onPositionChange.dispatch(this,{tileChanged:!1}))}computeSubCellOffset(e){let t={width:0,height:0};var i;e&&(i=(e-1)%2*2-1,r=2*Math.floor((e-1)/2)-1,t={width:i*Coords.LEPTONS_PER_TILE/4,height:r*Coords.LEPTONS_PER_TILE/4});var r=Coords.LEPTONS_PER_TILE/2;return new Vector2(r+t.width,r+t.height)}interpolateRampHeight(e,t,i){var r=rampHeights[i],s=r[1],i=r[0];return s*(1-e)*(1-t)+r[2]*e*(1-t)+i*(1-e)*t+r[3]*e*t}updateWorldPosition(t,i){var e=i.x+this._centerOffset.x,r=i.y+this._centerOffset.y,s=e/Coords.LEPTONS_PER_TILE,i=r/Coords.LEPTONS_PER_TILE;let a;if(void 0!==this._tileElevation){let e=0;0!==t.rampType&&(e=this.interpolateRampHeight(s,i,t.rampType)),a=Coords.tileHeightToWorld(t.z+e+this._tileElevation)}else a=this._absoluteElevation;this._worldPosition.set(t.rx*Coords.LEPTONS_PER_TILE+e,a,t.ry*Coords.LEPTONS_PER_TILE+r),void 0===this._tileElevation&&(this._computedTileElevation=this.computeTileElevationFromWorldPos())}computeTileElevationFromWorldPos(){if(!this._tile)return 0;var e=roundToDecimals(Coords.worldToTileHeight(this._worldPosition.y),14),t=(this._tileOffset.x+this._centerOffset.x)/Coords.LEPTONS_PER_TILE,i=(this._tileOffset.y+this._centerOffset.y)/Coords.LEPTONS_PER_TILE;let r=0;return 0!==this._tile.rampType&&(r=this.interpolateRampHeight(t,i,this._tile.rampType)),e-this._tile.z-r}clone(){let e=new ObjectPosition(this.tiles,this.tileOccupation);return e._worldPosition=this._worldPosition.clone(),e._tile=this._tile,e._tileOffset=this._tileOffset.clone(),e._centerOffset=this._centerOffset.clone(),e._tileElevation=this._tileElevation,e._absoluteElevation=this._absoluteElevation,e._computedTileElevation=this._computedTileElevation,e}}const AIR_DETONATION_Z_THRESH=1.5,WALL_HEIGHT=2,UNIT_HEIGHT=1.1;class CollisionHelper{constructor(e){this.tileOccupation=e}checkCollisions(e,t,i){var r,s=e.tile;let a,n,o;for(r of this.tileOccupation.getObjectsOnTile(s))r.isOverlay()&&r.isBridge()&&(a=r),r.isOverlay()&&r.wallTrait&&(o=r),r.isTechno()&&!r.isDestroyed&&(n=r);if(i.walls){if(e.tileElevation<=WALL_HEIGHT&&s.landType===LandType.Wall)return{type:CollisionType.Wall,target:o};if(i.units&&n?.tile===s&&(!n.isUnit()||n.zone===ZoneType.Ground)&&e.tileElevation<=UNIT_HEIGHT&&i.units(n.owner))return{type:CollisionType.Wall,target:n}}if(i.shore&&s.landType!==LandType.Water)return{type:CollisionType.Shore};if(i.ground&&e.tileElevation<0)return{type:CollisionType.Ground};var l=e.tileElevation+s.z,h=t.tileElevation+t.tile.z;if(a?.isHighBridge()){var c=a.tile.z+a.tileElevation;if(c<h&&l<=c||h<c&&c-1<=l)return h<c?{type:CollisionType.UnderBridge,target:a}:{type:CollisionType.OnBridge,target:a}}else if(a?.isLowBridge()&&i.shore)return{type:CollisionType.UnderBridge,target:a};if(i.cliffs){t=s.z-t.tile.z;if(e.tileElevation<0&&4<=t)return{type:CollisionType.Cliff}}return{type:CollisionType.None}}computeDetonationZone(e,t,i){let r=this.tileOccupation.getBridgeOnTile(e);return i===CollisionType.None&&t>AIR_DETONATION_Z_THRESH+(r?.tileElevation??0)?ZoneType.Air:r&&t>AIR_DETONATION_Z_THRESH||e.terrainType!==TerrainType.Water||r?.isLowBridge()?ZoneType.Ground:ZoneType.Water}}const CRUISING_ELEVATION_TILE_THRESH=2,CRUISING_ELEVATION_BASE=2,CRUISING_ELEVATION_TILES=3,HOMING_ELEVATION_Z_SPEED=.25,LIMBO_TELEPORT_TICKS=10,MAX_OVERSHOOT_TILES=2;!function(e){e[e.Travel=0]="Travel",e[e.Impact=1]="Impact",e[e.Detonation=2]="Detonation"}(ProjectileState=ProjectileState||{});class Projectile extends GameObject{get fromObject(){return this._fromObject}set fromObject(e){(this._fromObject=e)&&e.veteranTrait&&!e.isDestroyed&&(this.veteranDamageMult=e.veteranTrait.getVeteranDamageMultiplier())}get rot(){return this.fromWeapon.rules.isSonic?ObjectRules.iniRotToDegsPerTick(this.iniRot):this.rules.rot}get iniRot(){return this.fromWeapon.rules.isSonic?10:this.rules.iniRot}static factory(e,t,i,r){return new this(e,t,i,r)}constructor(e,t,i,r){super(ObjectType.Projectile,e,t,i),this.tileOccupation=r,this.state=ProjectileState.Travel,this.detonationTimer=0,this.collisionType=CollisionType.None,this.direction=0,this.zone=ZoneType.Air,this.isShrapnel=!1,this.isNuke=!1,this.baseDamageMultiplier=1,this.veteranDamageMult=1,this.snapToTarget=!1,this.targetLockLost=!1,this.limboTravelTicks=0,this.homingTravelDistance=0,this.homingTravelTicks=0,this.velocity=new Vector3_Vector3,this.sonicVisitedObjects=new Map,this.collisionHelper=new CollisionHelper(r)}onSpawn(a){var e;if(super.onSpawn(a),this.initialSelfPosition=this.position.worldPosition.clone(),!this.target.obj||this.fromWeapon.type===WeaponType.DeathWeapon||this.fromWeapon.rules.limboLaunch||!this.isHoming()&&this.fromWeapon.speed===Number.POSITIVE_INFINITY||this.rules.inaccurate||this.rules.arcing||this.rules.flakScatter||0<(e=this.computeBaseDamage(a))&&(e=this.fromWeapon.warhead.computeDamage(e,this.target.obj,a),this.target.obj.healthTrait?.projectDamage(e)),a.afterTick(()=>{let e=new RangeHelper(this.tileOccupation);var t=e.distance2(this.target.getWorldCoords(),this)/Coords.LEPTONS_PER_TILE;this.initialTileDistToTarget=t,this.maxSpeed=this.computeMaxSpeed(this.fromWeapon.speed,t,a.rules.audioVisual.gravity)}),this.isHoming()){if(1===this.iniRot&&(this.homingMoveDir=this.target.getWorldCoords().clone().sub(this.position.worldPosition)),this.fromObject?.isAircraft()&&this.rules.isAntiGround&&!this.rules.isAntiAir){let e=this.target.obj;!e?.isVehicle()||e.isDestroyed||e.veteranLevel!==VeteranLevel.Elite||e.unitOrderTrait.hasTasks()||e.unitOrderTrait.addTask(new ScatterTask(a))}}else if(this.rules.vertical){let e=this.position.clone();e.tileElevation=this.fromWeapon.warhead.rules.nukeMaker?Coords.worldToTileHeight(this.fromWeapon.projectileRules.detonationAltitude):0,this.aimPoint=e.worldPosition.clone()}else{let s=this.target.getWorldCoords().clone();a.afterTick(()=>{let e=this.target.getWorldCoords().clone().sub(s);var t=e.length()>Coords.LEPTONS_PER_TILE;let i=t?s:this.target.obj?.isUnit()&&this.target.obj.moveTrait.velocity.length()&&isFinite(this.maxSpeed)?this.computeAimPointVersusMovingTarget(this.target.obj,this.maxSpeed,this.position.worldPosition,a.map):this.target.getWorldCoords().clone();this.aimPoint=i,this.snapToTarget=!t&&isFinite(this.maxSpeed)&&!this.fromWeapon.warhead.rules.sonic,(this.rules.inaccurate||this.rules.flakScatter)&&(this.adjustAimForBallisticScatter(a,i),this.snapToTarget=!1),!t&&this.rules.arcing&&(this.rules.inaccurate?(this.overshootTiles=this.calculateInaccurateBallisticOvershoot(a),this.snapToTarget=!1):this.target.obj?.isVehicle()&&this.target.obj.moveTrait.isMoving()&&(this.overshootTiles=this.calculateBallisticOvershootVsMoving(a,this.target.obj),this.overshootTiles&&(this.snapToTarget=!1)));let r=i.clone().sub(this.position.worldPosition);r.length()<this.fromWeapon.speed&&this.update(a)})}}adjustAimForBallisticScatter(e,t){let i=e.rules.combatDamage.ballisticScatter,r;r=this.rules.flakScatter?(this.rules.inviso&&(i*=2),e.generateRandom()*i):i/2+e.generateRandom()*(i/2);let s=r*Coords.LEPTONS_PER_TILE;this.rules.flakScatter&&(n=t.clone().sub(this.initialSelfPosition).length(),s*=n/(this.fromWeapon.range*Coords.LEPTONS_PER_TILE));var a=rotateVec2(new Vector2(s,0),e.generateRandomInt(0,360)),n=Coords.vecWorldToGround(t).add(a).multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor();e.map.tiles.getByMapCoords(n.x,n.y)&&t.add(new Vector3_Vector3(a.x,0,a.y))}calculateBallisticOvershootVsMoving(e,t){let i=this.target.getWorldCoords().clone().sub(this.initialSelfPosition);var r=angleDegBetweenVec2(Coords.vecWorldToGround(i),Coords.vecWorldToGround(t.moveTrait.velocity)),t=(90<r?180-r:r)/90,r=i.length()/Coords.LEPTONS_PER_TILE,t=t*r/5;return e.generateRandom()<=t?Math.min(1,r/5)*MAX_OVERSHOOT_TILES:0}calculateInaccurateBallisticOvershoot(e){return e.generateRandom()<=.5?MAX_OVERSHOOT_TILES:0}update(o){if(void 0!==this.maxSpeed)if(super.update(o),this.state!==ProjectileState.Impact){var s=this.velocity.clone(),l=this.position.clone();if(this.velocity.set(0,0,0),this.fromWeapon.rules.limboLaunch){if(!this.fromObject)throw new Error("Limbo launch projectile must be fired from a unit");if(this.fromObject.isDestroyed)return void o.destroyObject(this)}var h=this.updateSpeed(this.maxSpeed);this.speed=h;let n=this.target.getWorldCoords();if(this.lastTargetLockPosition&&(this.targetLockLost||n.clone().sub(this.lastTargetLockPosition).length()>=Coords.LEPTONS_PER_TILE)?(n=this.lastTargetLockPosition,this.targetLockLost=!0):this.lastTargetLockPosition=n.clone(),this.isHoming()){if(this.target.obj?.isUnit()&&(this.target.obj.isDestroyed||this.target.obj.isCrashing||!this.target.obj.isSpawned)&&(this.fromWeapon.rules.limboLaunch||this.homingTravelDistance>=2*Coords.LEPTONS_PER_TILE))return void this.detonate(o);if(this.homingMoveDir||(u=FacingUtil.toMapCoords(this.direction),this.homingMoveDir=new Vector3_Vector3(u.x,0,u.y),this.fromObject?.isAircraft()&&(this.homingMoveDir.y=-9999999,this.homingMoveDir.normalize())),this.fromWeapon.rules.limboLaunch){if(!this.targetLockLost){if(this.limboTravelTicks>LIMBO_TELEPORT_TICKS)return this.position.moveToLeptons(this.target.obj.position.getMapPosition()),this.position.tileElevation=this.target.obj.position.tileElevation,void this.detonate(o);this.limboTravelTicks++}}else if(!this.isInHomingRange(n,o))return void this.detonate(o);let e=new RangeHelper(this.tileOccupation);var c=Math.floor(e.distance2(n,this)/Coords.LEPTONS_PER_TILE),u=c>CRUISING_ELEVATION_TILE_THRESH&&1<this.iniRot;let t=n.clone().sub(this.position.worldPosition),i=0;this.homingTravelTicks<this.rules.courseLockDuration||(u?(rotateVec3Towards(this.homingMoveDir,new Vector3_Vector3(t.x,this.homingMoveDir.y,t.z),this.rot),this.rules.level||(c=clamp(Math.floor(this.initialTileDistToTarget)-1,0,CRUISING_ELEVATION_BASE)+clamp(c-CRUISING_ELEVATION_TILE_THRESH,0,CRUISING_ELEVATION_TILES),d=this.tileOccupation.getBridgeOnTile(this.tile)?.tileElevation??0,(d=c-(this.position.tileElevation-d))&&(p=HOMING_ELEVATION_Z_SPEED+6/this.iniRot*.1,i=Coords.tileHeightToWorld(Math.sign(d)*Math.min(Math.abs(d),p))))):rotateVec3Towards(this.homingMoveDir,t,this.rot)),this.direction=FacingUtil.fromMapCoords(new Vector2(this.homingMoveDir.x,this.homingMoveDir.z));var d=t.length(),p=Math.min(d,h);this.homingTravelDistance+=p,this.homingTravelTicks++;let r=!1,s=CollisionType.None,a;if(1<=p){let e=this.homingMoveDir.clone().setLength(p);i&&(e.y+=i),p===h&&this.velocity.copy(e);var g=e.clone().add(this.position.worldPosition);o.map.mapBounds.isWithinHardBounds(g)?this.position.moveByLeptons3(e):r=!0;var m=this.checkObstacles(l,o);s=m.type,a=m.target,(s||p<h)&&(r=!0)}else this.position.moveByLeptons3(t),r=!0;if(r){if(a&&s===CollisionType.Wall){let e=a.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}this.collisionType=s,this.detonate(o,s)}}else{let t=this.aimPoint.clone().sub(this.position.worldPosition);this.rules.vertical||(this.direction=FacingUtil.fromMapCoords(new Vector2(t.x,t.z))),this.rules.arcing&&(t.y=0);d=Math.min(t.length(),h);if(t.setLength(d),this.rules.arcing){let e=Coords.vecWorldToGround(this.position.worldPosition.clone().sub(this.initialSelfPosition).add(t));var g=this.aimPoint.clone().sub(this.initialSelfPosition),a=e.length(),m=Coords.vecWorldToGround(g).length(),p=g.y,g=o.rules.audioVisual.gravity;t.y=(p/m*h+g/2*m/h)*a/h-g*(a/h)*(a/h)/2+this.initialSelfPosition.y-this.position.worldPosition.y}let e=!1;a=t.clone().add(this.position.worldPosition);o.map.isWithinHardBounds(a)?this.position.moveByLeptons3(t):e=!0;let i=CollisionType.None,r;if(1<=d?(d!==h&&!this.overshootTiles||this.velocity.copy(t),l=this.checkObstacles(l,o),i=l.type,r=l.target,(i||d<h)&&(e=!0)):e=!0,e){if(i){if(r&&i===CollisionType.Wall){let e=r.isBuilding()?Coords.tile3dToWorld(r.tile.rx+.5,r.tile.ry+.5,r.tile.z):r.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}}else if(this.overshootTiles){var y=Coords.vecWorldToGround(s).setLength(this.overshootTiles*Coords.LEPTONS_PER_TILE);if(rotateVec2(y,o.generateRandomInt(-45,45)),a=Coords.vecGroundToWorld(y).add(this.position.worldPosition),!o.map.isWithinHardBounds(a))return void o.unspawnObject(this);this.position.moveByLeptons(y.x,y.y)}else if(this.snapToTarget&&!this.targetLockLost){if(!o.map.isWithinHardBounds(n))return void o.unspawnObject(this);this.position.moveByLeptons3(n.clone().sub(this.position.worldPosition))}this.collisionType=i,this.isNuke?(this.state=ProjectileState.Impact,this.detonationTimer=2.5*GameSpeed.BASE_TICKS_PER_SECOND):this.detonate(o,i)}}let e=this.fromWeapon.warhead;if(e.rules.sonic){var t,i,y=11/30*Coords.LEPTONS_PER_TILE,y=this.position.worldPosition.clone().add(this.velocity.clone().setLength(y)),y=Coords.vecWorldToGround(y).multiplyScalar(1/Coords.LEPTONS_PER_TILE).floor(),r=o.map.tiles.getByMapCoords(y.x,y.y);if(r&&r!==this.fromObject?.tile){var T,f=o.map.getTileZone(r);for(T of o.map.getGroundObjectsOnTile(r))if((!T.isUnit()||!T.onBridge)&&(!T.isTechno()||!T.rules.typeImmune||T.owner!==this.fromPlayer||T.name!==this.fromObject?.name)&&(!T.isAircraft()||!T.rules.spawned)&&e.canDamage(T,r,f)){let e=this.sonicVisitedObjects.get(T)??new Set;e.add(r),this.sonicVisitedObjects.set(T,e)}}for([t,i]of this.sonicVisitedObjects)for(var v of i)o.map.tileOccupation.isTileOccupiedBy(v,t)&&t.isSpawned&&(v=this.fromWeapon.rules.ambientDamage*this.veteranDamageMult*this.baseDamageMultiplier,v=e.computeDamage(v,t,o),e.inflictDamage(v,t,{player:this.fromPlayer,weapon:this.fromWeapon,obj:this.fromObject},o,t!==this.target.obj))}}else 0<this.detonationTimer?this.detonationTimer--:this.detonate(o,this.collisionType)}isHoming(){return!!this.rot&&!this.rules.arcing}isInHomingRange(t,i){let r=!0,s=this.target.obj;if(s?.isUnit()&&this.fromObject){let e=new RangeHelper(this.tileOccupation);i=e.computeWeaponRangeVsTarget(this.fromObject,s,this.fromWeapon,i.rules).range;this.fromWeapon.rules.limboLaunch?r=e.isInRange3(this.initialSelfPosition,t,0,i+.5):(t=s.moveTrait.velocity.length())&&(this.fromObject.rules.movementZone===MovementZone.Fly?5<this.speed/t&&(r=e.isInRange2(this.initialSelfPosition,this.position.worldPosition,0,i)):isFinite(this.fromWeapon.speed)&&3.5<this.fromWeapon.speed/s.rules.speed&&(r=e.isInRange3(this.initialSelfPosition,this.position.worldPosition,0,i)))}return r}updateSpeed(e){let t;return t=this.isHoming()||this.rules.vertical?void 0===this.speed?Math.min(e,this.rules.acceleration):Math.min(e,this.speed+this.rules.acceleration):e,t}computeMaxSpeed(e,t,i){let r=e;return this.rules.arcing&&(r*=(1+i/6)/2,t=Math.floor(t),r*=t<=8?1:1+t/8*.5),this.fromWeapon.warhead.rules.sonic&&(r=Math.ceil(t*Coords.LEPTONS_PER_TILE/21)),r}checkObstacles(e,t){return this.fromWeapon.rules.limboLaunch?{type:CollisionType.None}:this.collisionHelper.checkCollisions(this.position,e,{cliffs:this.rules.subjectToCliffs,ground:this.isHoming(),shore:this.rules.level,walls:this.rules.subjectToWalls,units:!this.rules.inaccurate&&(e=>this.fromPlayer!==e&&!t.alliances.areAllied(this.fromPlayer,e))})}computeBaseDamage(e){var t=this.fromWeapon,i=t.warhead;let r=t.rules.damage;t.type===WeaponType.DeathWeapon&&i.rules.ivanBomb&&(r=e.rules.combatDamage.ivanDamage);let s=r*this.baseDamageMultiplier;return t.type===WeaponType.DeathWeapon&&this.fromObject&&(s*=this.fromObject.rules.deathWeaponDamageModifier),s*=this.veteranDamageMult,s}detonate(n,e=CollisionType.None){var i=this.fromWeapon;let r=i.warhead;var t,s=this.zone=this.collisionHelper.computeDetonationZone(this.tile,this.tileElevation,e);let o=this.tile;i.type===WeaponType.DeathWeapon&&r.rules.ivanBomb&&(r=new Warhead(n.rules.getWarhead(n.rules.combatDamage.ivanWarhead)));let a=this.computeBaseDamage(n);n.destroyObject(this),this.state=ProjectileState.Detonation;let l=this.target.obj,h=!1;if(r.rules.parasite&&l?.isUnit()&&o===l.tile&&r.canDamage(l,o,s))if(l.isInfantry())a=Number.POSITIVE_INFINITY;else if(l.parasiteableTrait&&this.fromObject?.isUnit()){if(!(this.fromWeapon instanceof Weapon))throw new Error("Projectile with parasite warhead must have a weapon reference");l.parasiteableTrait.infest(this.fromObject,this.fromWeapon),h=!0}let c=!0;if(h&&(c=!1),r.rules.sonic&&(c=!1),r.rules.ivanBomb&&(c=!1,!l?.isTechno()||!l.tntChargeTrait||l.tntChargeTrait.hasCharge()||l.isDestroyed||l.warpedOutTrait.isInvulnerable()||(t=n.rules.combatDamage.ivanTimedDelay,l.tntChargeTrait.setCharge(t,n.currentTick,{player:this.fromPlayer,obj:this.fromObject}))),r.rules.bombDisarm&&(c=!1,l?.isTechno()&&l.tntChargeTrait?.hasCharge()&&!l.isDestroyed&&l.tntChargeTrait.removeCharge()),r.rules.mindControl&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&l?.isTechno()&&l.mindControllableTrait&&!l.mindControllableTrait?.isActive()&&!n.areFriendly(l,this.fromObject)&&r.canDamage(l,o,s)&&!l.invulnerableTrait.isActive()&&this.fromObject.mindControllerTrait.control(l,n)),r.rules.temporal&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&l?.isTechno()&&r.canDamage(l,o,s)&&!l.invulnerableTrait.isActive()&&(r.inflictDamage(0,l,{player:this.fromPlayer,weapon:i,obj:this.fromObject},n),this.fromObject.temporalTrait.updateTarget(l,i,n))),r.rules.makesDisguise&&(c=!1,this.fromObject&&!this.fromObject.isDestroyed&&(this.fromObject.isInfantry()||this.fromObject.isVehicle())&&l?.isUnit()&&l.type===this.fromObject.type&&this.fromObject.disguiseTrait?.disguiseAs(l,this.fromObject,n)),r.rules.electricAssault&&(this.fromObject?.isUnit()&&!this.fromObject.isDestroyed&&l?.isBuilding()&&!l.isDestroyed&&l.overpoweredTrait&&l.owner===this.fromPlayer&&l.overpoweredTrait.chargeFrom(this.fromObject),c=!1),c&&r.detonate(n,a,o,this.tileElevation,this.position.worldPosition,s,e,this.target,{player:this.fromPlayer,weapon:i,obj:this.fromObject},this.isShrapnel?SpecialWarheadType.Shrapnel:SpecialWarheadType.None,this.impactAnim),r.rules.nukeMaker){let e;e=this.fromObject?(u=Weapon.factory(Weapon.NUKE_PAYLOAD_NAME,WeaponType.Primary,this.fromObject,n.rules),n.createProjectile(u.projectileRules.name,this.fromObject,u,this.target,!1)):n.createLooseProjectile(Weapon.NUKE_PAYLOAD_NAME,this.fromPlayer,this.target),e.isNuke=!0,e.impactAnim="NUKEBALL";var u=this.target.tile;e.position.moveToTileCoords(u.rx+.5,u.ry+.5),e.position.tileElevation=this.position.tileElevation,n.spawnObject(e,u)}if(this.rules.shrapnelCount&&this.rules.shrapnelWeapon&&((this.target.obj?!this.target.obj.isBuilding():n.map.getGroundObjectsOnTile(this.target.tile).some(e=>e.isTerrain())&&!i.projectileRules.isAntiAir)||this.isShrapnel)){let t=n.rules.getWeapon(this.rules.shrapnelWeapon);var d,p=n.rules.getProjectile(t.projectile);let i=this.rules.shrapnelCount,r=new RangeHelper(n.map.tileOccupation),e=new RadialTileFinder(n.map.tiles,n.map.mapBounds,o,{width:1,height:1},1,t.range,e=>r.isInTileRange(o,e,t.minimumRange,t.range)),s=new Set;for(;0<Math.floor(i);){var g,m=e.getNextTile();if(!m)break;for(g of n.map.tileOccupation.getObjectsOnTileByLayer(m,p.isAntiAir?LayerType.Air:LayerType.Ground).filter(e=>n.isValidTarget(e)&&(e.isTerrain()||e.isTechno()&&e.owner!==this.fromPlayer&&!n.alliances.areAllied(e.owner,this.fromPlayer)&&!(e.isInfantry()&&e.stance===StanceType.Paradrop))))if(!s.has(g)&&(s.add(g),i=Math.max(0,i-1-(g.isTechno()?.5:0)),Math.floor(i)<=0))break}for(d of s){var y=n.createTarget(d.isTerrain()?void 0:d,d.tile);this.createShrapnel(n,y,t.name)}i=Math.floor(i);let a=new RandomTileFinder(n.map.tiles,n.map.mapBounds,o,t.range,n,e=>r.isInTileRange(o,e,t.minimumRange,t.range));for(let e=0;e<i;e++){var T=a.getNextTile();if(!T)break;T=n.createTarget(void 0,T);this.createShrapnel(n,T,t.name)}}if(i.rules.limboLaunch&&!h&&this.fromObject?.isUnit()){let s=this.fromObject;r.rules.parasite&&(this.target.obj.isVehicle()||this.target.obj?.isAircraft())&&this.target.obj.parasiteableTrait&&(this.target.obj.parasiteableTrait.beingBoarded=!1);let t,a;i=s.rules.movementZone===MovementZone.Fly;if(i)t=o,a=!1;else{let i=this.target.obj.isUnit()&&this.target.obj.tile.onBridgeLandType&&!this.target.obj.onBridge?void 0:n.map.tileOccupation.getBridgeOnTile(o),r=new MovePositionHelper(n.map),e=new RadialTileFinder(n.map.tiles,n.map.mapBounds,o,{width:1,height:1},0,1,e=>{var t=n.map.tileOccupation.getBridgeOnTile(e);return 0<n.map.terrain.getPassableSpeed(e,s.rules.speedType,s.isInfantry(),!!t)&&r.isEligibleTile(e,t,i,o)&&(e===o||!n.map.terrain.findObstacles({tile:e,onBridge:i},s).length)});t=e.getNextTile(),a=!!t?.onBridgeLandType}t?(!i&&this.target.obj.isUnit()&&(s.onBridge=a,s.position.tileElevation=a?n.map.tileOccupation.getBridgeOnTile(t)?.tileElevation??0:0),n.unlimboObject(s,t),s.isInfantry()&&(s.position.subCell=this.target.obj.position.subCell),s.direction=this.direction):s.owner.removeOwnedObject(s)}}createShrapnel(e,t,i){let r=e.createLooseProjectile(i,this.fromPlayer,t);r.isShrapnel=!0,r.veteranDamageMult=this.veteranDamageMult,r.position.moveToLeptons(this.position.getMapPosition()),r.position.tileElevation=this.position.tileElevation,e.spawnObject(r,r.position.tile)}computeAimPointVersusMovingTarget(t,i,e,r){let s=t.position.worldPosition,a=s.clone();var n=i,i=t.moveTrait.velocity.length();if(n<3*i)return s.clone();let o=TargetUtil.computeInterceptPoint(e,n,s,t.moveTrait.velocity);if(o.length()){let e=o.clone().sub(s);n=e.length(),i=i,n=i?Math.ceil(n/i):0;if(o=s.clone().add(e.setLength(n*i)),r.isWithinHardBounds(o))if(t.zone!==ZoneType.Air){o.multiplyScalar(1/Coords.LEPTONS_PER_TILE);let e=t.position.clone();e.moveToTileCoords(o.x,o.z),a=e.worldPosition}else a=o;else a=s}return a.clone()}}const DEPLOY_FIRE_DELAY_TICKS=15;!function(e){e[e.None=0]="None",e[e.PreparingToFire=1]="PreparingToFire",e[e.FiringUp=2]="FiringUp",e[e.Firing=3]="Firing"}(DeployFireState=DeployFireState||{});class DeployerTrait{constructor(e){this.gameObject=e,this.deployed=!1,this.deployFireDelay=0,this.deployFireState=DeployFireState.None,this.fireUpDelay=0,this.deployFireCount=0}isDeployed(){return this.deployed}setDeployed(t){var e=this.deployed;if((this.deployed=t)!==e){let e=this.gameObject;e.isInfantry()&&(e.stance=t?StanceType.Deployed:StanceType.None),t?(this.deployFireState=DeployFireState.PreparingToFire,t=this.gameObject.armedTrait?.getDeployFireWeapon(),this.deployWeapon=t?.rules.areaFire?t:void 0,this.deployFireDelay=DEPLOY_FIRE_DELAY_TICKS+((t===e.primaryWeapon?e.secondaryWeapon:e.primaryWeapon)?.getCooldownTicks()??0),this.deployFireCount=0,this.undeployDelay=this.gameObject.rules.undeployDelay||void 0):(this.deployFireState===DeployFireState.FiringUp&&(e.isFiring=!1),this.deployFireState=DeployFireState.None,this.deployWeapon=void 0)}}toggleDeployed(){this.setDeployed(!this.isDeployed())}[NotifyTick_NotifyTick.onTick](e,t){if(void 0!==this.undeployDelay&&(0<this.undeployDelay&&this.undeployDelay--,this.undeployDelay<=0&&[DeployFireState.None,DeployFireState.PreparingToFire].includes(this.deployFireState)))return this.undeployDelay=void 0,void this.setDeployed(!1);if(this.deployWeapon&&this.deployFireState!==DeployFireState.None){if(this.deployFireState===DeployFireState.PreparingToFire){if(0<this.deployFireDelay--||0===e.ammo)return;if(0<this.computeDeployFireCooldown(this.deployWeapon,t))return;this.fireUpDelay=Math.max(1,e.art.fireUp),this.deployFireState=DeployFireState.FiringUp}if(this.deployFireState===DeployFireState.FiringUp){if(e.isFiring=!0,0<this.fireUpDelay--)return;this.deployFireState=DeployFireState.Firing}var i;this.deployFireState===DeployFireState.Firing&&(e.isFiring=!1,i=e.onBridge?t.map.tileOccupation.getBridgeOnTile(e.tile):void 0,this.deployWeapon.fire(t.createTarget(i,e.tile),t),this.deployFireCount++,(this.deployWeapon===e.primaryWeapon?e.secondaryWeapon:e.primaryWeapon)?.resetCooldown(),this.deployWeapon.rules.fireOnce?(this.deployFireState=DeployFireState.None,this.deployWeapon=void 0):this.deployFireState=DeployFireState.PreparingToFire)}}computeDeployFireCooldown(t,i){if(t.rules.radLevel&&t.rules.areaFire){var r=this.gameObject.tile,r=i.mapRadiationTrait.getRadSiteLevel(r);if(!r)return 0;i=i.rules.radiation;let e=Math.max(0,r*i.radDurationMultiple-i.radLevelDelay);return 1===this.deployFireCount&&(i=i.radDurationMultiple*t.rules.radLevel,e=Math.max(0,e-Math.floor(.25*i))),e}return t.getCooldownTicks()}getHash(){return this.deployed?1:0}debugGetState(){return{deployed:this.deployed}}dispose(){this.gameObject=void 0}}(NotifyHealthChange=NotifyHealthChange||{}).onChange=Symbol();class InflictDamageEvent{constructor(e,t,i,r,s){this.target=e,this.attacker=t,this.damageHitPoints=i,this.currentHealth=r,this.prevHealth=s,this.type=EventType.InflictDamage}}(NotifyHealthChange_NotifyHealthChange=NotifyHealthChange_NotifyHealthChange||{}).onChange=Symbol(),function(e){e[e.Green=0]="Green",e[e.Yellow=1]="Yellow",e[e.Red=2]="Red"}(HealthLevel=HealthLevel||{});class HealthChangeEvent{constructor(e,t,i){this.target=e,this.currentHealth=t,this.prevHealth=i,this.type=EventType.HealthChange}}const MIN_PROJECTED_HIT_POINTS=-30,PROJECTED_HEALTH_DECAY_FRAMES=4;class HealthTrait{get health(){return this._computedHealth}set health(e){this.setHitPoints(0<e?Math.max(1,Math.floor(e*this.maxHitPoints/100)):0),this.projectedHitPoints=this.hitPoints}get level(){return this.health>100*this.conditionYellow?HealthLevel.Green:this.health>100*this.conditionRed?HealthLevel.Yellow:HealthLevel.Red}constructor(e,t,i,r){this.maxHitPoints=e,this.gameObject=t,this.conditionYellow=i,this.conditionRed=r,this.setHitPoints(e),this.projectedHitPoints=this.hitPoints}setHitPoints(e){if(e!==Math.floor(e))throw new Error(`Value ${e} is not an integer`);this.hitPoints=clamp(e,0,this.maxHitPoints),this._computedHealth=this.hitPoints/this.maxHitPoints*100}getHitPoints(){return this.hitPoints}getProjectedHitPoints(){return this.projectedHitPoints}inflictDamage(t,i,r){var e=this.hitPoints,s=this.health;this.applyHitPoints(e-t,r),e!==this.hitPoints&&0<t&&(this.gameObject.traits.filter(NotifyDamage).forEach(e=>{e[NotifyDamage.onDamage](this.gameObject,r,t,i)}),r.events.dispatch(new InflictDamageEvent(this.gameObject,i,t,this.health,s)))}healBy(e,i,r){if(e<0)throw new Error("Can't heal by negative value "+e);if(this.hitPoints<this.maxHitPoints){var s=this.hitPoints;this.applyHitPoints(this.hitPoints+e,r),this.projectedHitPoints=this.hitPoints;let t=this.hitPoints-s;this.gameObject.traits.filter(NotifyHeal).forEach(e=>{e[NotifyHeal.onHeal]?.(this.gameObject,r,t,i)})}}healToFull(i,r){if(this.hitPoints<this.maxHitPoints){var e=this.hitPoints;this.applyHitPoints(this.maxHitPoints,r),this.projectedHitPoints=this.hitPoints;let t=this.hitPoints-e;this.gameObject.traits.filter(NotifyHeal).forEach(e=>{e[NotifyHeal.onHeal]?.(this.gameObject,r,t,i)})}}applyHitPoints(e,t){let i=this.health;this.setHitPoints(e),i!==this.health&&(t.traits.filter(NotifyHealthChange).forEach(e=>{e[NotifyHealthChange.onChange](this.gameObject,t,i)}),this.gameObject.traits.filter(NotifyHealthChange_NotifyHealthChange).forEach(e=>{e[NotifyHealthChange_NotifyHealthChange.onChange](this.gameObject,t,i)}),t.events.dispatch(new HealthChangeEvent(this.gameObject,this.health,i)))}projectDamage(e){if(e<0)throw new Error("Projected damage must be positive");this.projectedHitPoints=Math.max(MIN_PROJECTED_HIT_POINTS,this.projectedHitPoints-e)}[NotifyTick_NotifyTick.onTick](e,t){t.currentTick%PROJECTED_HEALTH_DECAY_FRAMES==0&&(this.projectedHitPoints=Math.min(this.projectedHitPoints+1,this.hitPoints))}getHash(){return this.hitPoints}debugGetState(){return{hitPoints:this.hitPoints}}dispose(){this.gameObject=void 0}}class BridgeTrait{constructor(e){this.bridges=e,this.needsImageUpdate=!1,this.dominoHandled=!1}[NotifyDamage.onDamage](){this.needsImageUpdate=!0}[NotifyTick_NotifyTick.onTick](e){this.needsImageUpdate&&(this.needsImageUpdate=!1,this.bridges.handlePieceHealthChange(this.bridges.getPieceAtTile(e.tile)))}[NotifyDestroy.onDestroy](s,a,n){var e=this.bridges.getPieceAtTile(s.tile);this.dominoHandled||this.bridges.findDominoPieces(e).filter(e=>!e.obj.isDestroyed).forEach(e=>{e.obj.traits.get(BridgeTrait).dominoHandled=!0,a.destroyObject(e.obj,n)});let t=a.map.tileOccupation.calculateTilesForGameObject(s.tile,s);t.forEach(e=>{let i=getLandType(e.terrainType),r=a.rules.getLandRules(i);a.map.getGroundObjectsOnTile(e).forEach(e=>{if(e.isUnit()&&(e.onBridge||e.moveTrait.reservedPathNodes.some(e=>e.onBridge===s))&&!e.isDestroyed)if(s.isLowBridge()&&0<r.getSpeedModifier(e.rules.speedType)||e.isInfantry()&&e.stance===StanceType.Paradrop){e.onBridge&&(e.onBridge=!1,e.zone=getZoneType(i));for(var t of e.moveTrait.reservedPathNodes)t.onBridge===s&&(t.onBridge=void 0);e.moveTrait.currentWaypoint?.onBridge===s&&(e.moveTrait.currentWaypoint.onBridge=void 0)}else e.isInfantry()&&(e.infDeathType=InfDeathType.None),a.destroyObject(e,n,!0)})})}}const SPAWN_RADIUS=2,SPAWN_BAILS=1,SPAWN_INITIAL_BAILS=3;!function(e){e[e.Idle=0]="Idle",e[e.Spawning=1]="Spawning"}(SpawnStatus=SpawnStatus||{});class TiberiumTreeTrait{constructor(e){this.rules=e,this.ticksSinceLastSpawn=0,this.cooldownTicks=Math.floor(1/this.rules.animationProbability),this.status=SpawnStatus.Idle}[NotifyTick_NotifyTick.onTick](e,t){this.status=SpawnStatus.Idle,this.ticksSinceLastSpawn++>this.cooldownTicks&&(this.ticksSinceLastSpawn=0,this.status=SpawnStatus.Spawning,this.spawnTiberium(e.tile,t))}spawnTiberium(r,s){for(let i=1;i<=SPAWN_RADIUS;i++){let e=new RadialTileFinder(s.map.tiles,s.map.mapBounds,r,{width:1,height:1},i,i,e=>TiberiumTrait.canBePlacedOn(e,s.map));var a=e.getNextTile();if(a){var n=OreSpread.calculateOverlayId(OverlayTibType.Ore,a);if(void 0===n)throw new Error("Expected an overlayId");let e=s.createObject(ObjectType.Overlay,s.rules.getOverlayName(n));return e.overlayId=n,e.value=SPAWN_INITIAL_BAILS,void s.spawnObject(e,a)}e=new RadialTileFinder(s.map.tiles,s.map.mapBounds,r,{width:1,height:1},i,i,e=>e.landType===LandType.Tiberium);let t;for(;!t;){var o=e.getNextTile();if(!o)break;t=s.map.getObjectsOnTile(o).find(e=>e.isOverlay()&&e.isTiberium()&&e.traits.get(TiberiumTrait).getBailCount()+SPAWN_BAILS<=TiberiumTrait.maxBails)}if(t)return void t.traits.get(TiberiumTrait).spawnBails(SPAWN_BAILS)}}}class AutoRepairTrait{constructor(e=!1){this.freeRepair=e,this.disabled=!0,this.cooldownTicks=0,this.healLeftover=0}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}[NotifyTick_NotifyTick.onTick](t,i){if(!this.isDisabled())if(100===t.healthTrait.health&&this.setDisabled(!0),this.cooldownTicks<=0){var r=i.rules.general.repair,s=t.isInfantry()?r.iRepairRate:t.isBuilding()?r.repairRate:r.uRepairRate;this.cooldownTicks+=GameSpeed.BASE_TICKS_PER_SECOND*s*60;var a=t.isInfantry()?r.iRepairStep:r.repairStep,s=this.freeRepair?0:r.repairPercent;let e;s?(r=s*t.purchaseValue/t.healthTrait.maxHitPoints,(s=Math.min(t.owner.credits,Math.max(1,Math.floor(r*a))))?(e=r?s/r:a,t.owner.credits-=s):(e=0,this.setDisabled(!0))):e=a,e&&(e+=this.healLeftover,e=Math.min(t.healthTrait.maxHitPoints-t.healthTrait.getHitPoints(),e),e&&(a=Math.floor(e),this.healLeftover=e-a,a&&t.healthTrait.healBy(a,t,i)))}else this.cooldownTicks--}[NotifyOwnerChange.onChange](){this.setDisabled(!0)}}(NotifyTargetDestroy=NotifyTargetDestroy||{}).onDestroy=Symbol();class UnitPromoteEvent{constructor(e){this.target=e,this.type=EventType.UnitPromote}}class SelfHealingTrait{constructor(){this.cooldownTicks=0}[NotifyTick_NotifyTick.onTick](e,t){100!==e.healthTrait.health&&(this.cooldownTicks<=0?(this.cooldownTicks+=GameSpeed.BASE_TICKS_PER_SECOND*t.rules.general.repair.repairRate*60,e.healthTrait.healBy(1,e,t)):this.cooldownTicks--)}}class ArmedTrait{constructor(e,t){this.gameObject=e,this.rules=t,this.specialWeaponIndex=0;t=e.veteranLevel===VeteranLevel.Elite;e.rules.weaponCount?(this.selectSpecialWeapon(0,t),this.guardWeaponRangeOverride=this.primaryWeapon?.range):this.selectStandardWeapons(t)}selectStandardWeapons(e=!1){var t=this.gameObject,i=e&&t.rules.elitePrimary||t.rules.primary;i?(s=e?t.art.elitePrimaryFireFlh:t.art.primaryFireFlh,this.primaryWeapon=Weapon.factory(i,WeaponType.Primary,t,this.rules,s)):this.primaryWeapon=void 0;var r,s=e&&t.rules.eliteSecondary||t.rules.secondary;s?(r=e?t.art.eliteSecondaryFireFlh:t.art.secondaryFireFlh,this.secondaryWeapon=Weapon.factory(s,WeaponType.Secondary,t,this.rules,r)):this.secondaryWeapon=void 0,(t.explodes||t.crashableTrait)&&(r=t.rules.deathWeapon||!!t.crashableTrait&&this.secondaryWeapon?.rules.name||this.primaryWeapon?.rules.name||this.rules.combatDamage.deathWeapon,this.deathWeapon=Weapon.factory(r,WeaponType.DeathWeapon,t,this.rules))}selectSpecialWeapon(e,t=!1){let i=this.gameObject;var r=i.rules.weaponCount;if(r<1)throw new Error(`Object "${i.name}" doesn't support special weapons`);if(r-1<e)throw new RangeError(`Weapon index ${e} out of bounds (max ${r}) for object `+i.name);r=t&&i.rules.getEliteWeaponAtIndex(e)||i.rules.getWeaponAtIndex(e);if(!r)throw new Error(`Missing weapon at index ${e} for object "${i.name}"`);t=i.art.getSpecialWeaponFlh(e);this.primaryWeapon=Weapon.factory(r,WeaponType.Primary,i,this.rules,t),this.secondaryWeapon=void 0,this.specialWeaponIndex=e,this.deathWeapon=this.primaryWeapon.rules.suicide?Weapon.factory(i.rules.deathWeapon||this.primaryWeapon.name,WeaponType.DeathWeapon,i,this.rules):void 0}toggleEliteWeapons(e){this.gameObject.rules.weaponCount?this.selectSpecialWeapon(this.specialWeaponIndex,e):this.selectStandardWeapons(e)}getSpecialWeaponIndex(){return this.specialWeaponIndex}computeGuardScanRange(t){var e=this.guardWeaponRangeOverride??[this.primaryWeapon,this.secondaryWeapon].filter(e=>e===t||e?.rules.neverUse).reduce((e,t)=>Math.max(e,t.range),0),e=Math.max(e,this.gameObject.rules.guardRange);return Math.min(15,2*e-1)}getDeployFireWeapon(){if(this.gameObject.rules.deployFire)return this.gameObject.rules.deployFireWeapon===WeaponType.Primary?this.primaryWeapon:this.secondaryWeapon}isEquippedWithWeapon(e){return[this.primaryWeapon,this.secondaryWeapon].includes(e)}getWeapons(){return[this.primaryWeapon,this.secondaryWeapon].filter(isNotNullOrUndefined)}[NotifyTick_NotifyTick.onTick](){this.primaryWeapon&&this.primaryWeapon.tick(),this.secondaryWeapon&&this.secondaryWeapon.tick()}[NotifyDestroy.onDestroy](t,e,i){!this.deathWeapon||i?.weapon?.warhead.rules.temporal||t.crashableTrait&&!t.isCrashing||i?.obj?.isVehicle()&&i.weapon?.rules.suicide&&i.obj.transportTrait?.units.find(e=>e===t)||this.deathWeapon.fire(e.createTarget(t,t.tile),e)}dispose(){this.gameObject=void 0,this.primaryWeapon=void 0,this.secondaryWeapon=void 0,this.deathWeapon=void 0}}class SensorsTrait{}class VeteranTrait{constructor(e,t){this.gameObject=e,this.veteranRules=t,this.veteranLevel=VeteranLevel.None,this.xp=0,this.promotionThresh=e.rules.cost*t.veteranRatio+1}[NotifyTargetDestroy.onDestroy](e,t,i,r){e.isDestroyed&&!e.isCrashing||t.isTechno()&&(t.rules.dontScore||t.rules.insignificant||(i&&(i.warhead.rules.temporal||i.warhead.rules.parasite&&e.rules.organic)||!r.areFriendly(e,t))&&(this.veteranLevel>=this.veteranRules.veteranCap||this.gainXP(t.rules.cost*(t.veteranLevel+1))&&this.handlePromotion(e,r)))}setRelativeXP(e){this.gainXP(Math.floor(e*this.promotionThresh))}gainXP(e){if(this.xp+=e,this.xp>=this.promotionThresh){var t=Math.min(this.veteranLevel+Math.floor(this.xp/this.promotionThresh),this.veteranRules.veteranCap),e=t-this.veteranLevel;if(e)return this.xp-=e*this.promotionThresh,this.setVeteranLevel(t),!0}return!1}promote(e,t){e=Math.min(this.veteranLevel+e,this.veteranRules.veteranCap);e-this.veteranLevel&&(this.setVeteranLevel(e),this.handlePromotion(this.gameObject,t))}isMaxLevel(){return this.veteranLevel===this.veteranRules.veteranCap}isElite(){return this.veteranLevel===VeteranLevel.Elite}setVeteranLevel(e){this.veteranLevel=e,this.veteranLevel===VeteranLevel.Elite&&this.gameObject.armedTrait?.toggleEliteWeapons(!0)}handlePromotion(e,t){this.hasVeteranAbility(VeteranAbility.SELF_HEAL)&&(e.traits.find(SelfHealingTrait)||t.addObjectTrait(e,new SelfHealingTrait)),this.hasVeteranAbility(VeteranAbility.CLOAK)&&(e.cloakableTrait||(e.cloakableTrait=new CloakableTrait(e,t.rules.general.cloakDelay),t.addObjectTrait(e,e.cloakableTrait))),this.hasVeteranAbility(VeteranAbility.EXPLODES)&&(e.explodes||(e.explodes=!0,e.armedTrait||(e.armedTrait=new ArmedTrait(e,t.rules),t.addObjectTrait(e,e.armedTrait)))),this.hasVeteranAbility(VeteranAbility.RADAR_INVISIBLE)&&(e.radarInvisible||(e.radarInvisible=!0)),this.hasVeteranAbility(VeteranAbility.SENSORS)&&(e.sensorsTrait||(e.sensorsTrait=new SensorsTrait,t.addObjectTrait(e,e.sensorsTrait))),e.isInfantry()&&this.hasVeteranAbility(VeteranAbility.FEARLESS)&&e.suppressionTrait?.disable(),this.hasVeteranAbility(VeteranAbility.C4)&&(e.c4||(e.c4=!0)),this.hasVeteranAbility(VeteranAbility.GUARD_AREA)&&(e.defaultToGuardArea||(e.defaultToGuardArea=!0,e.unitOrderTrait.isIdle()&&e.resetGuardModeToIdle())),this.hasVeteranAbility(VeteranAbility.CRUSHER)&&(e.crusher||(e.crusher=!0)),t.events.dispatch(new UnitPromoteEvent(e))}getVeteranSightMultiplier(){return this.getVeteranAbilityMultiplier(VeteranAbility.SIGHT)}getVeteranSpeedMultiplier(){return this.getVeteranAbilityMultiplier(VeteranAbility.FASTER)}getVeteranArmorMultiplier(){return this.getVeteranAbilityMultiplier(VeteranAbility.STRONGER)}getVeteranDamageMultiplier(){return this.getVeteranAbilityMultiplier(VeteranAbility.FIREPOWER)}getVeteranRofMultiplier(){return this.getVeteranAbilityMultiplier(VeteranAbility.ROF)}hasVeteranAbility(e){return this.veteranLevel===VeteranLevel.Veteran&&this.gameObject.rules.veteranAbilities.has(e)||this.veteranLevel>=VeteranLevel.Elite&&this.gameObject.rules.eliteAbilities.has(e)}getVeteranAbilityMultiplier(e){let t=1;return(this.veteranLevel===VeteranLevel.Veteran&&this.gameObject.rules.veteranAbilities.has(e)||this.veteranLevel>=VeteranLevel.Elite&&this.gameObject.rules.eliteAbilities.has(e))&&(t=this.getVeteranRulesMultiplier(e)),t}getVeteranRulesMultiplier(e){switch(e){case VeteranAbility.FASTER:return this.veteranRules.veteranSpeed;case VeteranAbility.STRONGER:return this.veteranRules.veteranArmor;case VeteranAbility.FIREPOWER:return this.veteranRules.veteranCombat;case VeteranAbility.ROF:return this.veteranRules.veteranROF;case VeteranAbility.SIGHT:return this.veteranRules.veteranSight;default:throw new Error("Unhandled VeteranAbility "+e)}}dispose(){this.gameObject=void 0}}class AmmoTrait{constructor(e,t=e){this.maxAmmo=e,this.ammo=t}get ammo(){return this._ammo}set ammo(e){this._ammo=clamp(e,0,this.maxAmmo)}isFull(){return this.ammo===this.maxAmmo}}class ObjectDisguiseChangeEvent{constructor(e){this.target=e,this.type=EventType.ObjectDisguiseChange}}class DisguiseTrait{constructor(){this.isActive=!1,this.cooldownTicks=0}isDisguised(){return this.isActive}getDisguise(){return this.isActive?this.disguisedAs:void 0}hasTerrainDisguise(){return this.getDisguise()?.rules.type===ObjectType.Terrain}disguiseAs(e,t,i){this.disguisedAs={rules:e.rules,owner:e.owner},this.isActive=!0,i.events.dispatch(new ObjectDisguiseChangeEvent(t))}revealDisguise(e,t){this.cooldownTicks=t.rules.general.infantryBlinkDisguiseTime,this.isActive=!1,t.events.dispatch(new ObjectDisguiseChangeEvent(e))}[NotifySpawn.onSpawn](e,t){var i;!this.disguisedAs&&e.rules.permaDisguise&&e.isInfantry()&&e.owner.country&&((i=this.getDefaultInfantryDisguise(e.owner.country.side,t.rules.general))&&(i=t.rules.getObject(i,ObjectType.Infantry),this.disguisedAs={rules:i,owner:e.owner},this.isActive=!0))}getDefaultInfantryDisguise(e,t){switch(e){case SideType.GDI:return t.alliedDisguise;case SideType.Nod:return t.sovietDisguise;case SideType.ThirdSide:return t.thirdDisguise;default:return}}[NotifyTick_NotifyTick.onTick](e,t){e.rules.permaDisguise||(e.attackTrait?.attackState===AttackState.JustFired||e.moveTrait.moveState!==MoveState.Idle?this.revealDisguise(e,t):0<this.cooldownTicks?this.cooldownTicks--:!this.isActive&&e.rules.disguiseWhenStill&&(this.isActive=!0,this.disguisedAs={rules:this.selectRandomMirageDisguise(t),owner:void 0},t.events.dispatch(new ObjectDisguiseChangeEvent(e))))}[NotifyDamage.onDamage](e,t){this.revealDisguise(e,t)}selectRandomMirageDisguise(e){var t=e.rules.general.defaultMirageDisguises;if(!t.length)throw new Error("No default mirage disguises are defined");t=t[e.generateRandomInt(0,t.length-1)];return e.rules.getObject(t,ObjectType.Terrain)}}class InvulnerableTrait{constructor(){this.timer=new Timer}isActive(){return this.timer.isActive()}setActiveFor(e,t){this.timer.setActiveFor(e,t)}[NotifyTick_NotifyTick.onTick](e,t){this.timer.tick(t.currentTick)}}class WarpedOutTrait{constructor(e){this.gameObject=e,this.ticksWhenWarpedOut=!0,this.remainingTicks=0,this.invulnerable=!1}isActive(){return 0<this.remainingTicks}setActive(e,t,i){this.remainingTicks=e?Number.POSITIVE_INFINITY:0,this.invulnerable=t,this.notifyChange(e,i)}setTimed(e,t,i){this.remainingTicks=e,this.invulnerable=t,this.notifyChange(!0,i)}debugSetActive(e){this.remainingTicks=e?Number.POSITIVE_INFINITY:0}notifyChange(t,i){i.traits.filter(NotifyWarpChange).forEach(e=>{e[NotifyWarpChange.onChange](this.gameObject,i,t)}),this.gameObject.traits.filter(NotifyWarpChange_NotifyWarpChange).forEach(e=>{e[NotifyWarpChange_NotifyWarpChange.onChange](this.gameObject,i,t)})}expire(e){this.remainingTicks=0,this.notifyChange(!1,e)}isInvulnerable(){return this.isActive()&&this.invulnerable}[NotifyTick_NotifyTick.onTick](e,t){0<this.remainingTicks&&(this.remainingTicks--,this.remainingTicks<=0&&this.notifyChange(!1,t))}dispose(){this.gameObject=void 0}}class TntChargeTrait{constructor(){this.timer=new Timer}hasCharge(){return this.timer.isActive()}setCharge(e,t,i){this.hasCharge()||(this.timer.setActiveFor(e,t),this.attackerInfo=i)}getChargeOwner(){return this.attackerInfo?.player}removeCharge(){this.timer.reset()}getTicksLeft(){return this.timer.getTicksLeft()}getInitialTicks(){return this.timer.getInitialTicks()}[NotifyTick_NotifyTick.onTick](e,t){this.timer.isActive()&&!0===this.timer.tick(t.currentTick)&&(e.isBuilding()&&e.cabHutTrait&&e.cabHutTrait.demolishBridge(t,this.attackerInfo),this.detonateIvanWarhead(t,e))}[NotifyDestroy.onDestroy](e,t,i){!this.timer.isActive()||i?.weapon?.warhead.rules.ivanBomb||[DeathType.None,DeathType.Temporal,DeathType.Sink].includes(e.deathType)||(this.timer.reset(),this.detonateIvanWarhead(t,e))}detonateIvanWarhead(e,t){var i=e.rules.combatDamage.ivanDamage;let r=new Warhead(e.rules.getWarhead(e.rules.combatDamage.ivanWarhead));var s=t.tile,a=t.tileElevation,n=t.isUnit()?t.zone:e.map.getTileZone(s),o=!!t.isUnit()&&t.onBridge;r.detonate(e,i,s,a,t.isBuilding()?Coords.tile3dToWorld(s.rx+.5,s.ry+.5,s.z+a):t.position.worldPosition,n,o?CollisionType.OnBridge:CollisionType.None,e.createTarget(t,s),{...this.attackerInfo,weapon:void 0},SpecialWarheadType.TntCharge)}}class MindControllableTrait{constructor(e){this.gameObject=e}getOriginalOwner(){return this.prevOwner}isActive(){return!!this.controller}getController(){return this.controller}controlBy(e,t){if(this.controller)throw new Error(`Object "${this.gameObject?.name}" is already mind controlled by "${e.name}"`);this.controller=e,this.prevOwner=this.gameObject.owner,t.changeObjectOwner(this.gameObject,e.owner)}restore(e){this.prevOwner&&(e.changeObjectOwner(this.gameObject,this.prevOwner),this.prevOwner=void 0,this.controller=void 0)}[NotifyUnspawn.onUnspawn](e,t){this.controller&&(this.controller.mindControllerTrait.cleanTarget(e),!e.isDestroyed&&e.limboData&&this.restore(t))}dispose(){this.gameObject=void 0}}class MindControllerTrait{constructor(e,t=1){this.gameObject=e,this.maxCapacity=t,this.targets=[]}isActive(){return 0<this.targets.length}isAtCapacity(){return this.targets.length===this.maxCapacity}getTargets(){return this.targets}control(e,t){if(!this.gameObject)throw new Error("Trait already disposed");if(!e.mindControllableTrait)throw new Error(`Target "${e.name}" cannot be mind controlled`);if(e.isDisposed)throw new Error(`Target "${e.name}" is disposed`);for(e.mindControllableTrait.controlBy(this.gameObject,t),this.targets.push(e);this.targets.length>this.maxCapacity;){let e=this.targets.shift();e.mindControllableTrait.restore(t)}}cleanTarget(e){e=this.targets.indexOf(e);-1!==e&&this.targets.splice(e,1)}[NotifyUnspawn.onUnspawn](e,t){for(var i of this.targets)i.mindControllableTrait.restore(t);this.targets.length=0}dispose(){this.gameObject=void 0}}class TemporalTrait{constructor(e){this.gameObject=e,this.ticksWhenWarpedOut=!0,this.attackers=new Set}[NotifyTick_NotifyTick.onTick](e,t){if(e.attackTrait&&(e.attackTrait.currentTarget&&!e.warpedOutTrait.isActive()||this.releaseCurrentTarget(t)),void 0!==this.eraseTicks)for(var i of this.attackers){var r=i.temporalTrait.currentWeapon;if(!r)throw new Error(`Attacker "${i.name}" is no longer targeting "${e.name}"`);var s=r.rules.damage;if(this.eraseTicks-=s,this.eraseTicks<=0){e.deathType=DeathType.Temporal,t.destroyObject(e,{player:i.owner,obj:i,weapon:r},!0),this.eraseTicks=void 0;break}}}getTarget(){return this.currentTarget}updateTarget(t,e,i){if(this.currentTarget!==t){this.releaseCurrentTarget(i),this.currentTarget=t,this.currentWeapon=e;e=t.temporalTrait.attackers.size;if(t.temporalTrait.attackers.add(this.gameObject),!e){t.warpedOutTrait.setActive(!0,!0,i);let e=t.unitOrderTrait.getCurrentTask();(e&&e instanceof AttackTask||e instanceof MoveTask)&&e.cancel(),t.temporalTrait.eraseTicks=10*t.healthTrait.maxHitPoints}}}releaseCurrentTarget(t){if(this.currentTarget){if(!this.currentTarget.isDisposed){let e=this.currentTarget.temporalTrait.attackers;e.delete(this.gameObject),e.size||(this.currentTarget.warpedOutTrait.expire(t),this.currentTarget.temporalTrait.eraseTicks=void 0)}this.currentTarget=void 0,this.currentWeapon=void 0}}[NotifyDestroy.onDestroy](e,t){this.releaseCurrentTarget(t)}dispose(){this.gameObject=void 0,this.attackers.clear()}}class AirSpawnTrait{constructor(){this.spawns=[],this.storage=[],this.missileLaunches=[],this.nextRegenTicks=[]}get availableSpawns(){return this.storage.length}debugSetStorage(e,t){this.storage.length=t,this.storage.fill(e,0,t)}isLaunchingMissiles(){return 0<this.missileLaunches.length}[NotifySpawn.onSpawn](t,i){var r=i.rules.getObject(t.rules.spawns,ObjectType.Aircraft);for(let e=0;e<t.rules.spawnsNumber;e++)this.pushNewSpawn(r,i,t)}[NotifyUnspawn.onUnspawn](e,t){this.destroySpawns(e,t)}[NotifyDestroy.onDestroy](e,t,i,r){this.destroySpawns(e,t,i,r)}pushNewSpawn(e,t,i){let r=t.createUnitForPlayer(e,i.owner);r.limboData={selected:!1,controlGroup:void 0},e.missileSpawn&&(r.pitch=90*t.rules.general.getMissileRules(e.name).pitchInitial),this.spawns.push(r),this.storage.push(r)}destroySpawns(e,t,i,r){for(var s of this.spawns)s.isDestroyed||(s.isSpawned&&!s.rules.missileSpawn&&s.crashableTrait?s.crashableTrait.crash(i):(s.isSpawned||(s.armedTrait&&(s.armedTrait.deathWeapon=void 0),s.position.tileElevation=e.position.tileElevation,s.zone=e.isUnit()?e.zone:ZoneType.Ground,s.onBridge=!!e.isUnit()&&e.onBridge,s.position.tile=e.tile),t.destroyObject(s,i,r)));this.spawns.length=0,this.storage.length=0,this.missileLaunches.length=0}[NotifyTick_NotifyTick.onTick](s,a){var t;if(this.spawns=this.spawns.filter(e=>!e.isDestroyed),this.missileLaunches=this.missileLaunches.filter(e=>!e.missile.isDestroyed),this.spawns.length<s.rules.spawnsNumber){var i=s.rules.spawnsNumber-this.spawns.length,r=a.rules.getObject(s.rules.spawns,ObjectType.Aircraft);for(let e=0;e<i;e++)r.missileSpawn&&e&&void 0===this.nextRegenTicks[e]?this.nextRegenTicks[e]=this.nextRegenTicks[0]:((t=this.nextRegenTicks)[e]??(t[e]=s.rules.spawnRegenRate),0<this.nextRegenTicks[e]&&this.nextRegenTicks[e]--),this.nextRegenTicks[e]<=0&&this.pushNewSpawn(r,a,s);this.nextRegenTicks=this.nextRegenTicks.filter(e=>0<e)}if(this.storage.length){if(this.nextReloadTicks??(this.nextReloadTicks=s.rules.spawnReloadRate),0<this.nextReloadTicks&&this.nextReloadTicks--,this.nextReloadTicks<=0){for(var e of this.storage)e.ammoTrait&&e.ammoTrait.ammo<e.ammoTrait.maxAmmo&&e.ammoTrait.ammo++;this.nextReloadTicks=s.rules.spawnReloadRate}}else this.nextReloadTicks=void 0;for(let r of this.missileLaunches.slice()){var n=a.rules.general.getMissileRules(r.missile.name);if(r.pauseFrames??(r.pauseFrames=n.pauseFrames),0<r.pauseFrames&&r.pauseFrames--,r.pauseFrames<=0){var o=90*n.pitchFinal,n=90*(n.pitchFinal-n.pitchInitial)/n.tiltFrames;let i=r.missile;if(i.pitch<o)i.pitch=Math.min(o,i.pitch+n);else{i.unitOrderTrait.addTask(new TaskGroup(new MoveTask(a,r.targetTile,!!r.targetBridge),new CallbackTask(()=>{var e,t;i.isDestroyed||(a.unspawnObject(i),i.dispose(),t=Coords.vecGroundToWorld(FacingUtil.toMapCoords(i.direction).multiplyScalar(1)),e=r.targetWorldPos.clone().add(t),t=a.map.getTileZone(r.targetTile),r.warhead.detonate(a,r.damage,r.targetTile,r.targetBridge?.tileElevation??0,e,t,r.targetBridge?CollisionType.OnBridge:CollisionType.None,r.target,{player:i.owner,obj:s,weapon:void 0}))})).setCancellable(!1));n=this.spawns.indexOf(i);if(-1===n)throw new Error("Missile not found in spawns list");this.spawns.splice(n,1),this.missileLaunches.splice(this.missileLaunches.indexOf(r),1)}}}}[NotifyOwnerChange.onChange](e,t,i){for(var r of this.spawns)r.isDestroyed||i.changeObjectOwner(r,e.owner)}[NotifyWarpChange_NotifyWarpChange.onChange](e,t,i){i&&this.removeMissileLaunches(t)}[NotifyTeleport.onBeforeTeleport](e,t,i,r){r||this.removeMissileLaunches(t)}removeMissileLaunches(e){if(this.missileLaunches.length){for(var t of this.missileLaunches){e.unspawnObject(t.missile),t.missile.dispose();t=this.spawns.indexOf(t.missile);if(-1===t)throw new Error("Missile not found in spawns list");this.spawns.splice(t,1)}this.missileLaunches.length=0}}prepareLaunch(r,s,a){if(this.storage.length){let i=this.storage[0];if(!i.ammo)return;if(this.storage.shift(),i.missileSpawnTrait){let e,t;var n=r.veteranTrait?.isElite(),o=a.rules;if(r.rules.spawns===o.general.v3Rocket.type)e=n?o.combatDamage.v3EliteWarhead:o.combatDamage.v3Warhead,t=n?o.general.v3Rocket.eliteDamage:o.general.v3Rocket.damage;else{if(r.rules.spawns!==o.general.dMisl.type)throw new Error(`Unhandled missile type "${r.rules.spawns}"`);e=n?o.combatDamage.dMislEliteWarhead:o.combatDamage.dMislWarhead,t=n?o.general.dMisl.eliteDamage:o.general.dMisl.damage}a=new Warhead(a.rules.getWarhead(e));i.missileSpawnTrait.setDamage(t).setWarhead(a).setLauncher(r),this.missileLaunches.push({missile:i,targetTile:(s.obj?.isUnit()?s.obj:s).tile,targetBridge:s.getBridge(),targetWorldPos:s.getWorldCoords().clone(),target:s,warhead:a,damage:t,pauseFrames:void 0})}else{if(!i.spawnLinkTrait)throw new Error(`Aircraft "${i.name}" must have Spawned=yes to be launchable`);i.spawnLinkTrait.setParent(r)}return i}}storeAircraft(e,t){if(!this.spawns.includes(e))throw new Error(`Object "${e.name}#${e.id}" not found in list of linked spawns`);if(e.limboData)throw new Error(`Object "${e.name}#${e.id}" is already in limbo`);t.limboObject(e,{selected:!1,controlGroup:void 0}),this.storage.push(e)}}class SpawnDebrisTrait{[NotifyCrash.onCrash](e,t){this.handleDestroy(e,t)}[NotifyDestroy.onDestroy](e,t,i){i?.weapon?.warhead.rules.temporal||e.isCrashing||e.deathType!==DeathType.Sink&&e.isSpawned&&this.handleDestroy(e,t)}handleDestroy(e,t){var i,r;(e.isVehicle()||e.isBuilding()||e.isOverlay())&&(i=e.isOverlay()?0:e.rules.minDebris,r=e.isOverlay()?t.rules.general.bridgeVoxelMax:e.rules.maxDebris,0<(r=t.generateRandomInt(i,r))&&this.spawnDebris(e,t,r))}spawnDebris(t,i,r){let s=t.position.getMapPosition();if(i.map.isWithinHardBounds(s)){let e=t.isOverlay()?[]:t.isVehicle()?t.rules.debrisTypes:t.rules.debrisAnims;e.length||(e=i.rules.audioVisual.metallicDebris),e=e.filter(e=>i.rules.hasObject(e,ObjectType.VoxelAnim)||i.art.hasObject(e,ObjectType.Animation)),new Array(r).fill(0).map(()=>e[i.generateRandomInt(0,e.length-1)]).map(e=>i.createObject(ObjectType.Debris,e)).forEach(e=>{e.position.moveToLeptons(s),e.position.tileElevation=t.position.tileElevation,i.spawnObject(e,e.position.tile)})}}}class Debris extends GameObject{static factory(e,t,i,r){return new this(e,t,i,r)}constructor(e,t,i,r){super(ObjectType.Debris,e,t,i),this.age=0,this.direction=0,this.rotationAxis=new Vector3_Vector3,this.angularVelocity=0,this.zone=ZoneType.Air,this.velocity=new Vector3_Vector3,this.collisionHelper=new CollisionHelper(r)}onSpawn(e){super.onSpawn(e),this.direction=e.generateRandomInt(0,359),this.xySpeed=lerp(0,this.rules.maxXYVel,e.generateRandom()),this.zSpeed=lerp(this.rules.minZVel,this.rules.maxZVel||1.5*this.rules.minZVel,e.generateRandom()),this.rotationAxis.set(e.generateRandom(),e.generateRandom(),e.generateRandom()).normalize(),this.angularVelocity=lerp(this.rules.minAngularVelocity,this.rules.maxAngularVelocity,e.generateRandom())}update(t){if(super.update(t),this.age++,this.rules.duration&&this.age>this.rules.duration)return this.velocity.set(0,0,0),void this.detonate(t);--this.zSpeed;var i=FacingUtil.toMapCoords(this.direction).setLength(this.xySpeed);let r=new Vector3_Vector3(i.x,this.zSpeed,i.y);var s=this.position.clone(),i=r.clone().add(this.position.worldPosition);if(t.map.isWithinHardBounds(i)){this.position.moveByLeptons3(r);let e=!1;var{type:i,target:s}=this.collisionHelper.checkCollisions(this.position,s,{cliffs:!0,ground:!0,shore:!1,walls:!0,units:!1});if(i&&(!([CollisionType.Ground,CollisionType.OnBridge].includes(i)&&0<this.rules.elasticity&&t.map.getTileZone(this.tile)!==ZoneType.Water)||Math.abs(this.zSpeed)<1?e=!0:(this.zSpeed=-this.zSpeed*this.rules.elasticity,this.velocity.y=-this.velocity.y*this.rules.elasticity,this.rotationAxis.negate())),e){if(this.velocity.set(0,0,0),s&&i===CollisionType.Wall){let e=s.position.worldPosition;this.position.moveByLeptons3(e.clone().sub(this.position.worldPosition))}this.detonate(t,i)}else this.velocity.copy(r)}else t.unspawnObject(this)}detonate(t,i=CollisionType.None){var e,r=this.rules.warhead?t.rules.getWarhead(this.rules.warhead):void 0,s=this.zone=this.collisionHelper.computeDetonationZone(this.tile,this.tileElevation,i);let a;s===ZoneType.Water?(e=t.rules.combatDamage.splashList,a=e[0]):(e=this.rules.expireAnim)&&t.rules.animationNames.has(e)&&(a=e),this.explodeAnim=a;let n=new AnimTerrainEffect;if(a&&n.spawnSmudges(a,this.tile,t),t.destroyObject(this),r){let e=new Warhead(r);e.detonate(t,this.rules.damage,this.tile,this.tileElevation,this.position.worldPosition,s,i,t.createTarget(void 0,this.tile),void 0,SpecialWarheadType.None,void 0,this.rules.damageRadius||void 0,!0)}}}class ObjectFactory{constructor(e,t,i,r){this.tiles=e,this.tileOccupation=t,this.bridges=i,this.nextObjectId=r}create(e,t,i,r){let s,a;e===ObjectType.Debris?s=i.hasObject(t,ObjectType.VoxelAnim)?(a=r.getObject(t,ObjectType.VoxelAnim),i.getObject(t,ObjectType.VoxelAnim)):(a=r.getAnimation(t),new DebrisRules(ObjectType.Debris,r.getIni().getOrCreateSection(t))):a=e===ObjectType.Projectile?(s=i.getProjectile(t),s.inviso?new ObjectArt(ObjectType.Projectile,s,new IniSection(t)):r.getProjectile(t)):(s=i.getObject(t,e),r.getObject(t,e));let n;switch(e){case ObjectType.Building:n=Building.factory(t,s,i,a,this.tiles,this.bridges);break;case ObjectType.Infantry:n=Infantry_Infantry.factory(t,s,a,this.tileOccupation);break;case ObjectType.Vehicle:n=Vehicle_Vehicle.factory(t,s,a,i,this.tileOccupation);break;case ObjectType.Aircraft:n=Aircraft_Aircraft.factory(t,s,a,i,this.tileOccupation);break;case ObjectType.Terrain:n=Terrain_Terrain.factory(t,s,a);break;case ObjectType.Overlay:n=Overlay_Overlay.factory(t,s,a);break;case ObjectType.Smudge:n=Smudge_Smudge.factory(t,s,a);break;case ObjectType.Projectile:n=Projectile.factory(t,s,a,this.tileOccupation);break;case ObjectType.Debris:n=Debris.factory(t,s,a,this.tileOccupation);break;default:throw new Error("Not implemented")}if(n.id=this.nextObjectId.value++,n.position=new ObjectPosition(this.tiles,this.tileOccupation),n.isUnit()?n.position.subCell=0:n.isBuilding()&&n.position.setCenterOffset(n.getFoundationCenterOffset()),n.isTechno()&&((n.rules.primary||n.rules.secondary||n.rules.weaponCount||n.rules.explodes)&&(n.armedTrait=new ArmedTrait(n,i),n.traits.add(n.armedTrait)),-1!==n.rules.ammo&&(o=n.rules.initialAmmo,n.ammoTrait=new AmmoTrait(n.rules.ammo,-1!==o?o:void 0),n.traits.add(n.ammoTrait)),n.unitOrderTrait=new UnitOrderTrait(n),n.traits.addToFront(n.unitOrderTrait),(n.primaryWeapon||n.secondaryWeapon)&&(n.attackTrait=new AttackTrait(this.tiles,this.tileOccupation),n.traits.add(n.attackTrait)),(n.isInfantry()||n.isVehicle())&&n.rules.deployer&&(n.deployerTrait=new DeployerTrait(n),n.traits.add(n.deployerTrait)),(n.isInfantry()||n.isVehicle())&&n.rules.canDisguise&&(n.disguiseTrait=new DisguiseTrait,n.traits.add(n.disguiseTrait)),n.rules.cloakable&&(n.cloakableTrait=new CloakableTrait(n,i.general.cloakDelay),n.traits.add(n.cloakableTrait)),n.rules.sensors&&(n.sensorsTrait=new SensorsTrait,n.traits.add(n.sensorsTrait)),n.autoRepairTrait=new AutoRepairTrait(!n.isBuilding()),n.traits.add(n.autoRepairTrait),n.rules.trainable&&(n.veteranTrait=new VeteranTrait(n,i.general.veteran),n.traits.add(n.veteranTrait)),n.rules.selfHealing&&n.traits.add(new SelfHealingTrait),n.invulnerableTrait=new InvulnerableTrait,n.traits.add(n.invulnerableTrait),n.warpedOutTrait=new WarpedOutTrait(n),n.traits.add(n.warpedOutTrait),n.temporalTrait=new TemporalTrait(n),n.traits.add(n.temporalTrait),n.rules.bombable&&(n.tntChargeTrait=new TntChargeTrait,n.traits.add(n.tntChargeTrait)),n.rules.immuneToPsionics||n.isBuilding()||(n.mindControllableTrait=new MindControllableTrait(n),n.traits.add(n.mindControllableTrait)),[n.primaryWeapon,n.secondaryWeapon].some(e=>e?.warhead.rules.mindControl)&&(n.mindControllerTrait=new MindControllerTrait(n),n.traits.add(n.mindControllerTrait)),n.rules.spawns&&(n.airSpawnTrait=new AirSpawnTrait,n.traits.add(n.airSpawnTrait)),n.rules.maxDebris&&n.traits.add(new SpawnDebrisTrait)),n.isTechno()||n.isOverlay()||n.isTerrain()){var o=n.isOverlay()&&BridgeOverlayTypes.isBridge(i.getOverlayId(n.name));let e=n.rules.strength;!e&&n.isTerrain()&&(e=i.general.treeStrength),o&&(e=i.combatDamage.bridgeStrength),(e||n.isTechno())&&(n.healthTrait=new HealthTrait(e,n,i.audioVisual.conditionYellow,i.audioVisual.conditionRed),n.traits.add(n.healthTrait)),n.isOverlay()&&o&&(n.bridgeTrait=new BridgeTrait(this.bridges),n.traits.add(n.bridgeTrait),BridgeOverlayTypes.getOverlayBridgeType(i.getOverlayId(n.name))===OverlayBridgeType.Concrete&&n.traits.add(new SpawnDebrisTrait))}return n.isOverlay()&&n.isOverlay()&&OreOverlayTypes.getOverlayTibType(i.getOverlayId(n.name))!==OverlayTibType.NotSpecial&&n.traits.add(new TiberiumTrait(n)),n.isTerrain()&&n.rules.spawnsTiberium&&n.traits.add(new TiberiumTreeTrait(n.rules)),n.cachedTraits.tick.push(...n.traits.filter(NotifyTick_NotifyTick)),n}}class World{constructor(){this.allObjects=new Map,this._onObjectSpawned=new EventDispatcher,this._onObjectRemoved=new EventDispatcher}get onObjectSpawned(){return this._onObjectSpawned.asEvent()}get onObjectRemoved(){return this._onObjectRemoved.asEvent()}spawnObject(e){if(this.allObjects.has(e.id))throw new Error("Trying to add an already existing object");this.allObjects.set(e.id,e),this._onObjectSpawned.dispatch(this,e)}removeObject(e){if(!this.allObjects.has(e.id))throw new Error("Trying to remove non-existent object");this.allObjects.delete(e.id),this._onObjectRemoved.dispatch(this,e)}hasObjectId(e){return this.allObjects.has(e)}getObjectById(e){if(!this.allObjects.has(e))throw new Error(`Object with id ${e} doesn't exist`);return this.allObjects.get(e)}getAllObjects(){return[...this.allObjects.values()]}}class Node{constructor(e,t){this.id=e,this.data=t,this.neighbors=new Set}addLink(e){this.neighbors.add(e),e!==this&&e.neighbors.add(this)}removeLink(e){this.neighbors.delete(e),e.neighbors.delete(this)}deleteLinks(){for(var e of this.neighbors)e.neighbors.delete(this);this.neighbors.clear()}}class Graph{constructor(){this.nodes=new Map}addNode(e,t){let i=this.getNode(e);return i?i.data=t:i=new Node(e,t),this.nodes.set(e,i),i}removeNode(e){let t=this.getNode(e);return!!t&&(t.deleteLinks(),this.nodes.delete(e),!0)}hasNode(e){return this.nodes.has(e)}getNode(e){return this.nodes.get(e)}getNodeCount(){return this.nodes.size}forEachNode(e){for(var t of this.nodes.values())e(t)}clear(){for(var e of this.nodes.values())e.deleteLinks();this.nodes.clear()}}class NodeHeap{constructor(e=[]){if(this.data=e,this.length=e.length,0<this.length)for(let e=this.length>>1;0<=e;e--)this.down(e);for(let e=0;e<this.length;++e)this.setNodeId(this.data[e],e)}compare(e,t){return e.fScore-t.fScore}setNodeId(e,t){e.heapIndex=t}push(e){this.data.push(e),this.setNodeId(e,this.length),this.length++,this.up(this.length-1)}pop(){if(0!==this.length){var e=this.data[0];return this.length--,0<this.length&&(this.data[0]=this.data[this.length],this.setNodeId(this.data[0],0),this.down(0)),this.data.pop(),e}}peek(){return this.data[0]}updateItem(e){this.down(e),this.up(e)}up(e){let t=this.data;for(var i=t[e];0<e;){var r=e-1>>1,s=t[r];if(0<=this.compare(i,s))break;t[e]=s,this.setNodeId(s,e),e=r}t[e]=i,this.setNodeId(i,e)}down(i){let r=this.data;for(var e=this.length>>1,s=r[i];i<e;){let e=1+(i<<1);var a=e+1;let t=r[e];if(a<this.length&&this.compare(r[a],t)<0&&(e=a,t=r[a]),0<=this.compare(t,s))break;r[i]=t,this.setNodeId(t,i),i=e}r[i]=s,this.setNodeId(s,i)}}class NodeSearchState{constructor(e){this.node=e,this.closed=!1,this.open=0,this.distanceToSource=Number.POSITIVE_INFINITY,this.fScore=Number.POSITIVE_INFINITY,this.heapIndex=-1}}function makeSearchStatePool(){let i=0,r=[];return{createNewState(e){let t=r[i];return t?(t.node=e,t.parent=void 0,t.closed=!1,t.open=0,t.distanceToSource=Number.POSITIVE_INFINITY,t.fScore=Number.POSITIVE_INFINITY,t.heapIndex=-1):(t=new NodeSearchState(e),r[i]=t),i++,t},reset(){i=0}}}function blindHeuristic(){return 0}function constantDistance(){return 1}function PathFinder(u,e={}){let d=e.bestEffort,p=e.maxExpandedNodes||Number.POSITIVE_INFINITY,g=e.heuristic??blindHeuristic,m=e.distance??constantDistance,y=e.excludedNodes,T=makeSearchStatePool();return{find:function(e,t){let i=u.getNode(e);if(!i)throw new Error("fromId is not defined in this graph: "+e);let r=u.getNode(t);if(!r)throw new Error("toId is not defined in this graph: "+t);if(i===r)return[];T.reset();let s=new Map,a=new NodeHeap,n=T.createNewState(i);if(s.set(e,n),n.fScore=y?.(r.data)?Number.POSITIVE_INFINITY:g(i,r),!Number.isFinite(n.fScore)&&i.neighbors.has(r))return[];n.distanceToSource=0,a.push(n),n.open=1;let o,l=n,h=0;for(;0<a.length;){if(o=a.pop(),o.node===r)return reconstructPath(o);if(h++,h>p)break;o.closed=!0,o.node.neighbors.forEach(c)}return d?reconstructPath(l):[];function c(e){let t=s.get(e.id);t||(t=T.createNewState(e),s.set(e.id,t)),t.closed||(0===t.open&&(a.push(t),t.open=1),(e=y?.(e.data)?Number.POSITIVE_INFINITY:o.distanceToSource+m(o.node,e))>=t.distanceToSource||(t.parent=o,t.distanceToSource=e,y?.(r.data)?t.fScore=Number.POSITIVE_INFINITY:t.fScore=e+g(t.node,r,t),t.fScore-t.distanceToSource<l.fScore-l.distanceToSource&&(l=t),a.updateItem(t.heapIndex)))}}}}function reconstructPath(e){let t=[e.node],i=e.parent;for(;i;)t.push(i.node),i=i.parent;return t}function distance(e,t){var i=Math.abs(e.data.tile.rx-t.data.tile.rx),t=Math.abs(e.data.tile.ry-t.data.tile.ry);return i+t+(Math.SQRT2-2)*Math.min(i,t)}function heuristic(e,t,i){var r=Math.abs(e.data.tile.rx-t.data.tile.rx),t=Math.abs(e.data.tile.ry-t.data.tile.ry);let s=r+t+(Math.SQRT2-2)*Math.min(r,t);return i?.parent&&(t=(r=i.parent.node).data.tile.rx-e.data.tile.rx,e=r.data.tile.ry-e.data.tile.ry,i.dirX=t,i.dirY=e,t===i.parent.dirX&&e===i.parent.dirY||(s+=.2)),s}class map_Terrain_Terrain{constructor(e,t,i,r,s){this.tiles=e,this.theaterType=t,this.mapBounds=i,this.tileOccupation=r,this.rules=s,this.passabilityGraphs=new Map,this.invalidatedTiles=new Map,this.handleTileOccupationUpdate=({tiles:e,object:r})=>{e=e.filter(e=>{let t=SpeedType.Foot,i=!0;return r.isTerrain()&&r.rules.getOccupationBits(this.theaterType)!==OccupationBits.All&&(t=SpeedType.Wheel,i=!1),r.isOverlay()&&(r.isBridge()||r.isTiberium())||this.isBlockerObject(r,e,!1,t,i)||this.isBlockerObject(r,e,!0,t,i)||r.isBuilding()&&r.rules.leaveRubble});e.length&&this.invalidateTiles(e)},this.handleMapBoundsResize=()=>{this.passabilityGraphs.clear()},r.onChange.subscribe(this.handleTileOccupationUpdate),i.onLocalResize.subscribe(this.handleMapBoundsResize)}getGraphKey(e,t){return e+"_"+Number(t)}invalidateTiles(i){i.length&&[...this.passabilityGraphs.keys()].forEach(e=>{let t=this.invalidatedTiles.get(e);t?i.forEach(e=>t.add(e)):this.invalidatedTiles.set(e,new Set(i))})}computePath(s,a,e,t,i,r,{maxExpandedNodes:n=Number.POSITIVE_INFINITY,bestEffort:o=!0,excludeTiles:l,ignoredBlockers:h=[]}={}){let c=this.computePassabilityGraph(s,a);var u=h.map(e=>this.tileOccupation.calculateTilesForGameObject(e.tile,e)).reduce((e,t)=>e.concat(t),[]);u.length&&this.updatePassability(u,s,a,c,h);var d=this.getNodeId(e,t),p=!!c.hasNode(d);p||this.updatePassability([e],s,a,c,h,1);var g=this.getNodeId(i,r),m=!!c.hasNode(g);let y;var T=p&&!u.length;if(T){let i=this.getIslandIdMap(s,a),r=i.get(e,t);y=(e,t)=>i.get(e,t)===r}else y=(e,t)=>0<this.getPassableSpeed(e,s,a,t,h);if(!m||!y(i,r)){var f=T?15:5,f=o?new RadialTileFinder(this.tiles,this.mapBounds,i,{width:1,height:1},1,f,e=>y(e,!1)&&Math.abs(e.z-i.z)<2&&!l?.({tile:e,onBridge:void 0})).getNextTile():void 0;if(f)i=f,r=!1;else{if(T)return u.length&&this.updatePassability(u,s,a,c),[];c.addNode(g,{tile:i,onBridge:void 0}),n=Math.min(n,500)}}let v=PathFinder(c,{bestEffort:o,maxExpandedNodes:n,excludedNodes:l,distance:distance,heuristic:heuristic}),b=v.find(this.getNodeId(e,t),this.getNodeId(i,r)).map(e=>({tile:e.data.tile,onBridge:e.data.onBridge}));return(b.length<2||l&&b.length&&(!o&&b[0].tile!==i||b[b.length-1].tile!==e))&&(b=[]),p||(c.removeNode(d),this.updatePassability([e],s,a,c)),m||c.removeNode(g),u.length&&this.updatePassability(u,s,a,c),b}computeAllPassabilityGraphs(){Object.keys(SpeedType).forEach(e=>{e=Number(e);isNaN(e)||e===SpeedType.Winged||(this.computePassabilityGraph(e,!1),this.computePassabilityGraph(e,!0))})}computePassabilityGraph(t,i){var r=this.getGraphKey(t,i);let s=this.passabilityGraphs.get(r);if(s){let e=this.invalidatedTiles.get(r);e?.size&&(this.updatePassability([...e],t,i,s),e.clear(),this.computeIslandIds(s))}else s=new Graph,this.passabilityGraphs.set(r,s),this.tiles.forEach(e=>{this.computePassability(e,t,i,s)}),this.computeIslandIds(s);return s}updatePassability(t,i,r,s,a=[],n){let o=new Set;t.forEach(e=>{[e,this.tiles.getNeighbourTile(e,TileDirection.Right),this.tiles.getNeighbourTile(e,TileDirection.BottomRight),this.tiles.getNeighbourTile(e,TileDirection.Bottom),this.tiles.getNeighbourTile(e,TileDirection.BottomLeft)].filter(isNotNullOrUndefined).forEach(e=>o.add(e))});let l=new Map;t.forEach(e=>{var t;for(t of[s.getNode(this.getNodeId(e,!1)),s.getNode(this.getNodeId(e,!0))])t&&(l.set(t.id,t.data.islandId),s.removeNode(t.id))}),o.forEach(e=>{this.computePassability(e,i,r,s,a,n&&t.includes(e)?n:void 0)}),l.forEach((e,t)=>{let i=s.getNode(t);i&&(i.data.islandId=e)})}computePassability(e,t,i,r,s=[],a){var n=[TileDirection.Left,TileDirection.TopLeft,TileDirection.Top,TileDirection.TopRight];if(a||this.getPassableSpeed(e,t,i,!1,s)){var o,l=this.getNodeId(e,!1);r.hasNode(l)||r.addNode(l,{tile:e,onBridge:void 0,forceLandSpeed:a});for(o of n)this.connectTiles(e,void 0,o,t,i,r,s)}var h=this.tileOccupation.getBridgeOnTile(e);if(h&&(a||this.getPassableSpeed(e,t,i,!0,s))){var c,l=this.getNodeId(e,!0);r.hasNode(l)||r.addNode(l,{tile:e,onBridge:h,forceLandSpeed:a});for(c of n)this.connectTiles(e,h,c,t,i,r,s)}}connectTiles(i,r,s,a,n,o,l=[]){var h=this.tiles.getNeighbourTile(i,s);if(h){let e=this.tileOccupation.getBridgeOnTile(h);s=r||e?0:1;if(Math.abs(i.z+(r?.tileElevation??0)-(h.z+(e?.tileElevation??0)))>s){if(!e?.isHighBridge()&&!r?.isHighBridge()||0!==Math.abs(i.z-h.z)||!o.hasNode(this.getNodeId(i,!1)))return;r=e=void 0}s=this.getNodeId(h,!!e);let t=o.getNode(s);this.getPassableSpeed(h,a,n,!!e,l,void 0,t?.data.forceLandSpeed)&&(t=t??o.addNode(s,{tile:h,onBridge:e}),r=this.getNodeId(i,!!r),o.getNode(r).addLink(t))}}getNodeId(e,t){return e.id+(t?"_bridge":"")}computeIslandIds(e){let t=1;e.forEachNode(e=>{e.data.islandId=void 0}),e.forEachNode(e=>{e.data.islandId||this.floodIslandId(e,t++)})}floodIslandId(e,t){let i=[e];for(;i.length;){let e=i.pop();e.data.islandId=t;for(var r of e.neighbors)r.data.islandId||i.push(r)}}getIslandIdMap(e,t){let i=this.computePassabilityGraph(e,t);return{get:(e,t)=>{t=this.getNodeId(e,t);return i.getNode(t)?.data.islandId}}}getPassableSpeed(e,t,i,r,s=[],a=!1,n){if(!this.mapBounds.isWithinBounds(e))return 0;let o=r?e.onBridgeLandType:e.landType;if(void 0===o)return 0;o===LandType.Wall&&t===SpeedType.Track&&(o=getLandType(e.terrainType));let l=this.rules.getLandRules(o);var h,n=n||l.getSpeedModifier(t);if(!n)return 0;if(!a)for(h of this.tileOccupation.getObjectsOnTile(e))if(this.isBlockerObject(h,e,r,t,i)&&!s.includes(h))return 0;return n}isBlockerObject(t,i,e,r,s){if(t.isTerrain()&&s&&t.rules.getOccupationBits(this.theaterType)!==OccupationBits.All)return!1;if(t.isBuilding()){if(t.rules.invisibleInGame)return!1;if(t.isDestroyed&&t.rules.leaveRubble)return!1;if(t.rules.gate)return!1;var a=t.art.foundation;let e=t.rules.numberImpassableRows;return s?e=a.width:t.rules.weaponsFactory&&!e&&(e=a.width-1),rectContainsPoint({x:t.tile.rx,y:t.tile.ry,width:(e||a.width)-1,height:a.height-1},{x:i.rx,y:i.ry})}return!(t.isAircraft()||t.isInfantry()||t.isVehicle()||t.isSmudge()||t.isOverlay()&&(e&&t.isBridge()||!e&&t.isHighBridge()||t.isTiberium()||t.rules.crate||t.isBridgePlaceholder())||[SpeedType.Track,SpeedType.Hover].includes(r)&&t.rules.crushable)}findObstacles(t,e){var i,r,s=e.rules.speedType,a=e.isInfantry();let n=[];for(i of this.tileOccupation.getGroundObjectsOnTile(t.tile))i!==e&&(((r=this.isBlockerObject(i,t.tile,!!t.onBridge,s,a))||i.isUnit()&&(i.tile===t.tile&&i.onBridge===!!t.onBridge||i.moveTrait.reservedPathNodes.find(e=>e.tile===t.tile&&!!e.onBridge==!!t.onBridge))||[SpeedType.Track,SpeedType.Hover].includes(s)&&i.rules.crushable||a&&i.isTerrain()||i.isBuilding()&&i.rules.gate)&&(r={obj:i,static:r},i.isInfantry()&&a?i.position.desiredSubCell===e.position.desiredSubCell&&n.push(r):i.isTerrain()&&a&&!i.rules.getOccupiedSubCells(this.theaterType).includes(e.position.desiredSubCell)||n.push(r)));return n}dispose(){this.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate),this.mapBounds.onLocalResize.unsubscribe(this.handleMapBoundsResize)}}class MapBounds{constructor(){this.mapCutoffHeight=0,this.mapBuildableSize={x:0,y:0,width:0,height:0},this.localSize={x:0,y:0,width:0,height:0},this.fullSize={width:0,height:0},this.clampedFullSize={x:0,y:0,width:0,height:0},this.rawLocalSize={x:0,y:0,width:0,height:0},this._onLocalResize=new EventDispatcher}get onLocalResize(){return this._onLocalResize.asEvent()}fromMapFile(e,t){this.fullSize={width:2*e.fullSize.width,height:2*e.fullSize.height},this.clampedFullSize={x:1,y:2,width:2*(e.fullSize.width-1)-1/Coords.ISO_TILE_SIZE,height:2*(e.fullSize.height-1)+1-1/Coords.ISO_TILE_SIZE},this.mapCutoffHeight=Math.max(9,t.getCutoffTileHeight());t=Math.max(2,e.localSize.x),e={x:t,y:e.localSize.y,width:Math.min(e.fullSize.width-2-t,e.localSize.width),height:e.localSize.height};return this.updateRawLocalSize(e),this}updateRawLocalSize(e){this.rawLocalSize.width&&this.rawLocalSize.height&&!rectContainsRect(e,this.rawLocalSize)?console.warn("New map limits must be outside old limits. Skipping."):rectEquals(e,this.rawLocalSize)||(this.localSize=this.computeLocalSize(e,this.fullSize.height/2,this.mapCutoffHeight),this.rawLocalSize={...e},this.mapBuildableSize={x:this.localSize.x,y:this.localSize.y+4,width:this.localSize.width-2,height:this.localSize.height-8},this._onLocalResize.dispatch(this))}computeLocalSize(e,t,i){return{x:2*e.x,y:2*e.y-4,height:Math.min(2*(e.height+5)-1,2*t-2*(e.y-3)-i),width:2*e.width}}getLocalSize(){return this.localSize}getRawLocalSize(){return this.rawLocalSize}getFullSize(){return this.fullSize}getClampedFullSize(){return this.clampedFullSize}isWithinBounds(e){return rectContainsPoint(this.mapBuildableSize,{x:e.dx,y:e.dy-e.z})}clampWithinBounds(e){let{x:t,y:i}=rectClampPoint(this.mapBuildableSize,{x:e.dx,y:e.dy-e.z});return i+=t%2-i%2,i>this.mapBuildableSize.y+this.mapBuildableSize.height&&(i-=2),{dx:t,dy:i}}isWithinHardBounds(e){var t=e.x/Coords.LEPTONS_PER_TILE,i=(e.z??e.y)/Coords.LEPTONS_PER_TILE,e=t-i+this.fullSize.width/2-1,i=t+i-this.fullSize.width/2-1;return rectContainsPoint(this.clampedFullSize,{x:++e,y:++i})}}class DirectionalTileFinder{constructor(e,t,i,r,s,a,n,o=()=>!0,l=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.maxDistance=s,this.dirX=a,this.dirY=n,this.predicate=o,this.checkBounds=l,this.finished=!1,this.distance=r}getNextTile(){if(!this.finished){let t;do{let e={x:this.startTile.rx,y:this.startTile.ry};e.x+=this.distance*Math.sign(this.dirX),e.y+=this.distance*Math.sign(this.dirY);var i=this.tiles.getByMapCoords(e.x,e.y);if(i&&(!this.checkBounds||this.mapBounds.isWithinBounds(i))&&this.predicate(i)&&(t=i),this.maxDistance&&this.distance>=this.maxDistance)return this.finished=!0,t}while(this.distance++,!t);return t}}}class FloodTileFinder{constructor(e,t,i,r,s,a=!0){this.tiles=e,this.mapBounds=t,this.startTile=i,this.areConnected=r,this.predicate=s,this.checkBounds=a,this.generator=this.generate()}getNextTile(){return this.generator.next().value}*generate(){let e=[this.startTile],t=new Set;for(;e.length;){var i,r=e.pop();if(!t.has(r)){t.add(r),this.checkBounds&&!this.mapBounds.isWithinBounds(r)||!this.predicate(r)||(yield r);for(i of this.tiles.getAllNeighbourTiles(r))this.areConnected(i,r)&&e.push(i)}}}}!function(e){e[e.None=0]="None",e[e.Start=1]="Start",e[e.End=2]="End"}(BridgeHeadType=BridgeHeadType||{});class Bridges{constructor(e,t,i,r,s){this.tileSets=e,this.tiles=t,this.tileOccupation=i,this.mapBounds=r,this.rules=s,this.pieces=new Set,this.piecesByTile=new Map,this.handleTileOccupationUpdate=({object:t,type:i})=>{if(t.isOverlay()&&t.isBridge()){var r=t.tile;let e=this.piecesByTile.get(r);if("added"===i){if(e)throw new Error(`A bridge piece already exists at tile (${r.rx},${r.ry})`);var s=this.findBridgeAdjacentTiles(t);e={obj:t,prev:void 0,next:void 0,headType:this.computeHead(t,s.prev,s.next)},this.piecesByTile.set(r,e),this.pieces.add(e),this.connectPiece(e,s.prev,s.next),this.updateOverlayData(e),e.prev&&this.updateOverlayData(e.prev),e.next&&this.updateOverlayData(e.next)}else{if(!e)throw new Error(`Bridge piece was alredy removed at tile (${r.rx},${r.ry})`);t=e.prev,s=e.next;this.disconnectPiece(e),this.piecesByTile.delete(r),this.pieces.delete(e),t&&this.updateOverlayData(t),s&&this.updateOverlayData(s)}}},i.onChange.subscribe(this.handleTileOccupationUpdate)}getPieceAtTile(e){return this.piecesByTile.get(e)}handlePieceHealthChange(e){this.updateOverlayData(e),e.prev&&this.updateOverlayData(e.prev),e.next&&this.updateOverlayData(e.next)}findDominoPieces(t){let i=[],r=!1,e=t.next;if(t.headType===BridgeHeadType.None||e)for(;e;){if(i.push(e),e.headType!==BridgeHeadType.None){r=!0;break}e=e.next}else r=!0;if(r){r=!1,i.length=0;let e=t.prev;if(t.headType===BridgeHeadType.None||e)for(;e;){if(i.push(e),e.headType!==BridgeHeadType.None){r=!0;break}e=e.prev}else r=!0;if(r)return[]}return i}findBridgeAdjacentTiles(e){var t=e.isXBridge(),t=new Vector2(Number(t),Number(!t));let i=new Vector2(e.tile.rx,e.tile.ry);e=i.clone().sub(t),e=this.tiles.getByMapCoords(e.x,e.y),t=i.clone().add(t);return{prev:e,next:this.tiles.getByMapCoords(t.x,t.y)}}connectPiece(e,t,i){t&&(e.prev=this.getPieceAtTile(t),e.prev&&(e.prev.next=e)),i&&(e.next=this.getPieceAtTile(i),e.next&&(e.next.prev=e))}disconnectPiece(e){e.next&&(e.next.prev=void 0,e.next=void 0),e.prev&&(e.prev.next=void 0,e.prev=void 0)}computeHead(e,t,i){var r=e.tile;if(e.isHighBridge()){r=r.z+e.tileElevation;return t?.z===r?BridgeHeadType.Start:i?.z===r?BridgeHeadType.End:BridgeHeadType.None}return BridgeOverlayTypes.isLowBridgeHead(e.overlayId)?BridgeOverlayTypes.isLowBridgeHeadStart(e.overlayId)?BridgeHeadType.Start:BridgeHeadType.End:BridgeHeadType.None}updateOverlayData(t){let i=t.obj,r=t.prev,s=t.next,a=!1;var n=i.isXBridge(),o=BridgeOverlayTypes.getOverlayBridgeType(i.overlayId);if(BridgeOverlayTypes.isLowBridgeHead(i.overlayId)){let e=0;BridgeOverlayTypes.isLowBridgeHeadStart(i.overlayId)?(e=n?20:22,s||e++):(e=n?18:24,r||e++),i.overlayId=(o===OverlayBridgeType.Wood?BridgeOverlayTypes.minLowBridgeWoodId:BridgeOverlayTypes.minLowBridgeConcreteId)+e,i.value=e,a=!0}else{let e;var l,h=(i.healthTrait?.health??100)<=50;e=t.headType!==BridgeHeadType.None?t.headType===BridgeHeadType.Start?s?h?6:(s.obj.healthTrait?.health??100)<=50?5:0:n?8:7:r?h?6:(r.obj.healthTrait?.health??100)<=50?4:0:n?7:8:(n||(l=r,r=s,s=l),r||s?r?s?(t=(r.obj.healthTrait?.health??100)<=50,l=(s.obj.healthTrait?.health??100)<=50,h||t&&l?6:t?4:l?5:0):8:7:0),n||(e+=9),i.isHighBridge()?i.value=e:(i.overlayId=(o===OverlayBridgeType.Wood?BridgeOverlayTypes.minLowBridgeWoodId:BridgeOverlayTypes.minLowBridgeConcreteId)+e,i.value=e,a=!0)}a&&(i.name=this.rules.getOverlayName(i.overlayId))}findClosestBridgeSpec(i){let e=new RadialTileFinder(this.tiles,this.mapBounds,i,{width:1,height:1},1,3,e=>{if(e.z!==i.z)return!1;let t=this.tileOccupation.getBridgeOnTile(e);return!(!t?.isLowBridge()||this.getPieceAtTile(t.tile)?.headType===BridgeHeadType.None)||!!this.tileSets.isHighBridgeBoundaryTile(e.tileNum)},!1);var o=e.getNextTile();if(o){let r,t,s,a;var l=!this.tileOccupation.getBridgeOnTile(o);let e;if(l){var h=this.findHighBridgeBoundary(o);if(!h)return;r=h.tile,t=OverlayBridgeType.Concrete,this.tileSets.getSetNum(o.tileNum)===this.tileSets.getGeneralValue("WoodBridgeSet")&&(t=OverlayBridgeType.Wood),s=h.headType===HighBridgeHeadType.TopLeft||h.headType===HighBridgeHeadType.BottomRight,a=h.headType===HighBridgeHeadType.TopLeft||h.headType===HighBridgeHeadType.TopRight,e=h.headType}else{r=this.tileOccupation.getBridgeOnTile(o).tile;let e=this.getPieceAtTile(r);if(!e)throw new Error("Bridge head is not defined");var c=BridgeOverlayTypes.getOverlayBridgeType(e.obj.overlayId);if(c===OverlayBridgeType.NotBridge)throw new Error("Expected a bridge type");t=c,s=e.obj.isXBridge(),a=e.headType===BridgeHeadType.Start}var u=Number(s)*(a?1:-1),d=Number(!s)*(a?1:-1);let n;if(l){o=new DirectionalTileFinder(this.tiles,this.mapBounds,r,1,100,u,d,e=>e.z===r.z&&this.tileSets.isHighBridgeBoundaryTile(e.tileNum),!1).getNextTile(),c=this.tileSets.getSetNum(r.tileNum);if(!o||this.tileSets.getSetNum(o.tileNum)!==c)return;o=this.findHighBridgeBoundary(o);if(!o)return;if(e!==this.tileSets.getOppositeHighBridgeHeadType(o.headType))return;n=o.tile}else{let t,i=1;for(var p=r.rx,g=r.ry;!t;){var m=this.tiles.getByMapCoords(p+u*i,g+d*i);if(!m)return;let e=this.getPieceAtTile(m);if(e&&e.obj.isXBridge()!==s)return;e?.headType===(a?BridgeHeadType.End:BridgeHeadType.Start)&&(t=e),i++}n=t.obj.tile}return{start:a?r:n,end:a?n:r,type:t,isHigh:l}}}findHighBridgeBoundary(s){var a,e=this.tileSets.getTile(s.tileNum),n=this.tileSets.getHighBridgeHeadType(e.index);if(void 0!==n){let i=0,r=0;switch(n){case HighBridgeHeadType.TopLeft:i=1,r=0;break;case HighBridgeHeadType.BottomRight:i=-1,r=0;break;case HighBridgeHeadType.TopRight:i=0,r=1;break;case HighBridgeHeadType.BottomLeft:i=0,r=-1;break;case HighBridgeHeadType.MiddleTlBr:i=1,r=0;break;case HighBridgeHeadType.MiddleTrBl:i=0,r=1;break;default:throw new Error(`Unhandled head type "${n}"`)}let e=new FloodTileFinder(this.tiles,this.mapBounds,s,e=>e.tileNum===s.tileNum,e=>e.terrainType===TerrainType.Pavement&&e.z>=s.z,!1),t=[];for(;a=e.getNextTile();)t.push(a);if(t.sort((e,t)=>100*(i?i*(t.rx-e.rx):r*(t.ry-e.ry))+(i?e.ry-t.ry:e.rx-t.rx)),t.length)return{tile:t[0],headType:n}}else console.warn(`Couldn't find a valid bridge type for index "${e.index}" @ ${s.rx},`+s.ry)}canBeRepaired(i){let e=this.createBridgePieceTileFinder(i,e=>!(this.getPieceAtTile(e)||this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===i.start.z)),r=!1,s;for(var a=i.start.rx!==i.end.rx?TileDirection.BottomLeft:TileDirection.BottomRight;s=e.getNextTile();){r=!0;let e=this.tiles.getNeighbourTile(s,a),t=this.tiles.getNeighbourTile(e,a);if(i.isHigh){if([s,e,t].find(e=>this.tileOccupation.getGroundObjectsOnTile(e).some(e=>e.isBuilding()&&!e.rules.invisibleInGame)))return!1}else if([s,e,t].find(e=>this.tileOccupation.getGroundObjectsOnTile(e).some(e=>!(e.isUnit()||e.isSmudge()||e.isOverlay()&&e.isBridgePlaceholder()))))return!1}return r}getPieceTiles(e){var t=e.obj.tile,i=e.obj.isXBridge()?TileDirection.BottomLeft:TileDirection.BottomRight,e=this.tiles.getNeighbourTile(t,i);return[t,e,this.tiles.getNeighbourTile(e,i)]}findMapHighBridgeHeadTiles(){var e,t=this.tiles.getAllBridgeSetTiles();let i=new Set;for(e of t){var r=this.findHighBridgeBoundary(e);r&&i.add(r.tile)}return i}findBridgeSpecsForHeadTiles(e){let t=new Map;for(var i of e){i=this.findClosestBridgeSpec(i);i&&t.set(i.start.id+":"+i.end.id,i)}return[...t.values()]}findAllBridgeTiles(e){let t=[];var i,r=e.start.rx!==e.end.rx?TileDirection.BottomLeft:TileDirection.BottomRight;for(i of this.findNonBuildablePieceTiles(e)){var s=this.tiles.getNeighbourTile(i,r),a=this.tiles.getNeighbourTile(s,r);t.push(i,s,a)}return t}findBridgePieces(e){let t=this.createBridgePieceTileFinder(e,e=>!!this.getPieceAtTile(e)),i=[];for(var r;r=t.getNextTile();)i.push(this.getPieceAtTile(r));return i}findDestroyedPieceTiles(t){let e=this.createBridgePieceTileFinder(t,e=>!(this.getPieceAtTile(e)||this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===t.start.z)),i=[];for(var r;r=e.getNextTile();)i.push(r);return i}findNonBuildablePieceTiles(t){let e=this.createBridgePieceTileFinder(t,e=>!(this.tileSets.isHighBridgeMiddleTile(e.tileNum)&&e.z===t.start.z)),i=[];for(var r;r=e.getNextTile();)i.push(r);return i}createBridgePieceTileFinder(e,t){var i=e.start.rx!==e.end.rx;return new DirectionalTileFinder(this.tiles,this.mapBounds,e.start,1,(i?e.end.rx-e.start.rx:e.end.ry-e.start.ry)-1,Number(i),Number(!i),t,!1)}dispose(){this.pieces.forEach(e=>{e.prev=void 0,e.next=void 0}),this.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate)}}var AllianceStatus,SelectionLevel,NotifySpawn_NotifySpawn,NotifyUnspawn_NotifyUnspawn,NotifyOwnerChange_NotifyOwnerChange,NotifyAllianceChange,NotifyDestroy_NotifyDestroy,AllianceEventType,QuadTree_THREE=__webpack_require__(70);const tmpVec2=new QuadTree_THREE.Vector2;class QuadTree{constructor(e,t){this.box=e,this.config=t,this.parentMap=new Map,this.objects=[]}add(e,t=!0){var i=this.config.getKey(e);if(this.box.containsPoint(i)){if(!this.regions)return this.parentMap.get(e)?.remove(e),this.parentMap.set(e,this),this.objects.push({key:i,value:e}),t&&this.update(),!0;for(var r of this.regions)if(r.add(e,t))return!0}return!1}remove(t,e=!0){let i=this.parentMap.get(t);i&&(i===this?(this.parentMap.delete(t),this.objects.splice(this.objects.findIndex(e=>e.value===t),1),e&&this.parent?.update()):i.remove(t,e))}updateObject(t){let i=this.parentMap.get(t);if(i){var e=this.config.getKey(t);if(i.box.containsPoint(e))i.objects.find(e=>e.value===t).key=e;else{i.remove(t,!1);let e=i.parent;for(;e&&!e.add(t,!1);)e=e.parent}}}queryRange(e,t=[]){if(this.box.intersectsBox(e))if(this.regions)for(var i of this.regions)i.queryRange(e,t);else for(var r of this.objects)e.containsPoint(r.key)&&t.push(r.value);return t}update(){let e=0;if(this.regions){for(var t of this.regions)e+=t.update();e<=this.config.joinThreshold&&this.join()}else e=this.objects.length,e>=this.config.splitThreshold&&this.split()&&this.update();return e}split(){if(this.regions||this.config.maxDepth<=1)return!1;var t,e,i={getKey:this.config.getKey,joinThreshold:this.config.joinThreshold,splitThreshold:this.config.splitThreshold,maxDepth:this.config.maxDepth-1},r=this.generateRegions(),s=this.objects;this.objects=[],this.regions=[];for(t of r){let e=new QuadTree(t,i);e.parentMap=this.parentMap,this.regions.push(e),e.parent=this}for(e of s)this.parentMap.delete(e.value),this.add(e.value,!1);return!0}join(){if(!this.regions)return!1;for(var e of this.regions){e.join(),e.parent=void 0;for(var t of e.objects)this.objects.push(t),this.parentMap.set(t.value,this)}return!(this.regions=void 0)}generateRegions(){let i=[this.box.clone()];var r=this.box.getCenter(tmpVec2);let s=i[0],a=s.clone();s.max.x=r.x,a.min.x=r.x,i.push(a);for(let e=0,t=i.length;e<t;e++)s=i[e],a=s.clone(),s.max.y=r.y,a.min.y=r.y,i.push(a);return i}}class TileOcclusion{constructor(e){this.tiles=e,this.tileOcclusion=[];let t=this.tileOcclusion;for(var i of e.getAll())t[i.rx]=t[i.rx]||[],t[i.rx][i.ry]=new Set}addOccluder(t){let e=this.calculateTilesForGameObject(t);e.forEach(e=>this.occludeTile(e,t))}removeOccluder(t){let e=this.calculateTilesForGameObject(t);e.forEach(e=>this.unoccludeTile(e,t))}calculateTilesForGameObject(e){var t=e.art.occupyHeight,i=Math.max(0,t-2);let r=[];var s=e.getFoundation();for(let t=1;t<=i;t++)for(let e=0;e<s.width;e++)r.push(new Vector2(e-t,-t));for(let t=1;t<=i;t++)for(let e=1;e<s.height;e++)r.push(new Vector2(-t,e-t));r.push(...e.art.addOccupy);for(let{x:t,y:i}of e.art.removeOccupy){var a=r.findIndex(e=>e.x===t&&e.y===i);-1!==a&&r.splice(a,1)}var n,o,l=e.tile;let h=[];for({x:n,y:o}of r){var c=this.tiles.getByMapCoords(l.rx+n,l.ry+o);c&&h.push(c)}return h}occludeTile(e,t){this.tileOcclusion[e.rx][e.ry].add(t),e.occluded=!0}unoccludeTile(e,t){let i=this.tileOcclusion[e.rx][e.ry];i.delete(t),e.occluded=0<i.size}isTileOccluded(e){return 0<this.tileOcclusion[e.rx][e.ry].size}}class AutoLat{static calculate(u,d){let p=new Map;u.forEach(e=>{var t=d.getSetNum(e.tileNum);p.set(e,t),d.isCLAT(t)&&(t=d.getLAT(t),p.set(e,t),e.tileNum=d.getTileNumFromSet(t))}),u.forEach(t=>{var i=p.get(t);if(d.isLAT(i)){let e=0;var r=u.getNeighbourTile(t,TileDirection.TopRight),s=u.getNeighbourTile(t,TileDirection.BottomRight),a=u.getNeighbourTile(t,TileDirection.BottomLeft),n=u.getNeighbourTile(t,TileDirection.TopLeft);r&&d.canConnectTiles(i,p.get(r))&&(e+=1),s&&d.canConnectTiles(i,p.get(s))&&(e+=2),a&&d.canConnectTiles(i,p.get(a))&&(e+=4),n&&d.canConnectTiles(i,p.get(n))&&(e+=8),0<e&&(n=d.getCLATSet(i),t.tileNum=d.getTileNumFromSet(n,e))}else if(i===d.getGeneralValue("RampBase")&&!(t.rampType<1||4<t.terrainType)){let e=-1;var o=u.getNeighbourTile(t,TileDirection.TopRight),l=u.getNeighbourTile(t,TileDirection.BottomRight),h=u.getNeighbourTile(t,TileDirection.BottomLeft),c=u.getNeighbourTile(t,TileDirection.TopLeft);switch(t.rampType){case 1:c&&0===c.rampType&&e++,l&&0===l.rampType&&(e+=2);break;case 2:o&&0===o.rampType&&e++,h&&0===h.rampType&&(e+=2);break;case 3:l&&0===l.rampType&&e++,c&&0===c.rampType&&(e+=2);break;case 4:h&&0===h.rampType&&e++,o&&0===o.rampType&&(e+=2)}-1!==e&&(t.tileNum=d.getTileNumFromSet(d.getGeneralValue("RampSmooth"),3*(t.rampType-1)+e))}})}}class GameMap{get startingLocations(){return this.mapFile.startingLocations}constructor(e,t,i,r){this.mapFile=e,this.tiles=new TileCollection(this.mapFile.tiles,t,i.general,r),this.mapBounds=(new MapBounds).fromMapFile(this.mapFile,this.tiles),this.tileOccupation=new TileOccupation(this.tiles),this.tileOcclusion=new TileOcclusion(this.tiles),this.terrain=new map_Terrain_Terrain(this.tiles,this.mapFile.theaterType,this.mapBounds,this.tileOccupation,i),this.bridges=new Bridges(t,this.tiles,this.tileOccupation,this.mapBounds,i);let s=this.mapFile.tags;for(let t of this.mapFile.cellTags){let e=this.tiles.getByMapCoords(t.coords.x,t.coords.y);e&&(e.tag=s.find(e=>e.id===t.tagId))}r=this.tiles.getMapSize(),i=Math.max(r.width,r.height)/5;this.technosByTile=new QuadTree(new Box2(new Vector2(0,0),new Vector2(r.width,r.height)),{getKey:e=>{e=e.isBuilding()?e.centerTile:e.tile;return new Vector2(e.rx,e.ry)},maxDepth:this.computeQuadDepth(i),splitThreshold:10,joinThreshold:5}),this.mapFile.theaterType!==TheaterType.Snow&&AutoLat.calculate(this.tiles,t)}computeQuadDepth(e){if(e<=1)return 1;let t=0;for(;1<=e/2;)e/=2,t++;return t+(1<e?1:0)}getLighting(){return this.mapFile.lighting}getIonLighting(){return this.mapFile.ionLighting}getTheaterType(){return this.mapFile.theaterType}getTags(){return this.mapFile.tags}getTriggers(){return this.mapFile.triggers}getCellTags(){return this.mapFile.cellTags}getVariables(){return this.mapFile.variables}getWaypoint(t){return this.mapFile.waypoints.find(e=>e.number===t)}getTileAtWaypoint(e){e=this.getWaypoint(e);if(e){e=this.tiles.getByMapCoords(e.rx,e.ry);if(e)return e}}isWithinBounds(e){return this.mapBounds.isWithinBounds(e)}clampWithinBounds(e){var t=this.mapBounds.clampWithinBounds(e);let i=this.tiles.getByDisplayCoords(t.dx,t.dy);if(i&&this.mapBounds.isWithinBounds(i)){let e=i,t=i.z;for(;0<=t&&e&&this.mapBounds.isWithinBounds(e);)i=e,e=this.tiles.getByDisplayCoords(e.dx,e.dy+2),t-=2}else{let e=0;for(;!i||!this.mapBounds.isWithinBounds(i);){if(30<e)throw new Error("Exceeded max elevation while trying to clamp tile to map bounds");i=this.tiles.getByDisplayCoords(t.dx,t.dy+e),e+=2}}return i}isWithinHardBounds(e){return this.mapBounds.isWithinHardBounds(e)}getInitialMapObjects(){return{terrains:this.mapFile.terrains,overlays:this.mapFile.overlays,smudges:this.mapFile.smudges,technos:[...this.mapFile.structures,...this.mapFile.infantries,...this.mapFile.vehicles,...this.mapFile.aircrafts]}}getObjectsOnTile(e){return this.tileOccupation.getObjectsOnTile(e)}getGroundObjectsOnTile(e){return this.tileOccupation.getGroundObjectsOnTile(e)}getTileZone(e,t=!1){return this.tileOccupation.getTileZone(e,t)}dispose(){this.terrain.dispose(),this.bridges.dispose()}}class PlayerPair{constructor(e,t){this.first=e,this.second=t}has(e){return this.first===e||this.second===e}equals(e){return this.first===e.first&&this.second===e.second||this.first===e.second&&this.second===e.first}}!function(e){e[e.Requested=0]="Requested",e[e.Formed=1]="Formed"}(AllianceStatus=AllianceStatus||{});class Alliances{constructor(e){this.playerList=e,this.alliances=[]}findByPlayers(e,t){let i=new PlayerPair(e,t);return this.alliances.find(e=>e.players.equals(i))}filterByPlayer(t){return this.alliances.filter(e=>e.players.first===t||e.players.second===t)}request(e,t){if(!this.canRequestAlliance(t))throw new Error(`Player ${t.name} is not a human combatant.`);if(this.canFormAlliance(e,t)){if(this.findByPlayers(e,t))throw new Error("Can't request alliance because an alliance is already pending or formed between "+`${e.name} and ${t.name}.`);return this.setAlliance(e,t,AllianceStatus.Requested)}}cancelRequest(e,t){var i=this.findByPlayers(e,t);if(!i||i.status!==AllianceStatus.Requested)throw new Error(`There is no pending alliance request for player ${t.name} from player `+e.name);if(i.players.first!==e)throw new Error(`Can't cancel request initiated by the other player (${t.name})`);this.alliances.splice(this.alliances.indexOf(i),1)}acceptRequest(t,i){if(this.canFormAlliance(t,i)){let e=this.findByPlayers(t,i);if(!e||e.status!==AllianceStatus.Requested)throw new Error(`There is no pending alliance request for player ${i.name} from player `+t.name);if(e.players.first!==t)throw new Error("Can't accept own alliance request for player "+i.name);e.status=AllianceStatus.Formed}}setAlliance(e,t,i){if(!this.canFormAlliance(e,t))throw new Error(`Can't form alliance between players "${e.name}" and "${t.name}"`);var r;if(r=this.findByPlayers(e,t))throw new Error(`An alliance already exists between players ${e.name} and `+t.name);return r={players:new PlayerPair(e,t),status:i},this.alliances.push(r),r}breakAlliance(e,t){var i=this.findByPlayers(e,t);if(!i||i.status!==AllianceStatus.Formed)throw new Error(`There is no alliance between player ${e.name} and player `+t.name);this.alliances.splice(this.alliances.indexOf(i),1)}areAllied(e,t){t=this.findByPlayers(e,t);return!!t&&t.status===AllianceStatus.Formed}getAllies(t){return this.filterByPlayer(t).filter(e=>e.status===AllianceStatus.Formed).map(e=>e.players.first===t?e.players.second:e.players.first)}haveSharedIntel(e,t){return e.isObserver||t.isObserver||e===t||this.areAllied(e,t)}canRequestAlliance(e){return e.isCombatant()&&!e.isAi}canFormAlliance(t,i){let e=this.getHostilePlayers();if(0===e.filter(e=>e.has(t)&&!e.has(i)).length)return!1;if(0===e.filter(e=>e.has(i)&&!e.has(t)).length)return!1;let r=new PlayerPair(t,i);return!!e.filter(e=>!e.equals(r)).length}getHostilePlayers(){var i,r=this.playerList.getCombatants();let s=[];for(let t=0;t<r.length;t++)for(let e=t+1;e<r.length;e++)this.getAllies(r[t]).includes(r[e])||(i=new PlayerPair(r[t],r[e]),s.push(i));return s}getHash(){return fnv32a(this.alliances.map(e=>[this.playerList.getPlayerNumber(e.players.first),this.playerList.getPlayerNumber(e.players.second),e.status]).flat())}debugGetState(){return this.alliances.map(e=>({first:e.players.first,second:e.players.second,status:e.status}))}}class PlayerList{constructor(){this.players=[]}addPlayer(e){this.players.push(e)}getPlayerAt(e){if(e>=this.players.length)throw new RangeError(`Player #${e} out of bounds`);return this.players[e]}getPlayerByName(t){var e=this.players.find(e=>e.name===t);if(!e)throw new Error(`Player with name "${t}" not found`);return e}getPlayerNumber(e){var t=this.players.indexOf(e);if(-1===t)throw new Error(`Player ${e.name} not found`);return t}getCombatants(){return this.players.filter(e=>e.isCombatant())}getNonNeutral(){return this.players.filter(e=>!e.isNeutral)}getCivilian(){return this.players.find(e=>e.country?.side===SideType.Civilian)}getAll(){return this.players}}!function(e){e[e.None=0]="None",e[e.Hover=1]="Hover",e[e.Selected=2]="Selected",e[e.SelectedHover=3]="SelectedHover"}(SelectionLevel=SelectionLevel||{});class SelectionModel{constructor(e){this.selectionLevel=SelectionLevel.None,e.isBuilding()&&e.rules.wall?this.maxSelectionLevel=SelectionLevel.None:this.maxSelectionLevel=e.rules.selectable?SelectionLevel.Selected|SelectionLevel.Hover:SelectionLevel.Hover}getSelectionLevel(){return this.selectionLevel}setSelectionLevel(e){this.selectionLevel=Math.min(this.maxSelectionLevel,e)}setHover(e){this.setSelectionLevel(e?this.selectionLevel|SelectionLevel.Hover:this.selectionLevel&~SelectionLevel.Hover)}setSelected(e){this.setSelectionLevel(e?this.selectionLevel|SelectionLevel.Selected:this.selectionLevel&~SelectionLevel.Selected)}isHovered(){return this.selectionLevel>>SelectionLevel.Hover&1}isSelected(){return this.selectionLevel>=SelectionLevel.Selected}getControlGroupNumber(){return this.controlGroupNumber}setControlGroupNumber(e){this.controlGroupNumber=e}}class UnitSelection{constructor(){this.selectedUnits=new Set,this.selectionModelsByUnit=new Map,this.groups=new Map,this.hashNeedsUpdate=!0}getOrCreateSelectionModel(e){let t=this.selectionModelsByUnit.get(e);return t||(t=new SelectionModel(e),this.selectionModelsByUnit.set(e,t)),t}deselectAll(){this.selectedUnits.forEach(e=>this.selectionModelsByUnit.get(e)?.setSelected(!1)),this.selectedUnits.clear(),this.hashNeedsUpdate=!0}addToSelection(e){this.selectedUnits.add(e),this.getOrCreateSelectionModel(e).setSelected(!0),this.hashNeedsUpdate=!0}removeFromSelection(e){e.forEach(e=>{this.selectedUnits.delete(e),this.getOrCreateSelectionModel(e).setSelected(!1)}),this.hashNeedsUpdate=!0}getSelectedUnits(){return[...this.selectedUnits].filter(e=>!e.isDestroyed&&!e.isCrashing&&!e.isDisposed&&e.isSpawned)}isSelected(e){return this.selectedUnits.has(e)}cleanupUnit(e){this.selectionModelsByUnit.delete(e),this.selectedUnits.delete(e),this.removeUnitsFromGroup([e]),this.hashNeedsUpdate=!0}updateHash(){this.hash=fnv32a([...this.selectedUnits].map(e=>e.id))}getHash(){return this.hashNeedsUpdate&&(this.updateHash(),this.hashNeedsUpdate=!1),this.hash}createGroup(e){this.addUnitsToGroup(e,this.getSelectedUnits())}addUnitsToGroup(e,t,i=!0){this.removeUnitsFromGroup(t);let r=this.groups.get(e);r||(r=new Set,this.groups.set(e,r)),i&&([...r.values()].forEach(e=>this.selectionModelsByUnit.get(e)?.setControlGroupNumber(void 0)),r.clear());for(var s of t)r.add(s),this.getOrCreateSelectionModel(s).setControlGroupNumber(e)}addGroupToSelection(e){if(this.groups.has(e))for(var t of[...this.groups.get(e)])this.addToSelection(t)}selectGroup(e){this.deselectAll(),this.addGroupToSelection(e)}getGroupUnits(e){return[...this.groups.get(e)??[]]}removeUnitsFromGroup(e){for(var t of this.groups.values())for(var i of e)t.delete(i),this.selectionModelsByUnit.get(i)?.setControlGroupNumber(void 0)}}class BoxedVar{constructor(e){this._onChange=new EventDispatcher,this.value=e}get value(){return this._value}set value(e){var t=e!==this._value;this._value=e,t&&this._onChange.dispatch(this,e)}get onChange(){return this._onChange.asEvent()}}class Player{get credits(){return this._credits}set credits(e){if(e<0)throw new RangeError("Can't set credits to a negative value");this._credits=e}constructor(e,t=void 0,i,r=new Color(255,0,0)){this.name=e,this.country=t,this.startLocation=i,this.color=r,this.isAi=!1,this.defeated=!1,this.resigned=!1,this.dropped=!1,this.objectsByType=new Map,this.objectsById=new Map,this.traits=new Traits,this._credits=0,this.score=0,this.limitedUnitsBuiltByName=new Map,this.unitsBuiltByType=new Map,this.unitsKilledByType=new Map,this.unitsLostByType=new Map,this.buildingsCaptured=0,this.cratesPickedUp=0,this.creditsGained=0,this.cheerCooldownTicks=0,this.isObserver=!t,this.isNeutral=!!t&&!t.isPlayable()}getOrCreateObjectsForType(e){let t=this.objectsByType.get(e);return t||(t=new Set,this.objectsByType.set(e,t)),t}addOwnedObject(e){let t=this.getOrCreateObjectsForType(e.type);t.add(e),(e.owner=this).objectsById.set(e.id,e)}removeOwnedObject(e){let t=this.objectsByType.get(e.type);if(!t||!t.has(e))throw new Error(`GameObject ${e.name} does not belong to player `+this.name);t.delete(e),this.objectsById.delete(e.id)}getOwnedObjectById(e){return this.objectsById.get(e)}getOwnedObjectsByType(e,t=!1){let i=[];return i=[...this.objectsByType.get(e)||new Set],t||(i=i.filter(e=>!e.limboData)),i}getOwnedObjects(e=!1){let t=[];return[...this.objectsByType.values()].forEach(e=>{e.forEach(e=>t.push(e))}),e||(t=t.filter(e=>!e.limboData)),t}removeAllOwnedObjects(){this.objectsByType.forEach(e=>e.clear()),this.objectsById.clear()}get buildings(){return this.getOrCreateObjectsForType(ObjectType.Building)}addUnitsBuilt(e,t){this.unitsBuiltByType.set(e.type,(this.unitsBuiltByType.get(e.type)??0)+t),e.buildLimit<0&&this.limitedUnitsBuiltByName.set(e.name,(this.limitedUnitsBuiltByName.get(e.name)??0)+t)}getUnitsBuilt(e){return void 0!==e?this.unitsBuiltByType.get(e)??0:[...this.unitsBuiltByType.values()].reduce((e,t)=>e+t,0)}getLimitedUnitsBuilt(e){return this.limitedUnitsBuiltByName.get(e)??0}addUnitsKilled(e,t){this.unitsKilledByType.set(e,(this.unitsKilledByType.get(e)??0)+t)}getUnitsKilled(e){return void 0!==e?this.unitsKilledByType.get(e)??0:[...this.unitsKilledByType.values()].reduce((e,t)=>e+t,0)}addUnitsLost(e,t){this.unitsLostByType.set(e,(this.unitsLostByType.get(e)??0)+t)}getUnitsLost(e){return void 0!==e?this.unitsLostByType.get(e)??0:[...this.unitsLostByType.values()].reduce((e,t)=>e+t,0)}isCombatant(){return!this.isNeutral&&!this.isObserver&&!this.defeated}canProduceVeteran(e){if(!this.production||!this.country)throw new Error("Non-combatants can't produce units");var t=this.production.getQueueTypeForObject(e),t=this.production.getFactoryTypeForQueueType(t);return this.production.hasVeteranType(t)||this.country.hasVeteranUnit(e.type,e.name)}getHash(){return fnv32a([this.credits,...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{name:this.name,credits:this.credits,traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.traits.dispose(),this.production?.dispose()}}class RadarTrait{constructor(){this.disabled=!0,this.activeEvents=[]}isDisabled(){return this.disabled}setDisabled(e){this.disabled=e}}const prereqCategIniVals=(new Map).set("POWER",PrereqCategory.Power).set("FACTORY",PrereqCategory.Factory).set("BARRACKS",PrereqCategory.Barracks).set("RADAR",PrereqCategory.Radar).set("TECH",PrereqCategory.Tech).set("PROC",PrereqCategory.Proc);class Production{static factory(e,t,i,r){let s=new Production(e,t.mpDialogSettings.techLevel,i,t,r);t=t.general.maximumQueuedObjects+1;return s.addQueue(QueueType.Structures,new ProductionQueue(QueueType.Structures,1,1)),s.addQueue(QueueType.Armory,new ProductionQueue(QueueType.Armory,1,1)),s.addQueue(QueueType.Infantry,new ProductionQueue(QueueType.Infantry,t,t)),s.addQueue(QueueType.Vehicles,new ProductionQueue(QueueType.Vehicles,t,t)),s.addQueue(QueueType.Ships,new ProductionQueue(QueueType.Ships,t,t)),s.addQueue(QueueType.Aircrafts,new ProductionQueue(QueueType.Aircrafts,0,t)),s}constructor(e,t,i,r,s){this.player=e,this.maxTechLevel=t,this.gameOpts=i,this.rules=r,this.allAvailableObjects=s,this.buildSpeedModifier=1,this.queues=new Map,this._onQueueUpdate=new EventDispatcher,this.primaryFactories=new Map,this.factoryCounts=new Map,this.veteranTypes=new Set,this.stolenTech=new Set}get onQueueUpdate(){return this._onQueueUpdate.asEvent()}addQueue(e,t){this.queues.set(e,t),t.onUpdate.subscribe(()=>this._onQueueUpdate.dispatch(this,t))}getQueue(e){var t=this.queues.get(e);if(!t)throw new Error("No queue found with type "+QueueType[e]);return t}getAllQueues(){return[...this.queues.values()]}getQueueTypeForObject(e){if(e.type===ObjectType.Building)return e.buildCat===BuildCat.Combat?QueueType.Armory:QueueType.Structures;if(e.type===ObjectType.Infantry)return QueueType.Infantry;if(e.type===ObjectType.Vehicle)return e.naval?QueueType.Ships:QueueType.Vehicles;if(e.type===ObjectType.Aircraft)return QueueType.Aircrafts;throw new Error("Unsupported object type "+ObjectType[e.type])}getQueueForObject(e){return this.getQueue(this.getQueueTypeForObject(e))}getQueueTypeForFactory(e){if(e===FactoryType.InfantryType)return QueueType.Infantry;if(e===FactoryType.UnitType)return QueueType.Vehicles;if(e===FactoryType.AircraftType)return QueueType.Aircrafts;if(e===FactoryType.NavalUnitType)return QueueType.Ships;throw new Error("Unsupported factory type "+FactoryType[e])}getFactoryTypeForQueueType(e){if(e===QueueType.Structures||e===QueueType.Armory)return FactoryType.BuildingType;if(e===QueueType.Infantry)return FactoryType.InfantryType;if(e===QueueType.Vehicles)return FactoryType.UnitType;if(e===QueueType.Aircrafts)return FactoryType.AircraftType;if(e===QueueType.Ships)return FactoryType.NavalUnitType;throw new Error("Unsupported queue type "+QueueType[e])}getQueueForFactory(e){return this.getQueue(this.getQueueTypeForFactory(e))}isAvailableForProduction(e){return-1!==e.techLevel&&e.techLevel<=this.maxTechLevel&&!(0===e.buildLimit&&!this.player.isAi)&&!(e.superWeapon&&this.rules.getSuperWeapon(e.superWeapon).disableableFromShell&&!this.gameOpts.superWeapons)&&this.hasFactoryFor(e)&&this.meetsPrerequisites(e)}getAvailableObjects(){return this.allAvailableObjects.filter(e=>this.isAvailableForProduction(e))}hasFactoryFor(i){if(i.owner.length){let t=this.getFactoryTypeFor(i);return!![...this.player.buildings].find(e=>e.factoryTrait?.type===t&&(t!==FactoryType.UnitType||e.rules.naval===i.naval)&&!!e.rules.owner.find(e=>i.owner.includes(e)))}return!0}meetsStolenTech(e){return e.requiresStolenAlliedTech?this.stolenTech.has(SideType.GDI):e.requiresStolenSovietTech?this.stolenTech.has(SideType.Nod):!e.requiresStolenThirdTech||this.stolenTech.has(SideType.ThirdSide)}getFactoryTypeFor(e){return e.type===ObjectType.Building?FactoryType.BuildingType:e.type===ObjectType.Infantry?FactoryType.InfantryType:e.type===ObjectType.Aircraft?FactoryType.AircraftType:e.naval?FactoryType.NavalUnitType:FactoryType.UnitType}meetsPrerequisites(e){let t=[...this.player.buildings].map(e=>e.name);for(var i of e.prerequisiteOverride)if(i=i.toUpperCase(),t.includes(i))return!0;if(!e.isAvailableTo(this.player.country))return!1;var r;for(r of e.prerequisite)if(r=r.toUpperCase(),prereqCategIniVals.has(r)){var s=prereqCategIniVals.get(r);if(void 0===s)throw new Error("Unknown prereqName "+r);var a,n=this.rules.general.prereqCategories.get(s);if(void 0===n)throw new Error(`Missing prerequisite category ${s} in rules`);let e=!1;for(a of n)if(-1!==t.indexOf(a)){e=!0;break}if(!e)return!1}else if(-1===t.indexOf(r))return!1;return!!this.meetsStolenTech(e)}getPrimaryFactory(e){return this.primaryFactories.get(e)}setPrimaryFactory(e){e.rules.factory&&this.primaryFactories.set(e.rules.factory,e)}isPrimaryFactory(e){return this.getPrimaryFactory(e.rules.factory)===e}incrementFactoryCount(e){this.factoryCounts.set(e,(this.factoryCounts.get(e)??0)+1)}decrementFactoryCount(e){if(!this.factoryCounts.get(e))throw new Error(`Can't decrement factory count ${FactoryType[e]}. Already 0`);this.factoryCounts.set(e,this.factoryCounts.get(e)-1)}getFactoryCount(e){return this.factoryCounts.get(e)??0}crownPrimaryFactoryHeir(t){var e=[...this.player.buildings].find(e=>e.rules.factory===t);e?this.primaryFactories.set(t,e):this.primaryFactories.delete(t)}hasAnyFactory(){return 0<this.primaryFactories.size}addVeteranType(e){this.veteranTypes.add(e)}hasVeteranType(e){return this.veteranTypes.has(e)}addStolenTech(e){this.stolenTech.add(e)}dispose(){this.queues.clear(),this.player=void 0}}class SuperWeaponsTrait_SuperWeaponsTrait{constructor(){this.superWeapons=new Map}getAll(){return[...this.superWeapons.values()]}add(e){this.superWeapons.set(e.name,e)}has(e){return this.superWeapons.has(e)}get(e){return this.superWeapons.get(e)}remove(e){this.superWeapons.delete(e)}}class SharedDetectDisguiseTrait{constructor(){this.objects=new Set}add(e){this.objects.add(e)}delete(e){this.objects.delete(e)}has(e){return this.objects.has(e)}dispose(){this.objects.clear()}}class PlayerFactory{constructor(e,t,i){this.rules=e,this.gameOpts=t,this.allAvailableObjects=i}createCombatant(e,t,i,r,s,a){let n=new Player(e,t,i,r);return n.isAi=s,n.aiDifficulty=a,n.powerTrait=new PowerTrait(n),n.traits.add(n.powerTrait),n.radarTrait=new RadarTrait,n.traits.add(n.radarTrait),n.superWeaponsTrait=new SuperWeaponsTrait_SuperWeaponsTrait,n.traits.add(n.superWeaponsTrait),n.production=Production.factory(n,this.rules,this.gameOpts,this.allAvailableObjects),n.sharedDetectDisguiseTrait=new SharedDetectDisguiseTrait,n}createObserver(e,t){let i=new Player(e,void 0,void 0,t.colors.get("LightGrey"));return i.radarTrait=new RadarTrait,i.traits.add(i.radarTrait),i.radarTrait.setDisabled(!1),i}createNeutral(e,t){var i=[...e.countryRules.values()].find(e=>e.side===SideType.Civilian);if(!i)throw new Error("Missing neutral country. No country found in rules with Civilian side");i=new Country(i);let r=new Player(t,i,void 0,e.colors.get("LightGrey"));return r.powerTrait=new PowerTrait(r),r.traits.add(r.powerTrait),r}}(NotifySpawn_NotifySpawn=NotifySpawn_NotifySpawn||{}).onSpawn=Symbol(),(NotifyUnspawn_NotifyUnspawn=NotifyUnspawn_NotifyUnspawn||{}).onUnspawn=Symbol(),(NotifyOwnerChange_NotifyOwnerChange=NotifyOwnerChange_NotifyOwnerChange||{}).onChange=Symbol();class PowerTrait_PowerTrait{[NotifySpawn_NotifySpawn.onSpawn](e,t){e.isTechno()&&e.rules.power&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"add",t)}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){e.isTechno()&&e.rules.power&&!e.warpedOutTrait.isActive()&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"remove",t)}[NotifyHealthChange.onChange](e,t){e.isTechno()&&e.rules.power&&!e.warpedOutTrait.isActive()&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,"update",t)}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){e.rules.power&&!e.warpedOutTrait.isActive()&&(this.isCapturablePower(e,t)||t.powerTrait?.updateFrom(e,"remove",i),this.isCapturablePower(e,e.owner)||e.owner.powerTrait?.updateFrom(e,"add",i))}[NotifyWarpChange.onChange](e,t,i){e.rules.power&&!this.isCapturablePower(e,e.owner)&&e.owner.powerTrait?.updateFrom(e,i?"remove":"add",t)}[NotifyTick.onTick](e){for(var t of e.getCombatants())t.powerTrait.updateBlackout(e)}isCapturablePower(e,t){return 0<e.rules.power&&t.isNeutral&&e.rules.needsEngineer}}class ObjectSellEvent{constructor(e){this.target=e,this.type=EventType.ObjectSell}}class SellTrait{constructor(e,t){this.game=e,this.generalRules=t}sell(t){if(!t.isBuilding()||!t.rules.unsellable){let e=this.computeRefundValue(t);e&&(t.rules.wall&&(e=0),t.traits.filter(NotifySell).forEach(e=>{e[NotifySell.onSell](t,this.game)}),t.isBuilding()?this.game.getConstructionWorker(t.owner).unplace(t,()=>this.afterObjectUnspawned(t,e)):(this.game.unspawnObject(t),this.afterObjectUnspawned(t,e)))}}afterObjectUnspawned(e,t){e.owner.credits+=t,this.game.events.dispatch(new ObjectSellEvent(e)),e.dispose()}computeRefundValue(e){let t=0;return 0<e.rules.soylent?t=e.rules.soylent:e.rules.cost&&(t=e.purchaseValue,e.owner.isAi||(t=Math.floor(t*this.generalRules.refundPercent))),t}computePurchaseValue(e,t){return e.cost}dispose(){this.game=void 0}}class RadarOnOffEvent{constructor(e,t){this.target=e,this.radarEnabled=t,this.type=EventType.RadarOnOff}}class RadarEvent{constructor(e,t,i){this.target=e,this.radarEventType=t,this.tile=i,this.type=EventType.RadarEvent}}class RadarTrait_RadarTrait{constructor(){this.activeLightningStrikes=new Map}[NotifySpawn_NotifySpawn.onSpawn](e,t){e.isBuilding()&&e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){e.isBuilding()&&e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[NotifyPower.onPowerLow](e,t){this.updateRadarForPlayer(e,t)}[NotifyPower.onPowerRestore](e,t){this.updateRadarForPlayer(e,t)}[NotifyPower.onPowerChange](){}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){e.rules.radar&&(this.updateRadarForPlayer(t,i),this.updateRadarForPlayer(e.owner,i))}[NotifyWarpChange.onChange](e,t){e.rules.radar&&this.updateRadarForPlayer(e.owner,t)}[NotifySuperWeaponActivate.onActivate](e,t,i){if(e===SuperWeaponType.LightningStorm){this.activeLightningStrikes.set(t,(this.activeLightningStrikes.get(t)??0)+1);for(var r of i.getCombatants())r===t||i.alliances.areAllied(r,t)||this.updateRadarForPlayer(r,i)}}[NotifySuperWeaponDeactivate.onDeactivate](e,t,i){if(e===SuperWeaponType.LightningStorm){e=(this.activeLightningStrikes.get(t)??0)-1;if(0<e?this.activeLightningStrikes.set(t,e):this.activeLightningStrikes.delete(t),e<=0)for(var r of i.getCombatants())this.updateRadarForPlayer(r,i)}}updateRadarForPlayer(i,r){var e,t;i.radarTrait&&(e=i.radarTrait?.isDisabled(),t=![...i.buildings].find(e=>e.rules.radar&&!e.warpedOutTrait.isActive())||i.powerTrait.level===PowerLevel.Low||[...this.activeLightningStrikes.entries()].some(([e,t])=>t&&e!==i&&!r.alliances.areAllied(e,i)),i.radarTrait.setDisabled(t),e!==t&&r.events.dispatch(new RadarOnOffEvent(i,!t)))}[NotifyAttack_NotifyAttack.onAttack](e,t,i){e.isTechno()&&(!e.isBuilding()||e.rules.canBeOccupied||e.rules.needsEngineer?e.isVehicle()&&e.harvesterTrait&&this.addEventForPlayer(RadarEventType.HarvesterUnderAttack,e.owner,e.tile,i):this.addEventForPlayer(RadarEventType.BaseUnderAttack,e.owner,e.tile,i))}addEventForPlayer(r,e,s,a){let n=e.radarTrait;if(n){let t=a.rules.general.radar;n.activeEvents=n.activeEvents.filter(e=>a.currentTick-e.startTick<t.getEventDuration(e.type));let i=new RangeHelper(a.map.tileOccupation);!!n.activeEvents.find(e=>e.type===r&&i.isInTileRange(s,e.tile,0,t.getEventSuppresionDistance(e.type)))||(n.activeEvents.push({startTick:a.currentTick,tile:s,type:r}),a.events.dispatch(new RadarEvent(e,r,s)))}}}class InsufficientFundsEvent{constructor(e){this.target=e,this.type=EventType.InsufficientFunds}}const SIDEBAR_CLOCK_FRAMES=55;class ProductionTrait{constructor(e,t){this.rules=e,this.speedCheat=t,this.availableObjectRules=new Set;t=60*e.general.buildSpeed*GameSpeed.BASE_TICKS_PER_SECOND;this.baseBuildSpeed=1/(t/1e3),[...e.buildingRules.values(),...e.infantryRules.values(),...e.vehicleRules.values(),...e.aircraftRules.values()].forEach(e=>{e.owner.length&&this.availableObjectRules.add(e)})}[NotifyTick.onTick](e){for(var t of e.getCombatants())for(var i of t.production.getAllQueues())this.tickQueue(i,t,e)}[NotifySpawn_NotifySpawn.onSpawn](e,t){var i;e.isBuilding()&&e.owner.production?(i=e.rules.factory)&&(e.owner.production.getPrimaryFactory(i)||e.owner.production.setPrimaryFactory(e),e.owner.production.incrementFactoryCount(i),i===FactoryType.AircraftType&&this.updateAircraftQueueMaxSize(e.owner,t)):e.isAircraft()&&e.owner.production&&this.rules.general.padAircraft.includes(e.name)&&this.updateAircraftQueueMaxSize(e.owner,t)}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){var i;e.isBuilding()&&e.owner.production?(this.ensurePrerequisites(e.owner),(i=e.rules.factory)&&(e.owner.production.getPrimaryFactory(i)===e&&e.owner.production.crownPrimaryFactoryHeir(i),e.owner.production.decrementFactoryCount(i),i===FactoryType.AircraftType&&this.updateAircraftQueueMaxSize(e.owner,t))):e.isAircraft()&&e.owner.production&&this.rules.general.padAircraft.includes(e.name)&&this.updateAircraftQueueMaxSize(e.owner,t)}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){var r;e.isBuilding()?(this.ensurePrerequisites(t),(r=e.rules.factory)&&(t.production?.getPrimaryFactory(r)===e&&t.production.crownPrimaryFactoryHeir(r),e.owner.production&&!e.owner.production.getPrimaryFactory(r)&&e.owner.production.setPrimaryFactory(e),t.production?.decrementFactoryCount(r),e.owner.production?.incrementFactoryCount(r),r===FactoryType.AircraftType&&(this.updateAircraftQueueMaxSize(e.owner,i),this.updateAircraftQueueMaxSize(t,i)))):e.isAircraft()&&this.rules.general.padAircraft.includes(e.name)&&(this.updateAircraftQueueMaxSize(e.owner,i),this.updateAircraftQueueMaxSize(t,i))}[NotifyPower.onPowerLow](e){e.production&&(e.production.buildSpeedModifier=this.computeLowPowerBuildSpeedModifier(e.powerTrait.power,e.powerTrait.drain))}[NotifyPower.onPowerRestore](e){e.production&&(e.production.buildSpeedModifier=1)}[NotifyPower.onPowerChange](e){e.powerTrait?.level===PowerLevel.Low&&e.production&&(e.production.buildSpeedModifier=this.computeLowPowerBuildSpeedModifier(e.powerTrait.power,e.powerTrait.drain))}computeLowPowerBuildSpeedModifier(e,t){e=1-Math.min(1,e/t),t=this.rules.general;return clamp(1-.3*t.lowPowerPenaltyModifier*e/.15,t.minLowPowerProductionSpeed,t.maxLowPowerProductionSpeed)}updateAircraftQueueMaxSize(i,r){i.production&&r.afterTick(()=>{var e=[...i.buildings].filter(e=>e.helipadTrait).reduce((e,t)=>e+t.dockTrait.numberOfDocks,0),t=i.getOwnedObjectsByType(ObjectType.Aircraft,!0).filter(e=>r.rules.general.padAircraft.includes(e.name)).length;i.production.getQueueForFactory(FactoryType.AircraftType).maxSize=Math.max(0,e-t)})}tickQueue(i,r,s){if(i.status===QueueStatus.Active){let e=!1,t=i.getFirst();var a,n=r.production.getFactoryTypeForQueueType(i.type),o=r.production.getFactoryCount(n),l=r.production.buildSpeedModifier,h=1/GameMath.pow(this.rules.general.multipleFactory,o-1),n=t.rules.wall?1/this.rules.general.wallBuildSpeedCoefficient:1,o=this.baseBuildSpeed*l*h*n,l=t.creditsEach,h=SIDEBAR_CLOCK_FRAMES-1,n=l&&!this.speedCheat.value?floorTo(l/o*t.rules.buildTimeMultiplier,h):h,n=Math.max(h,n),o=r.credits,h=t.creditsEach-t.creditsSpent,h=Math.min(r.credits,l/n+t.creditsSpentLeftover,h);0<h?(a=Math.floor(h),t.creditsSpentLeftover=h-a,a&&(t.creditsSpent+=a,t.progress=t.creditsSpent/t.creditsEach,r.credits-=a,e=!0)):t.creditsEach||(a=t.progress*n,t.progress=Math.min(1,(1+a)/n),e=!0),e&&1===t.progress&&(i.status=QueueStatus.Ready),0<o&&!r.credits&&s.events.dispatch(new InsufficientFundsEvent(r)),e&&i.notifyUpdated()}}ensurePrerequisites(e){if(e.production)for(var t of e.production.getAllQueues()){var i;for(i of t.getAll().map(e=>({rules:e.rules,quantity:e.quantity,creditsSpent:e.creditsSpent})))e.production.isAvailableForProduction(i.rules)||(t.pop(i.rules,i.quantity),e.credits+=i.creditsSpent)}}getAvailableObjects(){return[...this.availableObjectRules]}}(NotifyAllianceChange=NotifyAllianceChange||{}).onChange=Symbol();class MapShroudTrait{constructor(e,t){this.map=e,this.alliances=t,this.shroudByPlayer=new Map,this.revealedToAll=new Set,this.gapGenerators=new Set,this.handleTileOccupationUpdate=({object:e,type:t})=>{if("removed"!==t&&e.isTechno()){var i,t=e.owner;for(i of[t,...this.alliances.getAllies(t)])this.shroudByPlayer.get(i)?.revealFrom(e)}}}getPlayerShroud(e){return this.shroudByPlayer.get(e)}init(t){t.map.tileOccupation.onChange.subscribe(this.handleTileOccupationUpdate);let i=(new MapShroud).fromTiles(this.map.tiles);for(var r of t.getCombatants()){let e=i.clone();this.shroudByPlayer.set(r,e),this.revealObjects(e,r,t),e.update()}}[NotifyElevationChange.onElevationChange](e,t,i){if(Math.floor(e.tileElevation)!==Math.floor(i)){var r,i=e.owner;for(r of[i,...this.alliances.getAllies(i)])this.shroudByPlayer.get(r)?.revealFrom(e)}}[NotifyTick.onTick](e){for(var[t,i]of this.shroudByPlayer)t.defeated&&!t.isObserver?this.shroudByPlayer.delete(t):i.update()}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){if(e.isBuilding()&&e.rules.spySat&&(this.revealMap(e.owner,i),t.getOwnedObjectsByType(ObjectType.Building).find(e=>e.rules.spySat)||this.resetShroud(t,i)),e.isSpawned)for(var r of[e.owner,...i.alliances.getAllies(e.owner)])this.shroudByPlayer.get(r)?.revealFrom(e)}[NotifyAllianceChange.onChange](t,e,i){if(e){let e=this.getPlayerShroud(t.players.first);var r,s,t=i.alliances.getAllies(t.players.first).map(e=>this.getPlayerShroud(e)).filter(isNotNullOrUndefined);for(r of t)e.merge(r);e.invalidateFull();for(s of t)s.copy(e),s.invalidateFull()}}[NotifySpawn_NotifySpawn.onSpawn](e,t){if(e.isBuilding()){if(e.rules.spySat&&this.revealMap(e.owner,t),e.rules.revealToAll){this.revealedToAll.add(e);for(var i of t.getCombatants())i===e.owner||t.alliances.areAllied(e.owner,i)||(this.shroudByPlayer.get(i)?.revealObject(e),t.traits.get(RadarTrait_RadarTrait).addEventForPlayer(RadarEventType.EnemyObjectSensed,i,e.centerTile,t))}e.gapGeneratorTrait&&this.gapGenerators.add(e)}}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){e.isBuilding()&&(e.rules.spySat&&(e.owner.getOwnedObjectsByType(ObjectType.Building).find(e=>e.rules.spySat)||this.resetShroud(e.owner,t)),e.rules.revealToAll&&this.revealedToAll.delete(e),e.gapGeneratorTrait&&this.gapGenerators.delete(e))}[NotifyPower.onPowerLow](e,t){this.updateGaps(t,e)}[NotifyPower.onPowerRestore](e,t){this.updateGaps(t,e)}[NotifyPower.onPowerChange](e,t){}revealMap(e,t){this.shroudByPlayer.get(e)?.revealAll(),this.markOwnGapTiles(t,e),this.updateGaps(t)}resetShroud(e,t){let i=this.shroudByPlayer.get(e);i&&(i.reset(),this.markOwnGapTiles(t,e),this.revealObjects(i,e,t))}revealObjects(t,e,i){var r;for(r of[...e.getOwnedObjects(),...i.alliances.getAllies(e).map(e=>e.getOwnedObjects()).flat()])t.revealFrom(r);this.revealedToAll.forEach(e=>t.revealObject(e))}updateGaps(e,t){for(var i of this.gapGenerators)t&&i.owner!==t||i.gapGeneratorTrait.update(i,e)}markOwnGapTiles(e,t){for(var i of this.gapGenerators)i.owner!==t&&!e.alliances.areAllied(i.owner,t)||this.getPlayerShroud(t)?.toggleFlagsAround(i.tile,i.gapGeneratorTrait.radiusTiles,ShroudFlag.Darken,!0)}dispose(){this.map.tileOccupation.onChange.unsubscribe(this.handleTileOccupationUpdate)}}class PackBuildingTask extends Task{constructor(e){super(),this.game=e}onTick(e){return!(e.buildStatus!==BuildStatus.BuildDown&&(e.setBuildStatus(BuildStatus.BuildDown,this.game),!e.rules.wall))||(this.children.push(new WaitMinutesTask(this.game.rules.general.buildupTime)),!1)}}const isLegacyDisposable=e=>!e.dispose;class CompositeDisposable{constructor(){this.disposables=new Set}add(...e){e.map(e=>this.disposables.add("function"==typeof e?{dispose:e}:e))}remove(...e){e.map(e=>this.disposables.delete(e))}dispose(){this.disposables.forEach(e=>{"function"==typeof e?e():isLegacyDisposable(e)?e.destroy():e.dispose()}),this.disposables.clear()}}class ConstructionWorker{constructor(e,t,i,r,s){this.player=e,this.rules=t,this.art=i,this.map=r,this.game=s,this.adjacencyMaps=new Map,this.disposables=new CompositeDisposable;let a=({object:e})=>{e.isBuilding()&&this.adjacencyMaps.clear()};this.map.tileOccupation.onChange.subscribe(a),this.disposables.add(()=>this.map.tileOccupation.onChange.unsubscribe(a)),this.disposables.add(this.game.events.subscribe(EventType.AllianceChange,()=>this.adjacencyMaps.clear()),this.game.events.subscribe(EventType.ObjectOwnerChange,e=>{e.target.isBuilding()&&this.adjacencyMaps.clear()}),this.game.events.subscribe(EventType.ObjectDestroy,e=>{e.target.isBuilding()&&e.target.rules.leaveRubble&&this.adjacencyMaps.clear()}))}getAdjacentRect(e,t,i){return{x:e.rx-i,y:e.ry-i,width:t.width+2*i,height:t.height+2*i}}getAdjacencyMap(e){var t;let i=[];for(t of[...this.player.buildings,...this.game.gameOpts.buildOffAlly?this.game.alliances.getAllies(this.player).map(e=>[...e.buildings].filter(e=>e.rules.eligibileForAllyBuilding)).flat():[]])t.rules.baseNormal&&i.push(this.getAdjacentRect(t.tile,t.art.foundation,e));return i}meetsAdjacency(e,t){let i=this.adjacencyMaps.get(t);i||(i=this.getAdjacencyMap(t),this.adjacencyMaps.set(t,i));for(var r of i)if(rectIntersect(e,r))return!0;return!1}getPlacementPreview(e,t,i={}){var{normalizedTile:r=!1,ignoreObjects:s,ignoreAdjacent:i=!1}=i,a=this.rules.getBuilding(e),e=this.art.getObject(e,ObjectType.Building);let n=[];var o=e.foundation,l=r?t:this.normalizePlacementTileCoords(e,t);let h=!0;t={x:l.rx,y:l.ry,width:o.width,height:o.height};a.constructionYard||i||this.meetsAdjacency(t,a.adjacent)||(h=!1);for(let t=0;t<o.width;t++)for(let e=0;e<o.height;e++){var c={x:l.rx+t,y:l.ry+e},u=this.map.tiles.getByMapCoords(c.x,c.y);u&&n.push({rx:c.x,ry:c.y,buildable:h&&this.isTileBuildable(u,a,s)})}if(a.wall&&n[0].buildable){let e=this.getWallConnectingTiles(l,a);e.forEach(e=>{n.push({rx:e.rx,ry:e.ry,buildable:!0})})}return n}canPlaceAt(e,t,i={}){var{normalizedTile:r=!1,ignoreObjects:s,ignoreAdjacent:i=!1}=i,a=this.rules.getBuilding(e),e=this.art.getObject(e,ObjectType.Building),n=e.foundation,o=r?t:this.normalizePlacementTileCoords(e,t),t={x:o.rx,y:o.ry,width:n.width,height:n.height};if(!a.constructionYard&&!i&&!this.meetsAdjacency(t,a.adjacent))return!1;for(let t=0;t<n.width;t++)for(let e=0;e<n.height;e++){var l={x:o.rx+t,y:o.ry+e},l=this.map.tiles.getByMapCoords(l.x,l.y);if(!l||!this.isTileBuildable(l,a,s))return!1}return!0}placeAt(e,t,i=!1){let r=[],s=this.rules.getBuilding(e),a=i?t:this.normalizePlacementTile(e,t);if(s.wall){let t=[[a,s]],e=this.getWallConnectingTiles(a,s);e.forEach(e=>{e!==a&&t.push([e,s])});for(var n of t)r.push(this.executePlacement(n[0],n[1]))}else{var o,t=this.executePlacement(a,s);r.push(t);for(o of this.map.tileOccupation.calculateTilesForGameObject(a,t)){var l=this.map.getObjectsOnTile(o).find(e=>e.isSmudge());l&&this.game.unspawnObject(l)}}return r}normalizePlacementTileCoords(e,t){e=e.foundationCenter;return{rx:t.rx-e.x,ry:t.ry-e.y}}normalizePlacementTile(e,t){e=this.art.getObject(e,ObjectType.Building),e=this.normalizePlacementTileCoords(e,t),t=this.map.tiles.getByMapCoords(e.rx,e.ry);if(!t)throw new Error(`Can't build outside map (${e.rx}, ${e.ry})`);return t}unplace(e,t){e.unitOrderTrait.cancelAllTasks(),e.unitOrderTrait.addTasks(new TaskGroup(new PackBuildingTask(this.game),new CallbackTask(()=>{this.game.unspawnObject(e),t()})).setCancellable(!1)),e.unitOrderTrait[NotifyTick_NotifyTick.onTick](e,this.game)}executePlacement(e,t){let i=this.game.createObject(ObjectType.Building,t.name);return this.game.changeObjectOwner(i,this.player),i.purchaseValue=this.game.sellTrait.computePurchaseValue(t,this.player),this.game.spawnObject(i,e),i}getWallConnectingTiles(i,r){var s,a=r.guardRange+1;let n=[];for(s of[[0,1],[0,-1],[1,0],[-1,0]]){let t=[];for(let e=0;e<a;++e){var o={x:i.rx+s[0]*e,y:i.ry+s[1]*e},o=this.map.tiles.getByMapCoords(o.x,o.y);if(!o)break;if(this.map.getObjectsOnTile(o).find(e=>e.isBuilding()&&e.name===r.name&&e.owner===this.player)){n=n.concat(t);break}if(!this.isTileBuildable(o,r))break;t.push(o)}}return n}isTileBuildable(e,t,i){return!!this.map.isWithinBounds(e)&&(!this.game.mapShroudTrait.getPlayerShroud(this.player)?.isShrouded(e)&&(!this.map.getGroundObjectsOnTile(e).some(e=>!(i?.includes(e)||e.isBuilding()&&e.rules.invisibleInGame||e.isSmudge()))&&(t.waterBound?0<this.rules.getLandRules(e.landType).getSpeedModifier(SpeedType.Float):0===e.rampType&&this.rules.getLandRules(e.landType).buildable)))}dispose(){this.disposables.dispose()}}class StartingUnitsGenerator{static generate(e,t,i,r){var s,a=i.reduce((e,t)=>e+t.cost,0)/i.length*e;let n=[],o=a,l=(i=i.filter(e=>e.isAvailableTo(r)&&e.hasOwner(r))).filter(e=>t.includes(e.name));for(s of l){if(o<=0)break;var h=2/3/l.length,h=Math.ceil(h*a/s.cost);o-=h*s.cost,n.push({name:s.name,type:ObjectType.Vehicle,count:h})}var c,i=i.filter(e=>!l.includes(e)),u=o/i.length;for(c of i){if(o<=0)break;var d=Math.ceil(u/c.cost);o-=d*c.cost,n.push({name:c.name,type:ObjectType.Infantry,count:d})}return n}}class GameEventBus{constructor(){this.dispatcher=new EventDispatcher,this.dispatchersByType=new Map}dispatch(e){this.dispatcher.dispatch(void 0,e),this.dispatchersByType.get(e.type)?.dispatch(void 0,e)}subscribe(e,t){let i=void 0,r;return r="function"==typeof e?e:(i=e,t),void 0===i?(this.dispatcher.subscribe(r),()=>this.unsubscribe(r)):this.subscribeType(i,r)}unsubscribe(e,t){let i=void 0,r;r="function"==typeof e?e:(i=e,t),void 0===i?this.dispatcher.unsubscribe(r):this.unsubscribeType(i,r)}subscribeType(e,t){let i=this.dispatchersByType.get(e);return i||(i=new EventDispatcher,this.dispatchersByType.set(e,i)),i.subscribe(t),()=>this.unsubscribeType(e,t)}unsubscribeType(e,t){this.dispatchersByType.get(e)?.unsubscribe(t)}}class ObjectDestroyEvent{constructor(e,t,i){this.target=e,this.attackerInfo=t,this.incidental=i,this.type=EventType.ObjectDestroy}}class PlayerDefeatedEvent{constructor(e){this.target=e,this.type=EventType.PlayerDefeated}}(NotifyDestroy_NotifyDestroy=NotifyDestroy_NotifyDestroy||{}).onDestroy=Symbol();class ObjectOwnerChangeEvent{constructor(e,t){this.target=e,this.prevOwner=t,this.type=EventType.ObjectOwnerChange}}class ObjectUnspawnEvent{constructor(e){this.gameObject=e,this.type=EventType.ObjectUnspawn}}class ObjectSpawnEvent{constructor(e){this.gameObject=e,this.type=EventType.ObjectSpawn}}!function(e){e[e.Requested=0]="Requested",e[e.Formed=1]="Formed",e[e.Broken=2]="Broken"}(AllianceEventType=AllianceEventType||{});class AllianceChangeEvent{constructor(e,t,i){this.alliance=e,this.changeType=t,this.from=i,this.type=EventType.AllianceChange}}var NotifyObjectTraitAdd,GameStatus,ActionType,NotifyPlaceBuilding,PointerType,OrderFeedbackType,EvacState,EnterHospitalTask_State,EnterTransportTask_State,UpdateType,DebugCommandType,mersenne_twister=__webpack_require__(798),mersenne_twister_default=__webpack_require__.n(mersenne_twister);class Prng{static factory(e,t){t=Number.isNaN(Number(e))?Crc32.calculateCrc(binaryStringToUint8Array(e)):Number(e+""+t);return new Prng(t)}constructor(e){this.prng=new(mersenne_twister_default())(e)}generateRandomInt(e,t){var i=this.prng.random();return this.lastRandom=i,Math.round(i*(t-e))+e}generateRandom(){var e=this.prng.random();return this.lastRandom=e}getLastRandom(){return this.lastRandom}}class TriggerExecutor{constructor(e,t){this.action=e,this.trigger=t}getDebugName(){return`${this.action.triggerId}[${this.action.index}] (${this.trigger.name}).`}}class AddSuperWeaponExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.oneTimeOnly=i,this.superWeaponIdx=Number(e.params[1])}execute(i){var r=[...i.rules.superWeaponRules.values()].find(e=>e.index===this.superWeaponIdx);if(r){let t=i.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);if(t&&t.superWeaponsTrait&&!t.superWeaponsTrait.has(r.name)){let e=i.createSuperWeapon(r.name,t,this.oneTimeOnly);e.isGift=!0,t.superWeaponsTrait.add(e)}}else console.warn(`No superweapon found with index "${this.superWeaponIdx}". `+`Skipping action ${this.getDebugName()}.`)}}class ApplyDamageExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.damage=i}execute(t){var e=Number(this.action.params[1]),i=t.map.getTileAtWaypoint(e);if(i){var r=t.rules.getWarhead(Warhead.HE_WARHEAD_NAME);let e=new Warhead(r);var s=t.map.tileOccupation.getBridgeOnTile(i),a=s?.tileElevation??0,r=t.map.getTileZone(i);e.detonate(t,this.damage,i,a,Coords.tile3dToWorld(i.rx+.5,i.ry+.5,i.z+a),r,s?CollisionType.OnBridge:CollisionType.None,t.createTarget(s,i),void 0)}else console.warn(`No valid location found for waypoint ${e}. `+`Skipping action ${this.getDebugName()}.`)}}class ChangeHouseAllExecutor extends TriggerExecutor{execute(r){let t=r.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);if(t){let i=Number(this.action.params[1]),e;if(i>=ChangeHouseAllExecutor.locationHouseIdBegin&&i<ChangeHouseAllExecutor.locationHouseIdBegin+r.map.startingLocations.length){let t=i-ChangeHouseAllExecutor.locationHouseIdBegin;e=r.getAllPlayers().find(e=>e.startLocation===t)}else e=r.getAllPlayers().find(e=>e.country?.id===i);if(e)for(var s of t.getOwnedObjects(!0))r.changeObjectOwner(s,e)}}}ChangeHouseAllExecutor.locationHouseIdBegin=4475;class ChangeHouseExecutor extends TriggerExecutor{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e,t){let i;if(this.houseId>=ChangeHouseExecutor.locationHouseIdBegin&&this.houseId<ChangeHouseExecutor.locationHouseIdBegin+e.map.startingLocations.length){let t=this.houseId-ChangeHouseExecutor.locationHouseIdBegin;i=e.getAllPlayers().find(e=>e.startLocation===t)}else i=e.getAllPlayers().find(e=>e.country?.id===this.houseId);if(i)for(var r of t)r instanceof GameObject&&r.isSpawned&&e.changeObjectOwner(r,i)}}ChangeHouseExecutor.locationHouseIdBegin=4475;class CheerTask extends Task{constructor(){super(),this.executed=!1,this.cancellable=!1}onTick(e){return this.executed?(e.stance=StanceType.None,!0):!e.isInfantry()||!e.art.sequences.has(SequenceType.Cheer)||(e.stance!==StanceType.None&&e.stance!==StanceType.Guard||(e.stance=StanceType.Cheer,this.children.push(new WaitMinutesTask(1/60).setCancellable(!1)),!(this.executed=!0)))}}class CheerExecutor extends TriggerExecutor{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e){let t=e.getAllPlayers().filter(e=>e.country&&!e.defeated);if(-1!==this.houseId&&(t=t.filter(e=>e.country?.id===this.houseId)),t.length)for(var i of t[0].getOwnedObjectsByType(ObjectType.Infantry))i.unitOrderTrait.isIdle()&&i.unitOrderTrait.addTask(new CheerTask)}}const crateConfigs=new Map([[0,e=>{e=e.rules.powerups.powerups.find(e=>e.type===PowerupType.Money);return e?{...e,data:"5000"}:void 0}],[1,PowerupType.Unit],[2,PowerupType.HealBase],[3,PowerupType.Cloak],[4,PowerupType.Explosion],[5,PowerupType.Napalm],[6,PowerupType.Money],[7,PowerupType.Darkness],[8,PowerupType.Reveal],[9,PowerupType.Armor],[10,PowerupType.Speed],[11,PowerupType.Firepower],[12,PowerupType.ICBM],[13,void 0],[14,PowerupType.Veteran],[15,void 0],[16,PowerupType.Gas],[17,PowerupType.Tiberium],[18,void 0]]);class CreateCrateExecutor extends TriggerExecutor{execute(e){var t=Number(this.action.params[1]),i=this.action.params[6],r=e.map.getTileAtWaypoint(i);if(r)if(crateConfigs.has(t)){const s=crateConfigs.get(t);t="function"==typeof s?s(e):e.rules.powerups.powerups.find(e=>e.type===s);t&&e.crateGeneratorTrait.spawnCrateAt(r,t,e)}else e.crateGeneratorTrait.spawnRandomCrateAt(r,e);else console.warn(`No valid location found for waypoint ${i}. `+`Skipping action ${this.getDebugName()}.`)}}class CreateRadarEventExecutor extends TriggerExecutor{execute(e){var t=Number(this.action.params[1])-1;if(Object.values(RadarEventType).includes(t)){var i=this.action.params[6],r=e.map.getTileAtWaypoint(i);if(r)for(var s of e.getCombatants())e.traits.get(RadarTrait_RadarTrait).addEventForPlayer(t,s,r,e);else console.warn(`No valid location found for waypoint ${i}. `+`Skipping action ${this.getDebugName()}.`)}else console.warn(`Unknown radar event type "${1+t}". Skipping action ${this.getDebugName()}.`)}}class DestroyObjectExecutor extends TriggerExecutor{execute(e,t){for(var i of t)i instanceof GameObject&&i.isSpawned&&e.destroyObject(i)}}class DestroyTagExecutor extends TriggerExecutor{execute(e){var t=this.action.params[1];e.triggers.destroyTag(t)}}class DestroyTriggerExecutor extends TriggerExecutor{execute(e){var t=this.action.params[1];e.triggers.destroyTrigger(t)}}class DetonateWarheadExecutor extends TriggerExecutor{execute(r){var s=Number(this.action.params[1]),e=this.action.params[6],a=r.map.getTileAtWaypoint(e);if(a){let t;try{t=r.rules.getWeaponByInternalId(s)}catch(e){if(e instanceof RangeError)return void console.warn(`Weapon with internal ID "${s}" not found. `+`Skipping action ${this.getDebugName()}.`);throw e}let e;try{e=r.rules.getWarhead(t.warhead)}catch(e){return void console.warn(`Warhead "${t.warhead}" not found. `+`Skipping action ${this.getDebugName()}.`)}let i=new Warhead(e);var n=r.map.tileOccupation.getBridgeOnTile(a),o=n?.tileElevation??0,s=r.map.getTileZone(a);i.detonate(r,t.damage,a,o,Coords.tile3dToWorld(a.rx+.5,a.ry+.5,a.z+o),s,n?CollisionType.OnBridge:CollisionType.None,r.createTarget(n,a),void 0)}else console.warn(`No valid location found for waypoint ${e}. `+`Skipping action ${this.getDebugName()}.`)}}class EvictOccupiersExecutor extends TriggerExecutor{execute(e,t){for(var i of t)i instanceof GameObject&&i.isBuilding()&&i.garrisonTrait&&!i.isDestroyed&&i.garrisonTrait.evacuate(e)}}class FireSaleExecutor extends TriggerExecutor{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}execute(e){var t=e.getAllPlayers().find(e=>e.country?.id===this.houseId);if(t)for(var i of t.buildings)e.sellTrait.sell(i)}}class ForceEndExecutor extends TriggerExecutor{execute(e){e.end()}}class ForceTriggerExecutor extends TriggerExecutor{execute(e){var t=this.action.params[1];e.triggers.forceTrigger(t,e)}}class GlobalVariableExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.value=i,this.variableIdx=Number(e.params[1])}execute(e){e.triggers.toggleGlobalVariable(this.variableIdx,this.value)}}class IronCurtainExecutor extends TriggerExecutor{execute(e){var t,i,r=this.action.params[6],s=e.map.getTileAtWaypoint(r);s?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===SuperWeaponType.IronCurtain))&&e.traits.get(SuperWeaponsTrait).activateEffect(i,t,e,s,void 0,!0):console.warn(`No valid location found for waypoint ${r}. `+`Skipping action ${this.getDebugName()}.`)}}class LightningStrikeExecutor extends TriggerExecutor{execute(e){var t,i,r=this.action.params[6],s=e.map.getTileAtWaypoint(r);s?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===SuperWeaponType.LightningStorm))&&e.traits.get(SuperWeaponsTrait).activateEffect(i,t,e,s,void 0,!0):console.warn(`No valid location found for waypoint ${r}. `+`Skipping action ${this.getDebugName()}.`)}}class LocalVariableExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.value=i,this.variableIdx=Number(e.params[1])}execute(e){e.triggers.toggleLocalVariable(this.variableIdx,this.value)}}class NoActionExecutor extends TriggerExecutor{execute(){}}class NukeStrikeExecutor extends TriggerExecutor{execute(e){var t,i,r=this.action.params[6],s=e.map.getTileAtWaypoint(r);s?!(t=e.getAllPlayers().find(e=>!e.defeated&&e.country?.name===this.trigger.houseName))||(i=[...e.rules.superWeaponRules.values()].find(e=>e.type===SuperWeaponType.MultiMissile))&&e.traits.get(SuperWeaponsTrait).activateEffect(i,t,e,s,void 0,!0):console.warn(`No valid location found for waypoint ${r}. `+`Skipping action ${this.getDebugName()}.`)}}class TriggerAnimEvent{constructor(e,t){this.name=e,this.tile=t,this.type=EventType.TriggerAnim}}class PlayAnimAtExecutor extends TriggerExecutor{execute(e){var t,i=this.action,r=Number(i.params[1]),s=e.rules.getAnimationName(r);void 0!==s?(t=i.params[6],(i=e.map.getTileAtWaypoint(t))?e.events.dispatch(new TriggerAnimEvent(s,i)):console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)):console.warn(`No animation found for index "${r}". Skipping action `+this.getDebugName())}}class TriggerSoundFxEvent{constructor(e,t){this.soundId=e,this.tile=t,this.type=EventType.TriggerSoundFx}}class PlaySoundFxAtExecutor extends TriggerExecutor{execute(e){var t=this.action,i=t.params[1],r=t.params[6],t=e.map.getTileAtWaypoint(r);t?e.events.dispatch(new TriggerSoundFxEvent(i,t)):console.warn(`No valid location found for waypoint ${r}. `+`Skipping action ${this.getDebugName()}.`)}}class PlaySoundFxExecutor extends TriggerExecutor{execute(e){e.events.dispatch(new TriggerSoundFxEvent(this.action.params[1]))}}class TriggerEvaEvent{constructor(e){this.soundId=e,this.type=EventType.TriggerEva}}class PlaySpeechExecutor extends TriggerExecutor{execute(e){e.events.dispatch(new TriggerEvaEvent(this.action.params[1]))}}class ReshroudMapExecutor extends TriggerExecutor{execute(e){for(var t of e.getCombatants())e.mapShroudTrait.resetShroud(t,e)}}class ResizePlayerViewExecutor extends TriggerExecutor{execute(e){var[t,i,r,s]=this.action.params.slice(2,6).map(Number);e.map.mapBounds.updateRawLocalSize({x:t,y:i,width:r,height:s})}}class RevealAroundWaypointExecutor extends TriggerExecutor{execute(e){var t=Number(this.action.params[1]),i=e.map.getTileAtWaypoint(t);if(i)for(var r of e.getCombatants())e.mapShroudTrait.getPlayerShroud(r)?.revealAround(i,e.rules.general.revealTriggerRadius);else console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class RevealMapExecutor extends TriggerExecutor{execute(e){for(var t of e.getCombatants())e.mapShroudTrait.revealMap(t,e)}}class SellBuildingExecutor extends TriggerExecutor{execute(e,t){for(var i of t)i instanceof GameObject&&i.isBuilding()&&!i.isDestroyed&&e.sellTrait.sell(i)}}class SetAmbientLightExecutor extends TriggerExecutor{execute(e){var t=Number(this.action.params[1])/100;e.mapLightingTrait.setTargetAmbientIntensity(t)}}function int32ToFloat32(e){let t=new DataView(new ArrayBuffer(4));return t.setInt32(0,e),t.getFloat32(0)}class SetAmbientRateExecutor extends TriggerExecutor{execute(e){var t=int32ToFloat32(Number(this.action.params[1]));e.mapLightingTrait.setAmbientChangeRate(t)}}class SetAmbientStepExecutor extends TriggerExecutor{execute(e){var t=int32ToFloat32(Number(this.action.params[1]));e.mapLightingTrait.setAmbientChangeStep(t)}}class TriggerStopSoundFxEvent{constructor(e){this.tile=e,this.type=EventType.TriggerStopSoundFx}}class StopSoundFxAtExecutor extends TriggerExecutor{execute(e){var t=this.action.params[6],i=e.map.getTileAtWaypoint(t);i?e.events.dispatch(new TriggerStopSoundFxEvent(i)):console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class TriggerTextEvent{constructor(e){this.label=e,this.type=EventType.TriggerText}}class TextTriggerExecutor extends TriggerExecutor{execute(e){e.events.dispatch(new TriggerTextEvent(this.action.params[1]))}}class TimerExtendExecutor extends TriggerExecutor{execute(e){e.countdownTimer.addSeconds(Number(this.action.params[1]))}}class TimerSetExecutor extends TriggerExecutor{execute(e){e.countdownTimer.setSeconds(Number(this.action.params[1]))}}class TimerShortenExecutor extends TriggerExecutor{execute(e){e.countdownTimer.addSeconds(-Number(this.action.params[1]))}}class TimerStartExecutor extends TriggerExecutor{execute(e){e.countdownTimer.start()}}class TimerStopExecutor extends TriggerExecutor{execute(e){e.countdownTimer.stop()}}class TimerTextExecutor extends TriggerExecutor{execute(e){e.countdownTimer.text=this.action.params[1]}}class ToggleTriggerExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.triggerEnable=i}execute(e){var t=this.action.params[1];e.triggers.setTriggerEnabled(t,this.triggerEnable)}}class TurnOnOffBuildingExecutor extends TriggerExecutor{constructor(e,t,i){super(e,t),this.turnOn=i}execute(e,t){for(var i of t)i instanceof GameObject&&i.isBuilding()&&i.poweredTrait?.setTurnedOn(this.turnOn)}}class UnrevealAroundWaypointExecutor extends TriggerExecutor{execute(e){var t=Number(this.action.params[1]),i=e.map.getTileAtWaypoint(t);if(i)for(var r of e.getCombatants())e.mapShroudTrait.getPlayerShroud(r)?.unrevealAround(i,e.rules.general.revealTriggerRadius);else console.warn(`No valid location found for waypoint ${t}. `+`Skipping action ${this.getDebugName()}.`)}}class TriggerExecutorFactory{create(e,t){switch(e.type){case TriggerActionType.NoAction:return new NoActionExecutor(e,t);case TriggerActionType.FireSale:return new FireSaleExecutor(e,t);case TriggerActionType.TextTrigger:return new TextTriggerExecutor(e,t);case TriggerActionType.DestroyTrigger:return new DestroyTriggerExecutor(e,t);case TriggerActionType.ChangeHouse:return new ChangeHouseExecutor(e,t);case TriggerActionType.RevealMap:return new RevealMapExecutor(e,t);case TriggerActionType.RevealAroundWaypoint:return new RevealAroundWaypointExecutor(e,t);case TriggerActionType.PlaySoundFx:return new PlaySoundFxExecutor(e,t);case TriggerActionType.PlaySpeech:return new PlaySpeechExecutor(e,t);case TriggerActionType.ForceTrigger:return new ForceTriggerExecutor(e,t);case TriggerActionType.TimerStart:return new TimerStartExecutor(e,t);case TriggerActionType.TimerStop:return new TimerStopExecutor(e,t);case TriggerActionType.TimerExtend:return new TimerExtendExecutor(e,t);case TriggerActionType.TimerShorten:return new TimerShortenExecutor(e,t);case TriggerActionType.TimerSet:return new TimerSetExecutor(e,t);case TriggerActionType.GlobalSet:return new GlobalVariableExecutor(e,t,!0);case TriggerActionType.GlobalClear:return new GlobalVariableExecutor(e,t,!1);case TriggerActionType.DestroyObject:return new DestroyObjectExecutor(e,t);case TriggerActionType.AddOneTimeSuperWeapon:return new AddSuperWeaponExecutor(e,t,!0);case TriggerActionType.AddRepeatingSuperWeapon:return new AddSuperWeaponExecutor(e,t,!1);case TriggerActionType.AllChangeHouse:return new ChangeHouseAllExecutor(e,t);case TriggerActionType.ResizePlayerView:return new ResizePlayerViewExecutor(e,t);case TriggerActionType.PlayAnimAt:return new PlayAnimAtExecutor(e,t);case TriggerActionType.DetonateWarhead:return new DetonateWarheadExecutor(e,t);case TriggerActionType.ReshroudMap:return new ReshroudMapExecutor(e,t);case TriggerActionType.EnableTrigger:return new ToggleTriggerExecutor(e,t,!0);case TriggerActionType.DisableTrigger:return new ToggleTriggerExecutor(e,t,!1);case TriggerActionType.CreateRadarEvent:return new CreateRadarEventExecutor(e,t);case TriggerActionType.LocalSet:return new LocalVariableExecutor(e,t,!0);case TriggerActionType.LocalClear:return new LocalVariableExecutor(e,t,!1);case TriggerActionType.SellBuilding:return new SellBuildingExecutor(e,t);case TriggerActionType.TurnOffBuilding:return new TurnOnOffBuildingExecutor(e,t,!1);case TriggerActionType.TurnOnBuilding:return new TurnOnOffBuildingExecutor(e,t,!0);case TriggerActionType.ApplyOneHundredDamage:return new ApplyDamageExecutor(e,t,100);case TriggerActionType.ForceEnd:return new ForceEndExecutor(e,t);case TriggerActionType.DestroyTag:return new DestroyTagExecutor(e,t);case TriggerActionType.SetAmbientStep:return new SetAmbientStepExecutor(e,t);case TriggerActionType.SetAmbientRate:return new SetAmbientRateExecutor(e,t);case TriggerActionType.SetAmbientLight:return new SetAmbientLightExecutor(e,t);case TriggerActionType.NukeStrike:return new NukeStrikeExecutor(e,t);case TriggerActionType.PlaySoundFxAt:return new PlaySoundFxAtExecutor(e,t);case TriggerActionType.UnrevealAroundWaypoint:return new UnrevealAroundWaypointExecutor(e,t);case TriggerActionType.LightningStrike:return new LightningStrikeExecutor(e,t);case TriggerActionType.TimerText:return new TimerTextExecutor(e,t);case TriggerActionType.CreateCrate:return new CreateCrateExecutor(e,t);case TriggerActionType.IronCurtainAt:return new IronCurtainExecutor(e,t);case TriggerActionType.EvictOccupiers:return new EvictOccupiersExecutor(e,t);case TriggerActionType.Cheer:return new CheerExecutor(e,t);case TriggerActionType.StopSoundsAt:return new StopSoundFxAtExecutor(e,t);default:throw new Error(`Unhandled action type "${TriggerActionType[e.type]}"`)}}}class TriggerCondition{constructor(e,t){this.event=e,this.trigger=t,this.blocking=!1,this.targets=[]}init(e){e=e.getAllPlayers().find(e=>e.country?.name===this.trigger.houseName);e&&(this.player=e)}setTargets(e){this.targets=e}reset(){}getDebugName(){return`${this.event.triggerId}[${this.event.eventIndex}] (${this.trigger.name}).`}}class AmbientLightCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.type=i,this.threshold=Number(e.params[1])/100}check(e){var t=this.previousAmbient,e=e.mapLightingTrait.getAmbient().ambient;return this.previousAmbient=e,void 0!==t&&t!==e&&("above"===this.type?e>=this.threshold&&t<this.threshold:e<=this.threshold&&t>this.threshold)}}class AnyEventCondition extends TriggerCondition{check(e){return!0}}class AttackedByAnyCondition extends TriggerCondition{check(r,e){return e.filter(e=>{if(e.type!==EventType.ObjectAttacked)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;var i=e.attacker?.player;return(!i||!r.alliances.areAllied(i,t.owner)&&i!==t.owner)&&!e.incidental}).map(e=>e.target)}}class AttackedByHouseCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==EventType.ObjectAttacked)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;e=e.attacker?.player;return e&&(-1===this.houseId||e?.country?.id===this.houseId)}).map(e=>e.target)}}class BuildingExistsCondition extends TriggerCondition{constructor(e,t,i=!1){super(e,t),this.negate=i,this.objectIndex=Number(e.params[1])}check(){if(!this.player)return!1;for(var e of this.player.buildings)if(e.rules.index===this.objectIndex)return!this.negate;return this.negate}}class BuildObjectTypeCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.objectType=i,this.objectIndex=Number(e.params[1])}check(e,t){return t.some(e=>e.type===EventType.ObjectSpawn&&e.gameObject.type===this.objectType&&e.gameObject.rules.index===this.objectIndex)}}class ComesNearWaypointCondition extends TriggerCondition{constructor(e,t){super(e,t)}init(e){super.init(e);var t=Number(this.event.params[1]);this.waypointTile=e.map.getTileAtWaypoint(t),this.waypointTile||console.warn(`No valid location found for waypoint ${t}. `+`Skipping event ${this.getDebugName()}.`)}check(t,e){if(!this.waypointTile||!this.player)return!1;for(var i of e)if(i.type===EventType.EnterTile&&i.source.owner===this.player){let e=new RangeHelper(t.map.tileOccupation);if(e.tileDistance(i.target,this.waypointTile)<2)return!0}return!1}}class CreditsBelowCondition extends TriggerCondition{constructor(e,t){super(e,t),this.threshold=Number(e.params[1])}check(e,t){return!!this.player&&this.player.credits<this.threshold}}class CreditsExceedCondition extends TriggerCondition{constructor(e,t){super(e,t),this.threshold=Number(e.params[1])}check(e,t){return!!this.player&&this.player.credits>this.threshold}}class CrossHorizLineCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(t=>t.type===EventType.EnterTile&&t.source.zone!==ZoneType.Air&&this.targets.some(e=>e.ry===t.target.ry)&&(-1===this.houseId||t.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class CrossVertLineCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(t=>t.type===EventType.EnterTile&&t.source.zone!==ZoneType.Air&&this.targets.some(e=>e.rx===t.target.rx)&&(-1===this.houseId||t.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class DestroyedAllBuildingsCondition extends TriggerCondition{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;return!(!t.isBuilding()||t.owner.country?.id!==this.houseId)&&!t.owner.buildings.size})&&(this.allDestroyed=!0)}}class DestroyedAllCondition extends TriggerCondition{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;return!(!t.isTechno()||t.owner.country?.id!==this.houseId)&&!t.owner.getOwnedObjects(!0).length})&&(this.allDestroyed=!0)}}class DestroyedAllUnitsCondition extends TriggerCondition{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;return!(!t.isUnit()||t.owner.country?.id!==this.houseId)&&!this.hasUnitsLeft(t.owner)})&&(this.allDestroyed=!0)}hasUnitsLeft(e){var t;for(t of[ObjectType.Aircraft,ObjectType.Vehicle,ObjectType.Infantry])if(e.getOwnedObjectsByType(t,!0).length)return!0;return!1}}class DestroyedAllUnitsLandCondition extends TriggerCondition{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;return!(!t.isUnit()||t.owner.country?.id!==this.houseId)&&!this.hasLandUnitsLeft(t.owner)})&&(this.allDestroyed=!0)}hasLandUnitsLeft(e){var t;for(t of[ObjectType.Vehicle,ObjectType.Infantry])if(e.getOwnedObjectsByType(t,!0).filter(e=>!e.rules.naval).length)return!0;return!1}}class DestroyedAllUnitsNavalCondition extends TriggerCondition{constructor(e,t){super(e,t),this.allDestroyed=!1,this.houseId=Number(e.params[1])}check(e,t){return!!this.allDestroyed||!!t.some(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;return!(!t.isVehicle()||t.owner.country?.id!==this.houseId)&&!t.owner.getOwnedObjectsByType(ObjectType.Vehicle,!0).filter(e=>e.rules.naval).length})&&(this.allDestroyed=!0)}}class DestroyedBridgeCondition extends TriggerCondition{check(r,e){return e.filter(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;if(!t.isOverlay()||!t.isBridge())return!1;e=t.bridgeTrait?.bridgeSpec;if(!e)return!1;let i=r.map.bridges.findAllBridgeTiles(e);return i.find(e=>this.targets.includes(e))}).map(e=>e.target.tile)}}class DestroyedBuildingsCondition extends TriggerCondition{constructor(e,t){super(e,t),this.count=0,this.threshold=Number(e.params[1])}check(e,t){if(!this.player)return!1;if(this.count>=this.threshold)return!0;for(var i of t)if(i.type===EventType.ObjectDestroy){let e=i.target;e.isBuilding()&&e.owner.country?.id===this.houseId&&this.count++}return this.count>=this.threshold}}class DestroyedByAnyCondition extends TriggerCondition{check(r,e){return e.filter(e=>{if(e.type!==EventType.ObjectDestroy)return!1;let t=e.target;if(!t.isTechno()||!this.targets.includes(t))return!1;var i=e.attackerInfo?.player;return(!i||!r.alliances.areAllied(i,t.owner)&&i!==t.owner)&&!e.incidental}).map(e=>e.target)}}class DestroyedOrCapturedCondition extends TriggerCondition{check(e,t){return t.filter(e=>{if(e.type!==EventType.ObjectDestroy&&e.type!==EventType.ObjectOwnerChange)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))}).map(e=>e.target)}}class DestroyedOrCapturedOrInfiltratedCondition extends TriggerCondition{constructor(){super(...arguments),this.eventsFilter=[EventType.ObjectDestroy,EventType.ObjectOwnerChange,EventType.BuildingInfiltration]}check(e,t){return t.filter(e=>{if(!this.eventsFilter.includes(e.type))return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))}).map(e=>e.target)}}class DestroyedUnitsCondition extends TriggerCondition{constructor(e,t){super(e,t),this.count=0,this.threshold=Number(e.params[1])}check(e,t){if(!this.player)return!1;if(this.count>=this.threshold)return!0;for(var i of t)if(i.type===EventType.ObjectDestroy){let e=i.target;e.isUnit()&&e.owner.country?.id===this.houseId&&this.count++}return this.count>=this.threshold}}class ElapsedScenarioTimeCondition extends TriggerCondition{constructor(e,t){super(e,t),this.timerTicks=Number(this.event.params[1])*GameSpeed.BASE_TICKS_PER_SECOND}check(e){return e.currentTick>this.timerTicks}}class ElapsedTimeCondition extends TriggerCondition{constructor(e,t){super(e,t),this.elapsedTicks=0,this.timerTicks=Number(this.event.params[1])*GameSpeed.BASE_TICKS_PER_SECOND}check(e){return this.elapsedTicks++>this.timerTicks}reset(){this.elapsedTicks=0}}class EnteredByCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(e=>(e.type===EventType.EnterObject||e.type===EventType.EnterTile)&&this.targets.includes(e.target)&&(e.type!==EventType.EnterTile||e.source.zone!==ZoneType.Air)&&(-1===this.houseId||e.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class GlobalVariableCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.value=i,this.blocking=!0,this.variableIdx=Number(e.params[1])}check(e){return e.triggers.getGlobalVariable(this.variableIdx)===this.value}}class HealthBelowAnyCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.threshold=i}check(e,t){return t.filter(e=>{if(e.type!==EventType.HealthChange)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))&&(e.currentHealth<this.threshold&&e.prevHealth>this.threshold)}).map(e=>e.target)}}class HealthBelowCombatCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.threshold=i}check(e,t){return t.filter(e=>{if(e.type!==EventType.InflictDamage)return!1;let t=e.target;return!(!t.isTechno()||!this.targets.includes(t))&&(e.currentHealth<this.threshold&&e.prevHealth>this.threshold)}).map(e=>e.target)}}class LocalVariableCondition extends TriggerCondition{constructor(e,t,i){super(e,t),this.value=i,this.blocking=!0,this.variableIdx=Number(e.params[1])}check(e){return e.triggers.getLocalVariable(this.variableIdx)===this.value}}class LowPowerCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}init(e){super.init(e),this.targetPlayer=e.getAllPlayers().find(e=>e.country?.id===this.houseId)}check(){return!!this.targetPlayer?.powerTrait?.isLowPower()}}class NoEventCondition extends TriggerCondition{check(e){return!1}}class NoFactoriesLeftCondition extends TriggerCondition{check(){if(!this.player)return!1;for(var e of this.player.buildings)if(e.factoryTrait)return!1;return!0}}class PickupCrateAnyCondition extends TriggerCondition{check(e,t){return t.some(e=>e.type===EventType.CratePickup)}}class PickupCrateCondition extends TriggerCondition{check(e,t){return t.filter(e=>e.type===EventType.CratePickup&&this.targets.includes(e.source)).map(e=>e.source)}}class RandomDelayCondition extends TriggerCondition{constructor(){super(...arguments),this.elapsedTicks=0}check(e){return this.timerTicks??(this.timerTicks=Math.floor(e.generateRandomInt(50,150)/100*Number(this.event.params[1]))*GameSpeed.BASE_TICKS_PER_SECOND),this.elapsedTicks++>this.timerTicks}reset(){this.timerTicks=void 0,this.elapsedTicks=0}}class SpiedByCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(this.event.params[1])}check(e,t){return t.filter(e=>e.type===EventType.BuildingInfiltration&&this.targets.includes(e.target)&&(-1===this.houseId||e.source.owner.country?.id===this.houseId)).map(e=>e.target)}}class SpyEnteringAsHouseCondition extends TriggerCondition{constructor(e,t){super(e,t),this.houseId=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==EventType.BuildingInfiltration)return!1;var t=e.target;return!!this.targets.includes(t)&&(-1===this.houseId||e.source.disguiseTrait?.getDisguise()?.owner?.country?.id===this.houseId)}).map(e=>e.target)}}class SpyEnteringAsInfantryCondition extends TriggerCondition{constructor(e,t){super(e,t),this.infantryIdx=Number(e.params[1])}check(e,t){return t.filter(e=>{if(e.type!==EventType.BuildingInfiltration)return!1;var t=e.target;return!!this.targets.includes(t)&&e.source.disguiseTrait?.getDisguise()?.rules.index===this.infantryIdx}).map(e=>e.target)}}class TimerExpiredCondition extends TriggerCondition{check(e,t){return t.some(e=>e.type===EventType.TimerExpire)}}class TriggerConditionFactory{create(e,t){switch(e.type){case TriggerEventType.NoEvent:return new NoEventCondition(e,t);case TriggerEventType.EnteredBy:return new EnteredByCondition(e,t);case TriggerEventType.SpiedBy:return new SpiedByCondition(e,t);case TriggerEventType.AttackedByAny:return new AttackedByAnyCondition(e,t);case TriggerEventType.DestroyedByAny:return new DestroyedByAnyCondition(e,t);case TriggerEventType.AnyEvent:return new AnyEventCondition(e,t);case TriggerEventType.DestroyedAllUnits:return new DestroyedAllUnitsCondition(e,t);case TriggerEventType.DestroyedAllBuildings:return new DestroyedAllBuildingsCondition(e,t);case TriggerEventType.DestroyedAll:return new DestroyedAllCondition(e,t);case TriggerEventType.CreditsExceed:return new CreditsExceedCondition(e,t);case TriggerEventType.ElapsedTime:return new ElapsedTimeCondition(e,t);case TriggerEventType.MissionTimerExpired:return new TimerExpiredCondition(e,t);case TriggerEventType.DestroyedBuildings:return new DestroyedBuildingsCondition(e,t);case TriggerEventType.DestroyedUnits:return new DestroyedUnitsCondition(e,t);case TriggerEventType.NoFactoriesLeft:return new NoFactoriesLeftCondition(e,t);case TriggerEventType.BuildBuilding:return new BuildObjectTypeCondition(e,t,ObjectType.Building);case TriggerEventType.BuildUnit:return new BuildObjectTypeCondition(e,t,ObjectType.Vehicle);case TriggerEventType.BuildInfantry:return new BuildObjectTypeCondition(e,t,ObjectType.Infantry);case TriggerEventType.BuildAircraft:return new BuildObjectTypeCondition(e,t,ObjectType.Aircraft);case TriggerEventType.CrossesHorizontalLine:return new CrossHorizLineCondition(e,t);case TriggerEventType.CrossesVerticalLine:return new CrossVertLineCondition(e,t);case TriggerEventType.GlobalIsSet:return new GlobalVariableCondition(e,t,!0);case TriggerEventType.GlobalIsCleared:return new GlobalVariableCondition(e,t,!1);case TriggerEventType.DestroyedOrCaptured:return new DestroyedOrCapturedCondition(e,t);case TriggerEventType.LowPower:return new LowPowerCondition(e,t);case TriggerEventType.DestroyedBridge:return new DestroyedBridgeCondition(e,t);case TriggerEventType.BuildingExists:return new BuildingExistsCondition(e,t);case TriggerEventType.ComesNearWaypoint:return new ComesNearWaypointCondition(e,t);case TriggerEventType.LocalIsSet:return new LocalVariableCondition(e,t,!0);case TriggerEventType.LocalIsCleared:return new LocalVariableCondition(e,t,!1);case TriggerEventType.FirstDamagedCombat:return new HealthBelowCombatCondition(e,t,100);case TriggerEventType.HalfHealthCombat:return new HealthBelowCombatCondition(e,t,50);case TriggerEventType.QuarterHealthCombat:return new HealthBelowCombatCondition(e,t,25);case TriggerEventType.FirstDamagedAny:return new HealthBelowAnyCondition(e,t,100);case TriggerEventType.HalfHealthAny:return new HealthBelowAnyCondition(e,t,50);case TriggerEventType.QuarterHealthAny:return new HealthBelowAnyCondition(e,t,25);case TriggerEventType.AttackedByHouse:return new AttackedByHouseCondition(e,t);case TriggerEventType.AmbientLightBelow:return new AmbientLightCondition(e,t,"below");case TriggerEventType.AmbientLightAbove:return new AmbientLightCondition(e,t,"above");case TriggerEventType.ElapsedScenarioTime:return new ElapsedScenarioTimeCondition(e,t);case TriggerEventType.DestroyedOrCapturedOrInfiltrated:return new DestroyedOrCapturedOrInfiltratedCondition(e,t);case TriggerEventType.PickupCrate:return new PickupCrateCondition(e,t);case TriggerEventType.PickupCrateAny:return new PickupCrateAnyCondition(e,t);case TriggerEventType.RandomDelay:return new RandomDelayCondition(e,t);case TriggerEventType.CreditsBelow:return new CreditsBelowCondition(e,t);case TriggerEventType.SpyEnteringAsHouse:return new SpyEnteringAsHouseCondition(e,t);case TriggerEventType.SpyEnteringAsInfantry:return new SpyEnteringAsInfantryCondition(e,t);case TriggerEventType.DestroyedAllUnitsNaval:return new DestroyedAllUnitsNavalCondition(e,t);case TriggerEventType.DestroyedAllUnitsLand:return new DestroyedAllUnitsLandCondition(e,t);case TriggerEventType.BuildingNotExists:return new BuildingExistsCondition(e,t,!0);default:throw new Error(`Unhandled trigger event type "${TriggerEventType[e.type]}"`)}}}class TriggerManager{constructor(){this.disposables=new CompositeDisposable,this.triggerInstances=new Map,this.targetsByTag=new Map,this.conditionFactory=new TriggerConditionFactory,this.executorFactory=new TriggerExecutorFactory,this.pendingGameEvents=[],this.globalVariables=new Map,this.localVariables=new Map}init(i){var t,e,r,s,a=i.map.getInitialMapObjects()["technos"];for(let t of a)if(t.tag){let e=this.targetsByTag.get(t.tag);e||(e=[],this.targetsByTag.set(t.tag,e));var n=i.map.tiles.getByMapCoords(t.rx,t.ry);!n||(n=i.map.getObjectsOnTile(n).find(e=>e.name===t.name&&e.type===t.type))&&e.push(n)}for(t of i.map.getCellTags()){var o=i.map.tiles.getByMapCoords(t.coords.x,t.coords.y);if(o){let e=this.targetsByTag.get(t.tagId);e||(e=[],this.targetsByTag.set(t.tagId,e)),e.push(o)}else console.warn(`CellTag out of bounds at (${t.coords.x}, ${t.coords.y}). Skipping.`)}for([e,r]of i.map.getVariables())this.localVariables.set(e,r.clone());for(s of i.map.getTriggers())this.triggerInstances.set(s.id,this.createTriggerInstance(s,i));this.disposables.add(i.events.subscribe(e=>this.pendingGameEvents.push(e)))}createTriggerInstance(i,r){let s=this.targetsByTag.get(i.tag.id)??[];return{trigger:i,conditions:i.events.map(e=>{let t=this.conditionFactory.create(e,i);return t.setTargets(s),t.init(r),t}).sort((e,t)=>Number(t.blocking)-Number(e.blocking)),targets:s,remainingTargets:new Set(i.tag.repeatType===TagRepeatType.OnceAll?s:[]),disabled:i.disabled,finished:!1}}update(i){var r,s=this.pendingGameEvents.splice(0,this.pendingGameEvents.length);for(r of this.triggerInstances.values())if(!r.finished&&!r.disabled){let e=!0,t=[];for(var a of r.conditions){var n=a.check(i,s);if("boolean"==typeof n?n||(e=!1):n.length?t.push(...n):e=!1,a.blocking&&!e)break}if(e){var o=r.trigger;r.conditions.forEach(e=>e.reset?.());let e=[];if(o.tag.repeatType===TagRepeatType.OnceAll){for(var l of t)r.remainingTargets.delete(l);if(r.remainingTargets.size)continue;e=t.length?[t[t.length-1]]:[]}else e=r.targets;this.executeActions(o,e,i),o.tag.repeatType!==TagRepeatType.Repeat&&(r.finished=!0)}}}executeActions(t,i,r){for(var s of t.actions){let e=this.executorFactory.create(s,t);e.execute(r,i)}}setTriggerEnabled(e,t){let i=this.triggerInstances.get(e);i&&(i.disabled=!t)}forceTrigger(e,t){e=this.triggerInstances.get(e);e&&this.executeActions(e.trigger,e.targets,t)}destroyTrigger(e){this.triggerInstances.delete(e)}destroyTag(e){let t=[];for(var[i,r]of this.triggerInstances)r.trigger.tag.id===e&&t.push(i);for(var s of t)this.destroyTrigger(s)}getGlobalVariable(e){return!!this.globalVariables.get(e)?.value}toggleGlobalVariable(e,t){let i=this.globalVariables.get(e);void 0===i?this.globalVariables.set(e,new Variable("No name",t)):i.value=t}getLocalVariable(e){return!!this.localVariables.get(e)?.value}toggleLocalVariable(e,t){let i=this.localVariables.get(e);void 0===i?this.localVariables.set(e,new Variable("No name",t)):i.value=t}dispose(){this.disposables.dispose()}}class TimerExpireEvent{constructor(e){this.target=e,this.type=EventType.TimerExpire}}class CountdownTimer{constructor(){this.ticks=0,this.running=!1}getSeconds(){return Math.floor(this.ticks/GameSpeed.BASE_TICKS_PER_SECOND)}setSeconds(e){this.ticks=Math.max(0,Math.floor(GameSpeed.BASE_TICKS_PER_SECOND*e))}addSeconds(e){this.ticks=Math.max(0,this.ticks+Math.floor(GameSpeed.BASE_TICKS_PER_SECOND*e))}start(){this.running=!0}stop(){this.running=!1}isRunning(){return this.running}update(e){this.running&&(0<this.ticks?this.ticks--:(this.running=!1,e.events.dispatch(new TimerExpireEvent(this))))}}(NotifyObjectTraitAdd=NotifyObjectTraitAdd||{}).onAdd=Symbol(),function(e){e[e.NotStarted=0]="NotStarted",e[e.Started=1]="Started",e[e.Ended=2]="Ended"}(GameStatus=GameStatus||{});class Game{get onEnd(){return this._onEnd.asEvent()}constructor(e,t,i,r,s,a,n,o,l,h,c,u,d,p,g){this.updatableObjects=new Set,this.constructionWorkers=new Map,this.currentTick=0,this.currentTime=0,this.countdownTimer=new CountdownTimer,this._onEnd=new EventDispatcher,this.afterTickCallbacks=[],this.events=new GameEventBus,this.traits=new Traits,this.debugText=new BoxedVar(""),this.world=e,this.map=t,this.rules=i,this.art=r,this.ai=s,this.id=a,this.startTimestamp=n,this.prng=Prng.factory(a,n),this.gameOpts=o,this.gameModeType=l,this.playerList=h,this.unitSelection=c,this.alliances=u,this.desiredSpeed=new BoxedVar(GameSpeed.computeGameSpeed(o.gameSpeed)),this.speed=new BoxedVar(this.desiredSpeed.value),this.nextObjectId=d,this.objectFactory=p,this.botManager=g,this.triggers=new TriggerManager}addPlayer(e){this.playerList.addPlayer(e),this.constructionWorkers.set(e,this.createConstructionWorker(e))}getPlayer(e){return this.playerList.getPlayerAt(e)}getPlayerByName(e){return this.playerList.getPlayerByName(e)}getAiPlayerName(e){let t;return t="number"==typeof e?e:this.gameOpts.aiPlayers.indexOf(e),`@@AI${t+1}@@`}getPlayerNumber(e){return this.playerList.getPlayerNumber(e)}getCombatants(){return this.playerList.getCombatants()}getCivilianPlayer(){return this.playerList.getCivilian()}getAllPlayers(){return this.playerList.getAll()}getNonNeutralPlayers(){return this.playerList.getNonNeutral()}areFriendly(e,t){return e.owner===t.owner||this.alliances.areAllied(e.owner,t.owner)}getWorld(){return this.world}createConstructionWorker(e){return new ConstructionWorker(e,this.rules,this.art,this.map,this)}getConstructionWorker(e){var t=this.constructionWorkers.get(e);if(!t)throw new Error(`No construction worker found for player "${e.name}"`);return t}getUnitSelection(){return this.unitSelection}init(e){this.localPlayer=e,this.createMapObjects(),this.createPlayerInitialUnits(),this.map.terrain.computeAllPassabilityGraphs(),this.mapShroudTrait.init(this),this.crateGeneratorTrait.init(this),this.playerList.getAll().forEach(e=>e.credits=this.gameOpts.credits),this.rules.mpDialogSettings.alliesAllowed&&this.createInitialTeams(),this.botManager.init(this),this.triggers.init(this)}start(){this.status=GameStatus.Started,this.currentTick=0,this.currentTime=0,this.botManager.onGameStart()}createInitialTeams(){for(let t=0;t<this.gameOpts.maxSlots;t++){var i=[...this.gameOpts.humanPlayers,...this.gameOpts.aiPlayers].filter(e=>e?.teamId===t&&e.countryId!==OBS_COUNTRY_ID).map(e=>isHumanPlayerInfo(e)?e.name:this.getAiPlayerName(e));if(1<i.length)for(let t=0;t<i.length-1;t++)for(let e=t+1;e<i.length;e++){var r=this.getPlayerByName(i[t]),s=this.getPlayerByName(i[e]),s=this.alliances.setAlliance(r,s,AllianceStatus.Formed);this.onAllianceChange(s,r,!0)}}}createMapObjects(){var e=this.rules.general.harvesterUnit.every(e=>!isBetween(this.rules.getObject(e,ObjectType.Vehicle).techLevel,0,this.rules.mpDialogSettings.techLevel)),t=this.map.getInitialMapObjects();this.createInitialMapTerrains(t.terrains,e),this.createInitialMapOverlays(t.overlays,e),this.createInitialMapSmudges(t.smudges),this.createInitialMapTechnos(t.technos)}createInitialMapTerrains(e,t){for(var i of e){var r,s,a=i.name;this.validateMapObjectRulesAndArt(a,ObjectType.Terrain)&&((r=this.map.tiles.getByMapCoords(i.rx,i.ry))?(s=this.rules.getObject(a,ObjectType.Terrain),t&&s.spawnsTiberium||(a=this.createObject(ObjectType.Terrain,a),this.spawnObject(a,r))):console.warn(`Invalid map object location (${i.rx},${i.ry})`,i))}}createInitialMapOverlays(e,r){let s=new Map,a=new Map;for(var n of e){var o=this.rules.getOverlayName(n.id);if(this.validateMapObjectRulesAndArt(o,ObjectType.Overlay)){let e=this.createObject(ObjectType.Overlay,o);e.overlayId=n.id,e.value=n.value;let t=n.rx,i=n.ry;e.isBridge()&&e.isHighBridge()&&(e.position.tileElevation=4,t+=e.isXBridge()?0:-1,i+=e.isXBridge()?-1:0);var l=this.map.tiles.getByMapCoords(t,i);if(l)if(e.rules.tiberium&&(o=OreOverlayTypes.getOverlayTibType(n.id),void 0!==(o=OreSpread.calculateOverlayId(o,l))&&o!==n.id&&(e.dispose(),e=this.createObject(ObjectType.Overlay,this.rules.getOverlayName(o)),e.overlayId=o,e.value=n.value)),BridgeOverlayTypes.isLowBridge(n.id))BridgeOverlayTypes.isBridgePlaceholder(n.id)||(s.set(l,n.value),1===n.value?a.set(l,e):e.dispose());else{if(e.isTiberium()){if(![OverlayTibType.Ore,OverlayTibType.Gems,OverlayTibType.Vinifera].includes(OreOverlayTypes.getOverlayTibType(e.overlayId))){console.warn(`Found unsupported TS tiberium overlay ${e.overlayId} @${l.rx},${l.ry}. Skipping.`);continue}if(this.map.getObjectsOnTile(l).find(e=>e.isTerrain())){e.dispose();continue}}r&&e.isTiberium()?e.dispose():this.spawnObject(e,l)}else console.warn(`Invalid map object location (${t},${i})`,n),e.dispose()}}for(var[t,i]of a){var h=i.isXBridge(),c=this.map.tiles.getByMapCoords(t.rx+(h?0:-1),t.ry+(h?-1:0)),h=this.map.tiles.getByMapCoords(t.rx+(h?0:1),t.ry+(h?1:0));c&&h&&(0===s.get(c)||2===s.get(h))?(i.value=0,this.spawnObject(i,c)):(i.dispose(),console.warn(`Invalid bridge segment @${t.rx},${t.ry}. Skipping.`))}var u,d=[...a.keys()].filter(e=>this.map.bridges.getPieceAtTile(e)?.headType!==BridgeHeadType.None),e=this.map.bridges.findMapHighBridgeHeadTiles();let p=this.map.bridges.findBridgeSpecsForHeadTiles([...d,...e]);for(u of p)for(var g of this.map.bridges.findBridgePieces(u))g.obj.bridgeTrait.bridgeSpec=u;var m,e=p.map(e=>this.map.bridges.findAllBridgeTiles(e)).flat(),y=BridgeOverlayTypes.bridgePlaceholderIds[0],T=this.rules.getOverlayName(y);for(m of e){let e=this.createObject(ObjectType.Overlay,T);e.overlayId=y,this.spawnObject(e,m)}}createInitialMapSmudges(e){for(var t of e){var i=t.name,r=this.map.tiles.getByMapCoords(t.rx,t.ry);r?(i=this.createObject(ObjectType.Smudge,i),this.spawnObject(i,r)):console.warn(`Invalid map object location (${t.rx},${t.ry})`,t)}}createInitialMapTechnos(e){let t=new Map(this.playerList.getAll().filter(e=>!!e.country).map(e=>[e.country.name,e])),r=this.map.getTags();for(let i of e){var s=i.name;if(this.validateMapObjectRulesAndArt(s,i.type)){var a=this.map.tiles.getByMapCoords(i.rx,i.ry);if(a){var n=t.get(i.owner);if(n){if(n.isNeutral){let t=this.createObject(i.type,s);i.tag&&(t.tag=r.find(e=>e.id===i.tag)),t.healthTrait.health=i.health/256*100;let e=!1;if(!t.healthTrait.health){if(!t.isBuilding()||!t.rules.leaveRubble){t.dispose();continue}e=!0}if(i.isInfantry()||i.isVehicle()||i.isAircraft()){t.direction=(-i.direction/256*360+360)%360,i.isInfantry()&&(t.position.subCell=i.subCell);let e=!1;i.onBridge&&(void 0===a.onBridgeLandType?console.warn(`Cannot place unit "${i.name}" on a bridge because `+`no bridge was found at ${a.rx}, `+a.ry):e=!0),t.onBridge=e,t.zone=getZoneType(e?a.onBridgeLandType:a.landType),e&&(t.position.tileElevation+=this.map.tileOccupation.getBridgeOnTile(a)?.tileElevation??0),i.veterancy&&t.veteranTrait?.setRelativeXP(i.veterancy)}else t.poweredTrait?.setTurnedOn(i.poweredOn);this.changeObjectOwner(t,n),this.spawnObject(t,a),e&&this.destroyObject(t,void 0,!0)}}else console.warn(`Invalid owner "${i.owner}" for map object`,i)}else console.warn(`Invalid map object location (${i.rx},${i.ry})`,i)}}}validateMapObjectRulesAndArt(e,t){return this.rules.hasObject(e,t)?!!this.art.hasObject(e,t)||(console.warn(`Map object '${e}' has no art section. Skipping.`),!1):(console.warn(`Map object '${e}' has no rules section. Skipping.`),!1)}createPlayerInitialUnits(){let e=this.playerList.getCombatants().map(e=>e.country);var i=[...this.rules.infantryRules.values(),...this.rules.vehicleRules.values()].filter(t=>t.allowedToStartInMultiplayer&&!t.naval&&-1!==t.techLevel&&t.techLevel<=this.rules.mpDialogSettings.techLevel&&!this.rules.general.baseUnit.includes(t.name)&&e.some(e=>t.isAvailableTo(e)&&t.hasOwner(e)));for(let l of this.playerList.getCombatants()){var h=this.map.startingLocations[l.startLocation],c=this.map.tiles.getByMapCoords(h.x,h.y);let t=this.rules.general.baseUnit.find(e=>{let t=this.rules.getObject(e,ObjectType.Vehicle);return t.isAvailableTo(l.country)&&t.hasOwner(l.country)});if(!t)throw new Error("No suitable MCV found for player country "+l.country?.name);h=this.rules.getObject(t,ObjectType.Vehicle),h=this.createUnitForPlayer(h,l);this.spawnObject(h,c);let e=StartingUnitsGenerator.generate(this.gameOpts.unitCount,[...this.rules.vehicleRules.keys()],i,l.country);this.gameModeType===GameModeType.Unholy&&e.push(...this.rules.general.baseUnit.filter(e=>e!==t).map(e=>({name:e,type:ObjectType.Vehicle,count:1})));var u,d,p;let r=[],s=!1,a=new CardinalTileFinder(this.map.tiles,this.map.mapBounds,c,4,4,e=>!this.map.getGroundObjectsOnTile(e).find(e=>!(e.isSmudge()||e.isOverlay()&&e.isTiberium()))&&0<this.map.terrain.getPassableSpeed(e,SpeedType.Foot,!1,!1)),n=new Map,o=0;for({name:u,type:d,count:p}of e){let i=p;for(;0<i;){let t;if(s||(t=a.getNextTile(),t?r.push(t):s=!0),s&&r.length){var g=r[o];let e=n.get(g);e||(e=new CardinalTileFinder(this.map.tiles,this.map.mapBounds,g,1,0,e=>!this.map.getGroundObjectsOnTile(e).find(e=>!(e.isSmudge()||e.isOverlay()&&e.isTiberium()))&&0<this.map.terrain.getPassableSpeed(e,SpeedType.Foot,!1,!1)),n.set(g,e)),o=(o+1)%r.length,t=e.getNextTile()}if(t){var m,y=this.rules.getObject(u,d);if(d===ObjectType.Vehicle){g=this.createUnitForPlayer(y,l);this.applyInitialVeteran(g,l),this.spawnObject(g,t),i--}else{if(d!==ObjectType.Infantry)throw new Error("Should not reach this line");for(m of Infantry_Infantry.SUB_CELLS.slice(0,i)){let e=this.createUnitForPlayer(y,l);e.position.subCell=m,this.applyInitialVeteran(e,l),this.spawnObject(e,t),i--}}}else i--}}}}applyInitialVeteran(e,t){e.veteranTrait&&(this.rules.general.veteran.initialVeteran?e.veteranTrait.setVeteranLevel(VeteranLevel.Elite):t.country.hasVeteranUnit(e.type,e.name)&&e.veteranTrait.setVeteranLevel(VeteranLevel.Veteran))}createObject(e,t){return this.objectFactory.create(e,t,this.rules,this.art)}createUnitForPlayer(e,t){if(![ObjectType.Aircraft,ObjectType.Vehicle,ObjectType.Infantry].includes(e.type))throw new Error(`Attempted to create an invalid unit type "${e.type}"`);let i=this.createObject(e.type,e.name);return this.changeObjectOwner(i,t),i.purchaseValue=this.sellTrait.computePurchaseValue(i.rules,t),i}createProjectile(e,t,i,r,s){let a=this.createObject(ObjectType.Projectile,e);return a.fromWeapon=i,a.fromObject=t,a.fromPlayer=t.owner,a.target=r,a.isShrapnel=s,a}createLooseProjectile(e,t,i){var r=this.rules.getWeapon(e),s=r.projectile,a=this.rules.getProjectile(s),e=this.rules.getWarhead(r.warhead),e={minRange:0,projectileRules:a,range:Number.POSITIVE_INFINITY,rules:r,speed:Weapon.computeSpeed(r,a),type:WeaponType.Primary,warhead:new Warhead(e)};let n=this.createObject(ObjectType.Projectile,s);return n.fromWeapon=e,n.fromObject=void 0,n.fromPlayer=t,n.target=i,n}createSuperWeapon(e,t,i=!1){var r=this.rules.getSuperWeapon(e);return new SuperWeapon(e,r,t,i)}createTarget(e,t){return new Target(e,t,this.map.tileOccupation)}isValidTarget(e){if(e){if(!e.isSpawned||e.isCrashing)return!1;if(!(e.rules.legalTarget||e.isBuilding()&&e.rules.hospital))return!1;if(e.isBuilding()&&e.rules.invisibleInGame)return!1}return!0}spawnObject(e,t){if(e.isTechno()&&e.limboData)throw new Error(`Object ${e.name}#${e.id} is in limbo. Use unlimboObject instead or clear limboData first`);this.doSpawnObject(e,t)}unspawnObject(e){e.isTechno()&&e.owner&&e.owner.removeOwnedObject(e),this.doUnspawnObject(e)}limboObject(e,t){e.limboData=t,this.doUnspawnObject(e)}unlimboObject(e,t,i=!1){var r=e.limboData;if(!r)throw new Error(`Object ${e.name}#${e.id} has no limboData attached`);e.limboData=void 0,this.doSpawnObject(e,t);let s=this.getUnitSelection();r.selected&&!i&&s.addToSelection(e),void 0!==r.controlGroup&&s.addUnitsToGroup(r.controlGroup,[e],!1)}doSpawnObject(t,e){var i,r;t.position.tile=e,t.isBuilding()&&(r=t.art.foundationCenter,i=e.rx+r.x,r=e.ry+r.y,t.centerTile=this.map.tiles.getByMapCoords(i,r)??this.map.tiles.getPlaceholderTile(i,r)),this.world.spawnObject(t),(t.cachedTraits.tick.length||t.isProjectile()||t.isDebris()||t.isTechno())&&this.updatableObjects.add(t),t.isTechno()&&this.map.technosByTile.add(t),t.isProjectile()||t.isDebris()||this.map.tileOccupation.occupyTileRange(e,t),t.art.canHideThings&&this.map.tileOcclusion.addOccluder(t),t.onSpawn(this),this.traits.filter(NotifySpawn_NotifySpawn).forEach(e=>{e[NotifySpawn_NotifySpawn.onSpawn](t,this)}),this.events.dispatch(new ObjectSpawnEvent(t))}doUnspawnObject(t){var e=t.tile;t.isProjectile()||t.isDebris()||this.map.tileOccupation.unoccupyTileRange(e,t),t.art.canHideThings&&this.map.tileOcclusion.removeOccluder(t),t.isTechno()&&(this.unitSelection.cleanupUnit(t),this.map.technosByTile.remove(t)),this.world.removeObject(t),this.updatableObjects.delete(t),t.onUnspawn(this),this.traits.filter(NotifyUnspawn_NotifyUnspawn).forEach(e=>{e[NotifyUnspawn_NotifyUnspawn.onUnspawn](t,this)}),this.events.dispatch(new ObjectUnspawnEvent(t))}destroyObject(t,i,e=!1,r=!1){if(t.isDestroyed)throw new Error(`Object with ID "${t.id}" is already destroyed`);if(t.isTechno()){let e=t.mindControllableTrait?.getOriginalOwner()??t.owner;!i||t.isBuilding()&&!e.isCombatant()||(i.player.addUnitsKilled(t.type,1),i.player===e||this.alliances.areAllied(i.player,e)||(i.player.score+=t.rules.points)),e.isNeutral||e.addUnitsLost(t.type,1)}if(t.isDestroyed=!0,t.healthTrait&&(t.healthTrait.health=0),t.onDestroy(this,i,e),this.traits.filter(NotifyDestroy_NotifyDestroy).forEach(e=>{e[NotifyDestroy_NotifyDestroy.onDestroy](t,this,i)}),i?.obj?.traits.filter(NotifyTargetDestroy).forEach(e=>{e[NotifyTargetDestroy.onDestroy](i.obj,t,i.weapon,this)}),this.events.dispatch(new ObjectDestroyEvent(t,i,r)),t.isBuilding()&&t.rules.leaveRubble&&t.deathType!==DeathType.Temporal){t.owner.removeOwnedObject(t),this.unitSelection.cleanupUnit(t);r=this.map.tileOccupation.calculateTilesForGameObject(t.tile,t);this.map.terrain.invalidateTiles(r),t.art.canHideThings&&this.map.tileOcclusion.removeOccluder(t),this.updatableObjects.delete(t),t.onUnspawn(this),this.traits.filter(NotifyUnspawn_NotifyUnspawn).forEach(e=>{e[NotifyUnspawn_NotifyUnspawn.onUnspawn](t,this)}),this.events.dispatch(new ObjectUnspawnEvent(t))}else if(t.isSpawned)this.unspawnObject(t);else if(t.isTechno()&&t.owner){if(!t.limboData)throw new Error(`Object with ID "${t.id}" should be in limbo but has no limboData`);t.owner.removeOwnedObject(t)}t.dispose()}getObjectById(e){return this.world.getObjectById(e)}changeObjectOwner(t,e){const i=t.owner;i&&i.removeOwnedObject(t),e.addOwnedObject(t),i&&i!==e&&(this.traits.filter(NotifyOwnerChange_NotifyOwnerChange).forEach(e=>{e[NotifyOwnerChange_NotifyOwnerChange.onChange](t,i,this)}),t.onOwnerChange(i,this),this.events.dispatch(new ObjectOwnerChangeEvent(t,i)),i===this.localPlayer&&t.owner!==this.localPlayer&&(this.unitSelection.removeFromSelection([t]),this.unitSelection.removeUnitsFromGroup([t])))}addObjectTrait(t,i){t.addTrait(i),this.traits.filter(NotifyObjectTraitAdd).forEach(e=>{e[NotifyObjectTraitAdd.onAdd](t,i,this)})}onAllianceChange(t,e,i){this.events.dispatch(new AllianceChangeEvent(t,i?AllianceEventType.Formed:AllianceEventType.Broken,e)),this.traits.filter(NotifyAllianceChange).forEach(e=>{e[NotifyAllianceChange.onChange](t,i,this)})}update(){if(this.status!==GameStatus.NotStarted){this.botManager.update(this),this.status!==GameStatus.Ended&&(void 0===this.lastGameEndCheck||1e3<=this.currentTime-this.lastGameEndCheck)&&(this.checkGameEndConditions(),this.lastGameEndCheck=this.currentTime);for(var e of[...this.updatableObjects])e.isSpawned&&e.update(this);if(this.playerList.getCombatants().forEach(e=>e.cheerCooldownTicks=Math.max(0,e.cheerCooldownTicks-1)),this.traits.filter(NotifyTick).forEach(e=>{e[NotifyTick.onTick](this)}),this.localPlayer&&!this.localPlayer.isObserver&&!this.localPlayer.defeated){var t=this.unitSelection.getSelectedUnits();if(1===t.length){let i=t[0];if(i.isTechno()&&i.owner!==this.localPlayer){let t=this.mapShroudTrait.getPlayerShroud(this.localPlayer);this.map.tileOccupation.calculateTilesForGameObject(i.tile,i).find(e=>!t.isShrouded(e,i.tileElevation))||(this.unitSelection.deselectAll(),this.unitSelection.cleanupUnit(i))}}}for(var i of this.afterTickCallbacks)i();this.afterTickCallbacks.length=0,this.triggers.update(this),this.countdownTimer.update(this),this.currentTick++,this.currentTime+=1e3/GameSpeed.BASE_TICKS_PER_SECOND}}afterTick(e){this.afterTickCallbacks.push(e)}checkGameEndConditions(){this.updateDefeatedPlayers(this.playerList.getCombatants()),(this.localPlayer?.defeated&&!this.localPlayer.isObserver||!this.alliances.getHostilePlayers().length&&1<this.gameOpts.humanPlayers.length+this.gameOpts.aiPlayers.filter(e=>!!e).length)&&this.end()}end(){this.status!==GameStatus.Ended&&(this.status=GameStatus.Ended,this._onEnd.dispatch(this,void 0))}updateDefeatedPlayers(e){let r=this.stalemateDetectTrait?.isStale()&&0===this.stalemateDetectTrait.getCountdownTicks(),s=this.gameOpts.shortGame;e.forEach(t=>{let i;if(r)i=!0;else{let e;e=s?(e=[...t.getOwnedObjectsByType(ObjectType.Building,!0)].some(e=>!e.rules.insignificant),e||t.getOwnedObjects(!0).some(e=>this.rules.general.baseUnit.includes(e.name))):t.getOwnedObjects(!0).some(e=>!e.rules.insignificant&&!e.limboData?.inTransport),i=!e}var e;i&&(t.defeated=!0,(e=this.alliances.getHostilePlayers().some(e=>!e.first.isAi||!e.second.isAi))&&(t.isObserver=!0),this.removeAllPlayerAssets(t),this.events.dispatch(new PlayerDefeatedEvent(t)),e&&(this.mapShroudTrait.getPlayerShroud(t)?.revealAll(),e=t.radarTrait.isDisabled(),t.radarTrait.setDisabled(!1),e&&this.events.dispatch(new RadarOnOffEvent(t,!0))))})}removeAllPlayerAssets(e){e.getOwnedObjects().forEach(e=>{e.isDestroyed||(e.isBuilding()&&e.rules.returnable&&e.rules.needsEngineer&&!e.garrisonTrait?this.changeObjectOwner(e,this.getCivilianPlayer()):e.isBuilding()&&e.wallTrait||this.destroyObject(e,void 0,!0))}),e.getOwnedObjects(!0).forEach(e=>{e.isDestroyed||(e.limboData?.inTransport||e.isBuilding()&&e.wallTrait?this.changeObjectOwner(e,this.getCivilianPlayer()):this.destroyObject(e,void 0,!0))})}redistributeAllPlayerAssets(e){if(e.isObserver)return!1;if(!(this.rules.mpDialogSettings.mustAlly&&!this.rules.mpDialogSettings.allyChangeAllowed))return!1;let t=this.alliances.getAllies(e).filter(e=>!e.isAi&&!e.defeated);if(0<t.length){var i,r=[...t].sort((e,t)=>t.score-e.score)[0];for(i of e.getOwnedObjects(!0))this.changeObjectOwner(i,r);var s,a=Math.floor(e.credits/t.length),e=e.credits%t.length;for(s of t)s.credits+=a;return t[0].credits+=e,!0}return!1}generateRandomInt(e,t){return this.prng.generateRandomInt(e,t)}generateRandom(){return this.prng.generateRandom()}getHash(){return fnv32a([...new Uint8Array(new Float64Array([this.prng.getLastRandom()]).buffer),this.nextObjectId.value,...this.world.getAllObjects().map(e=>e.getHash()),...this.playerList.getAll().map(e=>e.getHash()),this.alliances.getHash(),...this.traits.getAll().map(e=>e.getHash?.()??0)])}debugGetState(){return{currentTick:this.currentTick,lastRandom:this.prng.getLastRandom(),nextObjectId:this.nextObjectId.value,objects:this.world.getAllObjects().map(e=>e.debugGetState()),players:this.playerList.getAll().map(e=>e.debugGetState()),alliances:this.alliances.debugGetState(),traits:this.traits.getAll().reduce((e,t)=>{var i=t.debugGetState?.();return void 0!==i&&(e[t.constructor.name]=i),e},{})}}dispose(){this.world.getAllObjects().forEach(e=>e.dispose()),this.playerList.getAll().forEach(e=>e.dispose()),this.constructionWorkers.forEach(e=>e.dispose()),this.botManager.dispose(),this.triggers.dispose(),this.map.dispose(),this.traits.dispose()}}const RAD_LEVEL_CAP=1e3,PERCENT_AT_MAX=0;class MapRadiationTrait{get onChange(){return this._onChange.asEvent()}constructor(e){this.map=e,this.radSites=new Map,this.radLevelByTile=new Map,this._onChange=new EventDispatcher}getRadLevel(e){return this.radLevelByTile.get(e)}[NotifyTick.onTick](e){var t;this.radLevelByTile.size&&(t=e.rules.radiation,void 0===this.nextDamage?this.nextDamage=Math.max(0,t.radApplicationDelay-1):this.nextDamage<=0?(this.applyDamage(e),this.nextDamage=Math.max(0,t.radApplicationDelay)):this.nextDamage--,void 0===this.nextDecay?this.nextDecay=Math.max(0,t.radLevelDelay-1):this.nextDecay<=0?(this.applyDecay(Math.ceil(t.radLevelDelay/t.radDurationMultiple)),this.radLevelByTile.size?this.nextDecay=Math.max(0,t.radLevelDelay):this.nextDecay=void 0):this.nextDecay--)}applyDamage(a){let n=a.rules.radiation,o=new Warhead(a.rules.getWarhead(n.radSiteWarhead));this.radLevelByTile.forEach((e,t)=>{var i,r,s=Math.min(n.radLevelMax,e)*n.radLevelFactor;for(i of a.map.getGroundObjectsOnTile(t).filter(e=>e.isUnit()&&!(e.isInfantry()&&e.stance===StanceType.Paradrop&&1<e.tileElevation)))o.canDamage(i,t,i.zone)&&(0<(r=o.computeDamage(s,i,a))&&o.inflictDamage(r,i,void 0,a,!0))})}applyDecay(r){var e=new Set(this.radLevelByTile.keys());this.radLevelByTile.clear(),this.radSites.forEach(({radLevel:e,radius:t},i)=>{e-=r;e<=0?this.radSites.delete(i):(this.radSites.set(i,{radLevel:e,radius:t}),this.setRadLevelAround(i,t,e))}),this._onChange.dispatch(this,e)}createRadSite(e,t,i){(t-=this.radSites.get(e)?.radLevel??0)<=0||(this.radSites.set(e,{radLevel:(this.radSites.get(e)?.radLevel??0)+t,radius:i}),(t=this.setRadLevelAround(e,i,t)).size&&this._onChange.dispatch(this,t))}setRadLevelAround(e,t,i){let r=new RangeHelper(this.map.tileOccupation),s=new RadialTileFinder(this.map.tiles,this.map.mapBounds,e,{width:1,height:1},0,t,e=>!!e,!1);var a;let n=new Set;for(;a=s.getNextTile();){var o=r.tileDistance(e,a);o<=t&&(o=Math.ceil(lerp(i,i*PERCENT_AT_MAX,o/t)),this.radLevelByTile.set(a,Math.min(RAD_LEVEL_CAP,(this.radLevelByTile.get(a)??0)+o)),n.add(a))}return n}getRadSiteLevel(e){return this.radSites.get(e)?.radLevel}}class ActionFactory{constructor(){this.factories=new Map}registerFactory(e,t){this.factories.set(e,t)}create(e){let t=this.factories.get(e);if(!t)throw new Error("No factory registered for action type "+e);return t.create()}}class UnitSelectionLite{constructor(e){this.player=e,this.selectedUnits=new Set}update(e){var t,i=[...e].reverse().find(e=>e.owner!==this.player);i&&(e=[i]),this.selectedUnits.clear();for(t of e)t.rules.selectable&&this.selectedUnits.add(t)}getSelectedUnits(){return[...this.selectedUnits].map(e=>e.isDisposed&&e.replacedBy?e.replacedBy:e).filter(e=>!e.isDestroyed&&!e.isCrashing)}isSelected(e){return this.selectedUnits.has(e)}}class OrderActionContext{constructor(){this.unitSelectionByPlayer=new Map}getOrCreateSelection(e){let t=this.unitSelectionByPlayer.get(e);return t||(t=new UnitSelectionLite(e),this.unitSelectionByPlayer.set(e,t)),t}}!function(e){e[e.NoAction=0]="NoAction",e[e.DropPlayer=1]="DropPlayer",e[e.ObserveGame=2]="ObserveGame",e[e.ResignGame=3]="ResignGame",e[e.DebugCommand=4]="DebugCommand",e[e.PlaceBuilding=5]="PlaceBuilding",e[e.SellObject=6]="SellObject",e[e.ToggleRepair=7]="ToggleRepair",e[e.SelectUnits=8]="SelectUnits",e[e.OrderUnits=9]="OrderUnits",e[e.UpdateQueue=10]="UpdateQueue",e[e.ToggleAlliance=11]="ToggleAlliance",e[e.ActivateSuperWeapon=12]="ActivateSuperWeapon",e[e.PingLocation=13]="PingLocation"}(ActionType=ActionType||{});class Action{constructor(e){this.actionType=e}unserialize(e){}serialize(){return new Uint8Array}print(){return""}}class NoAction extends Action{constructor(){super(ActionType.NoAction)}process(){}}class NoActionFactory{create(){return new NoAction}}class BuildingPlaceEvent{constructor(e){this.target=e,this.type=EventType.BuildingPlace}}class BuildingFailedPlaceEvent{constructor(e,t,i){this.name=e,this.player=t,this.tile=i,this.type=EventType.BuildingFailedPlace}}(NotifyPlaceBuilding=NotifyPlaceBuilding||{}).onPlace=Symbol();class PlaceBuildingAction extends Action{constructor(e){super(ActionType.PlaceBuilding),this.game=e}unserialize(e){let t=new DataStream(e);this.buildingRules=this.game.rules.getTechnoByInternalId(t.readUint32(),ObjectType.Building),this.tile={x:t.readUint16(),y:t.readUint16()}}serialize(){let e=new DataStream(8);return e.writeUint32(this.buildingRules.index),e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),e.toUint8Array()}print(){return`Place building ${this.buildingRules.name} at tile (${this.tile.x}, ${this.tile.y})`}process(){var e=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);if(e){var t=this.player;const i=this.tryPlaceBuilding(t,e);i?(this.game.traits.filter(NotifyPlaceBuilding).forEach(e=>{e[NotifyPlaceBuilding.onPlace](i,this.game)}),this.game.events.dispatch(new BuildingPlaceEvent(i))):this.game.events.dispatch(new BuildingFailedPlaceEvent(this.buildingRules.name,t,e))}else console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}tryPlaceBuilding(r,s){var a=this.buildingRules;if(r.production){let i=r.production.getQueueForObject(a);if(i.status===QueueStatus.Ready&&i.getFirst().rules===a){let t=this.game.getConstructionWorker(r);if(r.production.isAvailableForProduction(a)&&t.canPlaceAt(a.name,s,{normalizedTile:!0})){s=t.placeAt(a.name,s,!0);r.addUnitsBuilt(a,1),i.shift(a,1);let e=r.production.getPrimaryFactory(FactoryType.BuildingType);return e&&(e.factoryTrait.status=FactoryStatus.Delivering),s[0]}}}}}class PlaceBuildingActionFactory{constructor(e){this.game=e}create(){return new PlaceBuildingAction(this.game)}}class SellObjectAction extends Action{constructor(e){super(ActionType.SellObject),this.game=e}unserialize(e){this.objectId=new DataStream(e).readUint32()}serialize(){return new DataStream(4).writeUint32(this.objectId).toUint8Array()}print(){return"Sell object "+this.objectId}process(){var t=this.player;if(this.game.getWorld().hasObjectId(this.objectId)){let e=this.game.getObjectById(this.objectId);e.isTechno()&&t===e.owner&&e.isSpawned&&(e.isBuilding()?e.buildStatus===BuildStatus.Ready&&!e.warpedOutTrait.isActive():e.traits.find(DockableTrait)?.dock?.rules.unitSell)&&this.game.sellTrait.sell(e)}}}class SellObjectActionFactory{constructor(e){this.game=e}create(){return new SellObjectAction(this.game)}}const orderPriorities=[OrderType.Occupy,OrderType.Dock,OrderType.Attack,OrderType.Capture,OrderType.Repair,OrderType.EnterTransport,OrderType.PlaceBomb,OrderType.Deploy,OrderType.Gather];!function(e){e[e.Default=0]="Default",e[e.Mini=1]="Mini",e[e.Scroll=2]="Scroll",e[e.NoScroll=10]="NoScroll",e[e.Select=18]="Select",e[e.Move=31]="Move",e[e.NoMove=41]="NoMove",e[e.MoveMini=42]="MoveMini",e[e.NoActionMini=52]="NoActionMini",e[e.AttackRange=53]="AttackRange",e[e.AttackNoRange=58]="AttackNoRange",e[e.AttackMini=63]="AttackMini",e[e.Guard=68]="Guard",e[e.GuardMini=73]="GuardMini",e[e.Unknown1=78]="Unknown1",e[e.Unknown2=88]="Unknown2",e[e.Occupy=89]="Occupy",e[e.NoOccupy=99]="NoOccupy",e[e.OccupyMini=100]="OccupyMini",e[e.Deploy=110]="Deploy",e[e.NoDeploy=119]="NoDeploy",e[e.Unknown3=120]="Unknown3",e[e.Sell=129]="Sell",e[e.SellMini=139]="SellMini",e[e.NoSell=149]="NoSell",e[e.RepairMove=150]="RepairMove",e[e.SideRepair=170]="SideRepair",e[e.NoRepair=190]="NoRepair",e[e.Unknown4=191]="Unknown4",e[e.Unknown5=199]="Unknown5",e[e.Dynamite=204]="Dynamite",e[e.Unknown6=209]="Unknown6",e[e.Unknown7=214]="Unknown7",e[e.Unknown8=219]="Unknown8",e[e.Unknown9=224]="Unknown9",e[e.Unknown10=229]="Unknown10",e[e.Unknown11=234]="Unknown11",e[e.Unknwon12=239]="Unknwon12",e[e.Unknown13=249]="Unknown13",e[e.Para=259]="Para",e[e.Unknown14=269]="Unknown14",e[e.Storm=279]="Storm",e[e.EngineerDamage=299]="EngineerDamage",e[e.C4=309]="C4",e[e.Nuke=319]="Nuke",e[e.Unknown16=329]="Unknown16",e[e.Power=339]="Power",e[e.Unknown17=345]="Unknown17",e[e.Iron=346]="Iron",e[e.Unknown18=351]="Unknown18",e[e.Unknown19=356]="Unknown19",e[e.Chrono=357]="Chrono",e[e.DefuseBomb=369]="DefuseBomb",e[e.NoAction=384]="NoAction",e[e.Pan=385]="Pan",e[e.Unknown21=394]="Unknown21",e[e.AttackMove=404]="AttackMove",e[e.Unknown23=413]="Unknown23",e[e.Unknown24=422]="Unknown24",e[e.Unknown25=431]="Unknown25",e[e.Unknown26=432]="Unknown26",e[e.Unknown27=433]="Unknown27",e[e.Unknown28=434]="Unknown28",e[e.Beacon=435]="Beacon",e[e.ForceField=450]="ForceField",e[e.NoForceField=460]="NoForceField",e[e.Mutate=470]="Mutate",e[e.AirStrike=480]="AirStrike",e[e.Dominate=488]="Dominate",e[e.PsychicReveal=496]="PsychicReveal",e[e.SpyPlane=504]="SpyPlane",e[e.SpyPlaneMini=512]="SpyPlaneMini",e[e.NukeMini=513]="NukeMini",e[e.StormMini=514]="StormMini",e[e.PsychicRevealMini=515]="PsychicRevealMini",e[e.DominateMini=516]="DominateMini"}(PointerType=PointerType||{}),function(e){e[e.None=0]="None",e[e.Move=1]="Move",e[e.Attack=2]="Attack",e[e.Enter=3]="Enter",e[e.Capture=4]="Capture",e[e.SpecialAttack=5]="SpecialAttack"}(OrderFeedbackType=OrderFeedbackType||{});class Order{constructor(e){this.orderType=e,this.targetOptional=!0,this.minimapAllowed=!0,this.singleSelectionRequired=!1,this.terminal=!1,this.feedbackType=OrderFeedbackType.None}getPointerType(e,t){return e?PointerType.Mini:PointerType.Default}set(e,t){return this.sourceObject=e,this.target=t,this}isValid(){return!0}isAllowed(){return!0}onAdd(e,t){return!0}}class ObjectMorphEvent{constructor(e,t){this.from=e,this.to=t,this.type=EventType.ObjectMorph}}class MorphIntoTask extends Task{constructor(e){super(),this.game=e}onStart(e){if(!this.morphInto)throw new Error("morphInto not set");e.isBuilding()&&e.buildStatus!==BuildStatus.BuildDown&&this.morphInto.type!==ObjectType.Building&&this.children.push(new PackBuildingTask(this.game)),e.isVehicle()&&this.morphInto.type===ObjectType.Building&&this.children.push(new TurnTask(180))}onTick(t){if(!this.morphInto)throw new Error("morphInto not set");let e=this.game.getUnitSelection();var i=e.isSelected(t),r=e.getOrCreateSelectionModel(t).getControlGroupNumber(),s=this.morphInto;let a;if(s.type===ObjectType.Building){if(t.isVehicle()&&t.parasiteableTrait?.isInfested()&&!t.parasiteableTrait.beingBoarded)return!0;var n=t.tile;let e=this.game.getConstructionWorker(t.owner);if(!e.canPlaceAt(this.morphInto.name,n,{ignoreAdjacent:!0,ignoreObjects:[t]}))return!0;this.game.unspawnObject(t),t.dispose(),[a]=e.placeAt(this.morphInto.name,n),a.healthTrait.health=t.healthTrait.health}else{let e=t.unitOrderTrait.getTasks().filter(e=>e instanceof MoveTask);this.game.unspawnObject(t),t.dispose(),a=this.game.createUnitForPlayer(this.morphInto,t.owner),a.direction=180,a.healthTrait.health=t.healthTrait.health;n=t.art.foundationCenter;this.game.spawnObject(a,this.game.map.tiles.getByMapCoords(t.tile.rx+n.x,t.tile.ry+n.y)),e.forEach(e=>a.unitOrderTrait.addTask(e))}return a.purchaseValue=t.purchaseValue,t.replacedBy=a,i&&e.addToSelection(a),void 0!==r&&e.addUnitsToGroup(r,[a],!1),this.game.events.dispatch(new ObjectMorphEvent(t,a)),!0}}class UndeployIntoTask extends MorphIntoTask{onStart(e){var t=e.rules.undeploysInto;if(!t)throw new Error(`Object type "${e.name}" doesn't undeploy into anything`);this.morphInto=this.game.rules.getObject(t,ObjectType.Vehicle),super.onStart(e)}}class RallyPointChangeEvent{constructor(e){this.target=e,this.type=EventType.RallyPointChange}}class MoveToBlockTask extends Task{constructor(e,t){super(),this.game=e,this.target=t,this.preventOpportunityFire=!1,this.useChildTargetLines=!0,this.attackPerformed=!1}onStart(e){this.children.push(new MoveTask(this.game,this.target.centerTile,!1,{closeEnoughTiles:1,pathFinderIgnoredBlockers:[this.target],stopOnBlocker:this.target}))}onTick(e){if(this.attackPerformed||this.isCancelling()||!e.attackTrait||e.attackTrait.isDisabled())return!0;if(e.moveTrait.lastMoveResult!==MoveResult.CloseEnough)return!0;var t=e.attackTrait.selectWeaponVersus(e,this.target,this.game,!0);return!t||(this.children.push(e.attackTrait.createAttackTask(this.game,this.target,this.target.tile,t,{force:!0})),!(this.attackPerformed=!0))}}const TARGET_UPDATE_TILES=10;class MoveTargetTask extends MoveTask{constructor(e,t){super(e,t.tile,t.onBridge,{forceMove:!0,pathFinderIgnoredBlockers:[t]}),this.target=t,this.tilesSinceTargetUpdate=0}onTick(t){if(!(this.isCancelling()||t.moveTrait.moveState!==MoveState.ReachedNextWaypoint||this.target.tile===this.targetTile&&this.target.onBridge===this.toBridge&&this.target.moveTrait.isIdle())){let e=!1;var i;(t.tile===this.targetTile&&this.target.tile!==this.targetTile||this.tilesSinceTargetUpdate++>TARGET_UPDATE_TILES)&&(e=!0),e&&(this.tilesSinceTargetUpdate=0,(i=this.target.moveTrait.currentWaypoint)?this.updateTarget(i.tile,!!i.onBridge):this.updateTarget(this.target.tile,this.target.onBridge))}return super.onTick(t)}forceCancel(e){return super.forceCancel(e)}getTargetLinesConfig(e){return{target:this.target,pathNodes:[]}}}class MoveOrder extends Order{constructor(e,t,i,r=!1){super(r?OrderType.ForceMove:OrderType.Move),this.game=e,this.map=t,this.unitSelection=i,this.forceMove=r,this.targetOptional=!1,this.feedbackType=OrderFeedbackType.Move}getPointerType(e){let t=this.isAllowed();var i,r,s,a,n;return!t||this.forceMove||this.sourceObject.isBuilding()||this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)||(i=!!this.target.getBridge(),r=this.sourceObject.rules.speedType,s=this.sourceObject.isInfantry(),a=this.sourceObject.rules.movementZone===MovementZone.Fly,n=this.map.getObjectsOnTile(this.target.tile).some(e=>(e.isInfantry()||e.isVehicle())&&e.disguiseTrait?.hasTerrainDisguise()),t=a?this.sourceObject.rules.airportBound||this.target.tile.landType===LandType.Cliff||0<this.map.terrain.getPassableSpeed(this.target.tile,SpeedType.Amphibious,!1,i)&&!n:0<this.map.terrain.getPassableSpeed(this.target.tile,r,s,i)&&!n&&!(this.target.obj?.isTechno()&&!this.game.areFriendly(this.target.obj,this.sourceObject))),e?t?PointerType.MoveMini:PointerType.NoActionMini:t?PointerType.Move:PointerType.NoMove}isValid(){return!(this.sourceObject.isBuilding()&&(!this.sourceObject.rules.undeploysInto||this.sourceObject.rules.constructionYard&&!this.game.gameOpts.mcvRepacks)&&!this.sourceObject.rallyTrait?.getRallyPoint())&&(this.forceMove||!this.target.obj||(this.target.obj.isOverlay()||this.target.obj.isBuilding())&&this.target.obj.rules.wall||this.target.obj.isTechno()&&this.target.obj.owner===this.sourceObject.owner&&this.unitSelection.isSelected(this.target.obj)||(this.target.obj.isInfantry()||this.target.obj.isVehicle())&&!!this.target.obj.disguiseTrait?.hasTerrainDisguise()||this.target.obj.isTechno()&&!this.game.areFriendly(this.target.obj,this.sourceObject))}isAllowed(){return(!this.sourceObject.isUnit()||!this.sourceObject.moveTrait.isDisabled())&&(this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)?this.sourceObject.rules.moveToShroud:!(!this.forceMove&&this.target.obj?.isTechno()&&this.target.obj.owner===this.sourceObject.owner&&this.unitSelection.isSelected(this.target.obj)))}process(){const e=this.sourceObject;if(!e.isBuilding()||!e.rallyTrait?.getRallyPoint()){var t=this.game.rules.general.closeEnough;return e.isBuilding()&&e.rules.undeploysInto?[new UndeployIntoTask(this.game),new MoveTask(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:t,forceMove:this.forceMove})]:e.isUnit()?this.isEnemyBuildingBlock()?[new MoveToBlockTask(this.game,this.target.obj)]:this.isFollowMove()?[new MoveTargetTask(this.game,this.target.obj)]:[new MoveTask(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:t,forceMove:this.forceMove})]:void 0}}isEnemyBuildingBlock(){return this.forceMove&&this.sourceObject.isVehicle()&&!this.sourceObject.rules.consideredAircraft&&this.target.obj?.isBuilding()&&!this.game.areFriendly(this.sourceObject,this.target.obj)}isFollowMove(){return this.forceMove&&this.target.obj?.isInfantry()&&this.sourceObject.isVehicle()&&!this.sourceObject.rules.consideredAircraft&&!this.target.obj.moveTrait.isIdle()}onAdd(t,e){var i=this.sourceObject.isBuilding()&&this.sourceObject.rules.undeploysInto;if(i&&this.sourceObject.buildStatus===BuildStatus.BuildUp)return this.sourceObject.unitOrderTrait.getTasks().find(e=>e instanceof WaitForBuildUpTask)?.setCancellable(!0),!0;if(!i&&this.sourceObject.isBuilding()&&this.sourceObject.rallyTrait?.getRallyPoint())return this.sourceObject.rallyTrait.changeRallyPoint(this.target.tile,this.sourceObject,this.game),this.game.events.dispatch(new RallyPointChangeEvent(this.sourceObject)),!1;if(!this.isEnemyBuildingBlock()&&!this.isFollowMove()&&!e&&this.isValid()&&this.isAllowed()){this.sourceObject.attackTrait?.cancelOpportunityFire();let e=t.find(e=>e.constructor===MoveTask&&!e.isCancelling());if(e)return e.setForceMove(this.forceMove),e.updateTarget(this.target.tile,!!this.target.getBridge(),!0),e.children.length&&e.children[0]instanceof AttackTask&&e.children[0].cancel(),t.splice(t.indexOf(e)+1),this.sourceObject.unitOrderTrait.clearOrders(),!1;if(this.sourceObject.isUnit()&&this.sourceObject.rules.movementZone===MovementZone.Fly){let e=t.find(e=>[AttackTask,AttackMoveTask,AttackMoveTargetTask].includes(e.constructor)&&!e.isCancelling());e&&e.forceCancel(this.sourceObject)&&t.splice(t.indexOf(e))}}return!0}}class DeployIntoTask extends MorphIntoTask{onStart(e){var t=e.rules.deploysInto;if(!t)throw new Error(`Object type "${e.name}" doesn't deploy into anything`);this.morphInto=this.game.rules.getObject(t,ObjectType.Building),super.onStart(e)}onTick(e){return!!this.isCancelling()||super.onTick(e)}}class UnitDeployUndeployEvent{constructor(e,t){this.unit=e,this.deployType=t,this.type=EventType.UnitDeployUndeploy}}class PrimaryFactoryChangeEvent{constructor(e){this.target=e,this.type=EventType.PrimaryFactoryChange}}!function(e){e[e.None=0]="None",e[e.OnlyPassengers=1]="OnlyPassengers",e[e.All=2]="All"}(EvacState=EvacState||{});const MAX_EVAC_TRIES=3;class EvacuateTransportTask extends Task{constructor(e,t){super(),this.game=e,this.soft=t,this.evacState=EvacState.None,this.evacTries=0,this.turnPerformed=!1,this.preventLanding=!1}forceEvac(){this.evacState=EvacState.All}onStart(e){if(!e.transportTrait)throw new Error(`Object "${e.name}" is not a valid transport`);var t=e.transportTrait;0<t.units.length&&(this.evacState=this.evacState!==EvacState.OnlyPassengers&&1!==t.units.length||!e.rules.gunner?EvacState.OnlyPassengers:EvacState.All)}onTick(e){if(this.isCancelling()||this.evacState===EvacState.None)return!0;if(e.zone===ZoneType.Air)return this.children.push(new CallbackTask(()=>e.zone!==ZoneType.Air)),!1;let t=e.transportTrait.units;if(!t.length||e.rules.gunner&&1===t.length&&this.evacState!==EvacState.All)return!0;var i=t[t.length-1],r=this.findValidEvacTarget(e,i);if(r&&!this.turnPerformed){this.turnPerformed=!0;var s=(r.dir+180)%360;if(e.direction!==s)return this.children.push(new TurnTask(s)),!1}return this.evacuateUnit(i,e,r)?(t.pop(),this.children.push(new WaitMinutesTask(1/60)),!1):!(++this.evacTries<=MAX_EVAC_TRIES)||(this.children.push(new WaitMinutesTask(.05)),!1)}evacuateUnit(e,t,i){if(!i)return!this.soft&&(e.position.tile=t.tile,e.position.tileElevation=t.tileElevation,e.onBridge=t.onBridge,e.zone=t.zone,this.game.destroyObject(e,{player:e.owner}),!0);var{spawnNode:r,moveNode:i}=i;return e.position.tileElevation=r.onBridge?.tileElevation??0,e.onBridge=!!r.onBridge,e.zone=this.game.map.getTileZone(r.tile,!r.onBridge),this.game.unlimboObject(e,r.tile),e.unitOrderTrait.unmarkNextQueuedOrder(),i?e.unitOrderTrait.addTask(new MoveTask(this.game,i.tile,!!i.onBridge)):e.unitOrderTrait.addTask(new ScatterTask(this.game)),this.game.events.dispatch(new LeaveTransportEvent(t)),!0}findValidEvacTarget(a,n){let o=this.game.map,l=new MovePositionHelper(o);var h,c,u,d,p,t=a.onBridge?o.tileOccupation.getBridgeOnTile(a.tile):void 0,i=(a.direction+180)%360;let g;for(let e=0;e<=180;e+=45)for(h of e&&e<180?[i+e,i-e]:[i]){var m=FacingUtil.toMapCoords(h);let i=a.tile,r=t,s;for(let t=1;t<=2;t++){if(2===t){if(!s)break;i=s.tile,r=s.onBridge}var y,T=a.tile.rx+Math.sign(m.x)*t,f=a.tile.ry+Math.sign(m.y)*t,v=o.tiles.getByMapCoords(T,f);if(!v||!o.mapBounds.isWithinBounds(v))break;let e=[o.tileOccupation.getBridgeOnTile(v)];e[0]&&e.push(void 0);for(y of e)if(c=v,u=y,d=r,p=i,0<o.terrain.getPassableSpeed(c,n.rules.speedType,n.isInfantry(),!!u)&&l.isEligibleTile(c,u,d,p)&&!o.terrain.findObstacles({tile:c,onBridge:u},n).length){if(1!==t)return{spawnNode:s,moveNode:{tile:v,onBridge:y},dir:h};s={tile:v,onBridge:y},g={spawnNode:s,moveNode:void 0,dir:h}}}}if(g)return g}}class DeployOrder extends Order{constructor(e,t){super(t?OrderType.Deploy:OrderType.DeploySelected),this.game=e,this.targeted=t,this.minimapAllowed=!1,this.getPointerType=()=>this.isAllowed()?PointerType.Deploy:PointerType.NoDeploy,this.targetOptional=!t,this.singleSelectionRequired=t}isValid(){if(this.targeted&&(!this.target.obj||this.target.obj!==this.sourceObject))return!1;let e=this.sourceObject;return!!(e.isInfantry()&&e.deployerTrait&&![StanceType.Cheer].includes(e.stance)||e.isVehicle()&&e.deployerTrait||e.isVehicle()&&e.rules.deploysInto||e.isVehicle()&&e.transportTrait||e.isBuilding()&&e.rules.factory&&!e.owner.production?.isPrimaryFactory(e)||e.isBuilding()&&e.garrisonTrait?.units.length)}isAllowed(){let t=this.sourceObject;if(t.isVehicle()&&t.transportTrait)return!!(t.transportTrait.units.length&&0<this.game.map.terrain.getPassableSpeed(t.tile,SpeedType.Foot,!1,t.onBridge));if((t.isInfantry()||t.isVehicle())&&t.deployerTrait)return!0;if(t.isVehicle()&&t.rules.deploysInto){if(t.parasiteableTrait?.isInfested()&&!t.parasiteableTrait.beingBoarded)return!1;let e=this.game.getConstructionWorker(t.owner);if(t.moveTrait.currentWaypoint?.onBridge)return!1;var i=t.moveTrait.currentWaypoint?.tile??t.tile;return e.canPlaceAt(t.rules.deploysInto,i,{ignoreObjects:[t],ignoreAdjacent:!0})}if(t.isBuilding()&&t.rules.factory)return!0;if(t.isBuilding()&&t.garrisonTrait?.units.length)return!0;throw new Error("Shouldn't reach this point. Missed a case.")}process(){const e=this.sourceObject;return e.isVehicle()&&e.transportTrait?[new EvacuateTransportTask(this.game,!0)]:e.isBuilding()&&e.rules.factory?void 0:e.isVehicle()&&e.rules.deploysInto?[new DeployIntoTask(this.game)]:(e.isInfantry()||e.isVehicle())&&e.deployerTrait?[new CallbackTask(()=>{e.deployerTrait.toggleDeployed(),this.game.events.dispatch(new UnitDeployUndeployEvent(e,e.deployerTrait.isDeployed()?"undeploy":"deploy"))})]:e.isBuilding()&&e.garrisonTrait?.units.length?[new CallbackTask(()=>{e.garrisonTrait.evacuate(this.game,!0)})]:void 0}onAdd(t,e){let i=this.sourceObject;if(i.isBuilding()&&i.rules.factory)return i.owner.production.setPrimaryFactory(i),this.game.events.dispatch(new PrimaryFactoryChangeEvent(i)),!1;if(i.isVehicle()&&i.transportTrait&&!e&&this.isValid()&&this.isAllowed()){let e=t.find(e=>e.constructor===EvacuateTransportTask&&!e.isCancelling());if(e)return e.forceEvac(),!1}return!0}}class CheerEvent{constructor(e){this.player=e,this.type=EventType.Cheer}}class DeployNotAllowedEvent{constructor(e){this.target=e,this.type=EventType.DeployNotAllowed}}const ORDER_UNIT_LIMIT=128;class OrderUnitsAction extends Action{constructor(e,t,i,r){super(ActionType.OrderUnits),this.game=e,this.map=t,this.orderActionContext=i,this.orderFactory=r,this.queue=!1,this.isInvalid=!1}unserialize(t){let i=new DataStream(t);this.orderType=i.readUint8();var r=i.readUint8();if(0!==r){var s=i.readUint16(),t=i.readUint16();this.queue=2<r&&Boolean(i.readUint8());let e;if(3<r){r=i.readUint32();if(!this.game.getWorld().hasObjectId(r))return void(this.isInvalid=!0);e=this.game.getObjectById(r)}else e=void 0;t=this.map.tiles.getByMapCoords(s,t);t?this.target=this.game.createTarget(e,t):this.isInvalid=!0}}serialize(){let e=new DataStream(11);e.dynamicSize=!1,e.writeUint8(this.orderType);let t=0;e.writeUint8(t),this.target&&(e.writeUint16(this.target.tile.rx),e.writeUint16(this.target.tile.ry),t+=2,i=(this.target.obj||this.target.getBridge())?.id,!this.queue&&void 0===i||(e.writeUint8(Number(this.queue)),t+=1),void 0!==i&&(e.writeUint32(i),t+=1));var i=e.position;return 0<t&&(e.seek(1),e.writeUint8(t)),new Uint8Array(e.buffer,e.byteOffset,i)}print(){return this.isInvalid?"":OrderType[this.orderType]+" order "+(this.target?`[obj: ${(this.target.obj||this.target.getBridge())?.name||"<none>"}, `+`tile: ${this.target.tile.rx},${this.target.tile.ry}]`+(this.queue?"(queue)":""):"")}process(){if(!this.isInvalid){let n=this.player;const c=this.game.mapShroudTrait.getPlayerShroud(n);if(c){const u=this.target?.obj;if(u){let e=this.game.map.tileOccupation.calculateTilesForGameObject(u.tile,u);if(!e.find(e=>!c.isShrouded(e,u.tileElevation)))return}let e=this.validateOrders(n).slice(0,ORDER_UNIT_LIMIT),a=[],t=[],r=[],i=[],s=[];if(e.forEach(e=>{(e instanceof MoveOrder?t:e.orderType===OrderType.Scatter?r:e.orderType===OrderType.DeploySelected?i:e.orderType===OrderType.Cheer?s:a).push(e)}),t.length&&this.target){var o=t[0].isEnemyBuildingBlock(),l=t[0].isFollowMove();if(o||l)t.forEach(e=>a.push(e));else{let r=this.target.getBridge();var h=t[0].forceMove,l=t.map(e=>e.sourceObject);let s=new MovePositionHelper(this.map).findPositions(l,this.target.tile,r,h);t.forEach(e=>{var t=s.get(e.sourceObject),i=!r||r.isHighBridge()?this.map.tileOccupation.getBridgeOnTile(t):r,t=this.game.createTarget(i,t);e.target=t,a.push(e)})}}if(r.length){h=r.map(e=>e.sourceObject).filter(e=>e.isInfantry()||e.isVehicle());let i=new ScatterPositionHelper(this.game).findPositions(h);r.forEach(e=>{var t=i.get(e.sourceObject);t&&(t=this.game.createTarget(t.onBridge,t.tile),e.target=t,a.push(e))})}if(i.length){let t=[];i.forEach(e=>{((e.sourceObject.isInfantry()||e.sourceObject.isVehicle())&&e.sourceObject.deployerTrait?t:a).push(e)});let e=t.filter(e=>!e.sourceObject.deployerTrait.isDeployed());e.length?e.forEach(e=>a.push(e)):t.forEach(e=>a.push(e))}s.length&&(n.cheerCooldownTicks||(n.cheerCooldownTicks=this.game.rules.general.maximumCheerRate,a.push(...s),this.game.events.dispatch(new CheerEvent(n)))),a.forEach(e=>e.sourceObject.unitOrderTrait.addOrder(e,this.queue)),this.updateWaypointPaths(a)}}}validateOrders(e){let i=this.orderActionContext.getOrCreateSelection(e);var r,s=i.getSelectedUnits();let t=this.orderFactory.create(this.orderType,i);t.target=this.target;let a=[];for(r of s)if(!(r.owner!==e||r.rules.spawned||r.isDestroyed||r.isCrashing||r.isDisposed||r.warpedOutTrait.isActive()||(t.sourceObject=r,t instanceof DeployOrder&&t.isValid()&&!t.isAllowed()&&this.game.events.dispatch(new DeployNotAllowedEvent(r)),t.singleSelectionRequired&&1<s.length)))if(t.isValid()&&t.isAllowed()){let e=this.orderFactory.create(this.orderType,i);e.set(r,this.target),a.push(e)}else{let t=!1;for(var n of orderPriorities){let e=this.orderFactory.create(n,i);if(e.set(r,this.target),!(e.singleSelectionRequired&&1<s.length)&&(e.targetOptional===!this.target&&e.isValid()&&e.isAllowed())){a.push(e),t=!0;break}}if(!t&&this.target&&this.orderType!==OrderType.Deploy){let e=this.orderFactory.create(OrderType.Move,i);e.set(r,this.target),e.isValid()&&e.isAllowed()&&a.push(e)}}return a}updateWaypointPaths(i){if(this.queue&&this.target){let e=i.map(e=>e.sourceObject);var t=[...new Set(e.map(e=>e.unitOrderTrait.waypointPath).filter(isNotNullOrUndefined))];if(t.length<=1){i={orderType:this.orderType,target:this.target,terminal:i.some(e=>e.terminal),next:void 0};if(0===t.length){let t={units:e,waypoints:[i]};e.forEach(e=>{e.unitOrderTrait.waypointPath=t})}else{let e=t[0];e.waypoints[e.waypoints.length-1].next=i,e.waypoints.push(i)}}}}}class SelectUnitsAction extends Action{get unitIds(){return this._unitIds}set unitIds(e){this._unitIds=e.slice(0,ORDER_UNIT_LIMIT)}constructor(e,t){super(ActionType.SelectUnits),this.orderActionContext=t}unserialize(t){let i=new DataStream(t);this.unitIds=new Array(t.byteLength/4);for(let e=0;e<t.byteLength/4;e++)this.unitIds[e]=i.readUint32()}serialize(){let e=new DataStream(4*this.unitIds.length);e.dynamicSize=!1;for(var t of this.unitIds)e.writeUint32(t);return e.toUint8Array()}print(){return`Select unit(s) [${this.unitIds.join(",")}]`}process(){let e=this.player,t=[];for(var i of this.unitIds){i=e.getOwnedObjectById(i);i&&t.push(i)}this.orderActionContext.getOrCreateSelection(e).update(t)}}class SelectUnitsActionFactory{constructor(e,t){this.game=e,this.orderActionContext=t}create(){return new SelectUnitsAction(this.game,this.orderActionContext)}}class BuildingGarrisonEvent{constructor(e){this.target=e,this.type=EventType.BuildingGarrison}}class MoveOutsideTask extends MoveTask{constructor(e,t,i){super(e,i??t.tile,!1,{ignoredBlockers:[t]}),this.target=t,this.cancellable=!1}canStopAtTile(e,t,i){return!this.game.map.tileOccupation.isTileOccupiedBy(t,this.target)&&super.canStopAtTile(e,t,i)}}class MoveInsideTask extends MoveTask{static chooseTargetFoundationTile(t,i){if(t.isBuilding()){let e=t.centerTile;return i.map.mapBounds.isWithinBounds(e)||(e=i.map.tileOccupation.calculateTilesForGameObject(t.tile,t).find(e=>i.map.mapBounds.isWithinBounds(e))??t.tile),e}return t.tile}constructor(e,t){super(e,MoveInsideTask.chooseTargetFoundationTile(t,e),!1,{ignoredBlockers:[t],closeEnoughTiles:0}),this.target=t}hasReachedDestination(e){return super.hasReachedDestination(e)||this.canStopAtTile(e,e.tile,e.onBridge)}canStopAtTile(e,t,i){t=this.game.map.tileOccupation.isTileOccupiedBy(t,this.target);return(!this.isCancelling()||!t)&&!(!this.isCancelling()&&!t)}isCloseEnoughToDest(e,t,i){return this.game.map.tileOccupation.isTileOccupiedBy(t,this.target)}}class EnterObjectEvent{constructor(e,t){this.target=e,this.source=t,this.type=EventType.EnterObject}}class EnterBuildingTask extends Task{constructor(e,t){super(),this.game=e,this.target=t,this.aborted=!1,this.movePerformed=!1,this.preventOpportunityFire=!1}onTick(e){return!!(this.isCancelling()&&!this.movePerformed||this.aborted||e.moveTrait.isDisabled())||(this.movePerformed&&this.children.length?(e.tile===this.lastOutsideTile||this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)||(this.lastOutsideTile=e.tile),!1):this.game.map.tileOccupation.isTileOccupiedBy(e.tile,this.target)?!this.isAllowed(e)||this.isCancelling()?(this.children.push(new MoveOutsideTask(this.game,this.target,this.lastOutsideTile)),!(this.aborted=!0)):(this.game.events.dispatch(new EnterObjectEvent(this.target,e)),!1!==this.onEnter(e)||(this.children.push(new MoveOutsideTask(this.game,this.target,this.lastOutsideTile)),!(this.aborted=!0))):!!this.movePerformed||(this.children.push(new MoveInsideTask(this.game,this.target).setBlocking(!1)),this.movePerformed=!0,!(this.preventOpportunityFire=!0)))}getTargetLinesConfig(e){return{target:this.target,pathNodes:[]}}}class GarrisonBuildingTask extends EnterBuildingTask{isAllowed(e){return!this.target.isDestroyed&&!!this.target.garrisonTrait?.canBeOccupied()&&this.target.garrisonTrait.units.length<this.target.garrisonTrait.maxOccupants&&!(this.target.garrisonTrait.units.length&&this.target.garrisonTrait.units[0].owner!==e.owner)&&!e.mindControllableTrait?.isActive()}onEnter(e){this.game.limboObject(e,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(e).getControlGroupNumber()});let t=this.target.garrisonTrait;t.units.length||(e.owner.buildingsCaptured++,this.game.changeObjectOwner(this.target,e.owner),this.game.events.dispatch(new BuildingGarrisonEvent(this.target))),t.units.push(e)}}class UnitRecycleEvent{constructor(e){this.target=e,this.type=EventType.UnitRecycle}}class EnterRecyclerTask extends EnterBuildingTask{isAllowed(e){return e.rules.movementZone!==MovementZone.Fly&&e.rules.locomotor!==LocomotorType.Chrono&&!e.rules.engineer&&0<this.game.sellTrait.computeRefundValue(e)&&(e.isInfantry()&&this.target.rules.cloning||this.target.rules.grinding)&&!this.target.isDestroyed&&this.target.buildStatus===BuildStatus.Ready&&e.owner===this.target.owner}onEnter(e){this.game.sellTrait.sell(e),this.game.events.dispatch(new UnitRecycleEvent(e))}}class BuildingInfiltrationEvent{constructor(e,t){this.target=e,this.source=t,this.type=EventType.BuildingInfiltration}}class InfiltrateBuildingTask extends EnterBuildingTask{isAllowed(e){return e.rules.infiltrate&&this.target.rules.spyable&&!this.target.isDestroyed&&!this.game.areFriendly(e,this.target)}onEnter(e){this.game.unspawnObject(e),e.agentTrait?.infiltrate(e,this.target,this.game),this.game.events.dispatch(new BuildingInfiltrationEvent(this.target,e))}}!function(e){e[e.MoveToQueueingTile=0]="MoveToQueueingTile",e[e.WaitForTurn=1]="WaitForTurn",e[e.MoveToTarget=2]="MoveToTarget",e[e.EnterTarget=3]="EnterTarget",e[e.ClearTarget=4]="ClearTarget"}(EnterHospitalTask_State=EnterHospitalTask_State||{});class EnterHospitalTask extends Task{constructor(e,t){super(),this.game=e,this.target=t,this.movePerformed=!1}isAllowed(e){return e.rules.movementZone!==MovementZone.Fly&&e.healthTrait.health<100&&this.target.hospitalTrait&&!this.target.isDestroyed&&!this.target.warpedOutTrait.isActive()&&this.game.areFriendly(e,this.target)&&(!this.target.ammoTrait||0<this.target.ammoTrait.ammo)}onStart(e){if(!this.target.hospitalTrait)throw new Error(`Target ${this.target.name} is not a valid hospital`);0<this.target.hospitalTrait.addToHealQueue(e)?this.state=EnterHospitalTask_State.MoveToQueueingTile:this.state=EnterHospitalTask_State.MoveToTarget}onEnd(e){!this.target.isDestroyed&&e.isSpawned&&this.target.hospitalTrait.removeFromHealQueue(e)}onTick(i){if(this.isCancelling()&&this.state!==EnterHospitalTask_State.EnterTarget||this.state===EnterHospitalTask_State.ClearTarget||i.moveTrait.isDisabled())return!0;if(this.state===EnterHospitalTask_State.MoveToQueueingTile){let t=new MovePositionHelper(this.game.map);var e=new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>0<this.game.map.terrain.getPassableSpeed(e,i.rules.speedType,i.isInfantry(),!1)&&t.isEligibleTile(e,void 0,void 0,this.target.tile)).getNextTile();return!e||(this.children.push(new MoveTask(this.game,e,!1,{closeEnoughTiles:5})),this.children.push(new CallbackTask(()=>{[MoveResult.Success,MoveResult.CloseEnough].includes(i.moveTrait.lastMoveResult)||this.cancel()})),this.state=EnterHospitalTask_State.WaitForTurn,this.queueingTile=e,!1)}if(this.state===EnterHospitalTask_State.WaitForTurn){if(!this.target.hospitalTrait.unitIsFirstInHealQueue(i))return!1;this.queueingTile=void 0,this.state=EnterHospitalTask_State.MoveToTarget}if(this.state===EnterHospitalTask_State.MoveToTarget){if(this.movePerformed&&this.children.length)return i.tile===this.lastOutsideTile||this.game.map.tileOccupation.isTileOccupiedBy(i.tile,this.target)||(this.lastOutsideTile=i.tile),!1;if(!this.isAllowed(i))return!0;if(!this.game.map.tileOccupation.isTileOccupiedBy(i.tile,this.target))return!!this.movePerformed||(this.children.push(new MoveInsideTask(this.game,this.target).setBlocking(!1)),!(this.movePerformed=!0));this.state=EnterHospitalTask_State.EnterTarget}return this.state===EnterHospitalTask_State.EnterTarget&&(!this.isAllowed(i)||this.isCancelling()?(this.children.push(new MoveOutsideTask(this.game,this.target,this.lastOutsideTile)),this.state=EnterHospitalTask_State.ClearTarget,!1):(this.game.limboObject(i,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(i).getControlGroupNumber()}),this.target.hospitalTrait.startHealing(i),this.game.events.dispatch(new EnterObjectEvent(this.target,i)),!0))}getTargetLinesConfig(e){return{target:this.queueingTile?void 0:this.target,pathNodes:this.queueingTile?[{tile:this.queueingTile,onBridge:void 0}]:[]}}}class OccupyOrder extends Order{constructor(e){super(OrderType.Occupy),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=OrderFeedbackType.Capture}getPointerType(e){return e?this.isAllowed()?PointerType.OccupyMini:PointerType.NoActionMini:this.isAllowed()?PointerType.Occupy:PointerType.NoOccupy}isValid(){return!!(this.target.obj?.isSpawned&&this.target.obj?.isBuilding()&&this.sourceObject.isUnit())&&(!!this.isUnitRecycle(this.sourceObject,this.target.obj)||!!this.sourceObject.isInfantry()&&(this.target.obj.isBuilding()&&this.target.obj.hospitalTrait?this.game.areFriendly(this.sourceObject,this.target.obj)&&this.sourceObject.isInfantry():this.target.obj.garrisonTrait?this.target.obj.garrisonTrait.canBeOccupied()&&this.sourceObject.rules.occupier&&!(this.target.obj.garrisonTrait.units.length&&this.target.obj.garrisonTrait.units[0].owner!==this.sourceObject.owner)&&!this.sourceObject.mindControllableTrait?.isActive()&&!this.sourceObject.mindControllerTrait?.isActive():!(!this.target.obj.rules.spyable||!this.sourceObject.rules.infiltrate||this.game.areFriendly(this.sourceObject,this.target.obj))))}isUnitRecycle(e,t){return e.owner===t.owner&&(e.isInfantry()&&t.rules.cloning||t.rules.grinding)&&!e.rules.engineer}isAllowed(){var e=this.target.obj,t=this.sourceObject;return this.isUnitRecycle(t,e)?t.rules.movementZone!==MovementZone.Fly&&t.rules.locomotor!==LocomotorType.Chrono&&0<this.game.sellTrait.computeRefundValue(t):e.hospitalTrait?t.healthTrait.health<100&&t.rules.movementZone!==MovementZone.Fly:!e.garrisonTrait||e.garrisonTrait.units.length<e.rules.maxNumberOccupants}process(){var e=this.target.obj,t=this.sourceObject;return this.isUnitRecycle(t,e)?[new EnterRecyclerTask(this.game,e)]:e.hospitalTrait?[new EnterHospitalTask(this.game,e)]:e.garrisonTrait?[new GarrisonBuildingTask(this.game,e)]:[new InfiltrateBuildingTask(this.game,e)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof GarrisonBuildingTask||e instanceof InfiltrateBuildingTask);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new RangeHelper(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class PlantC4Task extends EnterBuildingTask{isAllowed(e){return!this.target.isDestroyed&&!this.target.invulnerableTrait.isActive()}onEnter(e){var t=Math.floor(60*this.game.rules.combatDamage.c4Delay*GameSpeed.BASE_TICKS_PER_SECOND);return this.target.c4ChargeTrait.setCharge(t,{player:e.owner,obj:e}),this.game.events.dispatch(new EnterObjectEvent(this.target,e)),!1}getTargetLinesConfig(e){return{target:this.target,pathNodes:[],isAttack:!0}}}class AttackOrder extends Order{constructor(e,{forceAttack:t,noIvanBomb:i}={}){super(t?OrderType.ForceAttack:OrderType.Attack),this.game=e,this.isC4=!1,this.forceAttack=!!t,this.ivanBombAllowed=!i||!!t,this.targetOptional=!1,this.feedbackType=OrderFeedbackType.None,this.rangeHelper=new RangeHelper(this.game.map.tileOccupation),this.losHelper=new LosHelper(this.game.map.tiles,e.map.tileOccupation)}getPointerType(e,t){if(!this.isAllowed())return e?PointerType.NoActionMini:PointerType.NoAction;if(this.isC4)return PointerType.C4;var i=this.sourceObject.attackTrait?.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);if(i?.rules.sabotageCursor)return PointerType.C4;if(this.ivanBombAllowed&&this.sourceObject.rules.ivan&&i?.warhead.rules.ivanBomb)return PointerType.Dynamite;if(i?.warhead.rules.bombDisarm)return PointerType.DefuseBomb;if(i&&i.rules.damage<0)return PointerType.RepairMove;t=t.every(e=>{if(!e.attackTrait)return!0;var t=e.attackTrait.selectWeaponVersus(e,this.target,this.game,this.forceAttack);return!t||this.rangeHelper.isInWeaponRange(e,this.target.obj||this.target.tile,t,this.game.rules)&&this.losHelper.hasLineOfSight(e,this.target.obj||this.target.tile,t)});return e?PointerType.AttackMini:t?PointerType.AttackRange:PointerType.AttackNoRange}isValid(){if(!this.sourceObject.attackTrait)return!1;if(this.forceAttack&&this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.isBuilding())return!1;let e=this.target.obj;var t=this.game.map.getGroundObjectsOnTile(this.target.tile).find(e=>e.isTerrain());if(this.terminal=!e&&!t,this.sourceObject.c4&&e?.isBuilding()&&e.c4ChargeTrait&&(this.forceAttack||!this.game.areFriendly(e,this.sourceObject)||e.cabHutTrait))return this.isC4=!0,this.feedbackType=OrderFeedbackType.SpecialAttack,!0;if(this.isC4=!1,this.feedbackType=OrderFeedbackType.Attack,!this.game.isValidTarget(e))return!1;if(!e&&t?.rules.immune)return!1;if(!(e||this.target.tile!==this.sourceObject.tile||this.sourceObject.isUnit()&&this.sourceObject.zone===ZoneType.Air))return!1;if(e===this.sourceObject)return!1;t=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);return!!t&&(!(!this.ivanBombAllowed&&t.warhead.rules.ivanBomb)&&(!(e?.isBuilding()&&e.cabHutTrait&&!t.warhead.rules.ivanBomb&&!t.warhead.rules.bombDisarm)&&(!!(this.sourceObject.isUnit()&&this.sourceObject.moveTrait&&!this.sourceObject.moveTrait.isDisabled()||this.rangeHelper.isInWeaponRange(this.sourceObject,e||this.target.tile,t,this.game.rules))&&(!(this.sourceObject.airSpawnTrait&&t.rules.spawner&&!this.game.map.isWithinBounds(this.target.tile))&&(!!this.forceAttack||(!e?.isBuilding()||!e.hospitalTrait)&&(!(!e||!e.healthTrait)&&(!e.isDestroyed&&!e.isCrashing&&(!(!e.isOverlay()||!(t.warhead.rules.wall||t.warhead.rules.wood&&e.rules.armor===ArmorType.Wood))||e.isTechno()))))))))}isAllowed(){return!this.sourceObject.attackTrait.isDisabled()}process(){if(this.isC4)return[new PlantC4Task(this.game,this.target.obj)];var e=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game,this.forceAttack);return[new AttackTask(this.game,this.target,e,{force:this.forceAttack})]}onAdd(t,e){let i=this.sourceObject;if(!e&&i.isUnit()&&this.isValid()&&this.isAllowed())if(i.rules.movementZone===MovementZone.Fly){let e=t.find(e=>(e.constructor===MoveTask||e.constructor===AttackTask)&&!e.isCancelling());e&&(i.moveTrait.currentWaypoint?.tile===this.target.tile||i.isAircraft()||e.constructor===AttackTask)&&e.forceCancel(i)&&t.splice(t.indexOf(e))}else{t.length&&i.isUnit()&&(i.rules.locomotor===LocomotorType.Vehicle||i.rules.locomotor===LocomotorType.Ship)&&(i.moveTrait.speedPenalty=.5);let e=t.find(e=>e.constructor===AttackTask&&!e.isCancelling());if(e?.getWeapon().warhead.rules.temporal)return e.setForceAttack(this.forceAttack),e.requestTargetUpdate(this.target),!1}return!0}}class StopOrder extends Order{constructor(e){super(OrderType.Stop),this.game=e,this.getPointerType=()=>PointerType.NoAction}isValid(){return this.sourceObject.isTechno()}isAllowed(){return!0}process(){return[new CallbackTask(e=>{!e.isUnit()||e.rules.locomotor!==LocomotorType.Vehicle&&e.rules.locomotor!==LocomotorType.Ship||(e.moveTrait.speedPenalty=0)})]}onAdd(e,t){let i=this.sourceObject;return t||!e.length||!i.isUnit()||i.rules.locomotor!==LocomotorType.Vehicle&&i.rules.locomotor!==LocomotorType.Ship||(i.moveTrait.speedPenalty=.5),i.isBuilding()&&i.rallyTrait?.getRallyPoint()&&(i.unitRepairTrait?.resetRallyPoint(i,this.game),i.factoryTrait?.resetRallyPoint(i,this.game)),!0}}class CheerOrder extends Order{constructor(){super(OrderType.Cheer),this.getPointerType=()=>PointerType.NoAction}isValid(){return this.sourceObject.isInfantry()&&[StanceType.None,StanceType.Guard].includes(this.sourceObject.stance)}isAllowed(){return!0}process(){return[new CheerTask]}}class DockOrder extends Order{constructor(e){super(OrderType.Dock),this.game=e,this.targetOptional=!1,this.feedbackType=OrderFeedbackType.Move}getPointerType(e){return e?this.isAllowed()?PointerType.OccupyMini:PointerType.NoActionMini:this.isAllowed()?PointerType.Occupy:PointerType.NoOccupy}isValid(){if(!this.target.obj?.isBuilding()||this.target.obj.isDestroyed||!this.target.obj.dockTrait||this.target.obj.buildStatus!==BuildStatus.Ready||!this.sourceObject.isUnit()||this.target.obj.warpedOutTrait.isActive())return!1;var e=!(this.target.obj.rules.refinery||this.target.obj.unitRepairTrait);return this.game.areFriendly(this.target.obj,this.sourceObject)&&this.target.obj.dockTrait.isValidUnitForDock(this.sourceObject)&&!this.target.obj.dockTrait.isDocked(this.sourceObject)&&!(this.target.obj.unitRepairTrait&&!this.sourceObject.rules.dock.includes(this.target.obj.name)&&100===this.sourceObject.healthTrait.health)&&(!e||(0<(this.target.obj.dockTrait.getAvailableDockCount()??0)||this.target.obj.dockTrait.hasReservedDockForUnit(this.sourceObject)))}isAllowed(){return!0}process(){var e=this.target.obj;return e.rules.refinery&&this.sourceObject.isVehicle()&&this.sourceObject.harvesterTrait?[new ReturnOreTask(this.game,e,!0,!0)]:e.unitRepairTrait||this.sourceObject.rules.dock.includes(e.name)?[new MoveToDockTask(this.game,e)]:[]}}class GatherOrder extends Order{constructor(e){super(OrderType.Gather),this.game=e,this.targetOptional=!1,this.feedbackType=OrderFeedbackType.Move}getPointerType(e){return e?PointerType.AttackMini:PointerType.AttackNoRange}isValid(){return!(!this.sourceObject.isVehicle()||!this.sourceObject.harvesterTrait||this.sourceObject.moveTrait.isDisabled()||this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation))&&this.target.isOre}isAllowed(){return!0}process(){return[new GatherOreTask(this.game,this.target.tile,!0)]}}class AttackMoveOrder extends AttackOrder{constructor(e,t){super(e),this.map=t,this.orderType=OrderType.AttackMove,this.targetOptional=!1,this.feedbackType=OrderFeedbackType.Move}getPointerType(t,i){if(this.isTargetted()){let e=super.getPointerType(t,i);return e!==PointerType.AttackRange&&e!==PointerType.AttackNoRange||(e=PointerType.AttackMove),e}let e=this.isAllowed();var r,s,a;return e&&(r=!!this.target.getBridge(),s=this.sourceObject.rules.speedType,a=this.sourceObject.isInfantry(),i=this.sourceObject.rules.movementZone===MovementZone.Fly,e=i||0<this.map.terrain.getPassableSpeed(this.target.tile,s,a,r)||!!this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)),t?e?PointerType.AttackMini:PointerType.NoActionMini:e?PointerType.AttackMove:PointerType.NoMove}isValid(){var e=this.sourceObject.isUnit()&&!!this.sourceObject.attackTrait&&!this.sourceObject.rules.preventAttackMove&&!(this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.rules.moveToShroud)&&(!this.isTargetted()||super.isValid());return this.feedbackType=OrderFeedbackType.Move,e}isAllowed(){return!(!this.isTargetted()&&this.sourceObject.moveTrait.isDisabled())&&super.isAllowed()}process(){if(this.isTargetted()){if(this.isC4)return[new PlantC4Task(this.game,this.target.obj)];var e=this.sourceObject.attackTrait.selectWeaponVersus(this.sourceObject,this.target,this.game);return[new AttackMoveTargetTask(this.game,this.target,e)]}return[new AttackMoveTask(this.game,this.target.tile,!!this.target.getBridge(),{closeEnoughTiles:this.game.rules.general.closeEnough})]}isTargetted(){return this.target.obj?.isTechno()}onAdd(t,e){let i=this.sourceObject;if(!e&&i.isUnit()&&this.isValid()&&this.isAllowed())if(i.rules.movementZone===MovementZone.Fly){let e=t.find(e=>[MoveTask,AttackTask,AttackMoveTask,AttackMoveTargetTask].includes(e.constructor)&&!e.isCancelling());if(e)if(this.isTargetted())(i.moveTrait.currentWaypoint?.tile===this.target.tile||i.isAircraft()||e.constructor!==MoveTask)&&e.forceCancel(i)&&t.splice(t.indexOf(e));else{if(e.constructor===AttackMoveTask)return e.updateTarget(this.target.tile,!!this.target.getBridge()),t.splice(t.indexOf(e)+1),i.unitOrderTrait.clearOrders(),!1;e.forceCancel(i)&&t.splice(t.indexOf(e))}}else this.isTargetted()&&t.length&&i.isUnit()&&(i.rules.locomotor===LocomotorType.Vehicle||i.rules.locomotor===LocomotorType.Ship)&&(i.moveTrait.speedPenalty=.5);return!0}}class BuildingRepairFullEvent{constructor(e,t){this.target=e,this.source=t,this.type=EventType.BuildingRepairFull}}class BridgeRepairEvent{constructor(e,t){this.source=e,this.tile=t,this.type=EventType.BridgeRepair}}class RepairBuildingTask extends EnterBuildingTask{isAllowed(e){return this.target.cabHutTrait?this.target.cabHutTrait.canRepairBridge():e.rules.engineer&&!this.target.isDestroyed&&this.target.rules.repairable&&this.target.healthTrait.health<100&&(!this.target.owner.isCombatant()&&!!this.target.garrisonTrait||this.game.areFriendly(e,this.target))}onEnter(e){this.game.unspawnObject(e),this.target.cabHutTrait?(this.target.cabHutTrait.repairBridge(this.game,e.owner),this.game.events.dispatch(new BridgeRepairEvent(e.owner,this.target.centerTile))):(this.target.healthTrait.healToFull(e,this.game),this.game.events.dispatch(new BuildingRepairFullEvent(this.target,e.owner)))}}class RepairOrder extends Order{constructor(e){super(OrderType.Repair),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=OrderFeedbackType.Capture}getPointerType(e){return e?this.isAllowed()?PointerType.OccupyMini:PointerType.NoActionMini:this.isAllowed()?PointerType.RepairMove:PointerType.NoRepair}isValid(){return!!this.target.obj?.isBuilding()&&!this.target.obj.isDestroyed&&this.sourceObject.isInfantry()&&this.sourceObject.rules.engineer&&(!this.target.obj.owner.isCombatant()&&(!!this.target.obj.garrisonTrait||!!this.target.obj.cabHutTrait)||this.game.areFriendly(this.target.obj,this.sourceObject))}isAllowed(){let e=this.target.obj;return e.cabHutTrait?e.cabHutTrait.canRepairBridge():!!(e.rules.repairable&&e.healthTrait.health<100)}process(){var e=this.target.obj;return[new RepairBuildingTask(this.game,e)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof RepairBuildingTask);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new RangeHelper(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class GuardAreaOrder extends Order{constructor(e,t){super(t?OrderType.GuardArea:OrderType.Guard),this.game=e,this.targeted=t,this.getPointerType=e=>e?this.isAllowed()?PointerType.GuardMini:PointerType.NoActionMini:this.isAllowed()?PointerType.Guard:PointerType.NoMove,this.terminal=!0,this.targetOptional=!t,this.minimapAllowed=t,this.feedbackType=t?OrderFeedbackType.Move:OrderFeedbackType.None}isValid(){return this.sourceObject.isUnit()&&(!!this.targetOptional||!this.sourceObject.moveTrait.isDisabled())&&!(this.target&&this.game.mapShroudTrait.getPlayerShroud(this.sourceObject.owner)?.isShrouded(this.target.tile,this.target.obj?.tileElevation)&&!this.sourceObject.rules.moveToShroud)}isAllowed(){return!0}process(){let t=this.targeted?this.target.tile:void 0;const e=this.sourceObject;let i=[];return t&&i.push(new MoveTask(this.game,t,!!this.target.getBridge(),{closeEnoughTiles:this.game.rules.general.closeEnough})),e.isVehicle()&&e.harvesterTrait?i.push(new CallbackTask(()=>e.harvesterTrait.lastOreSite=void 0),new GatherOreTask(this.game,void 0,!0)):i.push(new CallbackTask(e=>{t&&![MoveResult.Success,MoveResult.CloseEnough].includes(this.sourceObject.moveTrait?.lastMoveResult)||(this.sourceObject.guardMode=!0)})),i}}class ScatterOrder extends Order{constructor(e){super(OrderType.Scatter),this.game=e,this.getPointerType=()=>PointerType.NoAction}isValid(){return(this.sourceObject.isInfantry()||this.sourceObject.isVehicle())&&this.sourceObject.rules.movementZone!==MovementZone.Fly&&!this.sourceObject.moveTrait.isDisabled()}isAllowed(){return!0}process(){if(!this.target)throw new Error("Target should be set for executing a scatter order. See OrderUnitsAction.");return[new ScatterTask(this.game,{tile:this.target.tile,toBridge:!!this.target.getBridge()})]}}class EnterTransportEvent{constructor(e){this.target=e,this.type=EventType.EnterTransport}}!function(e){e[e.MoveToQueueingTile=0]="MoveToQueueingTile",e[e.WaitForTurn=1]="WaitForTurn",e[e.MoveToTransport=2]="MoveToTransport",e[e.EnterTransport=3]="EnterTransport",e[e.ClearTransport=4]="ClearTransport"}(EnterTransportTask_State=EnterTransportTask_State||{});class EnterTransportTask extends Task{constructor(e,t){super(),this.game=e,this.target=t,this.movePerformed=!1,this.preventOpportunityFire=!1}isAllowed(e){return!this.target.isDestroyed&&!this.target.isCrashing&&this.game.areFriendly(this.target,e)&&e.zone!==ZoneType.Air&&this.target.zone!==ZoneType.Air&&this.target.transportTrait.unitFitsInside(e)&&this.target.moveTrait.moveState===MoveState.Idle&&!this.target.warpedOutTrait.isActive()&&!e.mindControllableTrait?.isActive()&&!e.mindControllerTrait?.isActive()}onStart(e){if(!this.target.transportTrait)throw new Error(`Unit ${this.target.name} is not a valid transport`);this.initialTargetTile=this.target.tile,0<this.target.transportTrait.addToLoadQueue(e)?this.state=EnterTransportTask_State.MoveToQueueingTile:this.state=EnterTransportTask_State.MoveToTransport}onEnd(e){this.target.isDestroyed||this.target.transportTrait?.removeFromLoadQueue(e)}onTick(n){if(this.isCancelling()&&this.state!==EnterTransportTask_State.EnterTransport||this.state===EnterTransportTask_State.ClearTransport||n.moveTrait.isDisabled())return!0;if(this.target.tile!==this.initialTargetTile||this.target.moveTrait.moveState!==MoveState.Idle)return!0;if(this.state===EnterTransportTask_State.MoveToQueueingTile){let r=new MovePositionHelper(this.game.map),s=this.target.onBridge?this.game.map.tileOccupation.getBridgeOnTile(this.target.tile):void 0,a;var e=new RadialTileFinder(this.game.map.tiles,this.game.map.mapBounds,this.target.tile,this.target.getFoundation(),1,1,e=>{let t=[this.game.map.tileOccupation.getBridgeOnTile(e)];t[0]&&t.push(void 0);for(var i of t)if(0<this.game.map.terrain.getPassableSpeed(e,n.rules.speedType,n.isInfantry(),!!i)&&r.isEligibleTile(e,i,s,this.target.tile))return a=i,!0;return!1}).getNextTile();return!e||(this.children.push(new MoveTask(this.game,e,!!a,{closeEnoughTiles:5})),this.children.push(new CallbackTask(()=>{[MoveResult.Success,MoveResult.CloseEnough].includes(n.moveTrait.lastMoveResult)||this.cancel()})),this.queueingNode={tile:e,onBridge:a},this.state=EnterTransportTask_State.WaitForTurn,!1)}if(this.state===EnterTransportTask_State.WaitForTurn){if(!this.target.transportTrait.unitIsFirstInLoadQueue(n))return!1;this.queueingNode=void 0,this.state=EnterTransportTask_State.MoveToTransport}if(this.state===EnterTransportTask_State.MoveToTransport){if(!this.isAllowed(n))return!0;if(!this.game.map.tileOccupation.isTileOccupiedBy(n.tile,this.target))return!!this.movePerformed||(this.children.push(new MoveInsideTask(this.game,this.target)),this.movePerformed=!0,!(this.preventOpportunityFire=!0));this.state=EnterTransportTask_State.EnterTransport}return this.state===EnterTransportTask_State.EnterTransport&&(!this.isAllowed(n)||this.isCancelling()?(this.children.push(new MoveOutsideTask(this.game,this.target)),this.state=EnterTransportTask_State.ClearTransport,!1):(this.game.limboObject(n,{selected:!1,controlGroup:this.game.getUnitSelection().getOrCreateSelectionModel(n).getControlGroupNumber(),inTransport:!0}),this.game.events.dispatch(new EnterTransportEvent(this.target)),this.game.events.dispatch(new EnterObjectEvent(this.target,n)),this.target.transportTrait.units.push(n),!0))}getTargetLinesConfig(e){return{target:this.queueingNode?void 0:this.target,pathNodes:this.queueingNode?[this.queueingNode]:[]}}}class EnterTransportOrder extends Order{constructor(e){super(OrderType.EnterTransport),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=OrderFeedbackType.Enter}getPointerType(e){return e?this.isAllowed()?PointerType.OccupyMini:PointerType.NoActionMini:this.isAllowed()?PointerType.Occupy:PointerType.NoOccupy}isValid(){return!(!this.target.obj?.isVehicle()||!this.target.obj.transportTrait||this.target.obj.isDestroyed||this.target.obj===this.sourceObject||!this.game.areFriendly(this.target.obj,this.sourceObject)||!this.sourceObject.isVehicle()&&!this.sourceObject.isInfantry())}isAllowed(){let e=this.target.obj,t=this.sourceObject;return t.zone!==ZoneType.Air&&e.zone!==ZoneType.Air&&e.transportTrait.unitFitsInside(t)&&e.moveTrait.moveState===MoveState.Idle&&!e.warpedOutTrait.isActive()&&!t.mindControllableTrait?.isActive()&&!t.mindControllerTrait?.isActive()}process(){let e=this.sourceObject,t=this.target.obj;return this.game.map.terrain.getPassableSpeed(t.tile,e.rules.speedType,e.isInfantry(),e.onBridge)?[new EnterTransportTask(this.game,t)]:[new CallbackTask(()=>{t.unitOrderTrait.addTask(new MoveTask(this.game,e.tile,e.onBridge)),t.unitOrderTrait.addTask(new CallbackTask(()=>{this.game.map.terrain.getPassableSpeed(t.tile,e.rules.speedType,e.isInfantry(),e.onBridge)&&e.unitOrderTrait.addTask(new EnterTransportTask(this.game,t))}))})]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof EnterTransportTask);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new RangeHelper(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class BuildingCaptureEvent{constructor(e){this.target=e,this.type=EventType.BuildingCapture}}class CaptureBuildingTask extends EnterBuildingTask{isAllowed(e){return e.rules.engineer&&this.target.rules.capturable&&!this.target.isDestroyed&&this.target.buildStatus!==BuildStatus.BuildDown&&!this.game.areFriendly(e,this.target)}onEnter(t){if(this.game.unspawnObject(t),this.game.gameOpts.multiEngineer){var i=this.game.rules.general;if((!this.target.rules.needsEngineer||!i.engineerAlwaysCaptureTech)&&this.target.healthTrait.health>100*i.engineerCaptureLevel){var r=Math.floor(i.engineerDamage*this.target.healthTrait.maxHitPoints),i=Math.floor((1-Math.floor(1/i.engineerDamage)*i.engineerDamage)*this.target.healthTrait.maxHitPoints);if(0<(r=Math.min(r,this.target.healthTrait.getHitPoints()-i))){i=this.game.rules.combatDamage.c4Warhead;let e=new Warhead(this.game.rules.getWarhead(i));return void e.detonate(this.game,r,this.target.tile,0,this.target.position.worldPosition,ZoneType.Ground,CollisionType.None,this.game.createTarget(this.target,this.target.tile),{player:t.owner,obj:t,weapon:void 0},SpecialWarheadType.None,void 0,0)}}}t.owner.buildingsCaptured++,this.game.changeObjectOwner(this.target,t.owner),this.game.events.dispatch(new BuildingCaptureEvent(this.target))}}class CaptureOrder extends Order{constructor(e){super(OrderType.Capture),this.game=e,this.targetOptional=!1,this.terminal=!0,this.feedbackType=OrderFeedbackType.Capture}getPointerType(e){if(!this.isAllowed())return e?PointerType.NoActionMini:PointerType.NoOccupy;if(e)return PointerType.OccupyMini;if(this.game.gameOpts.multiEngineer){var t=this.game.rules.general,e=this.target.obj;if((!e.rules.needsEngineer||!t.engineerAlwaysCaptureTech)&&e.healthTrait.health>100*t.engineerCaptureLevel)return PointerType.EngineerDamage}return PointerType.Occupy}isValid(){return!(this.target.obj?.isDestroyed||!this.target.obj?.isBuilding()||!this.sourceObject.isInfantry())&&(this.target.obj.rules.capturable&&this.sourceObject.rules.engineer&&!this.game.areFriendly(this.sourceObject,this.target.obj))}isAllowed(){return!0}process(){return[new CaptureBuildingTask(this.game,this.target.obj)]}onAdd(t,e){if(!e){let e=t.find(e=>e instanceof CaptureBuildingTask);if(this.isValid()&&this.isAllowed()&&e&&!e.isCancelling()&&e.target===this.target.obj)if(new RangeHelper(this.game.map.tileOccupation).isInTileRange(this.sourceObject,this.target.obj,0,Math.SQRT2))return!1}return!0}}class OrderFactory{constructor(e,t){this.game=e,this.map=t}create(e,t){switch(e){case OrderType.Deploy:return new DeployOrder(this.game,!0);case OrderType.DeploySelected:return new DeployOrder(this.game,!1);case OrderType.ForceMove:return new MoveOrder(this.game,this.map,t,!0);case OrderType.Move:return new MoveOrder(this.game,this.map,t);case OrderType.ForceAttack:return new AttackOrder(this.game,{forceAttack:!0});case OrderType.Attack:return new AttackOrder(this.game,{noIvanBomb:!0});case OrderType.PlaceBomb:return new AttackOrder(this.game);case OrderType.AttackMove:return new AttackMoveOrder(this.game,this.map);case OrderType.Capture:return new CaptureOrder(this.game);case OrderType.Occupy:return new OccupyOrder(this.game);case OrderType.Stop:return new StopOrder(this.game);case OrderType.Cheer:return new CheerOrder;case OrderType.Dock:return new DockOrder(this.game);case OrderType.Gather:return new GatherOrder(this.game);case OrderType.Repair:return new RepairOrder(this.game);case OrderType.Guard:return new GuardAreaOrder(this.game,!1);case OrderType.GuardArea:return new GuardAreaOrder(this.game,!0);case OrderType.Scatter:return new ScatterOrder(this.game);case OrderType.EnterTransport:return new EnterTransportOrder(this.game);default:throw new Error("Unhandled order type "+OrderType[e])}}}class OrderUnitsActionFactory{constructor(e,t,i){this.game=e,this.map=t,this.orderActionContext=i}create(){return new OrderUnitsAction(this.game,this.map,this.orderActionContext,new OrderFactory(this.game,this.map))}}!function(e){e[e.Add=0]="Add",e[e.Cancel=1]="Cancel",e[e.Pause=2]="Pause",e[e.Resume=3]="Resume",e[e.AddNext=4]="AddNext"}(UpdateType=UpdateType||{});class UpdateQueueAction extends Action{constructor(e){super(ActionType.UpdateQueue),this.game=e}unserialize(e){let t=new DataStream(e);var i;this.queueType=t.readUint8(),this.updateType=t.readUint8(),this.updateType!==UpdateType.Add&&this.updateType!==UpdateType.Cancel&&this.updateType!==UpdateType.AddNext||(i=t.readUint32(),e=t.readUint8(),this.item=this.game.rules.getTechnoByInternalId(i,e),this.quantity=t.readUint16())}serialize(){let e=new DataStream(9);if(e.dynamicSize=!1,e.writeUint8(this.queueType),e.writeUint8(this.updateType),this.updateType===UpdateType.Add||this.updateType===UpdateType.Cancel||this.updateType===UpdateType.AddNext){if(void 0===this.quantity)throw new Error("Missing quantity");if(65535<this.quantity)throw new Error("Maximum quantity exceeded");e.writeUint32(this.item.index),e.writeUint8(this.item.type),e.writeUint16(this.quantity)}return new Uint8Array(e.buffer,e.byteOffset,e.position)}print(){return this.updateType===UpdateType.Resume?"Resume queue "+QueueType[this.queueType]:this.updateType===UpdateType.Add?`Add to queue ${this.item.name} x `+this.quantity:this.updateType===UpdateType.AddNext?`Add next in queue ${this.item.name} x `+this.quantity:this.updateType===UpdateType.Pause?`Put queue ${QueueType[this.queueType]} on hold.`:this.updateType===UpdateType.Cancel?`Cancel ${this.item.name} x `+this.quantity:"Unhandled queue update type "+this.updateType}process(){let i=this.player,r=this.item,s=i.production.getQueue(this.queueType);if(this.updateType===UpdateType.Resume)s.status===QueueStatus.OnHold&&(s.status=QueueStatus.Active);else if(this.updateType===UpdateType.Add||this.updateType===UpdateType.AddNext){let e=s.find(r);if(s.status===QueueStatus.Active||s.status===QueueStatus.Idle||s.status===QueueStatus.OnHold&&e[0]!==s.getFirst()||s.status===QueueStatus.Ready&&r.type!==ObjectType.Building){let t;var a=e.reduce((e,t)=>e+t.quantity,0);if(Number.isFinite(r.buildLimit)){let e;e=0<=r.buildLimit?i.getOwnedObjectsByType(r.type,!0).filter(e=>e.name===r.name).length:i.getLimitedUnitsBuilt(r.name),t=Math.max(0,Math.abs(r.buildLimit)-(e+a))}else t=Number.POSITIVE_INFINITY;t&&i.production.isAvailableForProduction(r)&&(n=Math.min(s.maxSize-s.currentSize,s.maxItemQuantity-a,t),0<(o=Math.min(this.quantity,n))&&(this.updateType===UpdateType.AddNext?s.insertAfterFirst(r,o,r.cost):s.push(r,o,r.cost)))}}else if(this.updateType===UpdateType.Cancel){if([QueueStatus.Ready,QueueStatus.OnHold,QueueStatus.Active].includes(s.status)){let e=s.find(r);var n,o;e.length&&(n=e.reduce((e,t)=>e+t.quantity,0),0<(o=Math.min(n,this.quantity))&&(s.pop(r,o),o===n&&(i.credits+=e[0].creditsSpent)))}}else this.updateType===UpdateType.Pause&&s.status===QueueStatus.Active&&(s.status=QueueStatus.OnHold)}}class UpdateQueueActionFactory{constructor(e){this.game=e}create(){return new UpdateQueueAction(this.game)}}class PlayerDroppedEvent{constructor(e,t){this.target=e,this.assetsRedistributed=t,this.type=EventType.PlayerDropped}}class DropPlayerAction extends Action{constructor(e,t){super(ActionType.DropPlayer),this.game=e,this.localPlayerName=t}process(){if(this.localPlayerName!==this.player.name){let e=this.player;var t;e.defeated||(t=this.game.redistributeAllPlayerAssets(e),this.game.removeAllPlayerAssets(e),e.dropped=!0,this.game.events.dispatch(new PlayerDroppedEvent(e,t)))}}}class DropPlayerActionFactory{constructor(e,t){this.game=e,this.localPlayerName=t}create(){return new DropPlayerAction(this.game,this.localPlayerName)}}class BuildingRepairStartEvent{constructor(e){this.target=e,this.type=EventType.BuildingRepairStart}}class ToggleRepairAction extends Action{constructor(e){super(ActionType.ToggleRepair),this.game=e}unserialize(e){this.buildingId=new DataStream(e).readUint32()}serialize(){return new DataStream(4).writeUint32(this.buildingId).toUint8Array()}print(){return"Toggle repair "+this.buildingId}process(){var e=this.player;if(this.game.getWorld().hasObjectId(this.buildingId)){let t=this.game.getObjectById(this.buildingId);if(t.isBuilding()&&e===t.owner&&!t.isDestroyed&&t.rules.repairable&&t.rules.clickRepairable&&100!==t.healthTrait.health){let e=t.traits.get(AutoRepairTrait);e.setDisabled(!e.isDisabled()),e.isDisabled()||this.game.events.dispatch(new BuildingRepairStartEvent(t))}}}}class ToggleRepairActionFactory{constructor(e){this.game=e}create(){return new ToggleRepairAction(this.game)}}class ToggleAllianceAction extends Action{constructor(e){super(ActionType.ToggleAlliance),this.game=e}unserialize(e){this.toPlayer=this.game.getPlayer(e[0]),this.toggle=Boolean(e[1])}serialize(){return new Uint8Array([this.game.getPlayerNumber(this.toPlayer),this.toggle?1:0])}print(){return`Toggle alliance ${this.toggle?"on":"off"} with `+this.toPlayer.name}process(){var e=this.game.rules.mpDialogSettings;if(e.alliesAllowed&&e.allyChangeAllowed){var a,n=this.player,t=this.toPlayer,e=this.toggle;let i=n,r=t,s=this.game.alliances;if(!n.defeated&&s.canRequestAlliance(r)){let t=s.findByPlayers(i,r);t?t.status===AllianceStatus.Formed?e||(s.breakAlliance(i,r),this.game.onAllianceChange(t,i,!1)):t.status===AllianceStatus.Requested&&(t.players.first===r?e&&s.canFormAlliance(i,r)&&(s.acceptRequest(r,i),this.game.onAllianceChange(t,i,!0),1!==(n=this.game.getCombatants().filter(e=>e!==i&&!s.areAllied(i,e))).length||(a=s.findByPlayers(n[0],i))&&s.cancelRequest(a.players.first,a.players.second),1!==(a=this.game.getCombatants().filter(e=>e!==r&&!s.areAllied(r,e))).length||(a=s.findByPlayers(a[0],r))&&s.cancelRequest(a.players.first,a.players.second)):e||(s.cancelRequest(i,r),this.game.events.dispatch(new AllianceChangeEvent(t,AllianceEventType.Broken,i)),this.game.traits.filter(NotifyAllianceChange).forEach(e=>{e[NotifyAllianceChange.onChange](t,!1,this.game)}))):e&&s.canFormAlliance(i,r)&&((e=s.request(i,r))&&this.game.events.dispatch(new AllianceChangeEvent(e,AllianceEventType.Requested,i)))}}}}class ToggleAllianceActionFactory{constructor(e){this.game=e}create(){return new ToggleAllianceAction(this.game)}}class ActivateSuperWeaponAction extends Action{constructor(e){super(ActionType.ActivateSuperWeapon),this.game=e}unserialize(e){let t=new DataStream(e);this.superWeaponType=t.readUint8();e=t.readUint8();this.tile={x:t.readUint16(),y:t.readUint16()},this.tile2=2<e?{x:t.readUint16(),y:t.readUint16()}:void 0}serialize(){let e=new DataStream(6+(this.tile2?4:0));return e.dynamicSize=!1,e.writeUint8(this.superWeaponType),e.writeUint8(this.tile2?4:2),e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),this.tile2&&(e.writeUint16(this.tile2.x),e.writeUint16(this.tile2.y)),e.toUint8Array()}print(){return`Activate SuperW ${SuperWeaponType[this.superWeaponType]} at tile (${this.tile.x}, ${this.tile.y})`+(this.tile2?`, (${this.tile2.x}, ${this.tile2.y})`:"")}process(){var e,t=this.player,i=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);i?(e=this.tile2?this.game.map.tiles.getByMapCoords(this.tile2.x,this.tile2.y):void 0,this.game.traits.get(SuperWeaponsTrait).activateSuperWeapon(this.superWeaponType,t,this.game,i,e)):console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}}class ActivateSuperWeaponActionFactory{constructor(e){this.game=e}create(){return new ActivateSuperWeaponAction(this.game)}}class PingLocationEvent{constructor(e,t){this.tile=e,this.player=t,this.type=EventType.PingLocation}}class PingLocationAction extends Action{constructor(e){super(ActionType.PingLocation),this.game=e}unserialize(e){let t=new DataStream(e);this.tile={x:t.readUint16(),y:t.readUint16()}}serialize(){let e=new DataStream(4);return e.writeUint16(this.tile.x),e.writeUint16(this.tile.y),e.toUint8Array()}print(){return`Ping location at tile (${this.tile.x}, ${this.tile.y})`}process(){var e=this.player,t=this.game.map.tiles.getByMapCoords(this.tile.x,this.tile.y);if(t){this.game.events.dispatch(new PingLocationEvent(t,e));for(var i of[e,...this.game.alliances.getAllies(e)])this.game.events.dispatch(new RadarEvent(i,RadarEventType.GenericNonCombat,t))}else console.warn(`Tile ${this.tile.x},${this.tile.y} doesn't exist`)}}class PingLocationActionFactory{constructor(e){this.game=e}create(){return new PingLocationAction(this.game)}}class PlayerResignedEvent{constructor(e,t){this.target=e,this.assetsRedistributed=t,this.type=EventType.PlayerResigned}}class ObserveGameAction extends Action{constructor(e){super(ActionType.ObserveGame),this.game=e}process(){let e=this.player;var t;this.game.removeAllPlayerAssets(e),!e.isCombatant()||e.defeated||e.isObserver||(e.resigned=!0,e.defeated=!0,e.isObserver=!0,this.game.events.dispatch(new PlayerResignedEvent(e)),this.game.events.dispatch(new PlayerDefeatedEvent(e)),this.game.mapShroudTrait.getPlayerShroud(e)?.revealAll(),t=e.radarTrait.isDisabled(),e.radarTrait.setDisabled(!1),t&&this.game.events.dispatch(new RadarOnOffEvent(e,!0)))}}class ObserveGameActionFactory{constructor(e){this.game=e}create(){return new ObserveGameAction(this.game)}}class ResignGameAction extends Action{constructor(e,t){super(ActionType.ResignGame),this.game=e,this.localPlayerName=t}process(){if(this.localPlayerName!==this.player.name){let e=this.player;var t=this.game.redistributeAllPlayerAssets(e);this.game.removeAllPlayerAssets(e),e.isCombatant()&&(e.resigned=!0,this.game.events.dispatch(new PlayerResignedEvent(e,t)))}}}class ResignGameActionFactory{constructor(e,t){this.game=e,this.localPlayerName=t}create(){return new ResignGameAction(this.game,this.localPlayerName)}}!function(e){e[e.SetGlobalDebugText=0]="SetGlobalDebugText",e[e.SetUnitDebugText=1]="SetUnitDebugText"}(DebugCommandType=DebugCommandType||{});class DebugCommand{constructor(e,t){this.type=e,this.params=t}}class DebugAction extends Action{constructor(e){super(ActionType.DebugCommand),this.game=e}unserialize(e){let t=new DataStream(e);e=t.readUint8();e===DebugCommandType.SetUnitDebugText?this.command=new DebugCommand(e,{unitId:t.readUint32(),label:t.readCString()||void 0}):e===DebugCommandType.SetGlobalDebugText?this.command=new DebugCommand(e,{text:t.readCString()}):console.warn(`Debug command ${e} not implemented`)}serialize(){let e=new DataStream;if(e.writeUint8(this.command.type),this.command.type===DebugCommandType.SetUnitDebugText){var t=this.command.params;e.writeUint32(t.unitId),e.writeCString(t.label||"")}else{if(this.command.type!==DebugCommandType.SetGlobalDebugText)throw new Error(`Debug command ${this.command.type} not implemented`);t=this.command.params;e.writeCString(t.text)}return e.toUint8Array()}process(){if(this.command.type===DebugCommandType.SetUnitDebugText){var{unitId:t,label:i}=this.command.params;if(this.game.getWorld().hasObjectId(t)){let e=this.game.getObjectById(t);e.isTechno()&&(e.debugLabel=i)}}else this.command.type===DebugCommandType.SetGlobalDebugText?(i=this.command.params["text"],this.game.debugText.value=i):console.warn(`Debug command ${this.command.type} not implemented`)}}class DebugActionFactory{constructor(e){this.game=e}create(){return new DebugAction(this.game)}}class ActionFactoryReg{register(e,t,i){var r=new OrderActionContext;e.registerFactory(ActionType.NoAction,new NoActionFactory),e.registerFactory(ActionType.PlaceBuilding,new PlaceBuildingActionFactory(t)),e.registerFactory(ActionType.SellObject,new SellObjectActionFactory(t)),e.registerFactory(ActionType.ToggleRepair,new ToggleRepairActionFactory(t)),e.registerFactory(ActionType.SelectUnits,new SelectUnitsActionFactory(t,r)),e.registerFactory(ActionType.OrderUnits,new OrderUnitsActionFactory(t,t.map,r)),e.registerFactory(ActionType.UpdateQueue,new UpdateQueueActionFactory(t)),e.registerFactory(ActionType.ToggleAlliance,new ToggleAllianceActionFactory(t)),e.registerFactory(ActionType.ActivateSuperWeapon,new ActivateSuperWeaponActionFactory(t)),e.registerFactory(ActionType.PingLocation,new PingLocationActionFactory(t)),e.registerFactory(ActionType.DropPlayer,new DropPlayerActionFactory(t,i)),e.registerFactory(ActionType.ObserveGame,new ObserveGameActionFactory(t)),e.registerFactory(ActionType.ResignGame,new ResignGameActionFactory(t,i)),e.registerFactory(ActionType.DebugCommand,new DebugActionFactory(t))}}class SharedDetectDisguiseTrait_SharedDetectDisguiseTrait{constructor(){this.detectors=new Set}[NotifySpawn_NotifySpawn.onSpawn](e,t){this.isGlobalDetector(e)&&(this.detectors.add(e),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&this.detect(e,t)}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){e.isTechno()&&(this.isGlobalDetector(e)&&(this.detectors.delete(e),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&this.undetect(e,t))}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,i),this.isDisguisable(e)&&(this.undetect(e,i),this.detect(e,i))}[NotifyTileChange.onTileChange](e,t,i){this.isGlobalDetector(e)&&(this.updateAroundDetector(e,t,i),this.updateAroundDetector(e,t)),this.isDisguisable(e)&&(this.undetect(e,t),this.detect(e,t))}[NotifyPower.onPowerLow](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait&&!e.poweredTrait.isPoweredOn());this.updateAroundDetectors(i,e)}[NotifyPower.onPowerRestore](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait);this.updateAroundDetectors(i,e)}[NotifyPower.onPowerChange](e,t){}updateAroundDetectors(e,t){let i=new Set;for(var r of e)for(var s of this.findTechnosAroundDetector(r,t,r.tile))i.add(s);for(var a of i)this.isDisguisable(a)&&(this.undetect(a,t),this.detect(a,t))}updateAroundDetector(e,t,i=e.tile){var r;for(r of this.findTechnosAroundDetector(e,t,i))this.isDisguisable(r)&&(this.undetect(r,t),this.detect(r,t))}findTechnosAroundDetector(e,t,i){var r=e.getFoundation(),r=Math.max(r.width,r.height),e=e.rules.detectDisguiseRange+r,r=new Vector2(i.rx,i.ry).addScalar(-e),e=new Vector2(i.rx,i.ry).addScalar(e);return t.map.technosByTile.queryRange(new Box2(r,e))}detect(e,t){let i=new Set,r=new RangeHelper(t.map.tileOccupation);for(var s of this.detectors)if(!t.areFriendly(s,e)){var a=s.owner,n=s.rules.detectDisguiseRange;if(!i.has(a))if(!(s.isBuilding()&&s.poweredTrait&&!s.poweredTrait.isPoweredOn())&&r.tileDistance(e,s.tile)<=n)for(var o of[a,...t.alliances.getAllies(a)])i.add(o)}for(var l of i)l.sharedDetectDisguiseTrait?.add(e)}undetect(e,t){for(var i of t.getCombatants())i.sharedDetectDisguiseTrait?.delete(e)}isGlobalDetector(e){return!(!e.isTechno()||!e.rules.detectDisguiseRange)}isDisguisable(e){return!(!e.isInfantry()&&!e.isVehicle()||!e.disguiseTrait)}}class SharedDetectCloakTrait{constructor(){this.detectors=new Set}[NotifySpawn_NotifySpawn.onSpawn](e,t){this.isGlobalDetector(e)&&(this.detectors.add(e),this.updateAroundDetector(e,t)),this.isCloakable(e)&&this.detect(e,t)}[NotifyUnspawn_NotifyUnspawn.onUnspawn](e,t){e.isTechno()&&this.isGlobalDetector(e)&&this.detectors.delete(e)}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,i),this.isCloakable(e)&&this.detect(e,i)}[NotifyTileChange.onTileChange](e,t,i){this.isGlobalDetector(e)&&this.updateAroundDetector(e,t),this.isCloakable(e)&&this.detect(e,t)}[NotifyObjectTraitAdd.onAdd](e,t,i){e.isTechno()&&(t instanceof CloakableTrait?this.isCloakable(e)&&this.detect(e,i):t instanceof SensorsTrait&&this.isGlobalDetector(e)&&this.updateAroundDetector(e,i))}[NotifyPower.onPowerLow](e,t){}[NotifyPower.onPowerRestore](t,e){var i=[...this.detectors].filter(e=>e.owner===t&&e.isBuilding()&&e.poweredTrait);this.updateAroundDetectors(i,e)}[NotifyPower.onPowerChange](e,t){}[NotifyTick.onTick](e){for(var t of e.getCombatants()){var i;for(i of t.getOwnedObjects())i.cloakableTrait&&!i.cloakableTrait.isCloaked()&&this.detect(i,e)}}updateAroundDetectors(e,t){let i=new Set;for(var r of e)for(var s of this.findTechnosAroundDetector(r,t))i.add(s);for(var a of i)this.isCloakable(a)&&this.detect(a,t)}updateAroundDetector(e,t){var i;for(i of this.findTechnosAroundDetector(e,t))this.isCloakable(i)&&this.detect(i,t)}findTechnosAroundDetector(e,t){var i=e.getFoundation(),r=Math.max(i.width,i.height),i=e.rules.sensorsSight+r,r=new Vector2(e.tile.rx,e.tile.ry).addScalar(-i),i=new Vector2(e.tile.rx,e.tile.ry).addScalar(i);return t.map.technosByTile.queryRange(new Box2(r,i))}detect(e,t){let i=new RangeHelper(t.map.tileOccupation);for(var r of this.detectors)if(!t.areFriendly(r,e)){var s=r.rules.sensorsSight;if(!(r.isBuilding()&&r.poweredTrait&&!r.poweredTrait.isPoweredOn())&&i.tileDistance(e,r.tile)<=s){s=e.cloakableTrait?.isCloaked();if(e.cloakableTrait.uncloak(t),s)for(var a of[r.owner,...t.alliances.getAllies(r.owner)])t.traits.get(RadarTrait_RadarTrait).addEventForPlayer(RadarEventType.GenericNonCombat,a,e.tile,t);break}}}isGlobalDetector(e){return!(!e.isTechno()||!e.sensorsTrait&&!e.rules.sensorArray||!e.rules.sensorsSight)}isCloakable(e){return e.isTechno()&&!!e.cloakableTrait}}class StalemateDetectEvent{constructor(){this.type=EventType.StalemateDetect}}class StalemateDetectTrait{constructor(){this.stale=!1,this.allPlayersCredits=new Map,this.resetCountdown()}isStale(){return this.stale}getCountdownTicks(){return this.countdownTicks}resetCountdown(){this.countdownTicks=Math.floor(60*StalemateDetectTrait.graceMinutes*GameSpeed.BASE_TICKS_PER_SECOND)}clearStale(){this.stale=!1,this.resetCountdown()}[NotifyTick.onTick](e){0<this.countdownTicks?this.countdownTicks--:this.stale||(this.stale=!0,this.resetCountdown(),e.events.dispatch(new StalemateDetectEvent));for(var t of e.getCombatants()){var i=this.allPlayersCredits.get(t);i!==t.credits&&(this.allPlayersCredits.set(t,t.credits),t.credits>(i??0)&&t.production.hasAnyFactory()&&this.clearStale())}}[NotifyProduceUnit.onProduce](){this.clearStale()}[NotifyPlaceBuilding.onPlace](e){e.wallTrait||this.clearStale()}[NotifyDestroy_NotifyDestroy.onDestroy](e,t,i){!e.isBuilding()||e.owner.isNeutral||e.wallTrait||e.rules.insignificant||e.owner.defeated&&this.stale||i?.obj&&t.areFriendly(e,i.obj)||this.clearStale()}[NotifyOwnerChange_NotifyOwnerChange.onChange](e,t,i){e.isBuilding()&&!t.isNeutral&&(i.alliances.areAllied(e.owner,t)||this.clearStale())}}StalemateDetectTrait.graceMinutes=10;class GameOptSanitizer{static sanitize(e,t){t=t.mpDialogSettings;e.credits=Math.floor(clamp(e.credits,t.minMoney,t.maxMoney)),e.gameSpeed=Math.floor(clamp(e.gameSpeed,0,6)),e.unitCount=Math.floor(clamp(e.unitCount,t.minUnitCount,t.maxUnitCount))}}class GameOptRandomGen{static factory(e,t){return new this(Prng.factory(e,t))}constructor(e){this.prng=e}generateColors(e){let t=[...e.humanPlayers,...e.aiPlayers].filter(isNotNullOrUndefined),i=t.map(e=>e.colorId).filter(e=>e!==RANDOM_COLOR_ID);e=mpAllowedColors.length;let r=new Array(e).fill(0).map((e,t)=>t).filter(e=>!i.includes(e)),s=new Map;return t.forEach(e=>{if(e.countryId!==OBS_COUNTRY_ID&&e.colorId===RANDOM_COLOR_ID){if(r.length<1)throw new Error("Out of available colors to choose from");var t=this.prng.generateRandomInt(0,r.length-1);s.set(e,r[t]),r.splice(t,1)}}),s}generateCountries(e,t){let i=t.getMultiplayerCountries().length,r=[...e.humanPlayers,...e.aiPlayers].filter(isNotNullOrUndefined),s=new Map;return r.forEach(e=>{e.countryId===RANDOM_COUNTRY_ID&&s.set(e,this.prng.generateRandomInt(0,i-1))}),s}generateStartLocations(i,r){let e=[...i.humanPlayers,...i.aiPlayers].filter(isNotNullOrUndefined),t=e.filter(e=>e.startPos!==RANDOM_START_POS).map(e=>e.startPos),s=[...r.keys()].filter(e=>!t.includes(e)),a=[];for(;s.length;){var n=s.length?this.prng.generateRandomInt(0,s.length-1):0;a.push(...s.splice(n,1))}if(a.unshift(...t),3<=a.length)for(var o of[1,2])if(!(t.length-1>=o)){let e=a.map(e=>r[e]),t=this.findFarthestPointFrom(e.slice(0,o),e.slice(o));var l=e.findIndex(e=>e.x===t.x&&e.y===t.y);a.splice(o,0,...a.splice(l,1))}if(4<=a.length)if(t.length-1<3){let e=a.map(e=>r[e]),t=this.findFarthestPointFrom(e.slice(2,3),e.slice(3));i=e.findIndex(e=>e.x===t.x&&e.y===t.y);a.splice(3,0,...a.splice(i,1))}a.splice(0,t.length);let h=new Map,c=-1;return e.forEach(e=>{if(e.countryId!==OBS_COUNTRY_ID&&e.startPos===RANDOM_START_POS){if(c>=a.length-1)throw new RangeError("Map has fewer starting locations than players");h.set(e,a[++c])}}),h}findFarthestPointFrom(e,t){let r=e.map(e=>new Vector2(e.x,e.y)),s,a=0;if(!t.length)throw new Error("Search array must have at least one element");for(var n of t){let i=new Vector2(n.x,n.y);var o=r.reduce((e,t)=>e+i.distanceTo(t),0);o>=a&&(s=n,a=o)}return s}}class MapLightingTrait{get onChange(){return this._onChange.asEvent()}constructor(e,t){this.mapLighting=new MapLighting,this._onChange=new EventDispatcher,this.ambientChangeRate=e.ambientChangeRate,this.ambientChangeStep=e.ambientChangeStep,t&&this.mapLighting.copy(t)}setAmbientChangeRate(e){this.ambientChangeRate=e}setAmbientChangeStep(e){this.ambientChangeStep=e}setTargetAmbientIntensity(e){this.targetAmbient=e}getAmbient(){return this.mapLighting}[NotifyTick.onTick](){var e;void 0!==this.targetAmbient&&(this.ambientUpdateTicks??(this.ambientUpdateTicks=Math.floor(60*GameSpeed.BASE_TICKS_PER_SECOND*this.ambientChangeRate)),this.ambientUpdateTicks<=0?(this.ambientUpdateTicks=void 0,e=this.mapLighting.ambient,(e=this.targetAmbient-e)?(e=Math.sign(e)*Math.min(this.ambientChangeStep,Math.abs(e)),this.mapLighting.ambient+=e,this._onChange.dispatch(this,this.mapLighting)):this.targetAmbient=void 0):this.ambientUpdateTicks--)}}class Ai{constructor(e){this.ini=e}getIni(){return this.ini}}var _Bot_debugMode,BotState,__classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)},__classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i};class Bot{get game(){return this.context?.game}get player(){return this.context?.player}get gameApi(){return this.context?.game}get actionsApi(){return this.context?.player.actions}get productionApi(){return this.context?.player.production}get logger(){return this.context?.logger}constructor(e,t){this.name=e,this.country=t,_Bot_debugMode.set(this,!1)}setContext(e){this.context=e,this.context.logger.setDebugLevel(__classPrivateFieldGet(this,_Bot_debugMode,"f"))}setGameApi(e){}setActionsApi(e){}setProductionApi(e){}setLogger(e){}setDebugMode(e){return __classPrivateFieldSet(this,_Bot_debugMode,e,"f"),this.context?.logger.setDebugLevel(e),this}getDebugMode(){return __classPrivateFieldGet(this,_Bot_debugMode,"f")}onGameInit(e){}onGameStart(e){}onGameTick(e){}onGameEvent(e,t){}}_Bot_debugMode=new WeakMap,function(e){e[e.Initial=0]="Initial",e[e.Deployed=1]="Deployed",e[e.Attacking=2]="Attacking",e[e.Defeated=3]="Defeated"}(BotState=BotState||{});class DummyBot extends Bot{constructor(){super(...arguments),this.botState=BotState.Initial}onGameStart(t){var e=t.getTickRate();this.tickRatio=Math.ceil(e/5),this.enemyPlayers=t.getPlayers().filter(e=>e!==this.name&&!t.areAlliedPlayers(this.name,e))}onGameTick(e){if(e.getCurrentTick()%this.tickRatio==0)switch(this.botState){case BotState.Initial:{const i=e.getGeneralRules().baseUnit;if(e.getVisibleUnits(this.name,"self",e=>e.constructionYard).length){this.botState=BotState.Deployed;break}var t=e.getVisibleUnits(this.name,"self",e=>i.includes(e.name));t.length&&this.actionsApi.orderUnits([t[0]],OrderType.DeploySelected);break}case BotState.Deployed:break;case BotState.Attacking:e.getVisibleUnits(this.name,"self",e=>e.isSelectableCombatant).length||(this.botState=BotState.Defeated,this.actionsApi.quitGame())}}}class BotFactory{constructor(e){this.botsLib=e}create(e){if(!e.isAi)throw new Error(`Player "${e.name}" is not an AI`);switch(e.aiDifficulty){case AiDifficulty.Easy:return new DummyBot(e.name,e.country.name);case AiDifficulty.Medium:if(this.botsLib.SupalosaBot)return new this.botsLib.SupalosaBot(e.name,e.country.name);default:throw new Error(`Unsupported AI difficulty "${e.aiDifficulty}"`)}}}class ActionQueue{constructor(){this.actions=[]}push(...e){this.actions.push(...e)}getLast(){return this.actions[this.actions.length-1]}dequeueAll(){var e=[...this.actions];return this.actions.length=0,e}dequeueLast(){return this.actions.pop()}clear(){this.actions.length=0}}var ActionsApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},ActionsApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class ActionsApi{constructor(e,t,i,r,s){_ActionsApi_instances.add(this),_ActionsApi_actionFactory.set(this,void 0),_ActionsApi_actionQueue.set(this,void 0),_ActionsApi_game.set(this,void 0),_ActionsApi_bot.set(this,void 0),_ActionsApi_chatApi.set(this,void 0),ActionsApi_classPrivateFieldSet(this,_ActionsApi_actionFactory,t,"f"),ActionsApi_classPrivateFieldSet(this,_ActionsApi_actionQueue,i,"f"),ActionsApi_classPrivateFieldSet(this,_ActionsApi_game,e,"f"),ActionsApi_classPrivateFieldSet(this,_ActionsApi_bot,r,"f"),ActionsApi_classPrivateFieldSet(this,_ActionsApi_chatApi,s,"f")}placeBuilding(t,i,r){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.PlaceBuilding,e=>{e.buildingRules=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").rules.getBuilding(t),e.tile={x:i,y:r}})}sellObject(t){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.SellObject,e=>{e.objectId=t})}sellBuilding(e){this.sellObject(e)}toggleRepairWrench(t){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.ToggleRepair,e=>{e.buildingId=t})}toggleAlliance(t,i){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.ToggleAlliance,e=>{e.toPlayer=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").getPlayerByName(t),e.toggle=i})}pauseProduction(t){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.UpdateQueue,e=>{e.queueType=t,e.updateType=UpdateType.Pause})}resumeProduction(t){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.UpdateQueue,e=>{e.queueType=t,e.updateType=UpdateType.Resume})}queueForProduction(t,e,i,r){let s=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").rules.getObject(e,i);ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.UpdateQueue,e=>{e.queueType=t,e.updateType=UpdateType.Add,e.item=s,e.quantity=r})}unqueueFromProduction(t,e,i,r){let s=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").rules.getObject(e,i);ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.UpdateQueue,e=>{e.queueType=t,e.updateType=UpdateType.Cancel,e.item=s,e.quantity=r})}activateSuperWeapon(t,i,r){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.ActivateSuperWeapon,e=>{e.superWeaponType=t,e.tile={x:i.rx,y:i.ry},e.tile2=r?{x:r.rx,y:r.ry}:void 0})}orderUnits(t,i,r,s,a){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.SelectUnits,e=>{e.unitIds=t});let n;if(r){let e,t;if(s){e=void 0;var o=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").map.tiles.getByMapCoords(r,s);if(!o)throw new Error(`No tile found at rx,ry=${r},`+s);t=o,a&&(e=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").map.tileOccupation.getBridgeOnTile(o))}else{if(!ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").getWorld().hasObjectId(r))return;e=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").getObjectById(r),t=e.tile}n=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").createTarget(e,t)}ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.OrderUnits,e=>{e.orderType=i,e.target=n})}sayAll(e){ActionsApi_classPrivateFieldGet(this,_ActionsApi_chatApi,"f")?.sayAll(ActionsApi_classPrivateFieldGet(this,_ActionsApi_bot,"f").name,e)}setGlobalDebugText(t){ActionsApi_classPrivateFieldGet(this,_ActionsApi_bot,"f").getDebugMode()&&ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.DebugCommand,e=>{e.command=new DebugCommand(DebugCommandType.SetGlobalDebugText,{text:t||""})})}setUnitDebugText(t,i){ActionsApi_classPrivateFieldGet(this,_ActionsApi_bot,"f").getDebugMode()&&ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.DebugCommand,e=>{e.command=new DebugCommand(DebugCommandType.SetUnitDebugText,{unitId:t,label:i})})}quitGame(){ActionsApi_classPrivateFieldGet(this,_ActionsApi_instances,"m",_ActionsApi_pushAction).call(this,ActionType.ResignGame)}}var ApiEventType,_ActionsApi_actionFactory=new WeakMap,_ActionsApi_actionQueue=new WeakMap,_ActionsApi_game=new WeakMap,_ActionsApi_bot=new WeakMap,_ActionsApi_chatApi=new WeakMap,_ActionsApi_instances=new WeakSet,_ActionsApi_pushAction=function(e,t){let i=ActionsApi_classPrivateFieldGet(this,_ActionsApi_actionFactory,"f").create(e);i.player=ActionsApi_classPrivateFieldGet(this,_ActionsApi_game,"f").getPlayerByName(ActionsApi_classPrivateFieldGet(this,_ActionsApi_bot,"f").name),t?.(i),ActionsApi_classPrivateFieldGet(this,_ActionsApi_actionQueue,"f").push(i)},EventsApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},EventsApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};!function(e){e[e.ObjectOwnerChange=0]="ObjectOwnerChange",e[e.ObjectSpawn=1]="ObjectSpawn",e[e.ObjectUnspawn=2]="ObjectUnspawn",e[e.ObjectDestroy=3]="ObjectDestroy"}(ApiEventType=ApiEventType||{});class EventsApi{constructor(e){_EventsApi_instances.add(this),_EventsApi_eventBus.set(this,void 0),_EventsApi_listenerDisposers.set(this,[]),EventsApi_classPrivateFieldSet(this,_EventsApi_eventBus,e,"f")}subscribe(e,t){let i=void 0,r;r="function"==typeof e?e:(i=e,t);t=EventsApi_classPrivateFieldGet(this,_EventsApi_eventBus,"f").subscribe(e=>{e=EventsApi_classPrivateFieldGet(this,_EventsApi_instances,"m",_EventsApi_translateGameEvent).call(this,e);!e||void 0!==i&&i!==e.type||r(e)});return EventsApi_classPrivateFieldGet(this,_EventsApi_listenerDisposers,"f").push(t),t}dispose(){for(var e of EventsApi_classPrivateFieldGet(this,_EventsApi_listenerDisposers,"f"))e();EventsApi_classPrivateFieldGet(this,_EventsApi_listenerDisposers,"f").length=0}}var _EventsApi_eventBus=new WeakMap,_EventsApi_listenerDisposers=new WeakMap,_EventsApi_instances=new WeakSet,_EventsApi_translateGameEvent=function(t){switch(t.type){case EventType.ObjectOwnerChange:return{type:ApiEventType.ObjectOwnerChange,prevOwnerName:t.prevOwner.name,newOwnerName:t.target.owner.name,target:t.target.id};case EventType.ObjectSpawn:return{type:ApiEventType.ObjectSpawn,target:t.gameObject.id};case EventType.ObjectUnspawn:return{type:ApiEventType.ObjectUnspawn,target:t.gameObject.id};case EventType.ObjectDestroy:{let e=t;return e.target.isProjectile()?void 0:{type:ApiEventType.ObjectDestroy,target:e.target.id,attackerInfo:e.attackerInfo?{playerName:e.attackerInfo.player.name,objId:e.attackerInfo.obj?.id,weaponName:e.attackerInfo.weapon?.rules.name}:void 0}}default:return}},MapApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},MapApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class MapApi{constructor(e){_MapApi_instances.add(this),_MapApi_game.set(this,void 0),_MapApi_map.set(this,void 0),MapApi_classPrivateFieldSet(this,_MapApi_game,e,"f"),MapApi_classPrivateFieldSet(this,_MapApi_map,e.map,"f")}getRealMapSize(){return MapApi_classPrivateFieldGet(this,_MapApi_map,"f").tiles.getMapSize()}getStartingLocations(){return MapApi_classPrivateFieldGet(this,_MapApi_map,"f").startingLocations.map(e=>new Vector2(e.x,e.y))}getTheaterType(){return MapApi_classPrivateFieldGet(this,_MapApi_map,"f").getTheaterType()}getTile(e,t){t=MapApi_classPrivateFieldGet(this,_MapApi_map,"f").tiles.getByMapCoords(e,t);if(t&&MapApi_classPrivateFieldGet(this,_MapApi_map,"f").mapBounds.isWithinBounds(t))return t}getTilesInRect(e,t){let i=t?MapApi_classPrivateFieldGet(this,_MapApi_map,"f").tiles.getInRectangle(e,t):MapApi_classPrivateFieldGet(this,_MapApi_map,"f").tiles.getInRectangle(e);return i.filter(e=>MapApi_classPrivateFieldGet(this,_MapApi_map,"f").mapBounds.isWithinBounds(e))}getObjectsOnTile(e){return MapApi_classPrivateFieldGet(this,_MapApi_map,"f").getObjectsOnTile(e).map(e=>e.id)}hasBridgeOnTile(e){return!!e.onBridgeLandType}hasHighBridgeOnTile(e){return!!MapApi_classPrivateFieldGet(this,_MapApi_map,"f").tileOccupation.getBridgeOnTile(e)?.isHighBridge()}isPassableTile(e,t,i,r){return r=r??t===SpeedType.Foot,0<MapApi_classPrivateFieldGet(this,_MapApi_map,"f").terrain.getPassableSpeed(e,t,r,i)}findPath(e,t,i,r,s){let a=MapApi_classPrivateFieldGet(this,_MapApi_game,"f").map.terrain.computePath(e,t,i.tile,i.onBridge,r.tile,r.onBridge,{bestEffort:s?.bestEffort,excludeTiles:s?.excludeNodes?e=>s.excludeNodes({tile:e.tile,onBridge:!!e.onBridge}):void 0,maxExpandedNodes:s?.maxExpandedNodes});return a.map(e=>({tile:e.tile,onBridge:!!e.onBridge}))}getReachabilityMap(e,t){let i=MapApi_classPrivateFieldGet(this,_MapApi_game,"f").map.terrain.getIslandIdMap(e,t);return{isReachable(e,t){e=this.getRegionId(e),t=this.getRegionId(t);return void 0!==e&&e===t},getRegionId(e){return i.get(e.tile,e.onBridge)}}}isVisibleTile(e,t,i=0){var r=MapApi_classPrivateFieldGet(this,_MapApi_game,"f").getPlayerByName(t);if(!r)throw new Error(`Player "${t}" doesn't exist`);return!MapApi_classPrivateFieldGet(this,_MapApi_game,"f").mapShroudTrait.getPlayerShroud(r)?.isShrouded(e,i)}getTileResourceData(e){e=MapApi_classPrivateFieldGet(this,_MapApi_map,"f").getObjectsOnTile(e).find(e=>e.isOverlay()&&e.isTiberium()||e.isTerrain()&&e.rules.spawnsTiberium);return e?MapApi_classPrivateFieldGet(this,_MapApi_instances,"m",_MapApi_getTileResourceDataFromObject).call(this,e):void 0}getAllTilesResourceData(){var e;let t=[];for(e of MapApi_classPrivateFieldGet(this,_MapApi_game,"f").getWorld().getAllObjects()){var i=MapApi_classPrivateFieldGet(this,_MapApi_instances,"m",_MapApi_getTileResourceDataFromObject).call(this,e);i&&t.push(i)}return t}}var _MapApi_game=new WeakMap,_MapApi_map=new WeakMap,_MapApi_instances=new WeakSet,_MapApi_getTileResourceDataFromObject=function(t){let i;if(t.isOverlay()&&t.isTiberium()){let e=t.traits.get(TiberiumTrait);var r=e.getTiberiumType(),s=e.getBailCount();i={tile:t.tile,ore:r===TiberiumType.Ore?s:0,gems:r===TiberiumType.Gems?s:0,spawnsOre:!1}}else t.isTerrain()&&t.rules.spawnsTiberium&&(i={tile:t.tile,ore:0,gems:0,spawnsOre:!0});return i},RulesApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)},RulesApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i};class RulesApi{get allObjectRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").allObjectRules}get buildingRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").buildingRules}get infantryRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").infantryRules}get vehicleRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").vehicleRules}get aircraftRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").aircraftRules}get terrainRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").terrainRules}get overlayRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").overlayRules}get countryRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").countryRules}get general(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").general}get ai(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").ai}get crateRules(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").crateRules}get combatDamage(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").combatDamage}get radiation(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").radiation}constructor(e){_RulesApi_rules.set(this,void 0),RulesApi_classPrivateFieldSet(this,_RulesApi_rules,e,"f")}hasObject(e,t){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").hasObject(e,t)}getObject(e,t){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getObject(e,t)}getBuilding(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getBuilding(e)}getWeapon(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getWeapon(e)}getWarhead(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getWarhead(e)}getProjectile(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getProjectile(e)}getOverlayName(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getOverlayName(e)}getOverlayId(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getOverlayId(e)}getOverlay(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getOverlay(e)}getCountry(e){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getCountry(e)}getMultiplayerCountries(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getMultiplayerCountries()}getIni(){return RulesApi_classPrivateFieldGet(this,_RulesApi_rules,"f").getIni()}}var _RulesApi_rules=new WeakMap,GameApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},GameApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class GameApi{get mapApi(){return this.map}get rulesApi(){return this.rules}constructor(e,t){_GameApi_instances.add(this),_GameApi_game.set(this,void 0),_GameApi_useInternalRng.set(this,void 0),GameApi_classPrivateFieldSet(this,_GameApi_game,e,"f"),GameApi_classPrivateFieldSet(this,_GameApi_useInternalRng,t,"f"),this.map=new MapApi(e),this.rules=new RulesApi(e.rules)}isPlayerDefeated(e){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(e).defeated}areAlliedPlayers(e,t){var i=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(e);if(!i)throw new Error(`Player "${e}" doesn't exist`);e=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(t);if(!e)throw new Error(`Player "${t}" doesn't exist`);return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").alliances.areAllied(i,e)}canPlaceBuilding(e,t,i){var r=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(e);if(!r)throw new Error(`Player "${e}" doesn't exist`);return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getConstructionWorker(r).canPlaceAt(t,i,{normalizedTile:!0})}getBuildingPlacementData(e){e=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").art.getObject(e,ObjectType.Building);return{foundation:e.foundation,foundationCenter:e.foundationCenter}}getPlayers(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getNonNeutralPlayers().map(e=>e.name)}getPlayerData(e){let t=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(e);if(!t)throw new Error(`Player "${e}" doesn't exist`);return{name:t.name,country:t.country,startLocation:this.map.getStartingLocations()[t.startLocation??0],isObserver:t.isObserver,isAi:t.isAi,isCombatant:t.isCombatant(),credits:t.credits,power:{total:t.powerTrait?.power??0,drain:t.powerTrait?.drain??0,isLowPower:t.powerTrait?.level===PowerLevel.Low},radarDisabled:!!t.radarTrait?.isDisabled()}}getAllTerrainObjects(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getWorld().getAllObjects().filter(e=>e.isTerrain()).map(e=>e.id)}getAllUnits(t=()=>!0){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getWorld().getAllObjects().filter(e=>e.isTechno()&&t(e.rules)).map(e=>e.id)}getNeutralUnits(t=()=>!0){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getCivilianPlayer().getOwnedObjects().filter(e=>t(e.rules)).map(e=>e.id)}getUnitsInArea(e){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").map.technosByTile.queryRange(e).map(e=>e.id)}getVisibleUnits(e,r,t=()=>!0){const s=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getPlayerByName(e);if(!s)throw new Error(`Player "${e}" doesn't exist`);if("self"===r)return s.getOwnedObjects().filter(e=>t(e.rules)).map(e=>e.id);let a;if("allied"===r)a=e=>e.owner===s||GameApi_classPrivateFieldGet(this,_GameApi_game,"f").alliances.areAllied(e.owner,s);else{if("hostile"!==r&&"enemy"!==r)throw new Error("Unexpected type "+r);{let i=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").mapShroudTrait.getPlayerShroud(s);a=t=>GameApi_classPrivateFieldGet(this,_GameApi_game,"f").map.tileOccupation.calculateTilesForGameObject(t.tile,t).some(e=>!i?.isShrouded(e,t.tileElevation))&&t.owner!==s&&!GameApi_classPrivateFieldGet(this,_GameApi_game,"f").alliances.areAllied(t.owner,s)&&("enemy"!==r||t.owner.isCombatant())}}return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getWorld().getAllObjects().filter(e=>e.isTechno()&&!e.isDestroyed&&a(e)&&t(e.rules)).map(e=>e.id)}getGameObjectData(t){if(GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getWorld().hasObjectId(t)){let e=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getObjectById(t);return{id:e.id,type:e.type,name:e.name,rules:e.rules,tile:e.tile,tileElevation:e.tileElevation,worldPosition:e.position.worldPosition.clone(),foundation:e.getFoundation(),hitPoints:e.healthTrait?.getHitPoints(),maxHitPoints:e.healthTrait?.maxHitPoints,owner:e.isTechno()?e.owner.name:void 0}}}getUnitData(t){var i=this.getGameObjectData(t);if(i){let e=GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getObjectById(t);if(!e.isTechno())throw new Error(`Game object with id ${t} is not a Techno type`);return{...i,owner:e.owner.name,sight:e.sight,veteranLevel:e.veteranLevel,guardMode:e.guardMode,purchaseValue:e.purchaseValue,primaryWeapon:e.primaryWeapon?GameApi_classPrivateFieldGet(this,_GameApi_instances,"m",_GameApi_getWeaponData).call(this,e.primaryWeapon):void 0,secondaryWeapon:e.secondaryWeapon?GameApi_classPrivateFieldGet(this,_GameApi_instances,"m",_GameApi_getWeaponData).call(this,e.secondaryWeapon):void 0,deathWeapon:e.armedTrait?.deathWeapon?GameApi_classPrivateFieldGet(this,_GameApi_instances,"m",_GameApi_getWeaponData).call(this,e.armedTrait.deathWeapon):void 0,attackState:e.attackTrait?.attackState,direction:e.direction,onBridge:e.isInfantry()||e.isVehicle()?e.onBridge:void 0,zone:e.isUnit()?e.zone:void 0,buildStatus:e.isBuilding()?e.buildStatus:void 0,factory:e.isBuilding()&&e.factoryTrait?{deliveringUnit:e.factoryTrait.deliveringUnit?.id,status:e.factoryTrait.status}:void 0,rallyPoint:e.isBuilding()?e.rallyTrait?.getRallyPoint():void 0,isPoweredOn:e.isBuilding()&&e.poweredTrait?.isPoweredOn(),hasWrenchRepair:e.isBuilding()&&!e.autoRepairTrait.isDisabled(),turretFacing:e.isBuilding()||e.isVehicle()?e.turretTrait?.facing:void 0,turretNo:e.isVehicle()?e.turretNo:void 0,garrisonUnitCount:e.isBuilding()?e.garrisonTrait?.units.length:void 0,garrisonUnitsMax:e.isBuilding()?e.garrisonTrait?.maxOccupants:void 0,passengerSlotCount:e.isVehicle()?e.transportTrait?.getOccupiedCapacity():void 0,passengerSlotMax:e.isVehicle()?e.transportTrait?.getMaxCapacity():void 0,isIdle:!e.unitOrderTrait.hasTasks(),canMove:e.isUnit()?!e.moveTrait.isDisabled():void 0,velocity:e.isUnit()?e.moveTrait.velocity.clone():void 0,stance:e.isInfantry()?e.stance:void 0,harvestedOre:e.isVehicle()?e.harvesterTrait?.ore:void 0,harvestedGems:e.isVehicle()?e.harvesterTrait?.gems:void 0,ammo:e.isAircraft()?e.ammo:void 0,isWarpedOut:e.warpedOutTrait.isActive(),mindControlledBy:e.mindControllableTrait?.getController()?.id,tntTimer:e.tntChargeTrait?.getTicksLeft()}}}getAllSuperWeaponData(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").getCombatants().map(t=>t.superWeaponsTrait.getAll().map(e=>({playerName:t.name,type:e.rules.type,status:e.status,timerSeconds:e.getTimerSeconds()}))).flat()}getGeneralRules(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").rules.general}getRulesIni(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").rules.getIni()}getArtIni(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").art.getIni()}getAiIni(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").ai.getIni()}generateRandomInt(e,t){if(GameApi_classPrivateFieldGet(this,_GameApi_useInternalRng,"f"))return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").generateRandomInt(e,t);var i=this.generateRandom();return Math.round(i*(t-e))+e}generateRandom(){return GameApi_classPrivateFieldGet(this,_GameApi_useInternalRng,"f")?GameApi_classPrivateFieldGet(this,_GameApi_game,"f").generateRandom():Math.random()}getTickRate(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").speed.value*GameSpeed.BASE_TICKS_PER_SECOND}getBaseTickRate(){return GameSpeed.BASE_TICKS_PER_SECOND}getCurrentTick(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").currentTick}getCurrentTime(){return GameApi_classPrivateFieldGet(this,_GameApi_game,"f").currentTime/1e3}}function formatTimeDuration(e,t=!1){var i=Math.floor(e/3600);e-=3600*i;var r=Math.floor(e/60),e=e-=60*r;return[...i||!t?[i]:[],pad(r,"00"),pad(e,"00")].join(":")}var _GameApi_game=new WeakMap,_GameApi_useInternalRng=new WeakMap,_GameApi_instances=new WeakSet,_GameApi_getWeaponData=function(e){return{type:e.type,rules:e.rules,projectileRules:e.projectileRules,warheadRules:e.warhead.rules,minRange:e.minRange,maxRange:e.range,speed:e.speed,cooldownTicks:e.getCooldownTicks()}},LoggerApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},LoggerApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class LoggerApi{constructor(e,t){_LoggerApi_instances.add(this),_LoggerApi_logger.set(this,void 0),_LoggerApi_game.set(this,void 0),LoggerApi_classPrivateFieldSet(this,_LoggerApi_logger,e,"f"),LoggerApi_classPrivateFieldSet(this,_LoggerApi_game,t,"f")}setDebugLevel(e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").setLevel(e?AppLogger.DEBUG:AppLogger.WARN)}debug(...e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").debug(LoggerApi_classPrivateFieldGet(this,_LoggerApi_instances,"m",_LoggerApi_getLogPrefix).call(this),...e)}info(...e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").info(LoggerApi_classPrivateFieldGet(this,_LoggerApi_instances,"m",_LoggerApi_getLogPrefix).call(this),...e)}log(...e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").log(LoggerApi_classPrivateFieldGet(this,_LoggerApi_instances,"m",_LoggerApi_getLogPrefix).call(this),...e)}warn(...e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").warn(LoggerApi_classPrivateFieldGet(this,_LoggerApi_instances,"m",_LoggerApi_getLogPrefix).call(this),...e)}error(...e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").error(LoggerApi_classPrivateFieldGet(this,_LoggerApi_instances,"m",_LoggerApi_getLogPrefix).call(this),...e)}time(e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").time(e)}timeEnd(e){LoggerApi_classPrivateFieldGet(this,_LoggerApi_logger,"f").timeEnd(e)}}var _LoggerApi_logger=new WeakMap,_LoggerApi_game=new WeakMap,_LoggerApi_instances=new WeakSet,_LoggerApi_getLogPrefix=function(){return"["+formatTimeDuration(Math.floor(LoggerApi_classPrivateFieldGet(this,_LoggerApi_game,"f").getCurrentTime()))+"]"},ProductionApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},ProductionApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class ProductionApi{constructor(e){_ProductionApi_production.set(this,void 0),ProductionApi_classPrivateFieldSet(this,_ProductionApi_production,e,"f")}isAvailableForProduction(e){return ProductionApi_classPrivateFieldGet(this,_ProductionApi_production,"f").isAvailableForProduction(e)}getAvailableObjects(t){let e=ProductionApi_classPrivateFieldGet(this,_ProductionApi_production,"f").getAvailableObjects();return void 0!==t&&(e=e.filter(e=>this.getQueueTypeForObject(e)===t)),e}getQueueTypeForObject(e){return ProductionApi_classPrivateFieldGet(this,_ProductionApi_production,"f").getQueueTypeForObject(e)}getQueueData(e){let t=ProductionApi_classPrivateFieldGet(this,_ProductionApi_production,"f").getQueue(e);return{size:t.currentSize,maxSize:t.maxSize,status:t.status,type:t.type,items:t.getAll().map(e=>({rules:e.rules,quantity:e.quantity}))}}}var _PlayerApi_gameApi,SlotType,ReplayEventType,ChatRecipientType,_ProductionApi_production=new WeakMap,PlayerApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},PlayerApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class PlayerApi{constructor(e,t,i,r){this.name=e,this.actions=i,this.production=r,_PlayerApi_gameApi.set(this,void 0),PlayerApi_classPrivateFieldSet(this,_PlayerApi_gameApi,t,"f")}getPlayerData(){return PlayerApi_classPrivateFieldGet(this,_PlayerApi_gameApi,"f").getPlayerData(this.name)}isDefeated(){return PlayerApi_classPrivateFieldGet(this,_PlayerApi_gameApi,"f").isPlayerDefeated(this.name)}isAlliedWith(e){return PlayerApi_classPrivateFieldGet(this,_PlayerApi_gameApi,"f").areAlliedPlayers(this.name,e)}canPlaceBuilding(e,t){return PlayerApi_classPrivateFieldGet(this,_PlayerApi_gameApi,"f").canPlaceBuilding(this.name,e,t)}getVisibleUnits(e,t=()=>!0){return PlayerApi_classPrivateFieldGet(this,_PlayerApi_gameApi,"f").getVisibleUnits(this.name,e,t)}}_PlayerApi_gameApi=new WeakMap;class BotContext{constructor(e,t,i){this.game=e,this.player=t,this.logger=i}}class BotManager{static factory(e,t,i,r){return new this(e,new ActionQueue,t,i,r)}constructor(e,t,i,r,s){this.actionFactory=e,this.actionQueue=t,this.botFactory=i,this.botDebugIndex=r,this.actionLogger=s,this.bots=new Map,this.disposables=new CompositeDisposable}init(t){this.gameApi=new GameApi(t,!0);let e=new EventsApi(t.events);var i,r;for(i of t.getCombatants().filter(e=>e.isAi))this.bots.set(i,this.botFactory.create(i));this.updateDebugBotIndex(this.botDebugIndex.value,t);let s=e=>this.updateDebugBotIndex(e,t);this.botDebugIndex.onChange.subscribe(s),this.disposables.add(()=>this.botDebugIndex.onChange.unsubscribe(s)),e.subscribe(t=>this.bots.forEach(e=>e.onGameEvent(t,this.gameApi))),this.disposables.add(e);for(r of this.bots.values()){var a=new PlayerApi(r.name,this.gameApi,new ActionsApi(t,this.actionFactory,this.actionQueue,r),new ProductionApi(t.getPlayerByName(r.name).production)),n=new LoggerApi(AppLogger.get(r.name),this.gameApi);r.setGameApi(this.gameApi),r.setActionsApi(a.actions),r.setProductionApi(a.production),r.setLogger(n),r.setContext?.(new BotContext(this.gameApi,a,n)),r.onGameInit?.(this.gameApi)}}onGameStart(){if(!this.gameApi)throw new Error("Bot manager is not initialized");for(var e of this.bots.values())e.onGameStart(this.gameApi)}update(e){var t,i;for(t of this.actionQueue.dequeueAll()){t.process();var r=t.print();r&&this.actionLogger.debug(`(${t.player.name})@${e.currentTick}: `+r)}for(i of e.getCombatants().filter(e=>e.isAi))this.bots.get(i).onGameTick(this.gameApi)}updateDebugBotIndex(e,t){var i,r=0<e?t.getAiPlayerName(e):void 0;for(i of this.bots.values())i.setDebugMode(i.name===r)}dispose(){this.gameApi=void 0,this.bots.clear(),this.disposables.dispose()}}class GameFactory{static create(e,t,i,r,s,a,n,o,l,h,c,u,d,p,g,m,y){let T=i.clone().mergeWith(a);for(var f of n)T.mergeWith(f);T.mergeWith(e);var v=r.clone().mergeWith(e.artOverrides??new IniFile);let b=new Rules(T,p);a=new Art(b,v,e,p),n=new Ai(s);b.applySpecialFlags(e.specialFlags),GameOptSanitizer.sanitize(h,b);let w=new Rules(i),S=w.getMultiplayerCountries(),A=[...w.getMultiplayerColors().values()],_=Prng.factory(o,l),O=new GameMap(e,t,b,_.generateRandomInt.bind(_));r=new World,v=c.getById(h.gameMode).type,p=new PlayerList,s=new Alliances(p),i=new UnitSelection,e=new BoxedVar(1),t=new ObjectFactory(O.tiles,O.tileOccupation,O.bridges,e),c=new ActionFactory,d=new BotFactory(d),y=BotManager.factory(c,d,m,y);let E=new Game(r,O,b,a,n,o,l,h,v,p,i,s,e,t,y);(new ActionFactoryReg).register(c,E,void 0),E.traits.add(new PowerTrait_PowerTrait),E.sellTrait=new SellTrait(E,b.general),E.traits.add(E.sellTrait),E.traits.add(new RadarTrait_RadarTrait);let C=new ProductionTrait(b,g);E.traits.add(C),E.mapShroudTrait=new MapShroudTrait(O,s),E.traits.add(E.mapShroudTrait),E.mapRadiationTrait=new MapRadiationTrait(O),E.traits.add(E.mapRadiationTrait),E.mapLightingTrait=new MapLightingTrait(b.audioVisual,O.getLighting()),E.traits.add(E.mapLightingTrait),E.traits.add(new SuperWeaponsTrait),E.traits.add(new SharedDetectDisguiseTrait_SharedDetectDisguiseTrait),E.traits.add(new SharedDetectCloakTrait),E.crateGeneratorTrait=new CrateGeneratorTrait(h.cratesAppear),E.traits.add(E.crateGeneratorTrait),u||(E.stalemateDetectTrait=new StalemateDetectTrait,E.traits.add(E.stalemateDetectTrait));let k=new PlayerFactory(b,h,C.getAvailableObjects()),P=GameOptRandomGen.factory(o,l),I=P.generateColors(h),B=P.generateCountries(h,w),N=P.generateStartLocations(h,O.startingLocations),R=[...h.humanPlayers,...h.aiPlayers].filter(isNotNullOrUndefined);return R.forEach(e=>{let t,i,r;if(isHumanPlayerInfo(e)?(t=e.name,i=!1):(t=E.getAiPlayerName(e),i=!0,r=e.difficulty),e.countryId!==OBS_COUNTRY_ID){var s=B.get(e)??e.countryId,a=I.get(e)??e.colorId,e=N.get(e)??e.startPos;if(s===RANDOM_COUNTRY_ID)throw new Error("Random country should have been resolved by now");if(a===RANDOM_COLOR_ID)throw new Error("Random color should have been resolved by now");if(e===RANDOM_START_POS)throw new Error("Random start location should have been resolved by now");s=S[s].name,s=Country.factory(s,b),a=A[a];E.addPlayer(k.createCombatant(t,s,e,a,i,r))}else E.addPlayer(k.createObserver(t,b))}),E.addPlayer(k.createNeutral(b,"@@NEUTRAL@@")),E}}class AiPlayTurnManager{constructor(e,t,i,r,s,a){this.game=e,this.inputActions=t,this.replayRecorder=i,this.actionSerializer=r,this.actionFactory=s,this.actionLogger=a,this.errorState=!1}init(){this.gameTurnMillis=1e3/(this.game.speed.value*GameSpeed.BASE_TICKS_PER_SECOND)}setErrorState(){this.errorState=!0}getErrorState(){return this.errorState}getTurnMillis(){return this.gameTurnMillis}doGameTurn(){if(!this.errorState){if(this.game.status!==GameStatus.Ended){var t,e=this.inputActions.dequeueAll();const r=new Map;for(t of e){var i=this.actionSerializer.getActionPayload(t);let e=r.get(t.player);e||(e=[],r.set(t.player,e)),e.push(i)}this.replayRecorder.recordActions(this.game.currentTick,new Map([...r].map(([e,t])=>[this.game.getPlayerNumber(e),t]))),r.forEach((t,i)=>{if(!t.length){let e=new NoAction;e.player=i,t.push(this.actionSerializer.getActionPayload(e))}}),this.processActions(r)}this.game.update()}}processActions(e){[...e].forEach(([i,e])=>e.forEach(e=>{let t=this.actionFactory.create(e.id);t.player=i,t.unserialize(e.params),t.process();e=t.print();e&&this.actionLogger?.debug(`(${i.name})@${this.game.currentTick}: `+e)}))}dispose(){}}!function(e){e[e.Closed=0]="Closed",e[e.Open=1]="Open",e[e.OpenObserver=2]="OpenObserver",e[e.Player=3]="Player",e[e.Ai=4]="Ai"}(SlotType=SlotType||{});class MapNameLegacyEncoder{encode(e){let r=[],s=0;return e.split("").forEach((e,t)=>{var i=e.charCodeAt(0)<<2*t-7*s,e=127&i,t=i>>7&127,i=i>>14&127;i&&s++,r.push(e,t),i&&r.push(i)}),r.push(0,0),2<=e.length&&r.push(0),r=r.map(e=>128^e),r.map(e=>String.fromCharCode(e)).join("")}decode(e){let i=e.split("").map(e=>e.charCodeAt(0));for(i=i.map(e=>128^e);0===i[i.length-1];)i.pop();let r=[],s=0,a=0;for(;i.length;){var n=r.length,o=i.shift(),l=i.shift();let e=0,t=!1;(-1!==[1,2,3].indexOf(i[0])||n>s+3)&&(e=i.shift(),s=n,t=!0);n=(e<<14|l<<7|o)>>2*n-7*a;r.push(127&n),t&&a++}return r.map(e=>String.fromCharCode(e)).join("")}}class FileNameEncoder{encode(e){return e.match(/^[a-z0-9-_]+\.[a-z]{3}$/i)?e:Base64.encode(utf16ToBinaryString(e))}decode(e){return e.match(/\.[a-z]{3}$/i)?e:binaryStringToUtf16(Base64.decode(e))}}class Serializer{serializeOptions(e,t=!1){let i=e.gameMode,r=t?(new MapNameLegacyEncoder).encode(e.mapTitle):Base64.encode(utf16ToBinaryString(e.mapTitle)),s=(new FileNameEncoder).encode(e.mapName);t=["0","0",6-e.gameSpeed,e.credits,e.unitCount,Number(e.shortGame),Number(e.superWeapons),Number(e.buildOffAlly),Number(e.mcvRepacks),Number(e.cratesAppear),i,Number(e.hostTeams??!1),r,e.maxSlots,Number(e.mapOfficial),e.mapSizeBytes,s,e.mapDigest,Number(e.destroyableBridges),Number(e.multiEngineer),Number(e.noDogEngiKills),...e.unknown?[e.unknown]:[]].join(",");return t+`:${e.humanPlayers.map(e=>""+e.name+`,${e.countryId},${e.colorId},${e.startPos},${e.teamId},0,0,0`).join(",")}:@:${this.serializeAiOpts(e.aiPlayers)},`}serializeAiOpts(e){return e.map(e=>e?`${e.difficulty},${e.countryId},${e.colorId},${e.startPos},`+e.teamId:"0,-1,-1,-1,-1").join(",")}serializePingData(e){return e.length+","+e.map(e=>e.playerName+","+e.ping).join(",")}serializeSlotData(e){return e.map(e=>{if(e.type===SlotType.Closed)return"@Closed@";if(e.type===SlotType.Open)return"@Open@";if(e.type===SlotType.OpenObserver)return"@OpenObserver@";if(e.type===SlotType.Ai){if(e.difficulty===AiDifficulty.Easy)return"@EasyAI@";if(e.difficulty===AiDifficulty.Medium)return"@MediumAI@";if(e.difficulty===AiDifficulty.Brutal)return"@HardAI@"}else if(e.type===SlotType.Player)return e.name;throw new Error("Unexpected slot info with type "+SlotType[e.type])}).join(",")+","}serializeLoadInfo(e){return e.map(e=>[e.name,e.status,e.loadPercent,e.ping,e.lagAllowanceMillis].join(",")).join(",")}serializePlayerActions(e){let t=new DataStream;t.writeUint8(e.length);for(var{id:i,params:r}of e)if(t.writeUint8(i),t.writeUint16(r.byteLength),0<r.byteLength){if(r.byteLength>Serializer.MAX_ACTION_PAYLOAD_SIZE-t.position)throw console.error(`Action #${i} payload exceeds max data size`,r),new RangeError("Maximum payload data size exceeded");t.writeUint8Array(r)}return t.toUint8Array()}serializeAllPlayerActions(e,t){e.writeUint8(t.size);for(var[i,r]of t){e.writeUint8(i);var s=this.serializePlayerActions(r);if(e.writeUint16(s.byteLength),0<s.byteLength){if(s.byteLength>Serializer.MAX_ACTION_PAYLOAD_SIZE)throw console.error(`Player #${i} actions payload exceeds max data size`,r),new RangeError("Maximum payload data size exceeded");e.writeUint8Array(s)}}}serializeMapData(e){return binaryStringToUint8Array(e)}}Serializer.MAX_ACTION_PAYLOAD_SIZE=65536;class Parser{parseOptions(e){let t={},[i,r,,s]=e.split(":"),a=i.split(",");a.shift(),a.shift(),t.gameSpeed=6-Number(a.shift()),t.credits=Number(a.shift()),t.unitCount=Number(a.shift()),t.shortGame=Boolean(Number(a.shift())),t.superWeapons=Boolean(Number(a.shift())),t.buildOffAlly=Boolean(Number(a.shift())),t.mcvRepacks=Boolean(Number(a.shift())),t.cratesAppear=Boolean(Number(a.shift())),t.gameMode=Number(a.shift()),t.hostTeams=Boolean(Number(a.shift()));e=a.shift();return t.mapTitle=Base64.isBase64(e)?binaryStringToUtf16(Base64.decode(e)):(new MapNameLegacyEncoder).decode(e),t.maxSlots=Number(a.shift()),t.mapOfficial=Boolean(Number(a.shift())),t.mapSizeBytes=Number(a.shift()),t.mapName=(new FileNameEncoder).decode(a.shift()),t.mapDigest=a.shift(),t.destroyableBridges=Boolean(Number(a.shift()??"1")),t.multiEngineer=Boolean(Number(a.shift()??"0")),t.noDogEngiKills=Boolean(Number(a.shift()??"0")),t.unknown=a.length?a.join(","):void 0,t.humanPlayers=this.parsePlayerOpts(r),t.aiPlayers=this.parseAiOpts(s?.slice(0,-1)),t}parsePlayerOpts(e){var i=e.split(",");if(i.length%8!=0)throw new Error("Couldn't parse gameopt: unexpected players data length "+i.length);let r=[];for(let e=0,t=Math.floor(i.length/8);e<t;++e){var s={name:i[8*e],countryId:Number(i[8*e+1]),colorId:Number(i[8*e+2]),startPos:Number(i[8*e+3]),teamId:Number(i[8*e+4])};r.push(s)}return r}parseAiOpts(e){let i=[];if(e){var r=e.split(",");if(r.length%5!=0)throw new Error("Couldn't parse gameopt: unexpected ai data length "+r.length);for(let e=0,t=Math.floor(r.length/5);e<t;++e){var s={difficulty:Number(r[5*e]),countryId:Number(r[5*e+1]),colorId:Number(r[5*e+2]),startPos:Number(r[5*e+3]),teamId:Number(r[5*e+4])};i.push(-1!==s.countryId?s:void 0)}}return i}parseTopic(e){var t=e.split(",");if(!(t.length<6)){var i=t[0],r=Number(t[1]),s=i[2],a=t[2],n=t[3],e=t[4],i=(new FileNameEncoder).decode(t[5]);return{description:t[6]?binaryStringToUtf16(Base64.decode(t[6])):"",modHash:r,modName:t[7]?binaryStringToUtf16(Base64.decode(t[7])):void 0,aiPlayers:Number(a),maxPlayers:Number(s),observers:Number(n),observable:Boolean(Number(e)),mapName:i}}}parsePingData(e){var i=e.split(",").slice(1);if(i.length%2)throw new Error("Couldn't parse gameopt: unexpected ping data length "+i.length);let r=[];for(let e=0,t=Math.floor(i.length/2);e<t;++e)r.push({playerName:i[2*e],ping:Number(i[2*e+1])});return r}parseSlotData(e){var i;let r=[];for(i of e.slice(1,-1).split(",")){let t={};if("@Closed@"===i)t.type=SlotType.Closed;else if("@Open@"===i)t.type=SlotType.Open;else if("@OpenObserver@"===i)t.type=SlotType.OpenObserver;else if(-1!==["@EasyAI@","@MediumAI@","@HardAI@"].indexOf(i)){t.type=SlotType.Ai;let e;if("@EasyAI@"===i)e=AiDifficulty.Easy;else if("@MediumAI@"===i)e=AiDifficulty.Medium;else{if("@HardAI@"!==i)throw new Error("Couldn't parse gameopt: unknown slot type "+i);e=AiDifficulty.Brutal}t.difficulty=e}else t.type=SlotType.Player,t.name=i;r.push(t)}return r}parsePlayerActions(e){let t=new DataStream(e);var i=t.readUint8();let r=[];for(let e=0;e<i;++e){var s=t.readUint8(),a=t.readUint16(),a=0<a?t.readUint8Array(a):new Uint8Array;r.push({id:s,params:a})}return r}parseAllPlayerActions(t){var i=t.readUint8();let r=new Map;for(let e=0;e<i;++e){var s=t.readUint8(),a=t.readUint16(),a=0<a?t.readUint8Array(a):new Uint8Array,a=this.parsePlayerActions(a);r.set(s,a)}return r}parseMapData(e){return uint8ArrayToBinaryString(e)}}class ReplayEvent{constructor(e,t){this.type=e,this.tickNo=t}}!function(e){e[e.TurnActions=0]="TurnActions",e[e.ChatMessage=1]="ChatMessage",e[e.Taunt=2]="Taunt"}(ReplayEventType=ReplayEventType||{});class ChatMessageReplayEvent extends ReplayEvent{constructor(e){super(ReplayEventType.ChatMessage,e)}serialize(){return this.payload.playerId+":"+Base64.encode(utf16ToBinaryString(this.payload.message))}unserialize(e){var[t,e]=e.split(":"),t=Number(t),e=binaryStringToUtf16(Base64.decode(e));this.payload={playerId:t,message:e}}}class TauntReplayEvent extends ReplayEvent{constructor(e){super(ReplayEventType.Taunt,e)}serialize(){return this.payload.playerId+":"+this.payload.tauntNo}unserialize(e){var[t,e]=e.split(":"),t=Number(t),e=Number(e);this.payload={playerId:t,tauntNo:e}}}class TurnActionsReplayEvent extends ReplayEvent{constructor(e,t,i){super(ReplayEventType.TurnActions,i),this.gameOptsParser=e,this.gameOptsSerializer=t}serialize(){let e=new DataStream;return this.gameOptsSerializer.serializeAllPlayerActions(e,new Map(this.payload)),uint8ArrayToBase64String(e.toUint8Array())}unserialize(e){e=new DataStream(base64StringToUint8Array(e)),e=this.gameOptsParser.parseAllPlayerActions(e);this.payload=[...e]}}class ReplayEventFactory{constructor(e,t){this.gameOptsParser=e,this.gameOptsSerializer=t}create(e,t){switch(e){case ReplayEventType.TurnActions:return new TurnActionsReplayEvent(this.gameOptsParser,this.gameOptsSerializer,t);case ReplayEventType.ChatMessage:return new ChatMessageReplayEvent(t);case ReplayEventType.Taunt:return new TauntReplayEvent(t);default:throw new Error(`Unsupported replay event type "${e}" at game tick "${t}"`)}}}async function*makeTextFileLineIterator(e){const t=new TextDecoder("utf-8");let i=e.stream().getReader(),{value:r,done:s}=await i.read();r=r?t.decode(r,{stream:!0}):"";let a=/\r\n|\n|\r/gm,n=0;for(;;){var o=a.exec(r);if(o)yield r.substring(n,o.index),n=a.lastIndex;else{if(s)break;o=r.substr(n);({value:r,done:s}=await i.read()),r=o+(r?t.decode(r,{stream:!0}):""),n=a.lastIndex=0}}n<r.length&&(yield r.substr(n))}const REPLAY_VERSION=6,supportedReplayVersions=[5,6];class Replay{constructor(){this.name="",this.events=[]}static sanitizeFileName(e,t="_"){return e.replace(/[/?<>\\:*|"]/g,t).replace(/[\x00-\x1f\x7f\x80-\x9f]/g,t).slice(0,this.maxNameLength)}init(e,t,i,r,s){this.gameId=e,this.gameTimestamp=t,this.gameOpts=i,this.engineVersion=r,this.modHash=s,this.name=Replay.sanitizeFileName(this.gameOpts.mapTitle+" "+(new Date).toISOString().replace(/(\.|,)\d+Z$/,"Z")),this.timestamp=Date.now()}writeEvent(...e){this.events.push(...e)}finish(e){this.endTick=e}getEvents(){return this.events}*flush(){if(!this.gameOpts)throw new Error("Game options must be set first");if(!this.engineVersion)throw new Error("Engine version is not set");if(void 0===this.modHash)throw new Error("Mod hash is not set");let e=new Serializer,t=this.getHeaderTag()+"\n";for(t+=`ENGINE ${this.engineVersion} ${this.modHash}
|
|
2
|
+
`,t+=[this.gameId,this.gameTimestamp,e.serializeOptions(this.gameOpts)].join(" ")+"\n",yield t,t="";void 0===this.endTick||this.events.length;){for(var i of this.events)t+=i.tickNo+"="+i.type+"|"+i.serialize()+"\n";this.events.length=0,yield t,t=""}t+=this.getEndTag()+" "+this.endTick+"\n",this.debugInfo&&(t+=Base64.encode(utf16ToBinaryString(this.debugInfo))+"\n"),yield t}serialize(){if(void 0===this.endTick)throw new Error("Replay is not finished");let e="";var t,i=this.events.slice();for(t of this.flush())e+=t;return this.events=i,e}async parseHeader(e){let t=0,i,r,s,a,n,o;var l;for await(l of"string"==typeof e?e.split("\n"):makeTextFileLineIterator(e)){if(0===t)i=this.readReplayVersion(l);else if(1===t){if(!l.match(Replay.engineLineRegex))throw new Error("Missing or invalid game engine version line");var h=l.split(" ");r=h[1],s=Number(i<4?"0":h[2])}else{if(2!==t)break;if(!l.match(/^([a-zA-Z0-9-]+) \d+ .*$/))throw new Error("Missing or invalid game id/time/opts line");var[c,u,h]=l.split(" ");a=c,n=Number(u),o=i<6?Base64.decode(h):h}t++}if(t<3)throw new Error("Bad replay header");return{replayVersion:i,engineVersion:r,modHash:s,gameId:a,gameTimestamp:n,gameOptsSerialized:o}}unserialize(e,t){let i=e.split("\n");var r=this.readReplayVersion(i.shift()||"");if(!supportedReplayVersions.includes(r))throw new Error("Unsupported replay version "+r);let s=new Parser,a=i.shift();if(!a||!a.match(Replay.engineLineRegex))throw new Error("Missing or invalid game engine version line");var[,n,o]=a.split(" ");let l=i.shift();if(!l)throw new Error("Missing game id/time/opts line");e=l.match(/^([a-zA-Z0-9-]+) (\d+) (.*)$/);if(!e)throw new Error("Invalid game id/time/opts line");let[,h,c,u]=e;r<6&&(u=Base64.decode(u));r=s.parseOptions(u);this.init(h,Number(c),r,n,Number(o)),this.name=t.name,this.timestamp=t.timestamp;let d,p=!1;for(;d=i.shift();){if(d.startsWith(this.getEndTag())){p=!0;break}var g=d.match(/^(\d+)=(\d+)\|(.+)$/);if(!g)throw new Error(`Invalid event line "${d}"`);var[,m,y,g]=g,m=Number(m),y=Number(y);let e=new ReplayEventFactory(s,new Serializer).create(y,m);e.unserialize(g),this.writeEvent(e)}if(!p)throw new Error("Incomplete replay data");t=d.match(new RegExp(`^${this.getEndTag()} (\\d+)$`));if(!t)throw new Error("Invalid end tag");this.endTick=Number(t[1]),1<=i.length&&(this.debugInfo=binaryStringToUtf16(Base64.decode(i[0])))}getHeaderTag(){return"RA2TSREPL_v"+REPLAY_VERSION}readReplayVersion(e){e=e.match(/^RA2TSREPL_v(\d+)$/);if(!e||e.length<2)throw new Error("Unknown replay format");return Number(e[1])}getEndTag(){return"END"}}Replay.extension=".rpl",Replay.maxNameLength=128,Replay.engineLineRegex=/^ENGINE \d+\.\d+( \d+)?$/;class ReplayRecorder{constructor(e,t,i,r){this.replay=e,this.playerId=t,this.humanPlayers=i,this.actionSerializer=r}recordActions(t,i){if(Array.isArray(i)){let e=new TurnActionsReplayEvent(new Parser,new Serializer,t);e.payload=[[this.playerId,i.map(e=>this.actionSerializer.getActionPayload(e))]],this.replay.writeEvent(e)}else if(this.hasActualActions(i)){let e=new TurnActionsReplayEvent(new Parser,new Serializer,t);e.payload=[...i].map(([e,t])=>[e,t]),this.replay.writeEvent(e)}}recordChatMessage(e,t,i){let r=new ChatMessageReplayEvent(e);r.payload={playerId:this.humanPlayers.findIndex(e=>e.name===t),message:i},this.replay.writeEvent(r)}recordTaunt(e,t,i){let r=new TauntReplayEvent(e);r.payload={playerId:this.humanPlayers.findIndex(e=>e.name===t),tauntNo:i},this.replay.writeEvent(r)}hasActualActions(e){return!![...e.values()].find(e=>e.find(e=>e.id!==ActionType.NoAction))}}class ActionSerializer{getActionPayload(e){return{id:e.actionType,params:e.serialize()}}}class OperationCanceledError extends Error{constructor(e){super(),this.cancellationToken=e}}const CANCEL=Symbol(),REGISTER=Symbol();class CancellationToken{constructor(e){this.source=e,this.cancelled=!1}throwIfCancelled(){if(this.isCancelled())throw new OperationCanceledError(this)}isCancelled(){return!0===this.cancelled}[CANCEL](){this.cancelled=!0}register(e){this.source[REGISTER](e)}}class EventDispatcher_EventDispatcher{constructor(){this.listeners=new Set}subscribe(e){this.listeners.add(e)}unsubscribe(e){this.listeners.delete(e)}subscribeOnce(i){let r=(e,t)=>{i(e,t),this.unsubscribe(r),r=void 0};this.subscribe(r)}dispatch(t,i){this.listeners.forEach(e=>e(i,t))}asEvent(){return this}}class CancellationTokenSource{constructor(){this.onCancel=new EventDispatcher_EventDispatcher,this.token=new CancellationToken(this)}cancel(){this.token[CANCEL](),this.onCancel.dispatch(this,void 0)}[REGISTER](e){this.onCancel.subscribe(()=>e()),this.token.isCancelled()&&e()}}async function sleep(t){return new Promise(e=>{setTimeout(()=>e(),t)})}function throttle(r,s){let a=!1,n=Number.NEGATIVE_INFINITY;return async function(...e){var t,i;a||(i=(t=Date.now())-n,n=s<=i?t:(a=!0,await sleep(s-i),a=!1,Date.now()),await r.apply(this,e))}}function Throttle(s){return(e,t,i)=>{var r=i.value;i.value=throttle(r,s)}}class IrcConnection{constructor(e,t){this.options=e,this.logger=t,this.timeout=5,this._onMessage=new EventDispatcher,this._onError=new EventDispatcher,this._onClose=new EventDispatcher,this.messageBuffer=""}get onMessage(){return this._onMessage.asEvent()}get onError(){return this._onError.asEvent()}get onClose(){return this._onClose.asEvent()}async connect(r,s){let e=s?.timeoutSeconds?setTimeout(()=>this.close(),1e3*s.timeoutSeconds):void 0;return s?.cancelToken?.register(()=>{e&&(clearTimeout(e),this.close())}),new Promise((e,t)=>{this.socket=new WebSocket(r),"arraybuffer"!==this.socket.binaryType&&(this.socket.binaryType="arraybuffer");let i=e=>{this.socket.removeEventListener("error",i),s?.cancelToken?.isCancelled()?t(new OperationCanceledError(s.cancelToken)):t(new IrcConnection.ConnectError(`Connection to "${r}" failed`))};this.socket.addEventListener("open",()=>{this.socket.removeEventListener("error",i),this.socket.addEventListener("error",e=>this.handleError(e)),this.handleOpen(),e()}),this.socket.addEventListener("error",i),this.socket.addEventListener("close",e=>this.handleClose(e)),this.socket.addEventListener("message",e=>{e.data instanceof ArrayBuffer?this.handleMessage(new Uint8Array(e.data)):this.handleMessage(e.data)})}).finally(()=>{e&&clearTimeout(e)})}handleOpen(){this.logger.info("Connection open to "+this.socket.url)}handleError(e){this.logger.error("Connection error",e),this._onError.dispatch(this,e)}handleClose(e){this.logger.info(`Connection closed (${this.socket.url})`,e),this._onClose.dispatch(this,e)}handleMessage(e){if("string"!=typeof e){if(e[0]===this.options.binaryRplPrefix)return void this._onMessage.dispatch(this,e.slice(1));e=uint8ArrayToBinaryString(e)}this.logger.enabledFor(AppLogger.DEBUG)&&this.logger.debug("Got message:","string"==typeof e?this.options.logFilter?.(e)??e:e),e=this.messageBuffer+e,this.messageBuffer="";let t=e.split(/\r?\n/);e=t.pop();e.length&&(this.messageBuffer=e),t.filter(e=>!!e).forEach(e=>this._onMessage.dispatch(this,e))}async sendCommand(e,l){if(l.replyStartCode&&!l.replyEndCode)throw new Error("Invalid argument. Expected a reply end code, but got only a start code.");let h=[];return await this.sendRawCommand(e,(e,s,a,n)=>{let o=(e,t)=>{if("number"==typeof e)return t.code===e;let[i,r]=e;return t.code===i&&r(t)};if("string"!=typeof e){if(e[0]===this.options.binaryRplPrefix)return!1;e=uint8ArrayToBinaryString(e)}return l.replyRawText?(a(e.split(/\r?\n/).map(e=>({raw:e,time:s}))),!0):e.split(/\r?\n/).filter(e=>!!e).some(e=>(e=>{if(l.replyMatch){if(l.replyMatch.exec(e))return a([{raw:e,time:s}]),!0;if(!l.replyCodes)return!1}if(!l.replyEndCode&&!l.replyCodes)return a([{raw:e,time:s}]),!0;var[,t,...i]=e.split(" "),t=parseInt(t,10);let r={raw:e,code:t,params:i,time:s};if(l.replyEndCode)return l.replyCodes&&l.replyCodes.some(e=>o(e,r))?(a([r]),!0):(l.replyHeartbeatCodes&&-1!==l.replyHeartbeatCodes.indexOf(t)&&n(l.heartbeatTimeout),(t===l.replyStartCode||l.replyBodyCodes&&-1!==l.replyBodyCodes.indexOf(t)||t===l.replyEndCode)&&h.push(r),t===l.replyEndCode&&(a(h),!0));if(void 0===l.replyCodes)throw new Error("List of replyCodes must be specified when not using start/end codes");return!!l.replyCodes.some(e=>o(e,r))&&(a([r]),!0)})(e))},l.timeout)}async sendBinCommand(e,s){const a=this.options.binaryRplPrefix;if(!a)throw new Error("Must configure binary message reply prefix to send binary commands");const t=this.options.binaryReqPrefix;if(!t)throw new Error("Must configure binary message request prefix to send binary commands");if(e[0]!==t)throw new Error("Binary command must start with the magic prefix 0x"+t.toString(16));return await this.sendRawCommand(e,(e,t,i)=>{if("string"==typeof e||e[0]!==a)return!1;var r=e[1];return-1!==s.replyCodes.indexOf(r)&&(i({code:r,data:e.slice(2),time:t}),!0)},s.timeout)}sendRawCommand(u,d,p){return new Promise((t,i)=>{let e=!1,r,s=e=>{clearTimeout(r),void 0!==e&&Number.isFinite(e)&&(r=setTimeout(o,1e3*(e??p??this.timeout)))},a=e=>{clearTimeout(r),t(e)},n=e=>{this.socket.removeEventListener("message",c),this.socket.removeEventListener("close",l),clearTimeout(r),r=void 0,i(e)},o=()=>{var e="string"==typeof u?this.options.logFilter?.(u)??u:"0x"+u[1].toString(16);n(new IrcConnection.NoReplyError("Timeout reached for command "+e))},l=async()=>{for(;e;)await sleep(10);h||n(new IrcConnection.SocketError("Connection was closed prematurely"))},h=!1,c=e=>{var t;h||(t=Date.now(),e.data instanceof ArrayBuffer?h||d(new Uint8Array(e.data),t,a,s)&&(h=!0,this.socket.removeEventListener("message",c),this.socket.removeEventListener("close",l)):d(e.data,t,a,s)&&(h=!0,this.socket.removeEventListener("message",c),this.socket.removeEventListener("close",l)))};if(this.socket&&this.socket.readyState===WebSocket.OPEN){r=setTimeout(o,1e3*(p??this.timeout)),this.socket.addEventListener("message",c),this.socket.addEventListener("close",l);try{this.sendMessage(u)}catch(e){n(e)}}else n(new IrcConnection.SocketError("Send command failed. Socket is not open."+(this.socket?` (readyState = ${this.socket.readyState})`:"")))})}sendMessage(e){if(!this.socket||this.socket.readyState!==WebSocket.OPEN)throw new IrcConnection.SocketError("Socket is not open"+(this.socket?` (readyState = ${this.socket.readyState})`:""));this.logger.enabledFor(AppLogger.DEBUG)&&this.logger.debug("Sent message:","string"==typeof e?this.options.logFilter?.(e)??e:e),"string"==typeof e&&(e+="\r\n");let t;t="binary"===this.options.mode&&"string"==typeof e?binaryStringToUint8Array(e):e,this.socket.send(t)}async ping(e){var t=Date.now();return(await this.sendCommand("ping :"+t,{replyMatch:new RegExp("^:[^ ]+ PONG [^ :]+ :"+t,"i"),timeout:e}))[0].time-t}close(){this.socket&&this.socket.close()}isOpen(){return this.socket&&this.socket.readyState===WebSocket.OPEN}}!function(e){class t extends Error{constructor(e){super(e)}}e.NoReplyError=t;class i extends Error{constructor(e){super(e)}}e.SocketError=i;class r extends Error{constructor(e){super(e)}}e.ConnectError=r}(IrcConnection=IrcConnection||{});const RPL_CVERS_OK=10,RPL_CVERS_OUTDATED=11,RPL_CVERS_MISSING=12,RPL_LOGGED_IN=100,RPL_ALREADY_LOGGED_IN=101,RPL_NOT_LOGGED_IN=102,RPL_BAD_LOGIN=103,RPL_TOO_MANY_LOGIN_ATTEMPTS=104,RPL_INSTANCE_CREATED=200,RPL_INSTANCE_EXISTS=201,RPL_INSTANCE_TOO_MANY=202,RPL_NOT_ENOUGH_PARAMS=300,RPL_INVALID_PARAMS=301,RPL_RATE_LIMIT_EXCEEDED=302,RPL_INSTANCE_CONNECTED=400,RPL_INSTANCE_NONEXISTENT=401,RPL_INSTANCE_NOT_ALLOWED=402,RPL_INSTANCE_ALREADY_STARTED=403,RPL_NO_INSTANCE=404,RPL_INSTANCE_NOT_RUNNING=405,RPL_INSTANCE_VERS_MISMATCH=406,RPL_GAME_OPTS=500,RPL_LOAD_INFO=600,RPL_MAP_TOO_BIG=602,RPL_MAP_ALREADY_SENT=603,RPL_GAME_START=700,RPL_GAME_DESYNC=801,RPL_NET_RATE=802,RPL_TAUNT=803,RPL_PLAYER_DISCONNECT=804,RPL_PRIVMSG_NOT_ALLOWED=805,RPL_BIN_PREFIX=2,RPL_BIN_GAME_ACTIONS=1,RPL_BIN_MAP_DATA=2,REQ_BIN_PREFIX=2,REQ_BIN_GAME_ACTIONS=1,REQ_BIN_GAME_STATE_HASH=2,REQ_BIN_PUT_MAP=3,REQ_BIN_GET_MAP=4;class GservError extends Error{constructor(e,t){super(e),this.code=t}}!function(e){(e=e.Code||(e.Code={}))[e.Unknown=0]="Unknown",e[e.OutdatedClient=1]="OutdatedClient",e[e.BadLogin=2]="BadLogin",e[e.TooManyLoginAttempts=3]="TooManyLoginAttempts",e[e.AlreadyLoggedIn=4]="AlreadyLoggedIn",e[e.InstanceNonExistent=5]="InstanceNonExistent",e[e.InstanceAlreadyExists=6]="InstanceAlreadyExists",e[e.InstanceNotAllowed=7]="InstanceNotAllowed",e[e.InstanceAlreadyStarted=8]="InstanceAlreadyStarted",e[e.InstanceVersMismatch=9]="InstanceVersMismatch",e[e.CreatedTooManyInstances=10]="CreatedTooManyInstances"}(GservError=GservError||{});const API_VERSION=2,RECIPIENT_ALL="#all",RECIPIENT_TEAM="#team",TURN_TIMEOUT_MILLIS=3e4,LAG_STATE_THRESH_MILLIS=1e3,CON_INFO_THRESH_MILLIS=2e3,LAG_CHECK_INTERVAL_MILLIS=1e3,MAX_MAP_TRANSFER_BYTES=2097152;!function(e){e[e.Channel=0]="Channel",e[e.Page=1]="Page",e[e.Whisper=2]="Whisper"}(ChatRecipientType=ChatRecipientType||{});const gservErrorCodeMap=new Map([[RPL_BAD_LOGIN,GservError.Code.BadLogin],[RPL_TOO_MANY_LOGIN_ATTEMPTS,GservError.Code.TooManyLoginAttempts],[RPL_ALREADY_LOGGED_IN,GservError.Code.AlreadyLoggedIn],[RPL_INSTANCE_EXISTS,GservError.Code.InstanceAlreadyExists],[RPL_INSTANCE_TOO_MANY,GservError.Code.CreatedTooManyInstances],[RPL_INSTANCE_NONEXISTENT,GservError.Code.InstanceNonExistent],[RPL_INSTANCE_NOT_ALLOWED,GservError.Code.InstanceNotAllowed],[RPL_INSTANCE_ALREADY_STARTED,GservError.Code.InstanceAlreadyStarted],[RPL_INSTANCE_VERS_MISMATCH,GservError.Code.InstanceVersMismatch]]);class GservConnection{get onError(){return this.con.onError}get onClose(){return this.con.onClose}get onLoadInfo(){return this._onLoadInfo.asEvent()}get onGameStart(){return this._onGameStart.asEvent()}get onGameActions(){return this._onGameActions.asEvent()}get onGameDesync(){return this._onGameDesync.asEvent()}get onRateChange(){return this._onRateChange.asEvent()}get onChatMessage(){return this._onChatMessage.asEvent()}get onTaunt(){return this._onTaunt.asEvent()}get onPlayerDisconnect(){return this._onPlayerDisconnect.asEvent()}get onPrivMsgNotAllowed(){return this._onPrivMsgNotAllowed.asEvent()}static factory(e){return new this(new IrcConnection({mode:"text",binaryRplPrefix:RPL_BIN_PREFIX,binaryReqPrefix:REQ_BIN_PREFIX,logFilter:e=>e.replace(/^(user [^ ]+) ([^ ]+)/i,"$1 <redacted>").replace(/^((:.+!.+@.+)?privmsg ([^ ]+ )+):(.+)\r?\n?$/i,"$1:<redacted>")},e))}constructor(e){this._onLoadInfo=new EventDispatcher,this._onGameStart=new EventDispatcher,this._onGameActions=new EventDispatcher,this._onGameDesync=new EventDispatcher,this._onRateChange=new EventDispatcher,this._onChatMessage=new EventDispatcher,this._onTaunt=new EventDispatcher,this._onPlayerDisconnect=new EventDispatcher,this._onPrivMsgNotAllowed=new EventDispatcher,this.handleMessage=t=>{if("string"==typeof t){let e=t.split(" ");var i,r;"ping"===e[0]?this.isOpen()&&this.con.sendMessage("pong"+(e[1]?" "+e[1]:"")):"privmsg"===e[1].toLowerCase()?this.handlePrivMsg(t):e[1]===""+RPL_LOAD_INFO?this.handleLoadInfo(e[3]):e[1]===""+RPL_GAME_START?this.handleGameStart():e[1]===""+RPL_GAME_DESYNC?this._onGameDesync.dispatch(this):e[1]===""+RPL_NET_RATE?([i,r]=e[3].slice(1).split(","),this._onRateChange.dispatch(this,{rate:Number(i),turnNo:Number(r)})):e[1]===""+RPL_TAUNT?this._onTaunt.dispatch(this,{from:e[0].replace(/^:/,""),tauntNo:Number(e[3].replace(/^:/,""))}):e[1]===""+RPL_PLAYER_DISCONNECT?this._onPlayerDisconnect.dispatch(this,e[3].replace(/^:/,"")):e[1]===""+RPL_PRIVMSG_NOT_ALLOWED&&this._onPrivMsgNotAllowed.dispatch(this)}else t[0]===RPL_BIN_GAME_ACTIONS&&this.handlePlayerActions(t.slice(1))},this.con=e}getCurrentUser(){return this.currentUser}getServerName(){return this.serverName}async connect(e,t){return this.con.onMessage.subscribe(this.handleMessage),await this.con.connect(e,t)}close(){this.con.onMessage.unsubscribe(this.handleMessage),this.con.close(),this.currentUser=void 0}isOpen(){return this.con.isOpen()}async cvers(e){let t=await this.con.sendCommand(`cvers ${e} `+API_VERSION,{replyCodes:[RPL_CVERS_OK,RPL_CVERS_OUTDATED]});if(t[0].code===RPL_CVERS_OUTDATED){e=t[0].params?t[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new GservError("Cvers error: "+e,GservError.Code.OutdatedClient)}}async login(e,t){let i=await this.con.sendCommand(`user ${e} `+Base64.encode(t),{replyCodes:[RPL_LOGGED_IN,RPL_BAD_LOGIN,RPL_TOO_MANY_LOGIN_ATTEMPTS,RPL_ALREADY_LOGGED_IN],timeout:10});if(i[0].code!==RPL_LOGGED_IN){var r=gservErrorCodeMap.get(i[0].code)??GservError.Code.Unknown,t=i[0].params?i[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new GservError("Login error: "+t,r)}this.currentUser=e,this.serverName=i[0].raw.match(/^:([^\s]+)/)?.[1]||""}async createGame(e,t,i,r,s,a=!1){if(i.includes(" "))throw new Error("Game opts string cannot include spaces");let n=await this.con.sendCommand(`create ${e} ${t} ${i} ${r} ${s} `+Number(a),{replyCodes:[RPL_INSTANCE_CREATED,RPL_INSTANCE_EXISTS,RPL_INSTANCE_TOO_MANY,RPL_INSTANCE_NOT_ALLOWED]});if(n[0].code!==RPL_INSTANCE_CREATED){s=gservErrorCodeMap.get(n[0].code)??GservError.Code.Unknown,a=n[0].params?n[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new GservError("Create error: "+a,s)}}async joinGame(e,t,i){let r=await this.con.sendCommand(`join ${e} ${t} `+i,{replyCodes:[RPL_INSTANCE_CONNECTED,RPL_INSTANCE_NONEXISTENT,RPL_INSTANCE_NOT_ALLOWED,RPL_INSTANCE_ALREADY_STARTED,RPL_INSTANCE_VERS_MISMATCH]});if(r[0].code!==RPL_INSTANCE_CONNECTED){t=gservErrorCodeMap.get(r[0].code)??GservError.Code.Unknown,i=r[0].params?r[0].params.splice(1).join(" ").replace(/^:/,""):"unknown";throw new GservError("Join error: "+i,t)}}async gameOpts(){let e=await this.con.sendCommand("gameopts",{replyCodes:[RPL_GAME_OPTS]});if(!e[0].params)throw new Error("Unexpected server reply for getopts command. Missing params.");return e[0].params.splice(1).join(" ").replace(/^:/,"")}sendLoadedPercent(e){this.con.sendMessage("loaded "+e)}requestLoadInfo(){this.con.sendMessage("loadinfo")}sendGameStateHash(e,t){let i=new DataStream(10);i.dynamicSize=!1,i.writeUint8(REQ_BIN_PREFIX),i.writeUint8(REQ_BIN_GAME_STATE_HASH),i.writeUint32(e),i.writeUint32(t),this.con.sendMessage(i.toUint8Array())}sendPlayerActive(e){this.con.sendMessage("active "+(e?1:0))}sendTaunt(e){this.con.sendMessage("taunt "+e)}async ping(e){return await this.con.ping(e)}sendPlayerActions(e,t){let i=new DataStream(6);i.writeUint8(REQ_BIN_PREFIX),i.writeUint8(REQ_BIN_GAME_ACTIONS),i.writeUint32(e),i.writeUint8Array(t),this.con.sendMessage(i.toUint8Array())}sendMap(e){let t=new DataStream(2);t.writeUint8(REQ_BIN_PREFIX),t.writeUint8(REQ_BIN_PUT_MAP),t.writeUint8Array((new Serializer).serializeMapData(e)),this.con.sendMessage(t.toUint8Array())}async getMap(){let e=new DataStream(2);e.dynamicSize=!1,e.writeUint8(REQ_BIN_PREFIX),e.writeUint8(REQ_BIN_GET_MAP);var t=await this.con.sendBinCommand(e.toUint8Array(),{replyCodes:[RPL_BIN_MAP_DATA],timeout:15});return(new Parser).parseMapData(t.data)}handleLoadInfo(e){this._onLoadInfo.dispatch(this,e.replace(/^:/,""))}handleGameStart(){this._onGameStart.dispatch(this,void 0)}handlePlayerActions(e){this._onGameActions.dispatch(this,e)}sayChannel(e){this.privmsg([RECIPIENT_ALL],e)}privmsg(e,t){if(!this.currentUser)throw new Error("Must login before sending messages");t.length&&(e=e.join(","),this.con.sendMessage(`privmsg ${e} :`+t))}handlePrivMsg(e){var t=e.match(/^:([A-Za-z0-9-_]+) PRIVMSG ([A-Za-z0-9-_#']+) :(.*)/i);if(!t)throw new Error(`Unexpected PRIVMSG message format "${e}"`);var[,i,r,e]=t;let s;t=new Date;r===RECIPIENT_ALL?s={from:i,to:{type:ChatRecipientType.Channel,name:r},text:e,time:t}:r===this.currentUser&&(s={from:i,to:i===this.getServerName()?{type:ChatRecipientType.Page,name:r}:{type:ChatRecipientType.Channel,name:RECIPIENT_TEAM},text:e,time:t}),s&&this._onChatMessage.dispatch(this,s)}}const computeNetworkTurnMillis=(e,t)=>{return Math.max(1,Math.ceil(e/t))*t};class LockstepManager{get onLagStateChange(){return this._onLagStateChange.asEvent()}get onActionsSent(){return this._onActionsSent.asEvent()}get onActionsProcessed(){return this._onActionsProcessed.asEvent()}get onActionsReceived(){return this._onActionsReceived.asEvent()}constructor(e,t,i,r,s,a,n,o,l,h,c,u,d){this.game=e,this.gservCon=t,this.gameoptParser=i,this.gameoptSerializer=r,this.actionSerializer=s,this.actionFactory=a,this.inputActions=n,this.onDesync=o,this.actionLogger=l,this.netLogger=h,this.debugLogger=c,this.replayRecorder=u,this.debugGameState=d,this.debugGameStateHistory=[],this.queuedRateChanges=[],this.errorState=!1,this.passiveMode=!1,this.receivedActions=new Map,this.receivedNetworkTurn=0,this.lagState=!1,this._onLagStateChange=new EventDispatcher,this._onActionsSent=new EventDispatcher,this._onActionsProcessed=new EventDispatcher,this._onActionsReceived=new EventDispatcher,this.receiveActions=e=>{let t=new DataStream(e);var i=t.readUint32(),e=this.gameoptParser.parseAllPlayerActions(t);this.receivedNetworkTurn=i,this.receivedActions.set(i,e),this._onActionsReceived.dispatch(void 0,i)},this.handleGameDesync=()=>{this.setErrorState(),this.onDesync()}}init(){this.gameTurnMillis=1e3/(this.game.desiredSpeed.value*GameSpeed.BASE_TICKS_PER_SECOND),this.currentNetworkTurn=0,this.currentSubTurn=0,this.gservCon.onGameActions.subscribe(this.receiveActions),this.gservCon.onGameDesync.subscribe(this.handleGameDesync),this.debug("Init: gameTurnMillis = "+this.gameTurnMillis)}canAdvanceNetworkTurn(){return this.currentNetworkTurn<2||this.receivedActions.has(this.currentNetworkTurn-2)}setErrorState(){this.errorState=!0}getErrorState(){return this.errorState}setRate(e){if(this.debug(`Recv rate: ${e.rate} (turn ${e.turnNo})`),0===this.currentSubTurn&&0===this.currentNetworkTurn&&0===e.turnNo)this.updateRate(e.rate);else{if(e.turnNo<this.currentNetworkTurn-2)throw new Error("Rate change has turn number more than two turns in the past.");this.queuedRateChanges.push(e)}}updateRate(e){this.networkTurnMillis=computeNetworkTurnMillis(e,this.gameTurnMillis),this.hashCheckTurnInterval=Math.ceil(LockstepManager.PREFERRED_HASH_CHECK_MILLIS/this.networkTurnMillis),this.netLogger?.debug(`Rate set to ${e} (${this.networkTurnMillis}ms) @ `+this.currentNetworkTurn)}setPassiveMode(e){this.debug("Send passive: "+e),this.passiveMode=e,this.gservCon.sendPlayerActive(!e)}getTurnMillis(){return this.gameTurnMillis}doGameTurn(e){if(!this.errorState){if(!this.networkTurnMillis)throw new Error("Network turn rate should be set by now.");if(this.game.status!==GameStatus.Ended){if(0===this.currentSubTurn){var t=this.queuedRateChanges[0];if(t&&t.turnNo+2===this.currentNetworkTurn&&(this.debug(`Process rate ${t.rate} (turn ${t.turnNo})`),this.updateRate(t.rate),this.queuedRateChanges.shift()),!this.canAdvanceNetworkTurn())return this.handleCommsLag(!0,e),this.debug("Lag state: "+this.lagState),!1;this.debug("Advance turn"),this.commsLagStartTime&&0<e-this.commsLagStartTime&&this.netLogger?.debug(`Waited ${Math.round(e-this.commsLagStartTime)}ms `+"for other clients to catch up."),this.handleCommsLag(!1,e),!this.passiveMode&&this.currentNetworkTurn>=this.receivedNetworkTurn&&this.sendActions(),2<=this.currentNetworkTurn&&(i=this.receivedActions.get(this.currentNetworkTurn-2),this.replayRecorder.recordActions(this.game.currentTick,i),this.processActions(i),this.receivedActions.delete(this.currentNetworkTurn-2),this._onActionsProcessed.dispatch(void 0,this.currentNetworkTurn-2)),this.game.update(),this.passiveMode||this.currentNetworkTurn%this.hashCheckTurnInterval!=0||this.gservCon.sendGameStateHash(this.currentNetworkTurn,this.game.getHash()),this.networkTurnMillis>this.gameTurnMillis?this.currentSubTurn++:this.currentNetworkTurn++}else this.debug("Update"),this.game.update(),this.currentSubTurn++,this.currentSubTurn>=this.networkTurnMillis/this.gameTurnMillis&&(this.currentSubTurn=0,this.currentNetworkTurn++);var i;this.debugGameState&&(i=this.networkTurnMillis/this.gameTurnMillis*this.hashCheckTurnInterval,this.debugGameStateHistory.length>i&&this.debugGameStateHistory.shift(),this.debugGameStateHistory.push(this.game.debugGetState()))}else this.game.update()}}handleCommsLag(e,t){e?(this.commsLagStartTime||(this.commsLagStartTime=t),t-this.commsLagStartTime>LAG_STATE_THRESH_MILLIS&&this.updateLagState(!0)):(this.commsLagStartTime=void 0,this.updateLagState(!1))}updateLagState(e){e!==this.lagState&&(this.lagState=e,this._onLagStateChange.dispatch(void 0,e))}sendActions(){let e=this.inputActions.dequeueAll();e.length||e.push(new NoAction);var t=this.gameoptSerializer.serializePlayerActions(e.map(e=>this.actionSerializer.getActionPayload(e)));this.debug("Send actions: "+t),this.gservCon.sendPlayerActions(this.currentNetworkTurn,t),this._onActionsSent.dispatch(void 0,this.currentNetworkTurn)}processActions(e){[...e].forEach(([i,e])=>e.forEach(e=>{let t=this.actionFactory.create(e.id);t.player=this.game.getPlayer(i),t.unserialize(e.params),t.process();e=t.print();e&&this.actionLogger?.debug(`(${t.player.name})@${this.game.currentTick}: `+e)}))}debug(e){this.debugLogger?.(`${this.currentNetworkTurn}-${this.currentSubTurn}-${this.game.currentTick}: `+e)}dispose(){this.setErrorState(),this.gservCon.onGameActions.unsubscribe(this.receiveActions),this.gservCon.onGameDesync.unsubscribe(this.handleGameDesync)}}LockstepManager.PREFERRED_HASH_CHECK_MILLIS=1e3;const external_perf_hooks_namespaceObject=__WEBPACK_EXTERNAL_createRequire_require("perf_hooks");class AiAnimationLoop{constructor(e){this.gameTurnMgr=e,this.isStarted=!1}start(){this.isStarted||(this.isStarted=!0,this.startTime=void 0,this.lastGameFrame=0)}async waitForTick(){return new Promise((e,t)=>this.doWaitForTick(e,t))}doWaitForTick(e,t){try{this.isStarted||e();var i=external_perf_hooks_namespaceObject.performance.now(),r=this.updateDeltaGameFrames(i);if(0<r)if(!(!1===this.gameTurnMgr.doGameTurn(i)))return void e();setImmediate(()=>this.doWaitForTick(e,t))}catch(e){t(e)}}updateDeltaGameFrames(e){var t=this.gameTurnMgr.getTurnMillis(),i=t!==this.lastGameTurnMillis;this.lastGameTurnMillis=t,i&&(this.lastGameFrame=0,this.startTime=e);let r=0;return this.startTime?(i=e-this.startTime,t=Math.round(i/t),r=t-this.lastGameFrame,this.lastGameFrame=t):this.startTime=e,r}stop(){this.isStarted&&(this.isStarted=!1)}destroy(){this.stop()}}const external_fs_namespaceObject=__WEBPACK_EXTERNAL_createRequire_require("fs");var _GameInstanceApi_bots,_GameInstanceApi_game,_GameInstanceApi_gameApi,_GameInstanceApi_eventsApi,_GameInstanceApi_replay,_GameInstanceApi_turnMgr,_GameInstanceApi_aiAnimationLoop,_GameInstanceApi_onDispose,GameInstanceApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i},GameInstanceApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)};class GameInstanceApi{constructor(e,t,i,r,s,a,n,o,l){_GameInstanceApi_bots.set(this,void 0),_GameInstanceApi_game.set(this,void 0),_GameInstanceApi_gameApi.set(this,void 0),_GameInstanceApi_eventsApi.set(this,void 0),_GameInstanceApi_replay.set(this,void 0),_GameInstanceApi_turnMgr.set(this,void 0),_GameInstanceApi_aiAnimationLoop.set(this,void 0),_GameInstanceApi_onDispose.set(this,void 0),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_bots,e,"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_game,t,"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_gameApi,new GameApi(t,!1),"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_eventsApi,new EventsApi(t.events),"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_replay,i,"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_turnMgr,a,"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_aiAnimationLoop,o,"f"),GameInstanceApi_classPrivateFieldSet(this,_GameInstanceApi_onDispose,l,"f"),GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_eventsApi,"f").subscribe(t=>e.forEach(e=>e.onGameEvent(t,GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f")))),e.forEach(e=>{e.setContext(new BotContext(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f"),new PlayerApi(e.name,GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f"),new ActionsApi(t,r,s,e,n),new ProductionApi(t.getPlayerByName(e.name).production)),new LoggerApi(AppLogger.get(e.name),GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f")))),e.onGameInit(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f")),e.onGameStart(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f"))})}isFinished(){return GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_game,"f").status===GameStatus.Ended||GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_turnMgr,"f").getErrorState()}async update(){if(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_aiAnimationLoop,"f"))await GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_aiAnimationLoop,"f").waitForTick();else{if(!(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_turnMgr,"f")instanceof AiPlayTurnManager))throw new Error("Missing animation loop or turn manager");GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_turnMgr,"f").doGameTurn()}GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_bots,"f").forEach(e=>e.onGameTick(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f")))}getCurrentTick(){return GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f").getCurrentTick()}getTickRate(){return GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_gameApi,"f").getTickRate()}getPlayerStats(){return GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_game,"f").getNonNeutralPlayers().filter(e=>!e.isObserver).map(t=>({name:t.name,country:t.country,ai:t.isAi||GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_bots,"f").some(e=>e.name===t.name),defeated:t.defeated,credits:t.credits,startLocation:t.startLocation}))}saveReplay(e){let t=GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_replay,"f");t.finish(GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_game,"f").currentTick);var i=GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_game,"f").gameOpts.mapName+"_"+Date.now()+Replay.extension,r=t.serialize(),i=external_path_namespaceObject.resolve(e??process.cwd(),i);return external_fs_namespaceObject.writeFileSync(i,r,"utf-8"),process.stdout.write(`Replay saved to "${i}"
|
|
3
|
+
`),i}getDebugStateDump(){return GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_turnMgr,"f")instanceof LockstepManager?GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_turnMgr,"f").debugGameStateHistory:void 0}dispose(){GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_eventsApi,"f").dispose(),GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_bots,"f").length=0,GameInstanceApi_classPrivateFieldGet(this,_GameInstanceApi_onDispose,"f")?.call(this)}}_GameInstanceApi_bots=new WeakMap,_GameInstanceApi_game=new WeakMap,_GameInstanceApi_gameApi=new WeakMap,_GameInstanceApi_eventsApi=new WeakMap,_GameInstanceApi_replay=new WeakMap,_GameInstanceApi_turnMgr=new WeakMap,_GameInstanceApi_aiAnimationLoop=new WeakMap,_GameInstanceApi_onDispose=new WeakMap;class MixinRules{static getTypes(e){let t=[];return e.noDogEngiKills&&t.push(MixinRulesType.NoDogEngiKills),t}}class MapDigest{static compute(e){return Crc32.calculateCrc(e.getBytes()).toString(16)}}class OnlineBotChatApi{constructor(e,t,i){this.game=e,this.replayRecorder=t,this.gservCon=i,this.disposables=new CompositeDisposable,this.handleGservMessage=e=>{e.to.type===ChatRecipientType.Channel&&e.to.name===RECIPIENT_ALL&&this.replayRecorder.recordChatMessage(this.game.currentTick,e.from,e.text)}}init(){this.gservCon.onChatMessage.subscribe(this.handleGservMessage),this.disposables.add(()=>this.gservCon.onChatMessage.unsubscribe(this.handleGservMessage))}sayAll(e,t){this.gservCon.isOpen()?this.gservCon.sayChannel(t):console.warn("Can't send chat message. Network connection is already closed.")}dispose(){this.disposables.dispose()}}class OfflineBotChatApi{constructor(e,t){this.game=e,this.replayRecorder=t}sayAll(e,t){this.replayRecorder.recordChatMessage(this.game.currentTick,e,t)}}class RouteHelper{static getGameRoute(e){return"#/game/"+Base64.encode(JSON.stringify({gameId:e.gameId,gameTimestamp:e.gameTimestamp,gservUrl:e.gservUrl,playerName:e.playerName,gameOpts:e.gameOpts,tournament:e.tournament}))}static extractGameParams(e){return JSON.parse(Base64.decode(e))}}RouteHelper.modQueryStringName="mod";var PublicApi_classPrivateFieldGet=function(e,t,i,r){if("a"===i&&!r)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof t?e!==t||!r:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===i?r:"a"===i?r.call(e):r?r.value:t.get(e)},PublicApi_classPrivateFieldSet=function(e,t,i,r,s){if("m"===r)throw new TypeError("Private method is not writable");if("a"===r&&!s)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof t?e!==t||!s:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===r?s.call(e,i):s?s.value=i:t.set(e,i),i};const resDir=external_path_namespaceObject.resolve((0,external_es_dirname_namespaceObject.default)(),"./res");class PublicApi{constructor(){_PublicApi_instances.add(this),_PublicApi_gameModes.set(this,void 0),_PublicApi_iniLogger.set(this,void 0),_PublicApi_actionLogger.set(this,void 0),_PublicApi_netLogger.set(this,void 0),_PublicApi_isInitialized.set(this,!1),_PublicApi_mapList.set(this,void 0)}async init(e){PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_initLogging).call(this),globalThis.Blob||(globalThis.Blob=(await Promise.resolve().then(__webpack_require__.bind(__webpack_require__,422))).Blob);var t=await(0,external_file_system_access_namespaceObject.getOriginPrivateDirectory)(node_js_namespaceObject.default,external_path_namespaceObject.resolve(e)),i=await(0,external_file_system_access_namespaceObject.getOriginPrivateDirectory)(node_js_namespaceObject.default,resDir),e=await(0,external_file_system_access_namespaceObject.getOriginPrivateDirectory)(node_js_namespaceObject.default,process.cwd());Engine.setActiveEngine(EngineType.RedAlert2),Engine.initGameResSource(GameResSource.Local);let r=await Engine.initRfs(t);r.addDirectoryHandle(i),r.addDirectoryHandle(e);let s=await Engine.initVfs(r,AppLogger.get("vfs"));await s.loadStandaloneFiles(),await s.loadExtraMixFiles(Engine.getActiveEngine()),await s.addMixFile("ra2cd.mix"),await s.loadImplicitMixFiles(Engine.getActiveEngine()),Engine.loadRules(),PublicApi_classPrivateFieldSet(this,_PublicApi_mapList,await Engine.loadMapList(),"f"),PublicApi_classPrivateFieldSet(this,_PublicApi_gameModes,Engine.getMpModes(),"f"),PublicApi_classPrivateFieldSet(this,_PublicApi_isInitialized,!0,"f")}getAvailableMaps(){if(!PublicApi_classPrivateFieldGet(this,_PublicApi_isInitialized,"f"))throw new Error("API is not initialized. Call init() first.");return PublicApi_classPrivateFieldGet(this,_PublicApi_mapList,"f").getAll().map(e=>e.fileName.toLowerCase())}getAvailableGameModes(e){if(!PublicApi_classPrivateFieldGet(this,_PublicApi_isInitialized,"f"))throw new Error("API is not initialized. Call init() first.");let t=PublicApi_classPrivateFieldGet(this,_PublicApi_mapList,"f").getByName(e);if(!t)throw new Error(`Map "${e}" is not available`);return t.gameModes.map(e=>e.id)}async createGame(e){return e.online?await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_createOnlineGame).call(this,e):await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_createOfflineGame).call(this,e)}}var _PublicApi_gameModes=new WeakMap,_PublicApi_iniLogger=new WeakMap,_PublicApi_actionLogger=new WeakMap,_PublicApi_netLogger=new WeakMap,_PublicApi_isInitialized=new WeakMap,_PublicApi_mapList=new WeakMap,_PublicApi_instances=new WeakSet,_PublicApi_initLogging=function(){AppLogger.useDefaults(),AppLogger.setLevel(AppLogger.ERROR);const e=process.env.DEBUG_LOGGING;var t;if(e)if(isNaN(e))for(t of e.split(","))AppLogger.get(t).setLevel(AppLogger.DEBUG);else AppLogger.setLevel(Number(e)?AppLogger.DEBUG:AppLogger.ERROR);PublicApi_classPrivateFieldSet(this,_PublicApi_iniLogger,AppLogger.get("ini"),"f"),PublicApi_classPrivateFieldSet(this,_PublicApi_actionLogger,AppLogger.get("action"),"f"),PublicApi_classPrivateFieldSet(this,_PublicApi_netLogger,AppLogger.get("net"),"f")},_PublicApi_createOfflineGame=async function(e){if(!PublicApi_classPrivateFieldGet(this,_PublicApi_isInitialized,"f"))throw new Error("API is not initialized. Call init() first.");if(e.agents.some(e=>!(e instanceof Bot)))throw new Error("All players in the agents array must be bots in offline mode");var t=await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_generateGameOpts).call(this,e),i=e.agents.filter(e=>e instanceof Bot),r=new MapFile(await Engine.vfs.openFileWithRfs(t.mapName)),s=Math.floor(Date.now()/1e3),a=await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_initializeGame).call(this,"0",s,t,r,void 0),e=new ActionQueue,s=new ActionFactory;(new ActionFactoryReg).register(s,a,void 0);let n=new Replay;n.init(a.id,a.startTimestamp,t,Engine.getVersion(),Engine.getModHash());r=new ActionSerializer,t=new ReplayRecorder(n,0,a.gameOpts.humanPlayers,r);let o=new AiPlayTurnManager(a,e,t,r,s,PublicApi_classPrivateFieldGet(this,_PublicApi_actionLogger,"f"));o.init();t=new OfflineBotChatApi(a,t);return new GameInstanceApi(i,a,n,s,e,o,t)},_PublicApi_createOnlineGame=async function(e){if(!PublicApi_classPrivateFieldGet(this,_PublicApi_isInitialized,"f"))throw new Error("API is not initialized. Call init() first.");if(!e.serverUrl)throw new Error("Must specify a serverUrl");if(!e.clientUrl)throw new Error("Must specify a clientUrl");let t=[];for(var i of e.agents){if(!i.name.match(/^[a-z0-9-_]+$/i))throw new Error(`Agent name "${i.name}" must contain only alphanumeric characters, dash (-) or underscore (_)`);i instanceof Bot&&t.push(i)}if(!(e.agents[0]instanceof Bot))throw new Error("The first object in the agents array must be a Bot instance in online mode");if(e.agents.slice(1).some(e=>e instanceof Bot))throw new Error("Only the first player in the agents array can be a bot in online mode");var r=await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_generateGameOpts).call(this,e);let s=GservConnection.factory(PublicApi_classPrivateFieldGet(this,_PublicApi_netLogger,"f"));await s.connect(e.serverUrl),await s.cvers(Engine.getVersion()),await s.login(e.agents[0].name,e.botPassword);let a=new Serializer;var n,o=a.serializeOptions(r),l=external_node_crypto_namespaceObject.randomUUID(),h=Math.floor(Date.now()/1e3);process.stdout.write(`
|
|
4
|
+
You may use the following link(s) to join, after the game is created:
|
|
5
|
+
|
|
6
|
+
`);let c=new Map;for(n of e.agents.slice(1)){var u=e.clientUrl.replace(/\/$/,"")+("/"+RouteHelper.getGameRoute({gameId:l,gameTimestamp:h,gservUrl:e.serverUrl,playerName:n.name}));c.set(n,u),process.stdout.write(u+"\n")}e.nonInteractive||(process.stdout.write(`
|
|
7
|
+
|
|
8
|
+
Press ENTER to create the game now...
|
|
9
|
+
`),await new Promise(e=>process.stdin.once("data",e)),process.stdin.pause()),process.stdout.write(`Creating game...
|
|
10
|
+
`),await s.createGame(l,h,o,Engine.getVersion(),Engine.getModHash());let d=new Parser;var p=d.parseOptions(await s.gameOpts());let g=await Engine.vfs.openFileWithRfs(r.mapName);var m=new MapFile(g);r.mapOfficial||s.sendMap(g.readAsString());var y=e.agents[0].name;let T=await PublicApi_classPrivateFieldGet(this,_PublicApi_instances,"m",_PublicApi_initializeGame).call(this,l,h,p,m,y);o=new ActionSerializer,r=new ActionQueue,m=new ActionFactory;(new ActionFactoryReg).register(m,T,y);let f=new Replay;f.init(T.id,T.startTimestamp,p,Engine.getVersion(),Engine.getModHash());p=new ReplayRecorder(f,0,T.gameOpts.humanPlayers,o);let v=new LockstepManager(T,s,d,a,o,m,r,()=>{console.error("Desync detected."),process.exit(1)},PublicApi_classPrivateFieldGet(this,_PublicApi_actionLogger,"f"),void 0,void 0,p,e.debugStateDumps??!1);v.init();let b=new AiAnimationLoop(v);s.onRateChange.subscribe(e=>v.setRate(e)),T.onEnd.subscribe(()=>{process.stdout.write(`Game ended.
|
|
11
|
+
`),b.destroy()}),process.stdout.write(`
|
|
12
|
+
Game created.`),process.stdout.write(`
|
|
13
|
+
Waiting for players to join...
|
|
14
|
+
`),e.onGameCreate?.(c),await new Promise((e,t)=>{s.onGameStart.subscribeOnce(()=>{s.onClose.unsubscribe(t),b.start(),e()}),s.onClose.subscribeOnce(t),s.sendLoadedPercent(100)}),process.stdout.write(`Game started.
|
|
15
|
+
`);let w=new OnlineBotChatApi(T,p,s);w.init();return s.onClose.subscribeOnce(()=>v.dispose()),new GameInstanceApi(t,T,f,m,r,v,w,b,()=>{b.destroy(),w.dispose(),PublicApi_classPrivateFieldGet(this,_PublicApi_netLogger,"f").setLevel(AppLogger.OFF),s.close()})},_PublicApi_initializeGame=async function(e,t,i,r,s){if(!PublicApi_classPrivateFieldGet(this,_PublicApi_isInitialized,"f"))throw new Error("API is not initialized. Call init() first.");var a=Engine.getIni(PublicApi_classPrivateFieldGet(this,_PublicApi_gameModes,"f").getById(i.gameMode).rulesOverride),n=MixinRules.getTypes(i).map(e=>Engine.mixinRulesFileNames.get(e)).filter(isNotNullOrUndefined).map(e=>Engine.getIni(e));await Engine.loadTheater(r.theaterType);var o=Engine.getActiveEngine(),l=Engine.getTheaterSettings(o,r.theaterType),o=Engine.getTheaterIni(o,r.theaterType);let h=new TileSets(o);h.loadTileData(Engine.getTileData(),l.extension);let c=GameFactory.create(r,h,Engine.getRules(),Engine.getArt(),Engine.getAi(),a,n,e,t,i,PublicApi_classPrivateFieldGet(this,_PublicApi_gameModes,"f"),!1,{version:"0.0.0"},PublicApi_classPrivateFieldGet(this,_PublicApi_iniLogger,"f"),new BoxedVar(!1),new BoxedVar(0),PublicApi_classPrivateFieldGet(this,_PublicApi_actionLogger,"f"));return c.init(s?c.getPlayerByName(s):void 0),c.start(),c},_PublicApi_generateGameOpts=async function(t){let e=PublicApi_classPrivateFieldGet(this,_PublicApi_mapList,"f").getAll().find(e=>e.fileName.toLowerCase()===t.mapName.toLowerCase());if(!e)throw new Error(`Map ${t.mapName} not found.`);if(!e.gameModes.find(e=>e.id===t.gameMode))throw new Error(`Map "${e.fileName}" doesn't support game mode `+t.gameMode);let i=await Engine.vfs.openFileWithRfs(t.mapName),r=new Rules(Engine.getRules()).getMultiplayerCountries();return{gameMode:t.gameMode,shortGame:t.shortGame,mcvRepacks:t.mcvRepacks,cratesAppear:t.cratesAppear,superWeapons:t.superWeapons,gameSpeed:t.gameSpeed,credits:t.credits,unitCount:t.unitCount,buildOffAlly:t.buildOffAlly,destroyableBridges:t.destroyableBridges??!0,multiEngineer:t.multiEngineer??!1,noDogEngiKills:t.noDogEngiKills??!1,humanPlayers:t.agents.map((t,e)=>({name:t.name,countryId:void 0!==t.country?r.findIndex(e=>e.name===t.country):OBS_COUNTRY_ID,colorId:e,startPos:RANDOM_START_POS,teamId:NO_TEAM_ID})),aiPlayers:new Array(8).fill(void 0),mapName:e.fileName,mapDigest:MapDigest.compute(i),mapSizeBytes:i.getSize(),mapTitle:e.fileName,maxSlots:e.maxSlots,mapOfficial:e.official}},Euler_THREE=__webpack_require__(70);class Euler extends Euler_THREE.Euler{constructor(){super(...arguments),this.isEuler=!0}setFromRotationMatrix(e,t,i){var r=e.elements,s=r[0],a=r[4],n=r[8],o=r[1],l=r[5],h=r[9],c=r[2],e=r[6],r=r[10];return"XYZ"===(t=t||this._order)?(this._y=GameMath.asin(clamp(n,-1,1)),Math.abs(n)<.99999?(this._x=GameMath.atan2(-h,r),this._z=GameMath.atan2(-a,s)):(this._x=GameMath.atan2(e,l),this._z=0)):"YXZ"===t?(this._x=GameMath.asin(-clamp(h,-1,1)),Math.abs(h)<.99999?(this._y=GameMath.atan2(n,r),this._z=GameMath.atan2(o,l)):(this._y=GameMath.atan2(-c,s),this._z=0)):"ZXY"===t?(this._x=GameMath.asin(clamp(e,-1,1)),Math.abs(e)<.99999?(this._y=GameMath.atan2(-c,r),this._z=GameMath.atan2(-a,l)):(this._y=0,this._z=GameMath.atan2(o,s))):"ZYX"===t?(this._y=GameMath.asin(-clamp(c,-1,1)),Math.abs(c)<.99999?(this._x=GameMath.atan2(e,r),this._z=GameMath.atan2(o,s)):(this._x=0,this._z=GameMath.atan2(-a,l))):"YZX"===t?(this._z=GameMath.asin(clamp(o,-1,1)),Math.abs(o)<.99999?(this._x=GameMath.atan2(-h,l),this._y=GameMath.atan2(-c,s)):(this._x=0,this._y=GameMath.atan2(n,r))):"XZY"===t?(this._z=GameMath.asin(-clamp(a,-1,1)),Math.abs(a)<.99999?(this._x=GameMath.atan2(e,l),this._y=GameMath.atan2(n,s)):(this._x=GameMath.atan2(-h,r),this._y=0)):console.warn("THREE.Euler: .setFromRotationMatrix() given unsupported order: "+t),this._order=t,!1!==i&&this.onChangeCallback(),this}reorder(e){return q.setFromEuler(this),this.setFromQuaternion(q,e)}toVector3(e){return e?e.set(this._x,this._y,this._z):new Vector3_Vector3(this._x,this._y,this._z)}}const q=new Quaternion;var Spherical_THREE=__webpack_require__(70);class Spherical extends Spherical_THREE.Spherical{setFromVector3(e){return this.radius=e.length(),0===this.radius?(this.theta=0,this.phi=0):(this.theta=GameMath.atan2(e.x,e.z),this.phi=GameMath.acos(clamp(e.y/this.radius,-1,1))),this}}var Cylindrical_THREE=__webpack_require__(70);class Cylindrical extends Cylindrical_THREE.Cylindrical{setFromVector3(e){return this.radius=GameMath.sqrt(e.x*e.x+e.z*e.z),this.theta=GameMath.atan2(e.x,e.z),this.y=e.y,this}}const cdapi=new PublicApi;export{ApiEventType,ArmorType,AttackState,Bot,Box2,BuildCat,BuildStatus,Cylindrical,Euler,FactoryStatus,FactoryType,GameInstanceApi,GameMath,InfDeathType,LandTargeting,LandType,LocomotorType,Matrix4,MovementZone,NavalTargeting,ObjectType,OrderType,PipColor,PrereqCategory,PublicApi,Quaternion,QueueStatus,QueueType,RadarEventType,SideType,SpeedType,Spherical,StanceType,SuperWeaponStatus,SuperWeaponType,TagRepeatType,TerrainType,TheaterType,Vector2,Vector3_Vector3 as Vector3,VeteranAbility,VeteranLevel,VhpScan,WeaponType,ZoneType,cdapi};
|