ZoriaRPG

std_functions.zh for ZC 2.55

Nov 25th, 2016
117
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. //std_functions.zh for 2.50.2
  2. //25-NOV-2016 -
  3. // Since last .txtfile / docs: Added DistXY(), LeftOf(), RightOf(), Above(), Below(), FlipRef(), ReflectWeapon()
  4. //Fixed and updated AdjacentCombo: It now uses the same DIR_ values as everything else.
  5. //
  6. // Some utility routines
  7. //
  8.  
  9. //Wait for n frames
  10. void Waitframes(int n) {
  11.     while(n-- > 0) Waitframe();
  12. }
  13.  
  14. //Returns a if cond is true, else b. Overloaded.
  15. float Cond(bool cond, float a, float b) {
  16.     if (cond) return a;
  17.     else return b;
  18. }
  19.  
  20. bool Cond(bool cond, bool a, bool b) {
  21.     if (cond) return a;
  22.     else return b;
  23. }
  24.  
  25. npc Cond(bool cond, npc a, npc b) {
  26.     if (cond) return a;
  27.     else return b;
  28. }
  29.  
  30. item Cond(bool cond, item a, item b) {
  31.     if (cond) return a;
  32.     else return b;
  33. }
  34.  
  35. lweapon Cond(bool cond, lweapon a, lweapon b) {
  36.     if (cond) return a;
  37.     else return b;
  38. }
  39.  
  40. eweapon Cond(bool cond, eweapon a, eweapon b) {
  41.     if (cond) return a;
  42.     else return b;
  43. }
  44.  
  45. ffc Cond(bool cond, ffc a, ffc b) {
  46.     if (cond) return a;
  47.     else return b;
  48. }
  49.  
  50. itemdata Cond(bool cond, itemdata a, itemdata b) {
  51.     if (cond) return a;
  52.     else return b;
  53. }
  54.  
  55. // Chooses one of the options randomly and fairly.
  56. float Choose(float a, float b) {
  57.     if (Rand(0,1)==0) return a;
  58.     else return b;
  59. }
  60.  
  61. float Choose(float a, float b, float c) {
  62.     int r = Rand(0,2);
  63.     if (r==0) return a;
  64.     else if (r==1) return b;
  65.     else return c;
  66. }
  67.  
  68. float Choose(float a, float b, float c, float d) {
  69.     int r = Rand(0,3);
  70.     if (r==0) return a;
  71.     else if (r==1) return b;
  72.     else if (r==2) return c;
  73.     else return d;
  74. }
  75.  
  76. float Choose(float a, float b, float c, float d, float e) {
  77.     int r = Rand(0,4);
  78.     if (r==0) return a;
  79.     else if (r==1) return b;
  80.     else if (r==2) return c;
  81.     else if (r==3) return d;
  82.     else return e;
  83. }
  84.  
  85. float Choose(float a, float b, float c, float d, float e, float f) {
  86.     int r = Rand(0,5);
  87.     if (r==0) return a;
  88.     else if (r==1) return b;
  89.     else if (r==2) return c;
  90.     else if (r==3) return d;
  91.     else if (r==4) return e;
  92.     else return f;
  93. }
  94.  
  95. float Choose(float a, float b, float c, float d, float e, float f, float g) {
  96.     int r = Rand(0,6);
  97.     if (r==0) return a;
  98.     else if (r==1) return b;
  99.     else if (r==2) return c;
  100.     else if (r==3) return d;
  101.     else if (r==4) return e;
  102.     else if (r==5) return f;
  103.     else return g;
  104. }
  105.  
  106. float Choose(float a, float b, float c, float d, float e, float f, float g, float h) {
  107.     int r = Rand(0,7);
  108.     if (r==0) return a;
  109.     else if (r==1) return b;
  110.     else if (r==2) return c;
  111.     else if (r==3) return d;
  112.     else if (r==4) return e;
  113.     else if (r==5) return f;
  114.     else if (r==6) return g;
  115.     else return h;
  116. }
  117.  
  118. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i) {
  119.     int r = Rand(0,8);
  120.     if (r==0) return a;
  121.     else if (r==1) return b;
  122.     else if (r==2) return c;
  123.     else if (r==3) return d;
  124.     else if (r==4) return e;
  125.     else if (r==5) return f;
  126.     else if (r==6) return g;
  127.     else if (r==7) return h;
  128.     else return i;
  129. }
  130.  
  131. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  132.         float j) {
  133.     int r = Rand(0,9);
  134.     if (r==0) return a;
  135.     else if (r==1) return b;
  136.     else if (r==2) return c;
  137.     else if (r==3) return d;
  138.     else if (r==4) return e;
  139.     else if (r==5) return f;
  140.     else if (r==6) return g;
  141.     else if (r==7) return h;
  142.     else if (r==8) return i;
  143.     else return j;
  144. }
  145.  
  146. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  147.         float j, float k) {
  148.     int r = Rand(0,10);
  149.     if (r==0) return a;
  150.     else if (r==1) return b;
  151.     else if (r==2) return c;
  152.     else if (r==3) return d;
  153.     else if (r==4) return e;
  154.     else if (r==5) return f;
  155.     else if (r==6) return g;
  156.     else if (r==7) return h;
  157.     else if (r==8) return i;
  158.     else if (r==9) return j;
  159.     else return k;
  160. }
  161.  
  162. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  163.         float j, float k, float l) {
  164.     int r = Rand(0,11);
  165.     if (r==0) return a;
  166.     else if (r==1) return b;
  167.     else if (r==2) return c;
  168.     else if (r==3) return d;
  169.     else if (r==4) return e;
  170.     else if (r==5) return f;
  171.     else if (r==6) return g;
  172.     else if (r==7) return h;
  173.     else if (r==8) return i;
  174.     else if (r==9) return j;
  175.     else if (r==10) return k;
  176.     else return l;
  177. }
  178.  
  179. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  180.         float j, float k, float l, float m) {
  181.     int r = Rand(0,12);
  182.     if (r==0) return a;
  183.     else if (r==1) return b;
  184.     else if (r==2) return c;
  185.     else if (r==3) return d;
  186.     else if (r==4) return e;
  187.     else if (r==5) return f;
  188.     else if (r==6) return g;
  189.     else if (r==7) return h;
  190.     else if (r==8) return i;
  191.     else if (r==9) return j;
  192.     else if (r==10) return k;
  193.     else if (r==11) return l;
  194.     else return m;
  195. }
  196.  
  197. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  198.         float j, float k, float l, float m, float n) {
  199.     int r = Rand(0,13);
  200.     if (r==0) return a;
  201.     else if (r==1) return b;
  202.     else if (r==2) return c;
  203.     else if (r==3) return d;
  204.     else if (r==4) return e;
  205.     else if (r==5) return f;
  206.     else if (r==6) return g;
  207.     else if (r==7) return h;
  208.     else if (r==8) return i;
  209.     else if (r==9) return j;
  210.     else if (r==10) return k;
  211.     else if (r==11) return l;
  212.     else if (r==12) return m;
  213.     else return n;
  214. }
  215.  
  216. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  217.         float j, float k, float l, float m, float n, float o) {
  218.     int r = Rand(0,14);
  219.     if (r==0) return a;
  220.     else if (r==1) return b;
  221.     else if (r==2) return c;
  222.     else if (r==3) return d;
  223.     else if (r==4) return e;
  224.     else if (r==5) return f;
  225.     else if (r==6) return g;
  226.     else if (r==7) return h;
  227.     else if (r==8) return i;
  228.     else if (r==9) return j;
  229.     else if (r==10) return k;
  230.     else if (r==11) return l;
  231.     else if (r==12) return m;
  232.     else if (r==13) return n;
  233.     else return o;
  234. }
  235.  
  236. float Choose(float a, float b, float c, float d, float e, float f, float g, float h, float i,
  237.         float j, float k, float l, float m, float n, float o, float p) {
  238.     int r = Rand(0,15);
  239.     if (r==0) return a;
  240.     else if (r==1) return b;
  241.     else if (r==2) return c;
  242.     else if (r==3) return d;
  243.     else if (r==4) return e;
  244.     else if (r==5) return f;
  245.     else if (r==6) return g;
  246.     else if (r==7) return h;
  247.     else if (r==8) return i;
  248.     else if (r==9) return j;
  249.     else if (r==10) return k;
  250.     else if (r==11) return l;
  251.     else if (r==12) return m;
  252.     else if (r==13) return n;
  253.     else if (r==14) return o;
  254.     else return p;
  255. }
  256.  
  257.  
  258.  
  259. //Returns the logarithm of x to the given base
  260. float LogToBase(float x, float base){
  261.     return Ln(x)/Ln(base);
  262. }
  263.  
  264. //Truncates x to an integer
  265. int Floor(float x) {
  266.     if(x < 0)
  267.         return (x-.9999)<<0;
  268.     return x<<0;
  269. }
  270.  
  271. //Raises x to the nearest integer
  272. int Ceiling(float x) {
  273.     if(x < 0)
  274.         return x<<0;
  275.     return (x+.9999)<<0;
  276. }
  277.  
  278. //Rounds x to the nearest integer
  279. float Round(float x) {
  280.     if(x < 0)
  281.         return (x-.5)<<0;
  282.     return (x+.5)<<0;
  283. }
  284.  
  285. //Returns true if the integer is odd (or even in IsEven)
  286. bool IsOdd(int x) {
  287.     return ((x & 1) == 1);
  288. }
  289.  
  290. bool IsEven(int x) {
  291.     return ((x & 1) == 0);
  292. }
  293.  
  294. //Clamps x to the range of low, high.
  295. int Clamp(int x, int low, int high) {
  296.     if(x<low) x=low;
  297.     else if(x>high) x=high;
  298.     return x;
  299. }
  300.  
  301. //same as Clamp, but with reversed values.
  302. int VBound(int x, int high, int low) {
  303.     if(x<low) x=low;
  304.     else if(x>high) x=high;
  305.     return x;
  306. }
  307.  
  308. //Returns the Quotient only of x divided by y
  309. int Div(float x, float y) {
  310.     return (x/y)<<0;
  311. }
  312.  
  313. //Returns a random integer in the bounds of min and max
  314. //Permits reversed args.
  315. int Rand(int min, int max) {
  316.     if ( max < min ) return max+(Rand((1+min)-max));
  317.     else return min+(Rand((1+max)-min));
  318. }
  319.  
  320. //Returns a random floating point number up to n
  321. float Randf(float n) {
  322.     return (Rand(0x7fff)/0x7fff)*n;
  323. }
  324.  
  325. //Returns a random floating point number between min and max
  326. //Updated to allow reversed args
  327. float Randf(float n1, float n2) {
  328.     if ( n2 < n1 ) return n2 + (Rand(0x7fff)/(0x7fff))*(n1-n2);
  329.     else return n1 + (Rand(0x7fff)/(0x7fff))*(n2-n1);
  330. }
  331.  
  332. //Converts 'd' in degrees to radians
  333. float DegtoRad(float d) {
  334.     return d*0.0174;
  335. }
  336.  
  337. //Converts 'r' in radians to degrees
  338. float RadtoDeg(float r) {
  339.     return r*57.2958;
  340. }
  341.  
  342. //Returns the sign of n
  343. int Sign(int n) {
  344.     if (n > 0) return 1;
  345.     else if (n < 0) return -1;
  346.     else return 0;
  347. }
  348.  
  349. //Finds the location of a combo, given its (x,y) coordinates on the screen
  350. int ComboAt(int x, int y) {
  351.     x = VBound(x,255,0);
  352.     y = VBound(y,175,0);
  353.     return (y & 240)+(x>>4);
  354. }
  355.  
  356. //Snaps 'x' to the combo grid
  357. //Equivalent to calling ComboX(ComboAt(x,foo));
  358. int GridX(int x) {
  359.     return (x >> 4) << 4;
  360. }
  361.  
  362. //Snaps 'y' to the combo grid
  363. //Equivalent to calling ComboY(ComboAt(foo,y));
  364. int GridY(int y) {
  365.     return (y >> 4) << 4;
  366. }
  367.  
  368.  
  369. //Returns the correct offset to be at the front of a sprite facing in the direction 'dir'
  370. int AtFrontX(int dir) {
  371.     int x = 0;
  372.     if(dir == DIR_UP || dir == DIR_DOWN) x = 8;
  373.     else if(dir == DIR_RIGHT) x = 16;
  374.     return x;
  375. }
  376.  
  377. int AtFrontY(int dir) {
  378.     int y = 0;
  379.     if(dir == DIR_DOWN) y = 16;
  380.     else if(dir == DIR_LEFT || dir == DIR_RIGHT) y = 8;
  381.     return y;
  382. }
  383.  
  384. //Returns the correct offset to be 'dist' pixels away from the front of a sprite facing in the direction 'dir'
  385. int InFrontX(int dir, int dist) {
  386.     int x = 0;
  387.     if(dir == DIR_LEFT) x = -16+dist;
  388.     else if(dir == DIR_RIGHT) x = 16-dist;
  389.     return x;
  390. }
  391.  
  392. int InFrontY(int dir, int dist){
  393.     int y = 0;
  394.     if(dir == DIR_UP) y = -16+dist;
  395.     else if(dir == DIR_DOWN) y = 16-dist;
  396.     return y;
  397. }
  398.  
  399. // Get the X and Y coordinates at the center of a sprite.
  400. //Overloaded to accept all types.
  401. int CenterX(ffc anFFC) { return anFFC->X+8*anFFC->TileWidth; }
  402. int CenterY(ffc anFFC) { return anFFC->Y+8*anFFC->TileHeight; }
  403.  
  404. int CenterX(npc anNPC) {
  405.     if ( STD_CENTERXY_USES_HITBOXES ) return anNPC->Y+anNPC->HitWidth/2 + anNPC->HitXOffset;
  406.     else return anNPC->X+8*anNPC->TileWidth;
  407. }
  408.  
  409. int CenterY(npc anNPC) {
  410.     if ( STD_CENTERXY_USES_HITBOXES ) return anNPC->Y+anNPC->HitHeight/2 + anNPC->HitYOffset;
  411.     else return anNPC->Y+8*anNPC->TileHeight;
  412. }
  413.  
  414. int CenterX(item anItem) {
  415.     if ( STD_CENTERXY_USES_HITBOXES ) return anItem->Y+anItem->HitWidth/2 + anItem->HitXOffset;
  416.     else return anItem->X+8*anItem->TileWidth;
  417. }
  418.  
  419. int CenterY(item anItem) {
  420.     if ( STD_CENTERXY_USES_HITBOXES ) return anItem->Y+anItem->HitHeight/2 + anItem->HitYOffset;
  421.     else return anItem->Y+8*anItem->TileHeight;
  422. }
  423.  
  424.  
  425. int CenterX(eweapon anEWeapon) {
  426.     if ( STD_CENTERXY_USES_HITBOXES ) return anEWeapon->Y+anEWeapon->HitWidth/2 + anEWeapon->HitXOffset;
  427.     else return anEWeapon->X+8*anEWeapon->TileWidth;
  428. }
  429.  
  430. int CenterY(eweapon anEWeapon) {
  431.     if ( STD_CENTERXY_USES_HITBOXES ) return anEWeapon->Y+anEWeapon->HitHeight/2 + anEWeapon->HitYOffset;
  432.     else return anEWeapon->Y+8*anEWeapon->TileHeight;
  433. }
  434.  
  435. int CenterX(lweapon anLWeapon) {
  436.     if ( STD_CENTERXY_USES_HITBOXES ) return anLWeapon->Y+anLWeapon->HitWidth/2 + anLWeapon->HitXOffset;
  437.     else return anLWeapon->X+8*anLWeapon->TileWidth;
  438. }
  439.  
  440.  
  441. int CenterY(lweapon anLWeapon) {
  442.     if ( STD_CENTERXY_USES_HITBOXES ) return anLWeapon->Y+anLWeapon->HitHeight/2 + anLWeapon->HitYOffset;
  443.     else return anLWeapon->Y+8*anLWeapon->TileHeight;
  444. }
  445.  
  446. //Returns the X and Y coordinates of the centre of Link.
  447. int CenterLinkX() { return Link->X+8; }
  448. int CenterLinkY() { return Link->Y+8; }
  449.  
  450. //Return the coordinates of a combo on the screen
  451. int ComboX(int loc) {
  452.     return loc%16*16;
  453. }
  454.  
  455. int ComboY(int loc) {
  456.     return loc&0xF0;
  457. }
  458.  
  459. //Returns true if the combo at '(x, y)' has either an inherent or place flag of type 'flag'
  460. bool ComboFI(int x, int y, int flag){
  461.     int loc = ComboAt(x,y);
  462.     return Screen->ComboF[loc] == flag || Screen->ComboI[loc] == flag;
  463. }
  464.  
  465. //Returns true if the combo at 'loc' has either an inherent or place flag of type 'flag'
  466. bool ComboFI(int loc, int flag){
  467.     return Screen->ComboF[loc] == flag || Screen->ComboI[loc] == flag;
  468. }
  469.  
  470. //Sets bit 'bit' of Screen->D[] register 'd' to 'state'
  471. void SetScreenDBit(int dmap, int screen, int d, int bit, bool state){
  472.     int curstate = Game->GetDMapScreenD(dmap, screen, d);
  473.     if(state)   Game->SetDMapScreenD(dmap, screen, d, curstate |  (1 << bit));
  474.     else        Game->SetDMapScreenD(dmap, screen, d, curstate & ~(1 << bit));
  475. }
  476.  
  477. void SetScreenDBit(int screen, int d, int bit, bool state){
  478.     int curstate = Game->GetScreenD(screen, d);
  479.     if(state)   Game->SetScreenD(screen, d, curstate |  (1 << bit));
  480.     else        Game->SetScreenD(screen, d, curstate & ~(1 << bit));
  481. }
  482.  
  483. void SetScreenDBit(int d, int bit, bool state){
  484.     if(state)   Screen->D[d] |= (1 << bit);
  485.     else        Screen->D[d] &= ~(1 << bit);
  486. }
  487.  
  488. //Returns the state of bit 'bit' of Screen->D[] register 'd'
  489. bool GetScreenDBit(int dmap, int screen, int d, int bit){
  490.     return ( Game->GetDMapScreenD(dmap, screen, d) & (1 << bit) ) != 0;
  491. }
  492.  
  493. bool GetScreenDBit(int screen, int d, int bit){
  494.     return ( Game->GetScreenD(screen, d) & (1 << bit) ) != 0;
  495. }
  496.  
  497. bool GetScreenDBit(int d, int bit){
  498.     return (Screen->D[d] & (1 << bit)) != 0;
  499. }
  500.  
  501. //A shorthand way to get a combo on the current layer.
  502. //Layer 0 is the screen itself.
  503. int GetLayerComboD(int layer, int pos) {
  504.     if (layer==0) return Screen->ComboD[pos];
  505.     else return Game->GetComboData(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  506. }
  507.  
  508. //A shorthand way to set a combo on the current layer.
  509. //Layer 0 is the screen itself.
  510. void SetLayerComboD(int layer, int pos, int combo) {
  511.     if (layer == 0) Screen->ComboD[pos] = combo;
  512.     else Game->SetComboData(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, combo);
  513. }
  514.  
  515. //A shorthand way to get a combo flag on the current layer.
  516. //Layer 0 is the screen itself.
  517. int GetLayerComboF(int layer, int pos) {
  518.     if (layer==0) return Screen->ComboF[pos];
  519.     else return Game->GetComboFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  520. }
  521.  
  522. //A shorthand way to set a combo flag on the current layer.
  523. //Layer 0 is the screen itself.
  524. void SetLayerComboF(int layer, int pos, int flag) {
  525.     if (layer == 0) Screen->ComboF[pos] = flag;
  526.     else Game->SetComboFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, flag);
  527. }
  528.  
  529. //A shorthand way to get a combo type on the current layer.
  530. //Layer 0 is the screen itself.
  531. int GetLayerComboT(int layer, int pos) {
  532.     if (layer==0) return Screen->ComboT[pos];
  533.     else return Game->GetComboType(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  534. }
  535.  
  536. //A shorthand way to set a combo type on the current layer.
  537. //Layer 0 is the screen itself.
  538. void SetLayerComboT(int layer, int pos, int type) {
  539.     if (layer == 0) Screen->ComboT[pos] = type;
  540.     else Game->SetComboType(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, type);
  541. }
  542.  
  543. //A shorthand way to get a combo's solidity on the current layer.
  544. //Layer 0 is the screen itself.
  545. int GetLayerComboS(int layer, int pos) {
  546.     if (layer==0) return Screen->ComboS[pos];
  547.     else return Game->GetComboSolid(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  548. }
  549.  
  550. //A shorthand way to set a combo's solidity on the current layer.
  551. //Layer 0 is the screen itself.
  552. void SetLayerComboS(int layer, int pos, int solidity) {
  553.     if (layer == 0) Screen->ComboS[pos] = solidity;
  554.     if ( MIN_CONSTANT > -214747.9999 ) { //Not compile don 2.50.3
  555.         if ( layer == 1 )
  556.         Game->SetComboSolid(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, solidity);
  557.         else if ( layer > 1 ) {
  558.             int str[]="Setting solidity on layers higher than 1 causes this version of ZC to crash.";
  559.             TraceS(str);
  560.         }
  561.     }
  562.     else Game->SetComboSolid(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, solidity);
  563. }
  564.  
  565. //A shorthand way to get a combo inherent flag on the current layer.
  566. //Layer 0 is the screen itself.
  567. int GetLayerComboI(int layer, int pos) {
  568.     if (layer==0) return Screen->ComboI[pos];
  569.     else return Game->GetComboInherentFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  570. }
  571.  
  572. //A shorthand way to set a combo inherent flag on the current layer.
  573. //Layer 0 is the screen itself.
  574. void SetLayerComboI(int layer, int pos, int flag) {
  575.     if (layer == 0) Screen->ComboI[pos] = flag;
  576.     else Game->SetComboInherentFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, flag);
  577. }
  578.  
  579. //A shorthand way to get a combo CSet on the current layer.
  580. //Layer 0 is the screen itself.
  581. int GetLayerComboC(int layer, int pos) {
  582.     if (layer==0) return Screen->ComboC[pos];
  583.     else return Game->GetComboCSet(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos);
  584. }
  585.  
  586. //A shorthand way to set a combo CSet on the current layer.
  587. //Layer 0 is the screen itself.
  588. void SetLayerComboC(int layer, int pos, int cset) {
  589.     if (layer == 0) Screen->ComboC[pos] = cset;
  590.     else Game->SetComboCSet(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, cset);
  591. }
  592.  
  593.  
  594. //Copies the combos and csets from one screen to another.
  595. //Only copies layer 0!
  596. void ScreenCopy(int destmap, int destscr, int srcmap, int srcscr) {
  597.     for (int i = 0; i < 176; i++) {
  598.         Game->SetComboData(destmap,destscr, i, Game->GetComboData(srcmap,srcscr,i));
  599.         Game->SetComboCSet(destmap,destscr, i, Game->GetComboCSet(srcmap,srcscr,i));
  600.     }
  601. }
  602.  
  603. //Swaps a row of tiles of length 'length' between positions 'first' and 'second'
  604. void SwapTileRow(int first, int second, int length){
  605.     for(int i=0;i<length;i++) SwapTile(first+i,second+i);
  606. }
  607.  
  608. //Copies a row of tiles of length 'length' from 'source' onto 'dest'
  609. void CopyTileRow(int source, int dest, int length){
  610.     for(int i=0;i<length;i++) CopyTile(source+i,dest+i);
  611. }
  612.  
  613. //Clears a row of tiles of length 'length' starting from tile 'ref'
  614. void ClearTileRow(int ref, int length){
  615.     for(int i=0;i<length;i++) ClearTile(ref+i);
  616. }
  617.  
  618. //Swaps a block of tiles defined by diagonal corners 'first' and 'last'
  619. //with the block starting with top left tile 'second'
  620. void SwapTileBlock(int first, int last, int second){
  621.     if(last < first){
  622.         int swap = first;
  623.         first = last;
  624.         last = swap;
  625.     }
  626.     int w = last%20-first%20;
  627.     if(w < 0){
  628.         first -= w;
  629.         last += w;
  630.         w = -w;
  631.     }
  632.     for(int i=0;i<=last-first;i++) if(i%20 <= w) SwapTile(first+i,second+i);
  633. }
  634.  
  635. //Copies a block of tiles defined by diagonal corners 'sourcefirst' and 'sourcelast'
  636. //onto the block starting with top left tile 'destfirst'
  637. void CopyTileBlock(int sourcefirst, int sourcelast, int destfirst){
  638.     if(sourcelast < sourcefirst){
  639.         int swap = sourcefirst;
  640.         sourcefirst = sourcelast;
  641.         sourcelast = swap;
  642.     }
  643.     int w = sourcelast%20-sourcefirst%20;
  644.     if(w < 0){
  645.         sourcefirst -= w;
  646.         sourcelast += w;
  647.         w = -w;
  648.     }
  649.     for(int i=0;i<=sourcelast-sourcefirst;i++) if(i%20 <= w) CopyTile(sourcefirst+i,destfirst+i);
  650. }
  651.  
  652. //Clears a block of tiles defined by diagonal corners 'reffirst' and 'reflast'
  653. void ClearTileBlock(int reffirst, int reflast){
  654.     if(reflast < reffirst){
  655.         int swap = reffirst;
  656.         reffirst = reflast;
  657.         reflast = swap;
  658.     }
  659.     int w = reflast%20-reffirst%20;
  660.     if(w < 0){
  661.         reffirst -= w;
  662.         reflast += w;
  663.         w = -w;
  664.     }
  665.     for(int i=0;i<=reflast-reffirst;i++) if(i%20 <= w) ClearTile(reffirst+i);
  666. }
  667.  
  668.  
  669. //Overload to Screen->DrawString which includes a position to start drawing from in the string
  670. //Does not check for overflow
  671. void DrawString(int layer, int x, int y, int font, int color, int background_color, int format, int opacity,
  672.                 int string, int start){
  673.     int buffer[256];
  674.     for(int i=start;string[i]!=0;i++) buffer[i-start] = string[i];
  675.     Screen->DrawString(layer,x,y,font,color,background_color,format,opacity,buffer);
  676. }
  677.  
  678. //Overload to Screen->DrawString which includes a start and end position to draw the string
  679. //Does not check for overflow
  680. void DrawString(int layer, int x, int y, int font, int color, int background_color, int format, int opacity,
  681.                 int string, int start, int end){
  682.     int buffer[256];
  683.     for(int i=start;i<end;i++) buffer[i-start] = string[i];
  684.     Screen->DrawString(layer,x,y,font,color,background_color,format,opacity,buffer);
  685. }
  686.  
  687.  
  688. // A very simple layer 0 tile drawing routine.
  689. void DrawTileSimple(int x, int y, int tile, int color) {
  690.     Screen->FastTile(0, x, y, tile, color, 128);
  691. }
  692.  
  693.  
  694. //Returns the distance between two sets of coordinates using Pythagoras' Theorem
  695. float Distance(int x1, int y1, int x2, int y2) {
  696.     int x = (x1-x2);
  697.     int y = (y1-y2);
  698.     if ( STD_FORCE_OLD_DISTANCE ) return Sqrt(x*x+y*y);
  699.     else {
  700.         if ( ( x * y ) < 0 ) {
  701.            
  702.             if ( STD_DISTANCE_USE_SAFESQRT ) return SafeSqrt(x*x+y*y);
  703.             else {
  704.                
  705.                 //...or reduce factor by MAX_INT, Sqrt(factor) and add 464?
  706.                 //...which way does it roll over?
  707.                 //factor = ;
  708.                 int factor =  214747.9999 + (x*y);
  709.                 if ( factor > 0 ) return Sqrt(factor) + 464;
  710.                 else if ( factor == 0 ) return 464;
  711.                 else return Sqrt(214747.9999);
  712.                 //else return -1;
  713.                 //return Sqrt(( x*y ) * -1) + 464;
  714.             }
  715.         }
  716.     }
  717.         //
  718. }
  719.  
  720. //Returns the distance between two sets of coordinates using Pythagoras' Theorem
  721. //Allows scaling for large distance determinations.
  722. //Argument 'scale' represents a ratio of 1:scale.
  723. //Argument 'scale' is most precise when using powers of 10 (i.e. 1, 10, 100, 1000, 10000).
  724. //If arg 'scale' is set to 0, it defaults to '1'.
  725. //Returns -1 on error.
  726. float Distance(int x1, int y1, int x2, int y2, int scale) {
  727.     if ( scale == 0 ) scale = 1;
  728.     float x = (x1-x2) / scale;
  729.     float y = (y1-y2) / scale;
  730.     float factor = (x*x)+(y*y);
  731.     if ( factor < 0 ) return -1;
  732.     else return Sqrt(factor) * scale;
  733. }
  734.  
  735.  
  736.  
  737.  
  738. //Returns the distance between two sets of coordinates using Pythagoras' Theorem
  739. float SafeDistance(int x1, int y1, int x2, int y2) {
  740.     int x;
  741.     int y;
  742.     if ( x1 > x2 ) x = x1-x2;
  743.     else x = x2 - x1;
  744.     if ( y1 > y2 ) y = y1-y2;
  745.     else y = y2 - y1;
  746.     return Sqrt(x*x+y*y);
  747. }
  748.  
  749. //Returns the distance between two sets of coordinates using Pythagoras' Theorem
  750. //Arg specify_negative_value is used to specify a value to return is a negative number is parsed to
  751. //determine a square root.
  752. //float Distance(int x1, int y1, int x2, int y2, int specify_negative_value) {
  753. //  int x = (x1-x2);
  754. //  int y = (y1-y2);
  755. //  return SafeSqrt(x*x+y*y, specify_negative_value);
  756. //}
  757.  
  758.  
  759. //Returns the direction of the vector from point 1 to point 2, in degrees from -180 to 180. (0 = right)
  760. float Angle(int x1, int y1, int x2, int y2) {
  761.     return ArcTan(x2-x1, y2-y1)*57.2958;
  762. }
  763.  
  764. //The above, but in radians.
  765. float RadianAngle(int x1, int y1, int x2, int y2) {
  766.     return ArcTan(x2-x1, y2-y1);
  767. }
  768.  
  769. //Kills inputs from A, B, L, R, Start, Map, and Ex buttons.
  770. void NoInput(){
  771.     Link->InputA = false;
  772.     Link->InputB = false;
  773.     Link->InputL = false;
  774.     Link->InputR = false;
  775.     Link->InputEx1 = false;
  776.     Link->InputEx2 = false;
  777.     Link->InputEx3 = false;
  778.     Link->InputEx4 = false;
  779.     Link->InputStart = false;
  780.     Link->InputMap = false;
  781. }
  782.  
  783. //Kills presses from A, B, L, R, Start, Map, and Ex buttons.
  784. void NoPress(){
  785.     Link->PressA = false;
  786.     Link->PressB = false;
  787.     Link->PressL = false;
  788.     Link->PressR = false;
  789.     Link->PressEx1 = false;
  790.     Link->PressEx2 = false;
  791.     Link->PressEx3 = false;
  792.     Link->PressEx4 = false;
  793.     Link->PressStart = false;
  794.     Link->PressMap = false;
  795. }
  796.  
  797. //Kills inputs from A, B, L, R, Start, Map, and Ex buttons.
  798. void NoInput(bool stick){
  799.     Link->InputA = false;
  800.     Link->InputB = false;
  801.     Link->InputL = false;
  802.     Link->InputR = false;
  803.     Link->InputEx1 = false;
  804.     Link->InputEx2 = false;
  805.     Link->InputEx3 = false;
  806.     Link->InputEx4 = false;
  807.     Link->InputStart = false;
  808.     Link->InputMap = false;
  809.     if ( stick ) {
  810.         Link->InputAxisUp = false;
  811.         Link->InputAxisDown = false;
  812.         Link->InputAxisLeft = false;
  813.         Link->InputAxisRight = false;
  814.     }
  815. }
  816.  
  817. //Kills presses from A, B, L, R, Start, Map, and Ex buttons.
  818. void NoPress(bool stick){
  819.     Link->PressA = false;
  820.     Link->PressB = false;
  821.     Link->PressL = false;
  822.     Link->PressR = false;
  823.     Link->PressEx1 = false;
  824.     Link->PressEx2 = false;
  825.     Link->PressEx3 = false;
  826.     Link->PressEx4 = false;
  827.     Link->PressStart = false;
  828.     Link->PressMap = false;
  829.     if ( stick ) {
  830.         Link->PressAxisUp = false;
  831.         Link->PressAxisDown = false;
  832.         Link->PressAxisLeft = false;
  833.         Link->PressAxisRight = false;
  834.     }
  835. }
  836.  
  837.    
  838.    
  839. // Returns the X component of a vector with a degree angle.
  840. // A length of 3 and angle of 0 returns 3.
  841. // A length of 3 and angle of 45 returns approx. 1.57.
  842. // A length of 3 and angle of 90 returns 0.
  843. float VectorX(int len, float angle) {
  844.     return Cos(angle)*len;
  845. }
  846.  
  847. // Returns the Y component of a vector with a degree angle.
  848. // A length of 3 and angle of 0 returns 0.
  849. // A length of 3 and angle of 45 returns approx. 1.57.
  850. // A length of 3 and angle of 90 returns 3.
  851. float VectorY(int len, float angle) {
  852.     return Sin(angle)*len;
  853. }
  854.  
  855. //rotates X about a center point by an amount of degrees
  856. float RotatePointX(float x, float y, float centerX, float centerY, float degrees) {
  857.     float dx = x - centerX;
  858.     float dy = y - centerY;
  859.     return (Cos(degrees) * dx) - (Sin(degrees) * dy) + centerX;
  860. }
  861.  
  862. //rotates Y about a center point by an amount of degrees
  863. float RotatePointY(float x, float y, float centerX, float centerY, float degrees) {
  864.     float dx = x - centerX;
  865.     float dy = y - centerY;
  866.     return (Sin(degrees) * dx) - (Cos(degrees) * dy) + centerY;
  867. }
  868.  
  869. //scales X to centerX by a given scale
  870. float ScalePointX(float x, float centerX, float scale) {
  871.     return (scale * (x - centerX)) + centerX;
  872. }
  873.  
  874. //scales Y to centerY by a given scale
  875. float ScalePointY(float y, float centerY, float scale) {
  876.     return (scale * (y - centerY)) + centerY;
  877. }
  878.  
  879. //rotates and scales X about a center point by an amount of degrees
  880. float RotateScalePointX(float x, float y, float centerX, float centerY, float degrees, float scaleX, float scaleY) {
  881.     float dx = (x - centerX) * scaleX;
  882.     float dy = (y - centerY) * scaleY;
  883.     return (Cos(degrees) * dx) - (Sin(degrees) * dy) + centerX;
  884. }
  885.  
  886. //rotates and scales Y about a center point by an amount of degrees
  887. float RotateScalePointY(float x, float y, float centerX, float centerY, float degrees, float scaleX, float scaleY) {
  888.     float dx = (x - centerX) * scaleX;
  889.     float dy = (y - centerY) * scaleY;
  890.     return (Sin(degrees) * dx) - (Cos(degrees) * dy) + centerY;
  891. }
  892.  
  893.  
  894. // Interpolates between p1 and p2 given 't' clamped within range 0,1.
  895. float Lerp(float p1, float p2, float t) {
  896.     return (p1 + (p2 - p1) * t);
  897. }
  898.  
  899. // Returns the dot product of two vectors.
  900. float DotProduct( float x1, float y1, float x2, float y2 ) {
  901.     return (x1 * x2 + y1 * y2);
  902. }
  903.  
  904. // Returns the cross product of two vectors.
  905. float CrossProduct( float x1, float y1, float x2, float y2 ) {
  906.     return (x1 * y2 - y1 * x2);
  907. }
  908.  
  909. // Returns the squared distance of a vector.
  910. float DistanceSquared( float x, float y ) {
  911.     return (x * x + y * y);
  912. }
  913.  
  914. // Finds the center of p1 and p2.
  915. float Midpoint(float p1, float p2) {
  916.     return Lerp(p1, p2, 0.5);
  917. }
  918.  
  919. // Performs a "Smooth" Interpolation given 't' clamped within range 0,1.
  920. float SmoothStep(float p1, float p2, float t) {
  921.     t = (t * t) * (3.0 - (2.0 * t));
  922.     return Lerp(p1, p2, t);
  923. }
  924.  
  925. // Returns an angle pointing (t)percentage more accurate to the target than the specified radian_angle.
  926. float TurnTowards( int X, int Y, int targetX, int targetY, float radian_angle, float t ) {
  927.     float a = ArcTan( targetX - X, targetY - Y );
  928.     float d = WrapAngle(a - radian_angle);
  929.     if ( d > PI )
  930.         d =-( PI2 - d );
  931.     else if ( d < -PI )
  932.         d = PI2 + d;
  933.     return WrapAngle(radian_angle + d * t);
  934. }
  935.  
  936. // Wraps radian value towards the range of -PI,PI.
  937. float WrapAngle( float radians ) {
  938.     while (radians <= -PI) radians += PI2;
  939.     while (radians > PI) radians -= PI2;
  940.     return radians;
  941. }
  942.  
  943. // Wraps degree value towards the range of -180,180.
  944. float WrapDegrees( float degrees ) {
  945.     while (degrees <= -180) degrees += 360;
  946.     while (degrees > 180) degrees -= 360;
  947.     return degrees;
  948. }
  949.  
  950. // Converts a counterclockwise degree angle (from -180 to 180) into one of the eight
  951. // standard directions (DIR_UP etc.) used by ZC.
  952. int AngleDir8(float angle) {
  953.     if (angle <= 157.5 && angle > 112.5)
  954.         return DIR_LEFTDOWN;
  955.     else if (angle <= 112.5 && angle > 67.5)
  956.         return DIR_DOWN;
  957.     else if (angle <= 67.5 && angle > 22.5)
  958.         return DIR_RIGHTDOWN;
  959.     else if (angle <= 22.5 && angle > -22.5)
  960.         return DIR_RIGHT;
  961.     else if (angle <= -22.5 && angle > -67.5)
  962.         return DIR_RIGHTUP;
  963.     else if (angle <= -67.5 && angle > -112.5)
  964.         return DIR_UP;
  965.     else if (angle <= -112.5 && angle > -157.5)
  966.         return DIR_LEFTUP;
  967.     else
  968.         return DIR_LEFT;
  969. }
  970.  
  971. //The above, but for radian angles.
  972. int RadianAngleDir8(float angle) {
  973.     return AngleDir8(angle*57.2958);
  974. }
  975.  
  976. // Converts a counterclockwise degree angle (from -180 to 180) into one of the four
  977. // standard directions (DIR_UP, DIR_DOWN, DIR_LEFT, DIR_RIGHT) used by ZC.
  978. int AngleDir4(float angle) {
  979.     if (angle <= 135 && angle > 45)
  980.         return DIR_DOWN;
  981.     else if (angle <= 45 && angle > -45)
  982.         return DIR_RIGHT;
  983.     else if (angle <= -45 && angle > -135)
  984.         return DIR_UP;
  985.     else
  986.         return DIR_LEFT;
  987. }
  988.  
  989. //The above, but for radian angles.
  990. int RadianAngleDir4(float angle) {
  991.     return AngleDir4(angle*57.2958);
  992. }
  993.  
  994. //Returns the opposite direction to angle 'dir'
  995. int OppositeDir(int dir) {
  996.     return Cond(dir < 4, dir^1b, dir^11b);
  997. }
  998.  
  999. //Converts directions to go round in a circle rather than U, D, L, R
  1000. int SpinDir(int dir) {
  1001.     if(dir==0)
  1002.         return DIR_UP;
  1003.     else if(dir==1)
  1004.         return DIR_RIGHT;
  1005.     else if(dir==2)
  1006.         return DIR_DOWN;
  1007.     else if(dir==3)
  1008.         return DIR_LEFT;
  1009.     return -1;
  1010. }
  1011.  
  1012. //Draws an ffc to a given layer. If the ffc is larger than 1x1 its graphics must all be comboed
  1013. void DrawToLayer(ffc f, int layer, int opacity){
  1014.     Screen->DrawCombo(layer,f->X,f->Y,f->Data,f->TileWidth,f->TileHeight,f->CSet,-1,-1,0,0,0,-1,0,true,opacity);
  1015. }
  1016.  
  1017. //Draws an npc to a given layer
  1018. void DrawToLayer(npc n, int layer, int opacity){
  1019.     Screen->DrawTile(layer,n->X,n->Y,n->Tile,n->TileWidth,n->TileHeight,n->CSet,-1,-1,0,0,0,0,true,opacity);
  1020. }
  1021.  
  1022. //Draws an lweapon to a given layer
  1023. void DrawToLayer(lweapon l, int layer, int opacity){
  1024.     Screen->DrawTile(layer,l->X,l->Y,l->Tile,l->TileWidth,l->TileHeight,l->CSet,-1,-1,0,0,0,0,true,opacity);
  1025. }
  1026.  
  1027. //Draws an eweapon to a given layer
  1028. void DrawToLayer(eweapon e, int layer, int opacity){
  1029.     Screen->DrawTile(layer,e->X,e->Y,e->Tile,e->TileWidth,e->TileHeight,e->CSet,-1,-1,0,0,0,0,true,opacity);
  1030. }
  1031.  
  1032. //Draws an item to a given layer
  1033. void DrawToLayer(item i, int layer, int opacity){
  1034.     Screen->DrawTile(layer,i->X,i->Y,i->Tile,i->TileWidth,i->TileHeight,i->CSet,-1,-1,0,0,0,0,true,opacity);
  1035. }
  1036.  
  1037. //Generalized and optimized rectangle collision checking function.
  1038. //Returns true if the bounding box of box1 and box2 overlap.
  1039. bool RectCollision(int box1_x1, int box1_y1, int box1_x2, int box1_y2, int box2_x1, int box2_y1, int box2_x2, int box2_y2) {
  1040.     if( box1_y2 < box2_y1 ) return false;
  1041.     else if( box1_y1 > box2_y2 ) return false;
  1042.     else if( box1_x2 < box2_x1 ) return false;
  1043.     else if( box1_x1 > box2_x2 ) return false;
  1044.     return true;
  1045. }
  1046.  
  1047. //Check for collisions of two squares given upper-left coordinates and a side length for each.
  1048. bool SquareCollision(int c1x, int c1y, int side1, int c2x, int c2y, int side2) {
  1049.     return RectCollision(c1x, c1y, c1x+side1, c1y+side1, c2x, c2y, c2x+side2, c2y+side2);
  1050. }
  1051.  
  1052. //Check for collisions of two squares given center coordinates and a halved side length for each.
  1053. bool SquareCollision2(int c1x, int c1y, int radius1, int c2x, int c2y, int radius2) {
  1054.     if( c1y + radius1 < c2y - radius2 ) return false;
  1055.     else if( c1y - radius1 > c2y + radius2 ) return false;
  1056.     else if( c1x + radius1 < c2x - radius2 ) return false;
  1057.     else if( c1x - radius1 > c2x + radius2 ) return false;
  1058.     return true;
  1059. }
  1060.  
  1061. //Returns true if the two circles c1 and c2 overlap.
  1062. bool CircleCollision(int c1x, int c1y, int radius1, int c2x, int c2y, int radius2) {
  1063.     return (Distance(c1x,c1y,c2x,c2y) <= (radius1+radius2));
  1064. }
  1065.  
  1066. //Returns true if there is a collision between the hitboxes of an lweapon and an eweapon.
  1067. bool Collision(lweapon a, eweapon b) {
  1068.     int c[4];
  1069.     c[0] = a->X + a->HitXOffset;
  1070.     c[1] = b->X + b->HitXOffset;
  1071.     c[2] = a->Y + a->HitYOffset;
  1072.     c[3] = b->Y + b->HitYOffset;
  1073.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1074. }
  1075.  
  1076. //A collision between an lweapon and an lweapon.
  1077. bool Collision(lweapon a, lweapon b) {
  1078.     int c[4];
  1079.     c[0] = a->X + a->HitXOffset;
  1080.     c[1] = b->X + b->HitXOffset;
  1081.     c[2] = a->Y + a->HitYOffset;
  1082.     c[3] = b->Y + b->HitYOffset;
  1083.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1084. }
  1085.  
  1086. //A collision between an eweapon and an eweapon.
  1087. bool Collision(eweapon a, eweapon b) {
  1088.     int c[4];
  1089.     c[0] = a->X + a->HitXOffset;
  1090.     c[1] = b->X + b->HitXOffset;
  1091.     c[2] = a->Y + a->HitYOffset;
  1092.     c[3] = b->Y + b->HitYOffset;
  1093.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1094. }
  1095.  
  1096. //A collision between an lweapon and an npc.
  1097. bool Collision(lweapon a, npc b) {
  1098.     int c[4];
  1099.     c[0] = a->X + a->HitXOffset;
  1100.     c[1] = b->X + b->HitXOffset;
  1101.     c[2] = a->Y + a->HitYOffset;
  1102.     c[3] = b->Y + b->HitYOffset;
  1103.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1104. }
  1105.  
  1106. //A collision between an eweapon and an npc.
  1107. bool Collision(eweapon a, npc b) {
  1108.     int c[4];
  1109.     c[0] = a->X + a->HitXOffset;
  1110.     c[1] = b->X + b->HitXOffset;
  1111.     c[2] = a->Y + a->HitYOffset;
  1112.     c[3] = b->Y + b->HitYOffset;
  1113.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1114. }
  1115.  
  1116. //A collision between an npc and an npc.
  1117. bool Collision(npc a, npc b) {
  1118.     int c[4];
  1119.     c[0] = a->X + a->HitXOffset;
  1120.     c[1] = b->X + b->HitXOffset;
  1121.     c[2] = a->Y + a->HitYOffset;
  1122.     c[3] = b->Y + b->HitYOffset;
  1123.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1124. }
  1125.  
  1126. //A collision between an item and an lweapon.
  1127. bool Collision(item a, lweapon b) {
  1128.     int c[4];
  1129.     c[0] = a->X + a->HitXOffset;
  1130.     c[1] = b->X + b->HitXOffset;
  1131.     c[2] = a->Y + a->HitYOffset;
  1132.     c[3] = b->Y + b->HitYOffset;
  1133.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1134. }
  1135.  
  1136. //A collision between an item and an eweapon.
  1137. bool Collision(item a, eweapon b) {
  1138.     int c[4];
  1139.     c[0] = a->X + a->HitXOffset;
  1140.     c[1] = b->X + b->HitXOffset;
  1141.     c[2] = a->Y + a->HitYOffset;
  1142.     c[3] = b->Y + b->HitYOffset;
  1143.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1144. }
  1145.  
  1146. //A collision between an item and an npc.
  1147. bool Collision(item a, npc b) {
  1148.     int c[4];
  1149.     c[0] = a->X + a->HitXOffset;
  1150.     c[1] = b->X + b->HitXOffset;
  1151.     c[2] = a->Y + a->HitYOffset;
  1152.     c[3] = b->Y + b->HitYOffset;
  1153.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1154. }
  1155.  
  1156. //A collision between an item and an item.
  1157. bool Collision(item a, item b) {
  1158.     int c[4];
  1159.     c[0] = a->X + a->HitXOffset;
  1160.     c[1] = b->X + b->HitXOffset;
  1161.     c[2] = a->Y + a->HitYOffset;
  1162.     c[3] = b->Y + b->HitYOffset;
  1163.     return RectCollision(c[0], c[2], c[0]+a->HitWidth, c[2]+a->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (a->Z + a->HitZHeight >= b->Z) && (a->Z <= b->Z + b->HitZHeight);
  1164. }
  1165.  
  1166. //A collision between an ffc and an lweapon. Uses TileWidth and TileHeight for the FFC's bounding box. Ignores the Z axis.
  1167. bool Collision(ffc f, lweapon b) {
  1168.     int c[2];
  1169.     c[0] = b->X + b->HitXOffset;
  1170.     c[1] = b->Y + b->HitYOffset;
  1171.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), c[0], c[1], c[0]+b->HitWidth, c[1]+b->HitHeight);
  1172. }
  1173.  
  1174. //A collision between an ffc and an eweapon. Uses TileWidth and TileHeight for the FFC's bounding box. Ignores the Z axis.
  1175. bool Collision(ffc f, eweapon b) {
  1176.     int c[2];
  1177.     c[0] = b->X + b->HitXOffset;
  1178.     c[1] = b->Y + b->HitYOffset;
  1179.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), c[0], c[1], c[0]+b->HitWidth, c[1]+b->HitHeight);
  1180. }
  1181.  
  1182. //A collision between an ffc and an npc. Uses TileWidth and TileHeight for the FFC's bounding box. Ignores the Z axis.
  1183. bool Collision(ffc f, npc b) {
  1184.     int c[2];
  1185.     c[0] = b->X + b->HitXOffset;
  1186.     c[1] = b->Y + b->HitYOffset;
  1187.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), c[0], c[1], c[0]+b->HitWidth, c[1]+b->HitHeight);
  1188. }
  1189.  
  1190. //A collision between an ffc and an item. Uses TileWidth and TileHeight for the FFC's bounding box. Ignores the Z axis.
  1191. bool Collision(ffc f, item b) {
  1192.     int c[2];
  1193.     c[0] = b->X + b->HitXOffset;
  1194.     c[1] = b->Y + b->HitYOffset;
  1195.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), c[0], c[1], c[0]+b->HitWidth, c[1]+b->HitHeight);
  1196. }
  1197.  
  1198. //A collision between an ffc and an ffc. Uses TileWidth and TileHeight for the FFCs' bounding boxes.
  1199. bool Collision(ffc f, ffc f2) {
  1200.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), f2->X, f2->Y, f2->X+f2->TileWidth*16, f2->Y+f2->TileHeight*16);
  1201. }
  1202.  
  1203. //A circular collision between an ffc and an ffc. Uses TileWidth and TileHeight to find the centre of the FFCs.
  1204. bool Collision(ffc f, int radius1, ffc f2, int radius2) {
  1205.     return CircleCollision(f->X+f->TileWidth/2, f->Y+f->TileHeight/2, radius1,f2->X+f2->TileWidth/2, f2->Y+f2->TileHeight/2, radius2);
  1206. }
  1207.  
  1208. // So that you don't have to remember the ordering of the args
  1209. bool Collision(eweapon a, lweapon b) {
  1210.     return Collision(b, a);
  1211. }
  1212.  
  1213. bool Collision(npc a, lweapon b) {
  1214.     return Collision(b, a);
  1215. }
  1216.  
  1217. bool Collision(npc a, eweapon b) {
  1218.     return Collision(b, a);
  1219. }
  1220.  
  1221. bool Collision(lweapon a, item b) {
  1222.     return Collision(b, a);
  1223. }
  1224.  
  1225. bool Collision(eweapon a, item b) {
  1226.     return Collision(b, a);
  1227. }
  1228.  
  1229. bool Collision(npc a, item b) {
  1230.     return Collision(b, a);
  1231. }
  1232.  
  1233. bool Collision(lweapon a, ffc b) {
  1234.     return Collision(b, a);
  1235. }
  1236.  
  1237. bool Collision(eweapon a, ffc b) {
  1238.     return Collision(b, a);
  1239. }
  1240.  
  1241. bool Collision(npc a, ffc b) {
  1242.     return Collision(b, a);
  1243. }
  1244.  
  1245. bool Collision(item a, ffc b) {
  1246.     return Collision(b, a);
  1247. }
  1248.  
  1249. // Returns true if there is a collision between Link's hitbox and the eweapon's.
  1250. // This only checks hitboxes.
  1251. bool LinkCollision(eweapon b) {
  1252.     int c[4];
  1253.     c[0] = Link->X + Link->HitXOffset;
  1254.     c[1] = b->X + b->HitXOffset;
  1255.     c[2] = Link->Y + Link->HitYOffset;
  1256.     c[3] = b->Y + b->HitYOffset;
  1257.     return RectCollision(c[0], c[2], c[0]+Link->HitWidth, c[2]+Link->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (Link->Z + Link->HitZHeight >= b->Z) && (Link->Z <= b->Z + b->HitZHeight);
  1258. }
  1259.  
  1260. // Returns true if there is a collision between Link's hitbox and the lweapon's.
  1261. // This only checks hitboxes.
  1262. bool LinkCollision(lweapon b) {
  1263.     int c[4];
  1264.     c[0] = Link->X + Link->HitXOffset;
  1265.     c[1] = b->X + b->HitXOffset;
  1266.     c[2] = Link->Y + Link->HitYOffset;
  1267.     c[3] = b->Y + b->HitYOffset;
  1268.     return RectCollision(c[0], c[2], c[0]+Link->HitWidth, c[2]+Link->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (Link->Z + Link->HitZHeight >= b->Z) && (Link->Z <= b->Z + b->HitZHeight);
  1269. }
  1270.  
  1271.  
  1272. // Returns true if there is a collision between Link's hitbox and the item's.
  1273. // This only checks hitboxes.
  1274. bool LinkCollision(item b) {
  1275.     int c[4];
  1276.     c[0] = Link->X + Link->HitXOffset;
  1277.     c[1] = b->X + b->HitXOffset;
  1278.     c[2] = Link->Y + Link->HitYOffset;
  1279.     c[3] = b->Y + b->HitYOffset;
  1280.     return RectCollision(c[0], c[2], c[0]+Link->HitWidth, c[2]+Link->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (Link->Z + Link->HitZHeight >= b->Z) && (Link->Z <= b->Z + b->HitZHeight);
  1281. }
  1282.  
  1283.  
  1284. // Returns true if there is a collision between Link's hitbox and the npc's.
  1285. // This only checks hitboxes.  Uses TileWidth and TileHeight to find the centre of the FFCs.
  1286. bool LinkCollision(npc b) {
  1287.     int c[4];
  1288.     c[0] = Link->X + Link->HitXOffset;
  1289.     c[1] = b->X + b->HitXOffset;
  1290.     c[2] = Link->Y + Link->HitYOffset;
  1291.     c[3] = b->Y + b->HitYOffset;
  1292.     return RectCollision(c[0], c[2], c[0]+Link->HitWidth, c[2]+Link->HitHeight, c[1], c[3], c[1]+b->HitWidth, c[3]+b->HitHeight) && (Link->Z + Link->HitZHeight >= b->Z) && (Link->Z <= b->Z + b->HitZHeight);
  1293. }
  1294.  
  1295.  
  1296. // Returns true if there is a collision between Link's hitbox and the FFC's.
  1297. // This only checks hitboxes.
  1298. bool LinkCollision(ffc f) {
  1299.     int c[2];
  1300.     c[0] = Link->X + Link->HitXOffset;
  1301.     c[1] = Link->Y + Link->HitYOffset;
  1302.     return RectCollision(f->X, f->Y, f->X+(f->TileWidth*16), f->Y+(f->TileHeight*16), c[0], c[1], c[0]+Link->HitWidth, c[1]+Link->HitHeight);
  1303. }
  1304.  
  1305. // Returns the X coordinate of the left edge of the hitbox.
  1306. int HitboxLeft(eweapon a) {
  1307.     return (a->X + a->HitXOffset);
  1308. }
  1309.  
  1310. int HitboxLeft(lweapon a) {
  1311.     return (a->X + a->HitXOffset);
  1312. }
  1313.  
  1314. int HitboxLeft(item a) {
  1315.     return (a->X + a->HitXOffset);
  1316. }
  1317.  
  1318. int HitboxLeft(npc a) {
  1319.     return (a->X + a->HitXOffset);
  1320. }
  1321.  
  1322. int HitboxLeft(ffc a) {
  1323.     return a->X;
  1324. }
  1325.  
  1326. // Returns the X coordinate of the right edge of the hitbox.
  1327. int HitboxRight(eweapon a) {
  1328.     return (a->X + a->HitXOffset + a->HitWidth - 1);
  1329. }
  1330.  
  1331. int HitboxRight(lweapon a) {
  1332.     return (a->X + a->HitXOffset + a->HitWidth - 1);
  1333. }
  1334.  
  1335. int HitboxRight(item a) {
  1336.     return (a->X + a->HitXOffset + a->HitWidth - 1);
  1337. }
  1338.  
  1339. int HitboxRight(npc a) {
  1340.     return (a->X + a->HitXOffset + a->HitWidth - 1);
  1341. }
  1342.  
  1343. int HitboxRight(ffc a) {
  1344.     return a->X + a->TileWidth*16 - 1;
  1345. }
  1346.  
  1347. // Returns the Y coordinate of the top edge of the hitbox.
  1348. int HitboxTop(eweapon a) {
  1349.     return (a->Y + a->HitYOffset);
  1350. }
  1351.  
  1352. int HitboxTop(lweapon a) {
  1353.     return (a->Y + a->HitYOffset);
  1354. }
  1355.  
  1356. int HitboxTop(item a) {
  1357.     return (a->Y + a->HitYOffset);
  1358. }
  1359.  
  1360. int HitboxTop(npc a) {
  1361.     return (a->Y + a->HitYOffset);
  1362. }
  1363.  
  1364. int HitboxTop(ffc a) {
  1365.     return a->Y;
  1366. }
  1367.  
  1368. // Returns the Y coordinate of the bottom edge of the hitbox.
  1369. int HitboxBottom(eweapon a) {
  1370.     return (a->Y + a->HitYOffset + a->HitHeight - 1);
  1371. }
  1372.  
  1373. int HitboxBottom(lweapon a) {
  1374.     return (a->Y + a->HitYOffset + a->HitHeight - 1);
  1375. }
  1376.  
  1377. int HitboxBottom(item a) {
  1378.     return (a->Y + a->HitYOffset + a->HitHeight - 1);
  1379. }
  1380.  
  1381. int HitboxBottom(npc a) {
  1382.     return (a->Y + a->HitYOffset + a->HitHeight - 1);
  1383. }
  1384.  
  1385. //Uses TileWidth and TileHeight for the FFC's bounding box.
  1386. int HitboxBottom(ffc a) {
  1387.     return a->Y + (a->TileHeight*16) - 1;
  1388. }
  1389.  
  1390. //Returns the number of an FFC, and -1 for a non-valid FFC (which should never happen)
  1391. int FFCNum(ffc f) {
  1392.     for(int i=1; i<=32; i++)
  1393.         if(f == Screen->LoadFFC(i))
  1394.         return i;
  1395.     return -1;
  1396. }
  1397.  
  1398. //Functions for those who are not comfortable with binary
  1399. //Returns true if the left mouse button is pressed
  1400. bool InputLeftClick() {
  1401.     return (Link->InputMouseB&MB_LEFTCLICK) != 0;
  1402. }
  1403.  
  1404. //Returns true if the right mouse button is pressed
  1405. bool InputRightClick() {
  1406.     return (Link->InputMouseB&MB_RIGHTCLICK) != 0;
  1407. }
  1408.  
  1409. //Returns true if the central mouse button (if equipped) is pressed
  1410. bool InputMiddleClick() {
  1411.     return (Link->InputMouseB&MB_MIDDLECLICK) != 0;
  1412. }
  1413.  
  1414. //Returns the item ID of the item equipped to Link's A button
  1415. int GetEquipmentA() {
  1416.     return (Link->Equipment&0xFF);
  1417. }
  1418.  
  1419.  
  1420.  
  1421. //Returns the item ID of the item equipped to Link's B button
  1422. int GetEquipmentB() {
  1423.     return ((Link->Equipment&0xFF00)>>8);
  1424. }
  1425.  
  1426. //Returns true if Link is using item 'id'
  1427. bool UsingItem(int id){
  1428.     return (GetEquipmentA() == id && Link->InputA) || (GetEquipmentB() == id && Link->InputB);
  1429. }
  1430.  
  1431. //Returns the number of Triforce Pieces Link currently has
  1432. int NumTriforcePieces(){
  1433.     int ret = 0;
  1434.     for(int i=1;i<=8;i++)
  1435.         if(Game->LItems[i]&LI_TRIFORCE) ret++;
  1436.     return ret;
  1437. }
  1438.  
  1439.  
  1440.  
  1441. //Returns 1 if Screen Flag 'flag' is set from category 'category', 0 if it's not and -1 if an invalid flag is passed
  1442. //Flags are numbered starting from 0
  1443. int ScreenFlag(int category, int flag) {
  1444.     int catsizes[] = {3,7,5,3,2,4,4,2,3,7};
  1445.     if(flag < 0 || flag >= catsizes[category]) return -1;
  1446.     return Screen->Flags[category]&(1<<flag);
  1447. }
  1448.  
  1449. //Returns 1 if Screen Enemy Flag 'flag' is set from category 'category', 0 if it's not and -1 if an invalid flag is passed
  1450. //Flags are numbered starting from 0
  1451. int ScreenEFlag(int category, int flag) {
  1452.     int catsizes[] = {6,6,5};
  1453.     if(flag < 0 || flag >= catsizes[category]) return -1;
  1454.     return Screen->EFlags[category]&(1<<flag);
  1455. }
  1456.  
  1457. //Returns true if DMap Flag 'flag' is set on dmap 'dmap'
  1458. bool GetDMapFlag(int dmap, int flag){
  1459.     return (Game->DMapFlags[dmap]&flag)!=0;
  1460. }
  1461.  
  1462. //Sets a certain DMap flag to 'state'
  1463. void SetDMapFlag(int dmap, int flag, bool state){
  1464.     if(state) Game->DMapFlags[dmap] |= flag;
  1465.     else Game->DMapFlags[dmap] &= ~flag;
  1466. }
  1467.  
  1468. //Returns true if an item's Pickup state is set
  1469. //Use the IP_ constants for the 'pickup' argument of this function
  1470. bool GetItemPickup(item i, int pickup) {
  1471.     return (i->Pickup&pickup) != 0;
  1472. }
  1473.  
  1474. //Sets an item's Pickup state to 'state'
  1475. void SetItemPickup(item i, int pickup, bool state) {
  1476.     if(state) i->Pickup |= pickup;
  1477.     else i->Pickup &= ~pickup;
  1478. }
  1479.  
  1480. //Returns true if an npc's Misc. flag is set.
  1481. bool GetNPCMiscFlag(npc e, int flag) {
  1482.     return (e->MiscFlags&flag) != 0;
  1483. }
  1484.  
  1485. //Returns true if Link has the level item 'itm' from level 'level'
  1486. //Overloaded to use the current level if no 'level' arg is entered
  1487. //Use the LI_ constants for the 'itm' argument
  1488. bool GetLevelItem(int level, int itm) {
  1489.     return (Game->LItems[level]&itm) != 0;
  1490. }
  1491. bool GetLevelItem(int itm) {
  1492.     return (Game->LItems[Game->GetCurLevel()]&itm) != 0;
  1493. }
  1494. //Gives or removes a level item from Link's inventory
  1495. void SetLevelItem(int level, int itm, bool state) {
  1496.     if(state) Game->LItems[level] |= itm;
  1497.     else Game->LItems[level] &= ~itm;
  1498. }
  1499. void SetLevelItem(int itm, bool state) {
  1500.     if(state) Game->LItems[Game->GetCurLevel()] |= itm;
  1501.     else Game->LItems[Game->GetCurLevel()] &= ~itm;
  1502. }
  1503.  
  1504. //Create an NPC and set its X and Y position in one command
  1505. npc CreateNPCAt(int id, int x, int y) {
  1506.     npc nme = Screen->CreateNPC(id);
  1507.     if(nme->isValid()) {
  1508.         nme->X = x;
  1509.         nme->Y = y;
  1510.     }
  1511.     return nme;
  1512. }
  1513.  
  1514. //Create an Item and set its X and Y position in one command
  1515. item CreateItemAt(int id, int x, int y) {
  1516.     item it = Screen->CreateItem(id);
  1517.     if(it->isValid()) {
  1518.         it->X = x;
  1519.         it->Y = y;
  1520.     }
  1521.     return it;
  1522. }
  1523.  
  1524. //Create an LWeapon and set its X and Y position in one command
  1525. lweapon CreateLWeaponAt(int id, int x, int y) {
  1526.     lweapon lw = Screen->CreateLWeapon(id);
  1527.     if(lw->isValid()) {
  1528.         lw->X = x;
  1529.         lw->Y = y;
  1530.     }
  1531.     return lw;
  1532. }
  1533.  
  1534. //Create an EWeapon and set its X and Y position in one command
  1535. eweapon CreateEWeaponAt(int id, int x, int y) {
  1536.     eweapon ew = Screen->CreateEWeapon(id);
  1537.     if(ew->isValid()) {
  1538.         ew->X = x;
  1539.         ew->Y = y;
  1540.     }
  1541.     return ew;
  1542. }
  1543.  
  1544.  
  1545. //Creates an lweapon at 'distx,disty' away from where Link is facing
  1546. lweapon NextToLink(int id, int distx, int disty) {
  1547.     lweapon l = CreateLWeaponAt(id, Link->X+InFrontX(Link->Dir, distx), Link->Y+InFrontY(Link->Dir, disty));
  1548.     if(l->isValid()) {
  1549.         l->Dir = Link->Dir;
  1550.     }
  1551.     return l;
  1552. }
  1553.  
  1554. //Creates an lweapon 'dist' pixels away from the front of Link
  1555. lweapon NextToLink(int id, int dist) {
  1556.     return NextToLink(id, dist, dist);
  1557. }
  1558.  
  1559. eweapon NextToNPC(npc n, int id, int distx, int disty) {
  1560.     eweapon e = CreateEWeaponAt(id, n->X+InFrontX(n->Dir, distx), n->Y+InFrontY(n->Dir, disty));
  1561.     if(e->isValid()) {
  1562.         e->Dir = n->Dir;
  1563.     }
  1564.     return e;
  1565. }
  1566. eweapon NextToNPC(npc n, int id, int dist) {
  1567.     return NextToNPC(n, id, dist, dist);
  1568. }
  1569.  
  1570.  
  1571. //Aim-type constants, for use with AimEWeapon
  1572. //**Moved** to std_constants.zh
  1573.  
  1574. //Various methods for shooting at Link and at random
  1575. void AimEWeapon(eweapon e, int aimtype)
  1576. {
  1577.     int angle = RadianAngle(e->X, e->Y, Link->X, Link->Y);
  1578.     if(aimtype == AT_4DIR)
  1579.     {
  1580.         e->Dir = RadianAngleDir4(angle);
  1581.     }
  1582.     else if(aimtype == AT_8DIR)
  1583.     {
  1584.         e->Dir = RadianAngleDir8(angle);
  1585.     }
  1586.     else if(aimtype == AT_ANGULAR)
  1587.     {
  1588.         e->Angular = true;
  1589.         e->Angle = angle;
  1590.         e->Dir = RadianAngleDir8(angle);
  1591.     }
  1592.     else if(aimtype == AT_RAND4DIR)
  1593.     {
  1594.         e->Dir = Rand(4);
  1595.     }
  1596.     else if(aimtype == AT_RAND8DIR)
  1597.     {
  1598.         e->Dir = Rand(8);
  1599.     }
  1600.     else if(aimtype == AT_RANDANGULAR)
  1601.     {
  1602.         e->Angular = true;
  1603.         e->Angle = Randf(PI2);
  1604.         e->Dir = RadianAngleDir8(e->Angle);
  1605.     }
  1606. }
  1607.  
  1608. //Aiming at enemies and at random
  1609. void AimLWeapon(lweapon l, npc n, int aimtype)
  1610. {
  1611.     int angle = RadianAngle(l->X, l->Y, n->X, n->Y);
  1612.     if(aimtype == AT_4DIR)
  1613.     {
  1614.         l->Dir = RadianAngleDir4(angle);
  1615.     }
  1616.     else if(aimtype == AT_8DIR)
  1617.     {
  1618.         l->Dir = RadianAngleDir8(angle);
  1619.     }
  1620.     else if(aimtype == AT_ANGULAR)
  1621.     {
  1622.         l->Angular = true;
  1623.         l->Angle = angle;
  1624.         l->Dir = RadianAngleDir8(angle);
  1625.     }
  1626.     else
  1627.         AimLWeapon(l, aimtype);
  1628. }
  1629. void AimLWeapon(lweapon l, int aimtype)
  1630. {
  1631.     if(aimtype == AT_RAND4DIR)
  1632.     {
  1633.         l->Dir = Rand(4);
  1634.     }
  1635.     else if(aimtype == AT_RAND8DIR)
  1636.     {
  1637.         l->Dir = Rand(8);
  1638.     }
  1639.     else if(aimtype == AT_RANDANGULAR)
  1640.     {
  1641.         l->Angular = true;
  1642.         l->Angle = Randf(PI2);
  1643.         l->Dir = RadianAngleDir8(l->Angle);
  1644.     }
  1645. }
  1646.  
  1647. //Turns a WPN_ constant to an EW_ constant
  1648. int WeaponTypeToID(int wpnt)
  1649. {
  1650.     if(wpnt == WPN_ENEMYFLAME)      return EW_FIRE;
  1651.     else if(wpnt == WPN_ENEMYWIND)      return EW_WIND;
  1652.     else if(wpnt == WPN_ENEMYFIREBALL)  return EW_FIREBALL;
  1653.     else if(wpnt == WPN_ENEMYARROW)     return EW_ARROW;
  1654.     else if(wpnt == WPN_ENEMYBRANG)     return EW_BRANG;
  1655.     else if(wpnt == WPN_ENEMYSWORD)     return EW_BEAM;
  1656.     else if(wpnt == WPN_ENEMYROCK)      return EW_ROCK;
  1657.     else if(wpnt == WPN_ENEMYMAGIC)     return EW_MAGIC;
  1658.     else if(wpnt == WPN_ENEMYBOMB)      return EW_BOMB;
  1659.     else if(wpnt == WPN_ENEMYSBOMB)     return EW_SBOMB;
  1660.     else if(wpnt == WPN_ENEMYLITBOMB)   return EW_BOMBBLAST;
  1661.     else if(wpnt == WPN_ENEMYLITSBOMB)  return EW_SBOMBBLAST;
  1662.     else if(wpnt == WPN_ENEMYFIRETRAIL) return EW_FIRETRAIL;
  1663.     else if(wpnt == WPN_ENEMYFLAME2)    return EW_FIRE2;
  1664.     else if(wpnt == WPN_ENEMYFIREBALL2) return EW_FIREBALL2;
  1665.     return -1;
  1666. }
  1667.  
  1668.  
  1669. //Removes LWeapon 'l' from the screen
  1670. void Remove(lweapon l){
  1671.     if(!l->isValid()) return;
  1672.     l->DeadState = WDS_DEAD;
  1673.     l->X = 32768;
  1674. }
  1675.  
  1676. //Removes EWeapon 'e' from the screen
  1677. void Remove(eweapon e){
  1678.     if(!e->isValid()) return;
  1679.     e->DeadState = WDS_DEAD;
  1680.     e->X = 32768;
  1681. }
  1682.  
  1683. //Removes Item 'i' from the screen
  1684. void Remove(item i){
  1685.     if(!i->isValid()) return;
  1686.     i->X = 32768;
  1687. }
  1688.  
  1689. //Removes NPC 'n' from the screen
  1690. void Remove(npc n){
  1691.     if(!n->isValid()) return;
  1692.     n->X = 32768;
  1693.     n->HP = -1000;
  1694. }
  1695.  
  1696. //Remove an FFC by zeroing out all of its attributes, and freeing it for other use.
  1697. void Remove(ffc f){
  1698.     if ( f->Data == 0 && f->Script == 0 ) return;
  1699.     else {
  1700.         f->Data = 0;
  1701.         f->Script = 0;
  1702.         f->Script = 0;
  1703.         f->CSet = 0;
  1704.         f->Delay = 0;
  1705.         f->X = 0;
  1706.         f->Y = 0;
  1707.         f->Vx = 0;
  1708.         f->Vy = 0;
  1709.         f->Ax = 0;
  1710.         f->Ay = 0;
  1711.         for ( int q = 0; q < 10; q++ ) f->Flags[q] = 0;
  1712.         f->TileWidth = 0;
  1713.         f->TileHeight = 0;
  1714.         f->EffectWidth = 0;
  1715.         f->EffectHeight = 0;
  1716.         f->Link = 0;
  1717.         for ( int q = 0; q < 15; q++ ) f->Misc[q] = 0;
  1718.     }
  1719. }
  1720.  
  1721. //Creates a timeout item (like a rupee or heart)
  1722. item CreateTimeoutItem(int id, int x, int y) {
  1723.     item Spawn = Screen->CreateItem(id);
  1724.     SetItemPickup(Spawn, IP_TIMEOUT, true);
  1725.     Spawn->HitWidth = 16; Spawn->HitHeight = 16;
  1726.     Spawn->X = x; Spawn->Y = y;
  1727. }
  1728.  
  1729. //Creates a timeout item (like a rupee or heart)
  1730. //Allows constraining the HitWidth and HitHeight
  1731. item CreateTimeoutItem(int id, int x, int y, int width, int height) {
  1732.     item Spawn = Screen->CreateItem(id);
  1733.     SetItemPickup(Spawn, IP_TIMEOUT, true);
  1734.     Spawn->HitWidth = width; Spawn->HitHeight = height;
  1735.     Spawn->X = x; Spawn->Y = y;
  1736. }
  1737.  
  1738. // Use the I_ constants.
  1739. // Warning: these iterate over every onscreen item.
  1740. // Iterating over every onscreen lweapon multiple times per frame may
  1741. // cause slowdown in Zelda Classic.
  1742. int NumItemsOf(int type) {
  1743.     int ret = 0;
  1744.     item it;
  1745.     for (int i = Screen->NumItems(); i >0 ; i--) {
  1746.         it = Screen->LoadItem(i);
  1747.         if (it->ID == type)
  1748.         ret++;
  1749.     }
  1750.     return ret;
  1751. }
  1752.  
  1753.  
  1754. // Use the LW_ constants.
  1755. // Warning: these iterate over every onscreen lweapon.
  1756. // Iterating over every onscreen lweapon multiple times per frame may
  1757. // cause slowdown in Zelda Classic.
  1758. int NumLWeaponsOf(int type) {
  1759.     int ret = 0;
  1760.     lweapon w;
  1761.     for (int i = Screen->NumLWeapons(); i > 0; i--) {
  1762.         w = Screen->LoadLWeapon(i);
  1763.         if (w->ID == type)
  1764.         ret++;
  1765.     }
  1766.     return ret;
  1767. }
  1768.  
  1769. int NumEWeaponsOf(int type) {
  1770.     int ret = 0;
  1771.     eweapon w;
  1772.     for (int i = Screen->NumEWeapons(); i > 0; i--) {
  1773.         w = Screen->LoadEWeapon(i);
  1774.         if (w->ID == type)
  1775.         ret++;
  1776.     }
  1777.     return ret;
  1778. }
  1779.  
  1780. int NumNPCsOf(int type) {
  1781.     int ret = 0;
  1782.     npc n;
  1783.     for (int i = Screen->NumNPCs(); i > 0 ; i--) {
  1784.         n = Screen->LoadNPC(i);
  1785.         if (n->ID == type)
  1786.         ret++;
  1787.     }
  1788.     return ret;
  1789. }
  1790.  
  1791. // Returns the first LWeapon of the given type. Use the LW_ constants.
  1792. // If none exist, it returns an uninitialised pointer.
  1793. lweapon LoadLWeaponOf(int type) {
  1794.     lweapon w;
  1795.     for (int i=1; i <= Screen->NumLWeapons(); i++) {
  1796.         w = Screen->LoadLWeapon(i);
  1797.         if (w->ID == type) return w;
  1798.     }
  1799.     lweapon w2;
  1800.     return w2;
  1801. }
  1802.  
  1803. // Returns the first EWeapon of the given type. Use the EW_ constants.
  1804. // If none exist, it returns an uninitialised pointer.
  1805. eweapon LoadEWeaponOf(int type) {
  1806.     eweapon w;
  1807.     for (int i=1; i <= Screen->NumEWeapons(); i++) {
  1808.         w = Screen->LoadEWeapon(i);
  1809.         if (w->ID == type) return w;
  1810.     }
  1811.     eweapon w2;
  1812.     return w2;
  1813. }
  1814.  
  1815. // Returns the first NPC of the given type. Use the NPCT_ constants.
  1816. // If none exist, it returns an uninitialised pointer.
  1817. npc LoadNPCOfType(int type) {
  1818.     npc n;
  1819.     for (int i=1; i <= Screen->NumNPCs(); i++) {
  1820.         n = Screen->LoadNPC(i);
  1821.         if (n->Type == type) return n;
  1822.     }
  1823.     npc n2;
  1824.     return n2;
  1825. }
  1826.  
  1827. // Returns the first NPC of the given ID. Use the NPC_ constants.
  1828. // If none exist, it returns an uninitialised pointer.
  1829. npc LoadNPCOf(int type) {
  1830.     npc n;
  1831.     for (int i=1; i <= Screen->NumNPCs(); i++) {
  1832.         n = Screen->LoadNPC(i);
  1833.         if (n->ID == type) return n;
  1834.     }
  1835.     npc n2;
  1836.     return n2;
  1837. }
  1838.  
  1839. //Returns the position of the first instance of the given combo, or -1.
  1840. int FirstComboOf(int t, int layer) {
  1841.     for (int i = 0; i < 176; i++) {
  1842.         if (layer == 0) {
  1843.             if (Screen->ComboD[i] == t)
  1844.             return i;
  1845.         }
  1846.         else {
  1847.             if (GetLayerComboD(layer,i) == t)
  1848.             return i;
  1849.         }
  1850.     }
  1851.     return -1;
  1852. }
  1853.  
  1854. //Returns the position of the last instance of the given combo, or -1.
  1855. int LastComboOf(int t, int layer) {
  1856.     for (int i = 175; i >= 0; i--) {
  1857.         if (layer == 0) {
  1858.             if (Screen->ComboD[i] == t)
  1859.             return i;
  1860.         }
  1861.         else {
  1862.             if (GetLayerComboD(layer,i) == t)
  1863.             return i;
  1864.         }
  1865.     }
  1866.     return -1;
  1867. }
  1868.  
  1869. //Returns the position of the first instance of the given combo, or -1.
  1870. int FirstComboTypeOf(int t, int layer) {
  1871.     for (int i = 0; i < 176; i++) {
  1872.         if (layer == 0) {
  1873.             if (Screen->ComboT[i] == t)
  1874.             return i;
  1875.         }
  1876.         else {
  1877.             if (GetLayerComboT(layer,i) == t)
  1878.             return i;
  1879.         }
  1880.     }
  1881.     return -1;
  1882. }
  1883.  
  1884. //Returns the position of the last instance of the given combo, or -1.
  1885. int LastComboTypeOf(int t, int layer) {
  1886.     for (int i = 175; i >= 0; i--) {
  1887.         if (layer == 0) {
  1888.             if (Screen->ComboT[i] == t)
  1889.             return i;
  1890.         }
  1891.         else {
  1892.             if (GetLayerComboT(layer,i) == t)
  1893.             return i;
  1894.         }
  1895.     }
  1896.     return -1;
  1897. }
  1898.  
  1899. //Returns the position of the first instance of the given combo flag, or -1.
  1900. //Checks inherent flags too!
  1901. int FirstComboFlagOf(int t, int layer) {
  1902.     for (int i = 0; i < 176; i++) {
  1903.         if (layer == 0) {
  1904.             if (Screen->ComboF[i] == t || Screen->ComboI[i] == t) return i;
  1905.         }
  1906.         else {
  1907.             if (Game->GetComboFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer),i) == t
  1908.             || Game->GetComboInherentFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer),i) == t)
  1909.             return i;
  1910.         }
  1911.     }
  1912.     return -1;
  1913. }
  1914.  
  1915. //Returns the position of the last instance of the given combo flag, or -1.
  1916. //Checks inherent flags too!
  1917. int LastComboFlagOf(int t, int layer) {
  1918.     for (int i = 175; i >= 0; i--) {
  1919.         if (layer == 0) {
  1920.             if (Screen->ComboF[i] == t || Screen->ComboI[i] == t) return i;
  1921.         }
  1922.         else {
  1923.             if (Game->GetComboFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer),i) == t
  1924.             || Game->GetComboInherentFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer),i) == t)
  1925.             return i;
  1926.         }
  1927.     }
  1928.     return -1;
  1929. }
  1930.  
  1931. // Returns true if the combo at the given position is water.
  1932. bool IsWater(int position) {
  1933.     int combo=Screen->ComboT[position];
  1934.     if(combo==CT_WATER || combo==CT_SWIMWARP || combo==CT_DIVEWARP || (combo>=CT_SWIMWARPB && combo<=CT_DIVEWARPD))
  1935.         return true;
  1936.     else return false;
  1937. }
  1938.  
  1939. // Returns true if the combo at the given position is a pit.
  1940. bool IsPit(int position) {
  1941.     int combo=Screen->ComboT[position];
  1942.     if(combo==CT_PIT || combo==CT_PITR || (combo>=CT_PITB && combo<=CT_PITD))
  1943.         return true;
  1944.     else return false;
  1945. }
  1946.  
  1947. //Creates and returns an exact copy of the passed LWeapon. Assumes that the passed pointer is valid.
  1948. lweapon Duplicate(lweapon a) {
  1949.     lweapon b = Screen->CreateLWeapon(a->ID);
  1950.     b->X = a->X;
  1951.     b->Y = a->Y;
  1952.     b->Z = a->Z;
  1953.     b->Jump = a->Jump;
  1954.     b->Extend = a->Extend;
  1955.     b->TileWidth = a->TileWidth;
  1956.     b->TileHeight = a->TileHeight;
  1957.     b->HitWidth = a->HitWidth;
  1958.     b->HitHeight = a->HitHeight;
  1959.     b->HitZHeight = a->HitZHeight;
  1960.     b->HitXOffset = a->HitXOffset;
  1961.     b->HitYOffset = a->HitYOffset;
  1962.     b->DrawXOffset = a->DrawXOffset;
  1963.     b->DrawYOffset = a->DrawYOffset;
  1964.     b->DrawZOffset = a->DrawZOffset;
  1965.     b->Tile = a->Tile;
  1966.     b->CSet = a->CSet;
  1967.     b->DrawStyle = a->DrawStyle;
  1968.     b->Dir = a->Dir;
  1969.     b->OriginalTile = a->OriginalTile;
  1970.     b->OriginalCSet = a->OriginalCSet;
  1971.     b->FlashCSet = a->FlashCSet;
  1972.     b->NumFrames = a->NumFrames;
  1973.     b->Frame = a->Frame;
  1974.     b->ASpeed = a->ASpeed;
  1975.     b->Damage = a->Damage;
  1976.     b->Step = a->Step;
  1977.     b->Angle = a->Angle;
  1978.     b->Angular = a->Angular;
  1979.     b->CollDetection = a->CollDetection;
  1980.     b->DeadState = a->DeadState;
  1981.     b->Flash = a->Flash;
  1982.     b->Flip = a->Flip;
  1983.     for (int i = 0; i < 16; i++)
  1984.         b->Misc[i] = a->Misc[i];
  1985.     return b;
  1986. }
  1987.  
  1988. //Creates and returns an exact copy of the passed EWeapon. Assumes that the passed pointer is valid.
  1989. eweapon Duplicate(eweapon a) {
  1990.     eweapon b = Screen->CreateEWeapon(a->ID);
  1991.     b->X = a->X;
  1992.     b->Y = a->Y;
  1993.     b->Z = a->Z;
  1994.     b->Jump = a->Jump;
  1995.     b->Extend = a->Extend;
  1996.     b->TileWidth = a->TileWidth;
  1997.     b->TileHeight = a->TileHeight;
  1998.     b->HitWidth = a->HitWidth;
  1999.     b->HitHeight = a->HitHeight;
  2000.     b->HitZHeight = a->HitZHeight;
  2001.     b->HitXOffset = a->HitXOffset;
  2002.     b->HitYOffset = a->HitYOffset;
  2003.     b->DrawXOffset = a->DrawXOffset;
  2004.     b->DrawYOffset = a->DrawYOffset;
  2005.     b->DrawZOffset = a->DrawZOffset;
  2006.     b->Tile = a->Tile;
  2007.     b->CSet = a->CSet;
  2008.     b->DrawStyle = a->DrawStyle;
  2009.     b->Dir = a->Dir;
  2010.     b->OriginalTile = a->OriginalTile;
  2011.     b->OriginalCSet = a->OriginalCSet;
  2012.     b->FlashCSet = a->FlashCSet;
  2013.     b->NumFrames = a->NumFrames;
  2014.     b->Frame = a->Frame;
  2015.     b->ASpeed = a->ASpeed;
  2016.     b->Damage = a->Damage;
  2017.     b->Step = a->Step;
  2018.     b->Angle = a->Angle;
  2019.     b->Angular = a->Angular;
  2020.     b->CollDetection = a->CollDetection;
  2021.     b->DeadState = a->DeadState;
  2022.     b->Flash = a->Flash;
  2023.     b->Flip = a->Flip;
  2024.     for (int i = 0; i < 16; i++)
  2025.         b->Misc[i] = a->Misc[i];
  2026.     return b;
  2027. }
  2028.  
  2029. //This should allow any scripted object to easily mimic Link styled LOZ solidity collision
  2030. //checking, be it Link, FFCs, or enemies.
  2031. //Note - You should use full_tile=true if you don't want the upper eight pixels to overlap
  2032. //solid combos as per LOZ1 behavior.
  2033. bool CanWalk(int x, int y, int dir, int step, bool full_tile) {
  2034.     int c=8;
  2035.     int xx = x+15;
  2036.     int yy = y+15;
  2037.     if(full_tile) c=0;
  2038.     if(dir==0) return !(y-step<0||Screen->isSolid(x,y+c-step)||Screen->isSolid(x+8,y+c-step)||Screen->isSolid(xx,y+c-step));
  2039.     else if(dir==1) return !(yy+step>=176||Screen->isSolid(x,yy+step)||Screen->isSolid(x+8,yy+step)||Screen->isSolid(xx,yy+step));
  2040.     else if(dir==2) return !(x-step<0||Screen->isSolid(x-step,y+c)||Screen->isSolid(x-step,y+c+7)||Screen->isSolid(x-step,yy));
  2041.     else if(dir==3) return !(xx+step>=256||Screen->isSolid(xx+step,y+c)||Screen->isSolid(xx+step,y+c+7)||Screen->isSolid(xx+step,yy));
  2042.     return false; //invalid direction
  2043. }
  2044.  
  2045. //Returns true if Link is on a sideview screen
  2046. bool IsSideview() {
  2047.     return Screen->Flags[SF_ROOMTYPE] & 4;
  2048. }
  2049.  
  2050. //Returns true if Link is on a sideview screen
  2051. //bool IsSideviewFlag() {
  2052. //  return ScreenFlag(SF_ROOMTYPE, SFR_SIDEVIEW);
  2053. //}
  2054.  
  2055. //Returns true if Link is on a Dungeon (flagged) screen
  2056. bool IsDungeonFlag() {
  2057.     return Screen->Flags[SF_ROOMTYPE] & 1;
  2058. }
  2059.  
  2060. //Returns true if Link is on an Interior (flagged) screen
  2061. bool IsInteriorFlag() {
  2062.     return Screen->Flags[SF_ROOMTYPE] & 2;
  2063. }
  2064.  
  2065. //Returns true if Link is in a Dungeon Room
  2066. //int IsDungeon(){
  2067. //  return ScreenFlag(SF_ROOMTYPE, SFR_DUNGEON);
  2068. //}
  2069.  
  2070. //Returns true if Link is in an Interior Room
  2071. //int IsInterior(){
  2072. //  return ScreenFlag(SF_ROOMTYPE, SFR_INTERIOR);
  2073. //}
  2074.  
  2075. //Returns true if the sprite at (x,y) is standing on a sideview platform on a sideview screen, as worked out
  2076. //by ZC's internal code.
  2077. //For 16 pixel high sprites only.
  2078. bool OnSidePlatform(int x, int y) {
  2079.     return (Screen->isSolid(x+4,y+16) && Screen->isSolid(x+12,y+16) && Screen->Flags[SF_ROOMTYPE]&4);
  2080. }
  2081.  
  2082. //Returns true if a sprite of height 'h' at position (x,y) with an offset of (xOff,yOff) is standing
  2083. //on a sideview platform on a sideview screen.
  2084. bool OnSidePlatform(int x, int y, int xOff, int yOff, int h) {
  2085.     return (Screen->isSolid((x+xOff)+4,(y+yOff)+h) && Screen->isSolid((x+xOff)+12,(y+yOff)+h) && Screen->Flags[SF_ROOMTYPE]&4);
  2086. }
  2087.  
  2088. //Kills all of Link's inputs
  2089. void NoAction() {
  2090.     Link->InputUp = false; Link->PressUp = false;
  2091.     Link->InputDown = false; Link->PressDown = false;
  2092.     Link->InputLeft = false; Link->PressLeft = false;
  2093.     Link->InputRight = false; Link->PressRight = false;
  2094.     Link->InputR = false; Link->PressR = false;
  2095.     Link->InputL = false; Link->PressL = false;
  2096.     Link->InputA = false; Link->PressA = false;
  2097.     Link->InputB = false; Link->PressB = false;
  2098.     Link->InputEx1 = false; Link->PressEx1 = false;
  2099.     Link->InputEx2 = false; Link->PressEx2 = false;
  2100.     Link->InputEx3 = false; Link->PressEx3 = false;
  2101.     Link->InputEx4 = false; Link->PressEx4 = false;
  2102. }
  2103.  
  2104. //Kills all of Link's inputs
  2105. void NoAction(bool analogueStick) {
  2106.     Link->InputUp = false; Link->PressUp = false;
  2107.     Link->InputDown = false; Link->PressDown = false;
  2108.     Link->InputLeft = false; Link->PressLeft = false;
  2109.     Link->InputRight = false; Link->PressRight = false;
  2110.     Link->InputR = false; Link->PressR = false;
  2111.     Link->InputL = false; Link->PressL = false;
  2112.     Link->InputA = false; Link->PressA = false;
  2113.     Link->InputB = false; Link->PressB = false;
  2114.     Link->InputEx1 = false; Link->PressEx1 = false;
  2115.     Link->InputEx2 = false; Link->PressEx2 = false;
  2116.     Link->InputEx3 = false; Link->PressEx3 = false;
  2117.     Link->InputEx4 = false; Link->PressEx4 = false;
  2118.    
  2119.     if ( analogueStick ) {
  2120.         Link->InputAxisUp = false; Link->InputAxisRight = false;
  2121.         Link->InputAxisDown = false; Link->InputAxisLeft = false;
  2122.         Link->PressAxisUp = false; Link->PressAxisRight = false;
  2123.         Link->PressAxisDown = false; Link->PressAxisLeft = false;
  2124.     }
  2125. }
  2126.  
  2127.  
  2128. //NoAction, then Waitframe or (equivalent of) Waitframes
  2129. void WaitNoAction() {
  2130.     NoAction();
  2131.     Waitframe();
  2132. }
  2133.  
  2134. void WaitNoAction(int frames) {
  2135.     for(int i = 0; i < frames; i++)
  2136.         WaitNoAction();
  2137. }
  2138.  
  2139. //Get an NPC's name from an ID
  2140. void GetNPCName(int ID, int string) {
  2141.     npc n = Screen->CreateNPC(ID);
  2142.     n->GetName(string);
  2143.     Remove(n);
  2144. }
  2145.  
  2146. void GetMessage(int ID, int string) {
  2147.     Game->GetMessage(ID, string);
  2148.     int i;
  2149.     for(i = MAX_MESSAGELENGTH-2; string[i] == ' '; i--);
  2150.     string[i+1] = 0;
  2151. }
  2152.  
  2153. itemdata GetItemData(item i) {
  2154.     return Game->LoadItemData(i->ID);
  2155. }
  2156.  
  2157. int GetHighestLevelItem(int itemclass) {
  2158.     itemdata id;
  2159.     int ret = -1;
  2160.     int curlevel = -1000;
  2161.     //143 is default max items, increase if you add lots of your own
  2162.     for(int i = 0; i < 143; i++)
  2163.     {
  2164.         id = Game->LoadItemData(i);
  2165.         if(id->Family != itemclass)
  2166.             continue;
  2167.         if(id->Level > curlevel)
  2168.         {
  2169.             curlevel = id->Level;
  2170.             ret = i;
  2171.         }
  2172.     }
  2173.     return ret;
  2174. }
  2175.  
  2176. int GetHighestLevelItem(item i) {
  2177.     itemdata argid = GetItemData(i);
  2178.     int ret = i->ID;
  2179.     int curlevel = argid->Level;
  2180.     itemdata id;
  2181.     //143 is max items, decrease to improve speed if you need to
  2182.     for(int i = 0; i < 256; i++)
  2183.     {
  2184.         id = Game->LoadItemData(i);
  2185.         if(id->Family != argid->Family)
  2186.             continue;
  2187.         if(id->Level > curlevel)
  2188.         {
  2189.             curlevel = id->Level;
  2190.             ret = i;
  2191.         }
  2192.     }
  2193.     return ret;
  2194. }
  2195.  
  2196. // Convert between map and DMap screens
  2197. int DMapToMap(int screen, int dmap) {
  2198.     return screen+Game->DMapOffset[dmap];
  2199. }
  2200.  
  2201. int MapToDMap(int screen, int dmap) {
  2202.     return screen-Game->DMapOffset[dmap];
  2203. }
  2204.  
  2205. //Safe Sqrt functions if an irrational number would be involved.
  2206. //Returns '464' (square root of 215296), if the value passed is negative.
  2207. //Returns '0' on Sqrt(0).
  2208. float SafeSqrt(float val){
  2209.    
  2210.     if ( STD_NEVER_USE_SAFESQRT ) return Sqrt(val);
  2211.     else {
  2212.         //if ( val > 214748.3648 ) val = 214748.3648;
  2213.         if ( val > 0 && val <= 214747.9999 ) return Sqrt(val);
  2214.         //Return a predesignated square root, instead of performing a Sqrt(MAX_INT) would be more optimised.
  2215.         if ( val < 0 ) return 464;  //! This is the smallest integer square root value possible
  2216.                         //! that is greater than the square root of MAX_INT.
  2217.                         //! and would help identify errors.
  2218.         //if ( val < 0 ) return 463.4095; //The square root of 214798.3648
  2219.         //! We could also returm 363 here, which is the smallest square root over MAX_INT.
  2220.         //Returns the square root of MAX_INT if the value passed is a negative number.
  2221.         //if ( val < 0 ) return Sqrt(214747.9999);
  2222.         return 0;
  2223.     }
  2224. }
  2225.  
  2226.  
  2227.  
  2228. //Returns square root of 'val'. Returns 'specifyNegRet' if a negative value is passed as 'val'. Returns '0' for Sqrt(0).
  2229. float SafeSqrt(float val, float specifyNegRet){
  2230.     if ( val > 214747.9999 ) val = 214747.9999;
  2231.     if ( val > 0 && val <= 214747.9999 ) return Sqrt(val);
  2232.     if ( val < 0 ) return specifyNegRet;
  2233.     return 0;
  2234. }
  2235.  
  2236. //Fairly select between true or false.
  2237. int ChooseB(){
  2238.     return Rand(0,1);
  2239. }
  2240.  
  2241. // Chooses one of the boolean options randomly and fairly.
  2242. bool ChooseB(bool a, bool b) {
  2243.     if (Rand(0,1)==0) return a;
  2244.     else return b;
  2245. }
  2246.  
  2247. bool ChooseB(bool a, bool b, bool c) {
  2248.     int r = Rand(0,2);
  2249.     if (r==0) return a;
  2250.     else if (r==1) return b;
  2251.     else return c;
  2252. }
  2253.  
  2254. bool ChooseB(bool a, bool b, bool c, bool d) {
  2255.     int r = Rand(0,3);
  2256.     if (r==0) return a;
  2257.     else if (r==1) return b;
  2258.     else if (r==2) return c;
  2259.     else return d;
  2260. }
  2261.  
  2262. bool ChooseB(bool a, bool b, bool c, bool d, bool e) {
  2263.     int r = Rand(0,4);
  2264.     if (r==0) return a;
  2265.     else if (r==1) return b;
  2266.     else if (r==2) return c;
  2267.     else if (r==3) return d;
  2268.     else return e;
  2269. }
  2270.  
  2271. bool ChooseB(bool a, bool b, bool c, bool d, bool e, bool f) {
  2272.     int r = Rand(0,5);
  2273.     if (r==0) return a;
  2274.     else if (r==1) return b;
  2275.     else if (r==2) return c;
  2276.     else if (r==3) return d;
  2277.     else if (r==4) return e;
  2278.     else return f;
  2279. }
  2280.  
  2281.  
  2282. //Trace the indices of an array, with a space between each. max 20 per line.
  2283. //NOT overloaded to accept all array types. Trace() does nto work on ffc, item, itemdata, lweapon, or eweapon!
  2284. //Mayne next version.
  2285. void TraceArray(int arr){
  2286.     TraceNL();
  2287.     int _spc[2]=" ";
  2288.     for ( int q = 0; q < SizeOfArray(arr); q++ ) {
  2289.         Trace(arr[q]); TraceS(_spc);
  2290.         if ( q % 10 == 0 ) TraceNL();
  2291.     }
  2292. }
  2293.  
  2294. //Trace the indices of a Boolean array, with a space between each. max 20 per line.
  2295. void TraceArrayB(bool arr, int size){
  2296.     TraceNL();
  2297.     int _spc[2]=" ";
  2298.     for ( int q = 0; q < size; q++ ) {
  2299.         TraceB(arr[q]); TraceS(_spc);
  2300.         if ( q % 10 == 0 ) TraceNL();
  2301.     }
  2302. }
  2303.  
  2304. void TraceArray(int arr, bool verbose){
  2305.     if ( verbose )  {
  2306.         int str[]="Tracing array with Pointer: ";
  2307.         TraceNL(); TraceS(str); Trace(arr); TraceNL();
  2308.  
  2309.         for ( int q = 0; q < SizeOfArray(arr); q++ ) {
  2310.             int str2[]="Index: ";
  2311.             int str3[]="is : ";
  2312.             TraceS(str2); Trace(q); TraceS(str3); Trace(arr[q]);
  2313.             TraceNL();
  2314.         }
  2315.     }
  2316.     else {
  2317.         TraceNL();
  2318.         int _spc[2]=" ";
  2319.         for ( int q = 0; q < SizeOfArray(arr); q++ ) {
  2320.             Trace(arr[q]); TraceS(_spc);
  2321.             if ( q % 10 == 0 ) TraceNL();
  2322.         }
  2323.     }
  2324. }
  2325.  
  2326. //Trace the indices of a Boolean array, allows verbose logging.
  2327. void TraceArrayB(bool arr, int size, bool verbose){
  2328.     if ( verbose ) {
  2329.         //ZScript has no facility to read a pointer ID of an array with a type of bool, ffc, item, *weapon, or itemdata.
  2330.         //int str[]="Tracing array with Pointer: ";
  2331.         int str[]="Tracing Boolean Array: ";
  2332.         TraceNL(); TraceS(str); TraceNL();
  2333.        
  2334.         int _spc[2]=" ";
  2335.         for ( int q = 0; q < size; q++ ) {
  2336.             int str2[]="Index: ";
  2337.             int str3[]="is : ";
  2338.             TraceS(str2); Trace(q); TraceS(str3); TraceB(arr[q]); TraceS(_spc);
  2339.             TraceNL();
  2340.         }
  2341.     }
  2342.     else {
  2343.         TraceNL();
  2344.         int _spc[2]=" ";
  2345.         for ( int q = 0; q < size; q++ ) {
  2346.             TraceB(arr[q]); TraceS(_spc);
  2347.             if ( q % 10 == 0 ) TraceNL();
  2348.         }  
  2349.     }
  2350. }
  2351.  
  2352. //This doesn't work, as ZScript reads an invalid index as false, rather than not being able to read it. :(
  2353. //int SizeOfArrayB(bool arr){
  2354. //  int pass;
  2355. //  for ( int q = 0; q < 214747; q++ ) {
  2356. //      int val = -1;
  2357. //      if ( arr[q] == true ) val = 1;
  2358. //      if ( arr[q] == false ) val = 0;
  2359. //      if ( arr[q] != true && arr[q] != false ) return pass;
  2360. //      pass++;
  2361. //  }
  2362. //}
  2363.        
  2364.  
  2365. //void TraceArray(float arr){
  2366. //  TraceNL();
  2367. //  int _spc[2]=" ";
  2368. //  for ( int q = 0; q < SizeOfArray(arr); q++ ) {
  2369. //      Trace(arr[q]); TraceS(_spc);
  2370. //      if ( q % 10 == 0 ) TraceNL();
  2371. //  }
  2372. //}
  2373.  
  2374. //void TraceArray(lweapon arr, int size){
  2375. //  TraceNL();
  2376. //  int _spc[2]=" ";
  2377. //  for ( int q = 0; q < size; q++ ) {
  2378. //      int id = arr[q];
  2379. //      Trace(id); TraceS(_spc);
  2380. //      if ( q % 10 == 0 ) TraceNL();
  2381. //  }
  2382. //}
  2383.  
  2384. //void TraceArray(eweapon arr, int size){
  2385. //  TraceNL();
  2386. //  int _spc[2]=" ";
  2387. //  for ( int q = 0; q < size; q++ ) {
  2388. //      Trace(arr[q]); TraceS(_spc);
  2389. //      if ( q % 10 == 0 ) TraceNL();
  2390. //  }
  2391. //}
  2392.  
  2393. //void TraceArray(npc arr, int size){
  2394. //  TraceNL();
  2395. //  int _spc[2]=" ";
  2396. //  for ( int q = 0; q < size; q++ ) {
  2397. //      Trace(arr[q]); TraceS(_spc);
  2398. //      if ( q % 10 == 0 ) TraceNL();
  2399. //  }
  2400. //}
  2401.  
  2402. //void TraceArray(ffc arr, int size){
  2403. /// TraceNL();
  2404. //  int _spc[2]=" ";
  2405. //  for ( int q = 0; q < size; q++ ) {
  2406. //      Trace(arr[q]); TraceS(_spc);
  2407. //      if ( q % 10 == 0 ) TraceNL();
  2408. //  }
  2409. //}
  2410.  
  2411. //void TraceArray(item arr, int size){
  2412. //  TraceNL();
  2413. //  int _spc[2]=" ";
  2414. //  for ( int q = 0; q < size; q++ ) {
  2415. //      Trace(arr[q]); TraceS(_spc);
  2416. //      if ( q % 10 == 0 ) TraceNL();
  2417. //  }
  2418. //}
  2419.  
  2420. //void TraceArray(itemdata arr, int size){
  2421. //  TraceNL();
  2422. //  int _spc[2]=" ";
  2423. //  for ( int q = 0; q < size; q++ ) {
  2424. //      Trace(arr[q]); TraceS(_spc);
  2425. //      if ( q % 10 == 0 ) TraceNL();
  2426. //  }
  2427. //}
  2428.  
  2429.  
  2430. //Trace each index of an array, and print strings to make them legible.
  2431. //void TraceArray(int arr){
  2432. //  int str[]="Tracing array with Pointer: ";
  2433. //  int bufferPointer[7]=" ";
  2434. //  itoa(arr,bufferPointer);
  2435. //  int mainBuffer[40]=" ";
  2436. //  strcat(str,mainBuffer);
  2437. //  strcat(bufferPointer,mainBuffer);
  2438. //  TraceNL();
  2439. //  TraceS(mainBuffer);
  2440. //  TraceNL();
  2441.  
  2442. //  for ( int q = 0; q <= SizeOfArray(arr); q++ ) {
  2443. //      int str2[]="Index: ";
  2444. //      int str3[]="is : ";
  2445. //      int buffer[22]=" ";
  2446. //      int bufferAmt[7]=" ";
  2447. //      int bufferIndex[7]=" ";
  2448. //      itoa(arr[q],bufferAmt);
  2449. //      itoa(q,bufferIndex);
  2450. //      strcat(str2,buffer);
  2451. //      strcat(bufferIndex,buffer);
  2452. //      strcat(str3,buffer);
  2453. //      strcat(bufferAmt,buffer);
  2454. //      TraceS(buffer);
  2455. //      TraceNL();
  2456. //  }
  2457. //}
  2458.  
  2459. //Shorthand for TraceArray()
  2460. void TraceA(bool arr,int size){TraceArrayB(arr,size);}
  2461. void TraceA(float arr){TraceArray(arr);}
  2462. //void TraceA(npc arr,int size){TraceArray(arr,size);}
  2463. //void TraceA(ffc arr,int size){TraceArray(arr,size);}
  2464. //void TraceA(lweapon arr,int size){TraceArray(arr,size);}
  2465. //void TraceA(eweapon arr,int size){TraceArray(arr,size);}
  2466. //void TraceA(item arr,int size){TraceArray(arr,size);}
  2467. //void TraceA(itemdata arr,int size){TraceArray(arr,size);}
  2468.  
  2469. //Safely sets an equipment item, without lagging ZC.
  2470. //Sets an item 'itm' true if it is false, and false if it is true.
  2471. void SetLinkItem(int itm){
  2472.     if ( !Link->Item[itm] ) Link->Item[itm] = true;
  2473.     else if ( Link->Item[itm] ) Link->Item[itm] = false;
  2474. }
  2475.  
  2476. //Sets an item 'itm' to the boolean value of 'state'.
  2477. void SetLinkItem(int itm, bool state){
  2478.     if ( !Link->Item[itm] && state ) Link->Item[itm] = true;
  2479.     else if ( Link->Item[itm] && !state ) Link->Item[itm] = false;
  2480. }
  2481.  
  2482. //Randomly returns true, or false.
  2483. bool RandB(){
  2484.     int a = Rand(0,1);
  2485.     if ( a == 0 ) return false;
  2486.     else return true;
  2487. }
  2488.  
  2489.  
  2490. //Randomly returns true, or false, using input percentTrue to determine the percentage change of a 'true return'
  2491. bool RandB(int percentTrue){
  2492.     int a = Rand(1,100);
  2493.     if ( a <= percentTrue ) return true;
  2494.     else return false;
  2495. }
  2496.  
  2497.  
  2498. //Terminate an FFC, and set all its properties to 0.
  2499. void EndFFC(int ffc_id){
  2500.     ffc f = Screen->LoadFFC(ffc_id);
  2501.     f->Data = 0;
  2502.     f->Script = 0;
  2503.     f->CSet = 0;
  2504.     f->Delay = 0;
  2505.     f->X = 0;
  2506.     f->Y = 0;
  2507.     f->Vx = 0;
  2508.     f->Vy = 0;
  2509.     f->Ax = 0;
  2510.     f->Ay = 0;
  2511.     for ( int q = 0; q < 10; q++ ) f->Flags[q] = 0;
  2512.     f->TileWidth = 0;
  2513.     f->TileHeight = 0;
  2514.     f->EffectWidth = 0;
  2515.     f->EffectHeight = 0;
  2516.     f->Link = 0;
  2517.     for ( int q = 0; q < 15; q++ ) f->Misc[q] = 0;
  2518.     //Quit(); If this is called from a global script, it would be bad.
  2519. }
  2520.  
  2521. //Negates engine knockback for Link on land, or in water.
  2522. void NoLinkKnockback(){
  2523.     if ( Link->Action == LA_GOTHURTLAND || Link->Action == LA_GOTHURTWATER ) Link->HitDir = -1;
  2524. }
  2525.  
  2526. //Negates engine knockback for Link only on land.
  2527. void NoLinkKnockbackLand(){
  2528.     if ( Link->Action == LA_GOTHURTLAND ) Link->HitDir = -1;
  2529. }
  2530.  
  2531. //Negates engine knockback for Link only in water.
  2532. void NoLinkKnockbackWater(){
  2533.     if ( Link->Action == LA_GOTHURTWATER ) Link->HitDir = -1;
  2534. }
  2535.  
  2536.  
  2537.  
  2538. //Draws a screen specified by 'sourceMap and sourceScreen;, from layers specified by 'layerMin and layerMax',
  2539. //at a desired opacity, to the layer specified by 'destLayer' of the current screen.
  2540. void ScreenToLayer(int sourceMap, int sourceScreen, int layerMin, int layerMax, int drawOpacity, int destLayer){
  2541.     for (int i = layerMin; i < layerMax; i++){
  2542.         Screen->DrawLayer(destLayer, sourceMap, sourceScreen, i, 0, 0, 0, drawOpacity);
  2543.     }
  2544. }
  2545.  
  2546. //Draws all layers of a screen specified by 'sourceMap and sourceScreen;,
  2547. //at a desired opacity, to the layer specified by 'destLayer' of the current screen.
  2548. void ScreenToLayer(int sourceMap, int sourceScreen, int drawOpacity, int destLayer){
  2549.     for (int i = 0; i < 6; i++){
  2550.         Screen->DrawLayer(destLayer, sourceMap, sourceScreen, i, 0, 0, 0, drawOpacity);
  2551.     }
  2552. }
  2553.  
  2554. //Takes a float as input 'n', and returns the integer portion as int.
  2555. int GetHighFloat(int n) {
  2556.     return n >> 0;
  2557. }
  2558.  
  2559. //Takes a float as input 'n', and returns the decimal portion as int.
  2560. int GetLowFloat(int n) {
  2561.     return (n - (n >> 0)) * 10000;
  2562. }
  2563.  
  2564. //Converts floating point value 'v', after the decimal, to an integer.
  2565. int DecimalToInt(int v) {
  2566.     int r = (v - (v << 0)) * 10000;
  2567.     return r;
  2568. }
  2569.  
  2570. //Truncates decimals off floating point value 'v'.
  2571. int Truncate(int v) {
  2572.     int r = (v - (v << 0)) * 10000;
  2573.     return r;
  2574. }
  2575.  
  2576.  
  2577. //Extracts a single digit from n at the place specified.
  2578. //-4 is the ten-thousandTHs place, 0 is the ones spot, and 4 is the ten-thousanDs spot.
  2579. int GetDigitValue(int n, int place){
  2580.     place = Clamp(place, -4, 4);
  2581.     if( place < 0 ){
  2582.         n = DecimalToInt(n);
  2583.         place += 4;
  2584.     }
  2585.  
  2586.     int r = ((n / Pow(10, place)) % 10) << 0;
  2587.     return r;
  2588. }
  2589.  
  2590. //Extracts an integer using specific places of any value 'n', from position 'place' plus a number of places 'num'.
  2591. int GetPartialValue(int n, int place, int num){
  2592.     place = Clamp(place, -4, 4);
  2593.     int r;
  2594.     int adj = 1;
  2595.     for(int i = num-1; i > -1; i--){
  2596.         if(place - i < -4) continue;
  2597.         r += GetDigitValue(n, place - i) * adj;
  2598.         adj *= 10;
  2599.     }
  2600.     return r;
  2601. }
  2602.  
  2603. //Xor comparison of two boolean values.
  2604. bool Xor(bool valA, bool valB){
  2605.     if ( !valA && valB ) return true;
  2606.     else if ( valA && !valB ) return true;
  2607.     return false;
  2608. }
  2609.  
  2610. //Collision functions, to avoid errors when using Collision() where LinkCOllision() is needed.
  2611.  
  2612. bool Collision(ffc f) {
  2613.     return LinkCollision(f);
  2614. }
  2615.  
  2616. bool Collision(npc n){
  2617.     return LinkCollision(n);
  2618. }
  2619.  
  2620. bool Collision(lweapon l){
  2621.     return LinkCollision(l);
  2622. }
  2623.  
  2624. bool Collision(eweapon e){
  2625.     return LinkCollision(e);
  2626. }
  2627.  
  2628. bool Collision(item i){
  2629.     return LinkCollision(i);
  2630. }
  2631.  
  2632. //Returns a multiplication factor for ->Step based on direction.
  2633. // Specifically, return the x component of a line with a length of 1 extending
  2634. // in the given direction from origin.
  2635. //Step = step * DirX(dir);
  2636. //Valid only if dir is 0 to 7.
  2637.  
  2638. int DirX(int dir) {
  2639.     // Is a diagonal.
  2640.     if (dir & 100b) return Cond(dir & 001b, Sin(45), Sin(45)*-1);
  2641.     // Is horizontal.
  2642.     if (dir & 010b) return Cond(dir & 001b, 1, -1);
  2643.     return 0;
  2644. }
  2645.  
  2646. //Returns a multiplication factor for ->Step based on direction.
  2647. //Step = step * DirY(dir);
  2648. //Valid only if dir is 0 to 7.
  2649. // Specifically, return the y component of a line with a length of 1 extending
  2650. // in the given direction from origin.
  2651. int DirY(int dir) {
  2652.     // Is a diagonal.
  2653.     if (dir & 100b) return Cond(dir & 010b, Sin(45), Sin(45)*-1);
  2654.     // Is vertical.
  2655.     if (!(dir & 010b)) return Cond(dir & 001b, 1, -1);
  2656.     return 0;
  2657. }
  2658.  
  2659. //Matching - Comparison Functions: use an array (list) of values, and compare against a pointer, or pointer variable.
  2660.  
  2661. //Match a given lweapon to the contents of an array 'list'
  2662. //Returns true of any of the entries on the list match.
  2663. bool MatchLWeaponType(int list, lweapon l){
  2664.     bool match = false;
  2665.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2666.         if ( l->ID == list[q] ) match = true;
  2667.     }
  2668.     return match;
  2669. }
  2670.  
  2671. //Match a given eweapon to the contents of an array 'list'
  2672. //Returns true of any of the entries on the list match.
  2673. bool MatchEWeaponType(int list, eweapon e){
  2674.     bool match = false;
  2675.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2676.         if ( e->ID == list[q] ) match = true;
  2677.     }
  2678.     return match;
  2679. }
  2680.  
  2681. //Match a given npc ID number to the contents of an array 'list'
  2682. //Returns true of any of the entries on the list match.
  2683. bool MatchNPC(int list, npc n){
  2684.     bool match = false;
  2685.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2686.         if ( n->ID == list[q] ) match = true;
  2687.     }
  2688.     return match;
  2689. }
  2690.  
  2691. //Match a given NPC TYPE to the contents of an array 'list'
  2692. //Returns true of any of the entries on the list match.
  2693. bool MatchNPCT(int list, npc n){
  2694.     bool match = false;
  2695.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2696.         if ( n->Type == list[q] ) match = true;
  2697.     }
  2698.     return match;
  2699. }
  2700.  
  2701. //Match a given item ID number to the contents of an array 'list'
  2702. //Returns true of any of the entries on the list match.
  2703. bool MatchItem(int list, item i){
  2704.     bool match = false;
  2705.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2706.         if ( i->ID == list[q] ) match = true;
  2707.     }
  2708.     return match;
  2709. }
  2710.  
  2711. //Match the present Link->Action to those on array 'list'.
  2712. //Returns true of any of the entries on the list match.
  2713. //Checks if the present Link->Action is one from a predefined list.
  2714. bool MatchAction(int list){
  2715.     bool match = false;
  2716.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2717.         if ( Link->Action == list[q] ) match = true;
  2718.     }
  2719.     return match;
  2720. }
  2721.  
  2722. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2723. //Returns true of any of the entries on the list match its Data.
  2724. bool MatchComboD(int list, int cmb){
  2725.     bool match = false;
  2726.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2727.         if ( Screen->ComboD[cmb] == list[q] ) match = true;
  2728.     }
  2729.     return match;
  2730. }
  2731.  
  2732. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2733. //Returns true of any of the entries on the list match its Type.
  2734. bool MatchComboT(int list, int cmb){
  2735.     bool match = false;
  2736.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2737.         if ( Screen->ComboT[cmb] == list[q] ) match = true;
  2738.     }
  2739.     return match;
  2740. }
  2741.  
  2742. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2743. //Returns true of any of the entries on the list match its CSet.
  2744. bool MatchComboC(int list, int cmb){
  2745.     bool match = false;
  2746.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2747.         if ( Screen->ComboC[cmb] == list[q] ) match = true;
  2748.     }
  2749.     return match;
  2750. }
  2751.  
  2752. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2753. //Returns true of any of the entries on the list match its Flag.
  2754. bool MatchComboF(int list, int cmb){
  2755.     bool match = false;
  2756.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2757.         if ( Screen->ComboF[cmb] == list[q] ) match = true;
  2758.     }
  2759.     return match;
  2760. }
  2761.  
  2762. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2763. //Returns true of any of the entries on the list match its Inherent Flag.
  2764. bool MatchComboI(int list, int cmb){
  2765.     bool match = false;
  2766.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2767.         if ( Screen->ComboI[cmb] == list[q] ) match = true;
  2768.     }
  2769.     return match;
  2770. }
  2771.  
  2772. //Compares combo 'cmb' and compares it to the values in array 'list'.
  2773. //Returns true of any of the entries on the list match its Solidity.
  2774. bool MatchComboS(int list, int cmb){
  2775.     bool match = false;
  2776.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2777.         if ( Screen->ComboS[cmb] == list[q] ) match = true;
  2778.     }
  2779.     return match;
  2780. }
  2781.  
  2782. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2783. //Returns true of any of the entries on the list match its Data.
  2784. bool MatchLayerComboD(int list, int layer, int cmb){
  2785.     bool match = false;
  2786.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2787.         if ( GetLayerComboD(layer,cmb) == list[q] ) match = true;
  2788.     }
  2789.     return match;
  2790. }
  2791.  
  2792. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2793. //Returns true of any of the entries on the list match its Type.
  2794. bool MatchLayerComboT(int list, int layer, int cmb){
  2795.     bool match = false;
  2796.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2797.         if ( GetLayerComboT(layer,cmb) == list[q] ) match = true;
  2798.     }
  2799.     return match;
  2800. }
  2801.  
  2802. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2803. //Returns true of any of the entries on the list match its CSet.
  2804. bool MatchLayerComboC(int list, int layer, int cmb){
  2805.     bool match = false;
  2806.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2807.         if ( GetLayerComboC(layer,cmb) == list[q] ) match = true;
  2808.     }
  2809.     return match;
  2810. }
  2811.  
  2812. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2813. //Returns true of any of the entries on the list match its Flag.
  2814. bool MatchLayerComboF(int list, int layer, int cmb){
  2815.     bool match = false;
  2816.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2817.         if ( GetLayerComboF(layer,cmb) == list[q] ) match = true;
  2818.     }
  2819.     return match;
  2820. }
  2821.  
  2822. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2823. //Returns true of any of the entries on the list match its Inherent Flag.
  2824. bool MatchLayerComboI(int list, int layer, int cmb){
  2825.     bool match = false;
  2826.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2827.         if ( GetLayerComboI(layer,cmb) == list[q] ) match = true;
  2828.     }
  2829.     return match;
  2830. }
  2831.  
  2832. //Compares combo 'cmb' on Layer 'layer' and compares it to the values in array 'list'.
  2833. //Returns true of any of the entries on the list match its Solidity.
  2834. bool MatchLayerComboS(int list, int layer, int cmb){
  2835.     bool match = false;
  2836.     for ( int q = 0; q < SizeOfArray(list); q++ ) {
  2837.         if ( GetLayerComboS(layer,cmb) == list[q] ) match = true;
  2838.     }
  2839.     return match;
  2840. }
  2841.  
  2842. //Matches a running ffc script to script_id. Returns true if they match.
  2843. int MatchScript(int script_id){
  2844.     for ( int q = 1; q < 32; q++ ) {
  2845.         ffc MatchScript = Screen->LoadFFC(q);
  2846.         if ( MatchScript->Script == script_id ) return q;
  2847.     }
  2848.     return 0;
  2849. }
  2850.  
  2851. //Compares the scripts of all running ffcs, to all indices of an array 'list' searching for
  2852. //a match to ffc script 'script_id'.
  2853. //If there is a match, it MatchScript() will return the first match (FFC number) found.
  2854. int MatchScript(int script_id, int list){
  2855.     bool match;
  2856.     for ( int q = 1; q < 32; q++ ) {
  2857.         ffc MatchScript = Screen->LoadFFC(q);
  2858.         for ( int w = 0; w < SizeOfArray(list); w++ ) {
  2859.             if ( MatchScript->Script == script_id ) return q;
  2860.         }
  2861.     }
  2862.     return 0;
  2863. }
  2864.  
  2865.  
  2866. //Returns if Link has the Triforce piece for a given level.
  2867. int HasTriforce(int level){
  2868.         if(Game->LItems[level]&LI_TRIFORCE) return 1;
  2869.     return 0;
  2870. }
  2871.  
  2872. //Returns if Link has the compass for a given level.
  2873. int HasCompass(int level){
  2874.         if(Game->LItems[level]&LI_COMPASS) return 1;
  2875.     return 0;
  2876. }
  2877.  
  2878. //Returns if Link has the map for a given level.
  2879. int HasMap(int level){
  2880.         if(Game->LItems[level]&LI_MAP) return 1;
  2881.     return 0;
  2882. }
  2883.  
  2884. //Returns if Link has the map for a given level.
  2885. int HasBossKey(int level){
  2886.         if(Game->LItems[level]&LI_BOSSKEY) return 1;
  2887.     return 0;
  2888. }
  2889.  
  2890. //Returns if Link has defeated the dungeon boss for a given level.
  2891. int DefeatedLevelBoss(int level){
  2892.         if(Game->LItems[level]&LI_BOSS) return 1;
  2893.     return 0;
  2894. }
  2895.  
  2896. //Returns the item ID for the current screen, if there is one.
  2897. int ScreenItem(){
  2898.     if ( Screen->RoomType == RT_SPECIALITEM ) return Screen->RoomData;
  2899.     return -1;
  2900. }
  2901.  
  2902. //Returns the number of Level Keys Link currently has for a specific level
  2903. //int NumTriforcePieces(int level){
  2904.   //  int ret = 0;
  2905.     //for(int i=1;i<=8;i++)
  2906.       //  if(Game->LItems[level]&LI_TRIFORCE) ret++;
  2907.     //return ret;
  2908. //}
  2909.  
  2910. //Returns the number of Triforce Pieces Link currently has.
  2911. //Specify the highest level in your game with arg 'maxlevel'.
  2912. int NumTriforcePieces(int maxlevel){
  2913.     int ret = 0;
  2914.     for(int i=1;i<=maxlevel;i++)
  2915.         if(Game->LItems[i]&LI_TRIFORCE) ret++;
  2916.     return ret;
  2917. }
  2918.  
  2919. //Sets the values for combo at position 'pos' to those specified. Pass -1 to leave a value unchanged.
  2920. void SetCombo(int pos, int data, int type, int flag, int inh_flag, int cset, int solid){
  2921.     if ( data >=0 ) Screen->ComboD[pos] = data;
  2922.     if ( type >= 0 ) Screen->ComboT[pos] = type;
  2923.     if ( flag >= 0 ) Screen->ComboF[pos] = flag;
  2924.     if ( inh_flag >= 0 ) Screen->ComboI[pos] = inh_flag;
  2925.     if ( cset >= 0 ) Screen->ComboC[pos] = cset;
  2926.     if ( solid >= 0 ) Screen->ComboS[pos] = solid;
  2927. }
  2928.  
  2929. //Sets the values for a combo on layer 'layer', at position 'pos' to the values specified.
  2930. //Pass -1 to any value to leave it unchanged.
  2931. void SetLayerComboValues(int layer, int pos, int data, int type, int flag, int inh_flag, int cset, int solid){
  2932.     if ( data >=0 ) SetLayerComboD(layer,pos,data);
  2933.     if ( type >= 0 ) SetLayerComboT(layer,pos,type);
  2934.     if ( flag >= 0 ) SetLayerComboF(layer,pos,flag);
  2935.     if ( inh_flag >= 0 ) SetLayerComboI(layer,pos,inh_flag);
  2936.     if ( cset >= 0 ) SetLayerComboC(layer,pos,cset);
  2937.     if ( solid >= 0 ) SetLayerComboS(layer,pos,solid);
  2938. }
  2939.  
  2940. //Clones combo from position 'pos_a' to position 'pos_b'
  2941. void CloneCombo(int pos_a, int pos_b){
  2942.     Screen->ComboD[pos_b] = Screen->ComboD[pos_a];
  2943.     Screen->ComboT[pos_b] = Screen->ComboT[pos_a];
  2944.     Screen->ComboF[pos_b] = Screen->ComboF[pos_a];
  2945.     Screen->ComboI[pos_b] = Screen->ComboI[pos_a];
  2946.     Screen->ComboC[pos_b] = Screen->ComboC[pos_a];
  2947.     Screen->ComboS[pos_b] = Screen->ComboS[pos_a];
  2948. }
  2949.  
  2950. //Clones combo on layer 'layer' posigtion 'pos_a' to the same layer at position 'pos_b'
  2951. void CloneLayerCombo(int layer, int pos_a, int pos_b){
  2952.     SetLayerComboD(layer,pos_b,GetLayerComboD(layer,pos_a));
  2953.     SetLayerComboT(layer,pos_b,GetLayerComboT(layer,pos_a));
  2954.     SetLayerComboF(layer,pos_b,GetLayerComboF(layer,pos_a));
  2955.     SetLayerComboI(layer,pos_b,GetLayerComboI(layer,pos_a));
  2956.     SetLayerComboC(layer,pos_b,GetLayerComboC(layer,pos_a));
  2957.     SetLayerComboS(layer,pos_b,GetLayerComboS(layer,pos_a));
  2958. }
  2959.  
  2960. //Clones a combo on layer 'layer_a' at position 'pos_a', to layer 'layer_b" at position 'pos_b'.
  2961. void CloneLayerCombo(int layer_a, int layer_b, int pos_a, int pos_b){
  2962.     SetLayerComboD(layer_b,pos_b,GetLayerComboD(layer_a,pos_a));
  2963.     SetLayerComboT(layer_b,pos_b,GetLayerComboT(layer_a,pos_a));
  2964.     SetLayerComboF(layer_b,pos_b,GetLayerComboF(layer_a,pos_a));
  2965.     SetLayerComboI(layer_b,pos_b,GetLayerComboI(layer_a,pos_a));
  2966.     SetLayerComboC(layer_b,pos_b,GetLayerComboC(layer_a,pos_a));
  2967.     SetLayerComboS(layer_b,pos_b,GetLayerComboS(layer_a,pos_a));
  2968. }
  2969.    
  2970.  
  2971. ///// 2016
  2972.  
  2973. //int DirRev(int dir) {
  2974. //  int bypassshields = 0;
  2975. //  if ( dir > 7 ) {
  2976. //      bypassshields = 8;
  2977. //      dir = dir - 8;
  2978. //  }
  2979. //  if ( dir == DIR_LEFT) return DIR_RIGHT + bypassshields;
  2980. //  if ( dir == DIR_DOWN) return DIR_UP + bypassshields;
  2981. //  if ( dir == DIR_UP) return DIR_DOWN + bypassshields;
  2982. //  if ( dir == DIR_RIGHT) return DIR_LEFT + bypassshields;
  2983. //  if ( dir == DIR_LEFTUP) return DIR_RIGHTDOWN + bypassshields;
  2984. //  if ( dir == DIR_RIGHTDOWN) return DIR_LEFTUP + bypassshields;
  2985. //  if ( dir == DIR_LEFTDOWN) return DIR_RIGHTUP + bypassshields;
  2986. //  if ( dir == DIR_RIGHTUP) return DIR_LEFTDOWN + bypassshields;
  2987. //}
  2988.    
  2989.  
  2990. int DirRev(int dir) {
  2991.     if ( dir == DIR_LEFT) return DIR_RIGHT;
  2992.     if ( dir == DIR_DOWN) return DIR_UP;
  2993.     if ( dir == DIR_UP) return DIR_DOWN;
  2994.     if ( dir == DIR_RIGHT) return DIR_LEFT;
  2995.     if ( dir == DIR_LEFTUP) return DIR_RIGHTDOWN;
  2996.     if ( dir == DIR_RIGHTDOWN) return DIR_LEFTUP;
  2997.     if ( dir == DIR_LEFTDOWN) return DIR_RIGHTUP;
  2998.     if ( dir == DIR_RIGHTUP) return DIR_LEFTDOWN;
  2999. }
  3000.    
  3001.  
  3002. int SpeedRev(int speed, int reduceinertia){
  3003.     if ( speed > 0 ) speed = ((speed * -1) + reduceinertia);
  3004.     if ( speed < 0 ) speed = ((speed * -1) - reduceinertia);
  3005.     return speed;
  3006. }
  3007.  
  3008. //Accepts the mass, and velocity if two objects. Determins the acceleration on impact.
  3009. //Returns the net change that would affect both objects.
  3010. int ImpactVelocity(int mass1, int velocity1, int mass2, int velociy2 ) { //, int time){ //time is sed here, as the amount of time that both objects are in contact.
  3011.     int momentum1 = mass1*velocity1; //mv1
  3012.     int momentum2 = mass2*velociy2; //mv2
  3013.     //int accel1;
  3014.     //int accel2;
  3015.     return momentum1 - momentum2;
  3016. }
  3017.  
  3018. //Accepts the mass, and velocity if two objects. Determins the acceleration on impact.
  3019. //Returns the change of acceleration for object 'B'.
  3020. int ImpactVelocityA(int massA, int velocityA, int massB, int velociyB ) { //, int time){ //time is sed here, as the amount of time that both objects are in contact.
  3021.     int momentumA = massA*velocityA; //mv1
  3022.     int momentumB = massB*velociyB; //mv2
  3023.     return momentumA - momentumB;
  3024. }
  3025.  
  3026. //Accepts the mass, and velocity if two objects. Determins the acceleration on impact.
  3027. //Returns the change of acceleration for object 'B'.
  3028. int ImpactVelocityB(int massA, int velocityA, int massB, int velociyB ) { //, int time){ //time is sed here, as the amount of time that both objects are in contact.
  3029.     int momentumA = massA*velocityA; //mv1
  3030.     int momentumB = massB*velociyB; //mv2
  3031.     return momentumB - momentumA;
  3032. }
  3033.  
  3034. //Accepts the mass, and velocity if two weapons. Determins the acceleration on impact.
  3035. //Changes the Step of both to reflect their mass on collision.
  3036. void ImpactVelocity(lweapon a, eweapon b, int massA, int velocityA, int massB, int velociyB ) { //, int time){ //time is sed here, as the amount of time that both objects are in contact.
  3037.     int momentumA = massA*velocityA; //mv1
  3038.     int momentumB = massB*velociyB; //mv2
  3039.     int accelA = momentumA - momentumB;
  3040.     int accelB = momentumB - momentumA;
  3041.     a->Step += accelA;
  3042.     b->Step += accelB;
  3043. }
  3044.  
  3045. void ImpactVelocityF(){} //FFC version that will change the direction, and speed of moving ffcs on collision.
  3046.  
  3047. //Returns centre of lweapon, with option to use either its actual coordinates, or those of its sprite.
  3048. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3049. int CenterX(lweapon anLWeapon, bool usehitbox) {
  3050.     if ( usehitbox ) return anLWeapon->X+anLWeapon->HitWidth/2 + anLWeapon->HitXOffset;
  3051.     else return anLWeapon->X+8*anLWeapon->TileWidth + anLWeapon->DrawXOffset;
  3052. }
  3053.  
  3054. //Returns centre of lweapon, with option to use either its actual coordinates, or those of its sprite.
  3055. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3056. int CenterY(lweapon anLWeapon, bool usehitbox) {
  3057.     if ( usehitbox ) return anLWeapon->Y+anLWeapon->HitHeight/2 + anLWeapon->HitYOffset;
  3058.     else return  anLWeapon->Y+8*anLWeapon->TileHeight + anLWeapon->DrawYOffset;
  3059. }
  3060.  
  3061. //Returns centre of eweapon, with option to use either its actual coordinates, or those of its sprite.
  3062. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3063. int CenterX(eweapon anEWeapon, bool usehitbox) {
  3064.     if ( usehitbox ) return anEWeapon->X+anEWeapon->HitWidth/2 + anEWeapon->HitXOffset;
  3065.     else return  anEWeapon->X+8*anEWeapon->TileWidth + anEWeapon->DrawXOffset;
  3066. }
  3067.  
  3068. //Returns centre of eweapon, with option to use either its actual coordinates, or those of its sprite.
  3069. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3070. int CenterY(eweapon anEWeapon, bool usehitbox) {
  3071.     if ( usehitbox ) return anEWeapon->Y+anEWeapon->HitHeight/2 + anEWeapon->HitYOffset;
  3072.     else return anEWeapon->Y+8*anEWeapon->TileHeight + anEWeapon->DrawYOffset;
  3073. }
  3074.  
  3075. //Returns centre of npc, with option to use either its actual coordinates, or those of its sprite.
  3076. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3077. int CenterX(npc n, bool usehitbox) {
  3078.     if ( usehitbox ) return n->X+n->HitWidth/2 + n->HitXOffset;
  3079.     else return n->X+8*n->TileWidth + n->DrawXOffset;
  3080. }
  3081.  
  3082. //Returns centre of npc, with option to use either its actual coordinates, or those of its sprite.
  3083. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3084. int CenterY(npc n, bool usehitbox) {
  3085.     if ( usehitbox ) return n->Y+n->HitHeight/2 + n->HitYOffset;
  3086.     else return n->Y+8*n->TileHeight + n->DrawYOffset;
  3087. }
  3088.  
  3089. //Returns centre of npc, with option to use either its actual coordinates, or those of its sprite.
  3090. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3091. int CenterX(item i, bool usehitbox) {
  3092.     if ( usehitbox ) return i->X+i->HitWidth/2 + i->HitXOffset;
  3093.     else return i->X+8*i->TileWidth + i->DrawXOffset;
  3094. }
  3095.  
  3096. //Returns centre of npc, with option to use either its actual coordinates, or those of its sprite.
  3097. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3098. int CenterY(item i, bool usehitbox) {
  3099.     if ( usehitbox ) return i->Y+i->HitHeight/2 + i->HitYOffset;
  3100.     else return i->X+8*i->TileHeight + i->DrawYOffset;
  3101. }
  3102.  
  3103.  
  3104. ////////////////
  3105.  
  3106. //Returns centre of lweapon, with option to include its HitXOffset and DrawXOffset (individually).
  3107. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3108. int CenterX(lweapon anLWeapon, bool usehitbox, bool trueoffset, bool drawoffset) {
  3109.     int lx = anLWeapon->X;
  3110.     if ( usehitbox ) lx += anLWeapon->HitWidth/2;
  3111.     if ( !usehitbox ) lx += 8*anLWeapon->TileWidth;
  3112.     if ( trueoffset ) lx += anLWeapon->HitXOffset;
  3113.     if ( drawoffset ) lx += anLWeapon->DrawXOffset;
  3114.     return lx;
  3115. }
  3116.  
  3117. //Returns centre of lweapon, with option to include its HitYOffset and DrawYOffset (individually).
  3118. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3119. int CenterY(lweapon anLWeapon, bool usehitbox, bool trueoffset, bool drawoffset) {
  3120.     int ly = anLWeapon->Y;
  3121.     if ( usehitbox ) ly += anLWeapon->HitHeight/2;
  3122.     if ( !usehitbox ) ly += 8*anLWeapon->TileHeight;
  3123.     if ( trueoffset ) ly += anLWeapon->HitYOffset;
  3124.     if ( drawoffset ) ly += anLWeapon->DrawYOffset;
  3125.     return ly;
  3126. }
  3127.  
  3128. //Returns centre of eweapon, with option to include its HitXOffset and DrawXOffset (individually).
  3129. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3130. int CenterX(eweapon anEWeapon, bool usehitbox, bool trueoffset, bool drawoffset) {
  3131.     int ex = anEWeapon->X;
  3132.     if ( usehitbox ) ex += anEWeapon->HitWidth/2;
  3133.     if ( !usehitbox ) ex += 8*anEWeapon->TileWidth;
  3134.     if ( trueoffset ) ex += anEWeapon->HitXOffset;
  3135.     if ( drawoffset ) ex += anEWeapon->DrawXOffset;
  3136.     return ex;
  3137. }
  3138.  
  3139. //Returns centre of eweapon, with option to include its HitYOffset and DrawYOffset (individually).
  3140. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3141. int CenterY(eweapon anEWeapon, bool usehitbox, bool trueoffset, bool drawoffset) {
  3142.     int ey = anEWeapon->Y;
  3143.     if ( usehitbox ) ey += anEWeapon->HitHeight/2;
  3144.     if ( !usehitbox ) ey += 8*anEWeapon->TileHeight;
  3145.     if ( trueoffset ) ey += anEWeapon->HitYOffset;
  3146.     if ( drawoffset ) ey += anEWeapon->DrawYOffset;
  3147.     return ey;
  3148. }
  3149.  
  3150. //Returns centre of npc, with option to include its HitXOffset and DrawXOffset (individually).
  3151. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3152. int CenterX(npc n, bool usehitbox, bool trueoffset, bool drawoffset) {
  3153.     int nx = n->X;
  3154.     if ( usehitbox ) nx += n->HitWidth/2;
  3155.     if ( !usehitbox ) nx += 8*n->TileWidth;
  3156.     if ( trueoffset ) nx += n->HitXOffset;
  3157.     if ( drawoffset ) nx += n->DrawXOffset;
  3158.     return nx;
  3159. }
  3160.  
  3161. //Returns centre of npc, with option to include its HitYOffset and DrawYOffset (individually).
  3162. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3163. int CenterY(npc n, bool usehitbox, bool trueoffset, bool drawoffset) {
  3164.     int ny = n->Y;
  3165.     if ( usehitbox ) ny += n->HitHeight/2;
  3166.     if ( !usehitbox ) ny += 8*n->TileHeight;
  3167.     if ( trueoffset ) ny += n->HitYOffset;
  3168.     if ( drawoffset ) ny += n->DrawYOffset;
  3169.     return ny;
  3170. }
  3171.  
  3172. //Returns centre of item, with option to include its HitXOffset and DrawXOffset (individually).
  3173. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3174. int CenterX(item i, bool usehitbox, bool trueoffset, bool drawoffset) {
  3175.     int ix = i->X;
  3176.     if ( usehitbox ) ix += i->HitWidth/2;
  3177.     if ( !usehitbox ) ix += 8*i->TileWidth;
  3178.     if ( trueoffset ) ix += i->HitXOffset;
  3179.     if ( drawoffset ) ix += i->DrawXOffset;
  3180.     return ix;
  3181. }
  3182.  
  3183. //Returns centre of item, with option to include its HitYOffset and DrawYOffset (individually).
  3184. //Set 'usehitbox' true to use the hitbox centre, or false to use the sprite centre.
  3185. int CenterY(item i, bool usehitbox, bool trueoffset, bool drawoffset) {
  3186.     int iy = i->Y;
  3187.     if ( usehitbox ) iy += i->HitHeight/2;
  3188.     if ( !usehitbox ) iy += 8*i->TileHeight;
  3189.     if ( trueoffset ) iy += i->HitYOffset;
  3190.     if ( drawoffset ) iy += i->DrawYOffset;
  3191.     return iy;
  3192. }
  3193.  
  3194. ////////////////
  3195.  
  3196. //We need to modify these functions to allow the same options as the non-Link versions. g
  3197.  
  3198. int CenterLinkX(bool hitoffset) {
  3199.     if ( hitoffset ) return Link->X + 8 * Link->TileWidth + Link->HitXOffset;
  3200.     else return Link->X + 8 * Link->TileWidth;
  3201. }
  3202.  
  3203. int CenterLinkY(bool hitoffset) {
  3204.     if ( hitoffset ) return Link->Y + 8 * Link->TileHeight + Link->HitYOffset;
  3205.     else return Link->Y + 8 * Link->TileHeight;
  3206. }
  3207.  
  3208. int CenterLinkX(bool hitoffset, bool drawoffset) {
  3209.     int lx = Link->X + 8 * Link->TileWidth;
  3210.     if ( hitoffset ) lx += Link->HitXOffset;
  3211.     if ( drawoffset ) lx += Link->DrawXOffset; 
  3212.     return lx;
  3213. }
  3214.  
  3215. int CenterLinkY(bool hitoffset, bool drawoffset) {
  3216.     int ly = Link->Y + 8 * Link->TileHeight;
  3217.     if ( hitoffset ) ly += Link->HitYOffset;
  3218.     if ( drawoffset ) ly += Link->DrawYOffset; 
  3219.     return ly;
  3220. }
  3221.  
  3222.  
  3223. //Returns the direction of the vector from (0, 0) to point, in degrees from -180 to 180. (0 = right)
  3224. float Angle(int x, int y) {
  3225.   return ArcTan(x, y)*57.2958;
  3226. }
  3227.  
  3228. //Added: CenterX(item anItem) and CenterY(item anItem) 06-Jan-2016
  3229.  
  3230. //Returns the centre coordinates of a combo at position 'loc' similar to Center*() functions, and ComboX/Y.
  3231. int CenterComboX(int loc){
  3232.     return (loc%16*16) + 8;
  3233. }
  3234.  
  3235. int CenterComboY(int loc){
  3236.     return (loc&0xF0) +8;
  3237. }
  3238.  
  3239. bool Collision(ffc f, int cmb) { return Collision(cmb,f); }
  3240. bool Collision(lweapon l, int cmb) { return Collision(cmb,l); }
  3241. bool Collision(eweapon e, int cmb) { return Collision(cmb,e); }
  3242. bool Collision(npc n, int cmb) { return Collision(cmb,n); }
  3243. bool Collision(item i, int cmb) { return Collision(cmb,i); }
  3244.  
  3245.  
  3246.  
  3247. //Check for collision between lweapon 'l' and a combo at location 'cmb'.
  3248. //Set checkcoldetection to true if you wish to return false from an lweapon with ColDetection disabled.
  3249. bool Collision(lweapon l, int cmb, bool checkcoldetection) {
  3250.     if ( checkcoldetection && !l->CollDetection ) return false;
  3251.     else return Collision(cmb,l);
  3252. }
  3253.  
  3254. bool Collision(int cmb, lweapon l, bool checkcoldetection) {
  3255.     if ( checkcoldetection && !l->CollDetection ) return false;
  3256.     else return Collision(cmb,l);
  3257. }
  3258.  
  3259.  
  3260. //Check for collision between eweapon 'e' and a combo at location 'cmb' .
  3261. //Set checkcoldetection to true if you wish to return false from an eweapon with ColDetection disabled.
  3262. bool Collision(eweapon e, int cmb, bool checkcoldetection) {
  3263.     if ( checkcoldetection && !e->CollDetection ) return false;
  3264.     else return Collision(cmb,e);
  3265. }
  3266.  
  3267.  
  3268. bool Collision(int cmb, eweapon e, bool checkcoldetection) {
  3269.     if ( checkcoldetection && !e->CollDetection ) return false;
  3270.     else return Collision(cmb,e);
  3271. }
  3272.  
  3273. //Check for collision between NPC 'n' and a combo at location 'cmb' .
  3274. //Set checkcoldetection to true if you wish to return false from an NPC with ColDetection disabled.
  3275. bool Collision(npc n, int cmb, bool checkcoldetection) {
  3276.     if ( checkcoldetection && !n->CollDetection ) return false;
  3277.     else return Collision(cmb,n);
  3278. }
  3279.  
  3280. bool Collision(int cmb, npc n, bool checkcoldetection) {
  3281.     if ( checkcoldetection && !n->CollDetection ) return false;
  3282.     else return Collision(cmb,n);
  3283. }
  3284.  
  3285. //Check for collision between Link and a combo at location 'cmb' .
  3286. //Set checkcoldetection to true if you wish to return false from an NPC with ColDetection disabled.
  3287. bool Collision(int cmb, bool checkcoldetection) {
  3288.     if ( checkcoldetection && !Link->CollDetection ) return false;
  3289.     else return Collision(cmb);
  3290. }
  3291.  
  3292. //Check for collision between ffc 'f' and a combo at location 'cmb'.
  3293. bool Collision(int cmb, ffc f){
  3294.     int c[8];
  3295.     c[0] = ComboX(cmb);
  3296.     c[1] = ComboY(cmb);
  3297.     c[2] = ComboX(cmb)+16;
  3298.     c[3] = ComboY(cmb)+16;
  3299.     c[4] = (f->X);
  3300.     c[5] = (f->Y);
  3301.     c[6] = c[4]+(f->EffectWidth);
  3302.     c[7] = c[5]+(f->EffectHeight);
  3303.     return RectCollision( c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7] );
  3304. }
  3305.  
  3306. //Check for collision between lweapon 'l' and a combo at location 'cmb'.
  3307. bool Collision(int cmb, lweapon l){
  3308.     int c[8];
  3309.     c[0] = ComboX(cmb);
  3310.     c[1] = ComboY(cmb);
  3311.     c[2] = ComboX(cmb)+16;
  3312.     c[3] = ComboY(cmb)+16;
  3313.     c[4] = (l->X)+l->HitXOffset+l->DrawXOffset;
  3314.     c[5] = (l->Y)+l->HitYOffset+l->DrawYOffset;
  3315.     c[6] = c[4]+l->HitWidth;
  3316.     c[7] = c[5]+l->HitHeight;
  3317.     return RectCollision( c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7] );
  3318. }
  3319.  
  3320. //Check for collision between eweapon 'e' and a combo at location 'cmb'.
  3321. bool Collision(int cmb, eweapon e){
  3322.     int c[8];
  3323.     c[0] = ComboX(cmb);
  3324.     c[1] = ComboY(cmb);
  3325.     c[2] = ComboX(cmb)+16;
  3326.     c[3] = ComboY(cmb)+16;
  3327.     c[4] = (e->X)+e->HitXOffset+e->DrawXOffset;
  3328.     c[5] = (e->Y)+e->HitYOffset+e->DrawYOffset;
  3329.     c[5] = c[4]+e->HitWidth;
  3330.     c[7] = c[5]+e->HitHeight;
  3331.     return RectCollision( c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7] );
  3332. }
  3333.  
  3334. //Check for collision between npc 'n' and a combo at location 'cmb'.
  3335. bool Collision(int cmb, npc n){
  3336.     int c[8];
  3337.     c[0] = ComboX(cmb);
  3338.     c[1] = ComboY(cmb);
  3339.     c[2] = ComboX(cmb)+16;
  3340.     c[3] = ComboY(cmb)+16;
  3341.     c[4] = (n->X)+n->HitXOffset+n->DrawXOffset;
  3342.     c[5] = (n->Y)+n->HitYOffset+n->DrawYOffset;
  3343.     c[6] = c[4]+n->HitWidth;
  3344.     c[7] = c[5]+n->HitHeight;
  3345.     return RectCollision( c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7] );
  3346. }
  3347.  
  3348. //Check for collision between item 'i' and a combo at location 'cmb'.
  3349. bool Collision(int cmb, item i){
  3350.     int c[8];
  3351.     c[0] = ComboX(cmb);
  3352.     c[1] = ComboY(cmb);
  3353.     c[2] = ComboX(cmb)+16;
  3354.     c[3] = ComboY(cmb)+16;
  3355.     c[4] = (i->X)+i->HitXOffset+i->DrawXOffset;
  3356.     c[5] = (i->Y)+i->HitYOffset+i->DrawYOffset;
  3357.     c[6] = c[4]+i->HitWidth;
  3358.     c[7] = c[5]+i->HitHeight;
  3359.     return RectCollision( c[0], c[1], c[2], c[3], c[4], c[5], c[6], c[7] );
  3360. }
  3361.  
  3362.  
  3363. //Check for collision between Link and a combo at location 'cmb'.
  3364. bool Collision(int cmb){
  3365.     int c[4];
  3366.     c[0] = Link->X+Link->HitXOffset+Link->DrawXOffset;
  3367.     c[1] = Link->Y+Link->HitYOffset+Link->DrawYOffset;
  3368.     c[2] = c[0]+(Link->HitWidth);
  3369.     c[3] = c[1]+(Link->HitHeight);
  3370.     if ( !RectCollision( ComboX(cmb), ComboY(cmb), (ComboX(cmb)+16), (ComboY(cmb)+16), c[0], c[1], c[2], c[3]) ) return false;
  3371.     else if ( !(Distance(CenterLinkX(), CenterLinkY(), (ComboX(cmb)+8), (ComboY(cmb)+8)) < 8) ) return false;
  3372.     return true;
  3373. }
  3374.  
  3375. //Returns angle of the given direction.
  3376. int DirAngle(int dir){
  3377.     dir &=7;
  3378.     if (dir==DIR_UP) return 90;
  3379.     if (dir==DIR_DOWN) return 270;
  3380.     if (dir==DIR_LEFT) return 180;
  3381.     if (dir==DIR_RIGHT) return 0;
  3382.     if (dir==DIR_LEFTUP) return 135;
  3383.     if (dir==DIR_RIGHTUP) return 45;
  3384.     if (dir==DIR_LEFTDOWN) return 225;
  3385.     if (dir==DIR_RIGHTDOWN) return 315;
  3386.     return -1;
  3387. }
  3388.  
  3389. //Same as DirAngle, but return value is measured in radians.
  3390. int DirRad(int dir){
  3391.     return DirAngle(dir)*0.0174;
  3392. }
  3393.  
  3394. //Use SetCombo* on Layer 0 using LayerMap()
  3395. //A shorthand way to set a combo on the current layer.
  3396. //Layer 0 is the screen itself.
  3397. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3398. void SetLayerComboD(int layer, int pos, int combo, bool layer0) {
  3399.     if (layer==0 && !layer0) Screen->ComboD[pos] = combo;
  3400.     else Game->SetComboData(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, combo);
  3401. }
  3402.  
  3403.  
  3404. //A shorthand way to set a combo flag on the current layer.
  3405. //Layer 0 is the screen itself.
  3406. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3407. void SetLayerComboF(int layer, int pos, int flag, bool layer0) {
  3408.     if (layer==0 && !layer0) Screen->ComboF[pos] = flag;
  3409.     else Game->SetComboFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, flag);
  3410. }
  3411.  
  3412. //Layer 0 is the screen itself.
  3413. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3414. void SetLayerComboI(int layer, int pos, int flag, bool layer0) {
  3415.     if (layer==0 && !layer0) Screen->ComboI[pos] = flag;
  3416.     else Game->SetComboInherentFlag(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, flag);
  3417. }
  3418.  
  3419.  
  3420. //A shorthand way to set a combo CSet on the current layer.
  3421. //Layer 0 is the screen itself.
  3422. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3423. void SetLayerComboC(int layer, int pos, int cset, bool layer0) {
  3424.     if (layer==0 && !layer0) Screen->ComboC[pos] = cset;
  3425.     else Game->SetComboCSet(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, cset);
  3426. }
  3427.  
  3428.  
  3429. //A shorthand way to set a combo type on the current layer.
  3430. //Layer 0 is the screen itself.
  3431. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3432. void SetLayerComboT(int layer, int pos, int type, bool layer0) {
  3433.     if (layer==0 && !layer0) Screen->ComboT[pos] = type;
  3434.     else Game->SetComboType(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, type);
  3435. }
  3436.  
  3437.  
  3438. //A shorthand way to set a combo's solidity on the current layer.
  3439. //Layer 0 is the screen itself.
  3440. //Set layer0 to true to use LayerMap() to handle layer 0 combos. This should allow changes to remain static.
  3441. void SetLayerComboS(int layer, int pos, int solidity, bool layer0) {
  3442.     if (layer==0 && !layer0) Screen->ComboS[pos] = solidity;
  3443.     if ( MIN_CONSTANT > -214747.9999 ) { //Not compile don 2.50.3
  3444.         if ( layer == 1 )
  3445.         Game->SetComboSolid(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, solidity);
  3446.         else if ( layer > 1 ) {
  3447.             int str[]="Setting solidity on layers higher than 1 causes this version of ZC to crash.";
  3448.             TraceS(str);
  3449.         }
  3450.     }
  3451.     else Game->SetComboSolid(Screen->LayerMap(layer), Screen->LayerScreen(layer), pos, solidity);
  3452. }
  3453.  
  3454. //Read link's HitBox values
  3455. int HitboxTop() {
  3456.   return (Link->Y + Link->HitYOffset);
  3457. }
  3458.  
  3459. int HitboxLeft() {
  3460.   return (Link->X + Link->HitXOffset);
  3461. }
  3462.  
  3463. int HitboxRight() {
  3464.   return (Link->X + Link->HitXOffset + Link->HitWidth - 1);
  3465. }
  3466.  
  3467. int HitboxBottom() {
  3468.   return (Link->Y + Link->HitYOffset + Link->HitHeight - 1);
  3469. }
  3470.  
  3471. //! We need to add versions for every object type, too.
  3472.  
  3473.  
  3474. //! Array memory management Utilities
  3475. //now in mem.zh
  3476.    
  3477. //Converts the ID (type) of a given weapon to its opposite class.
  3478. //Returns -1 if the type is illegal.
  3479. int EWeaponToLWeaponID(int type){
  3480.     if ( type == EW_ARROW ) return LW_ARROW;
  3481.     if ( type == EW_BRANG ) return LW_BRANG;
  3482.     if ( type == EW_BEAM ) return LW_BEAM;
  3483.     if ( type == EW_MAGIC ) return LW_MAGIC;
  3484.     if ( type == EW_BOMB ) return LW_BOMB;
  3485.     if ( type == EW_BOMBBLAST ) return LW_BOMBBLAST;
  3486.     if ( type == EW_SBOMB ) return LW_SBOMB;
  3487.     if ( type == EW_SBOMBBLAST ) return LW_SBOMBBLAST;
  3488.     if ( type == EW_WIND ) return LW_WIND;
  3489.     if ( type >= 31 && type <= 40 ) return type;
  3490.     else return -1;
  3491. }
  3492.  
  3493. //Converts the ID (type) of a given weapon to its opposite class.
  3494. //Returns -1 if the type is illegal.
  3495. int LWeaponToEWeaponID(int type){
  3496.     if ( type == LW_ARROW ) return EW_ARROW;
  3497.     if ( type == LW_BRANG ) return EW_BRANG;
  3498.     if ( type == LW_BEAM ) return EW_BEAM;
  3499.     if ( type == LW_MAGIC ) return EW_MAGIC;
  3500.     if ( type == LW_BOMB ) return EW_BOMB;
  3501.     if ( type == LW_BOMBBLAST ) return EW_BOMBBLAST;
  3502.     if ( type == LW_SBOMB ) return EW_SBOMB;
  3503.     if ( type == LW_SBOMBBLAST ) return EW_SBOMBBLAST;
  3504.     if ( type == LW_WIND ) return EW_WIND;
  3505.     if ( type >= 31 && type <= 40 ) return type;
  3506.     else return -1;
  3507. }
  3508.  
  3509.  
  3510. //Copy the attributes of a given lweapon to an eweapon.
  3511. //Returns -1 on error, including if the type (weap->ID) conversion is illegal.
  3512. eweapon LWeaponToEWeapon(lweapon a, eweapon b){
  3513.     int type = LWeaponToEWeaponID(a->ID);
  3514.     //if ( type == -1 ) return type;
  3515.     b->ID = type;
  3516.     b->X = a->X;
  3517.     b->Y = a->Y;
  3518.     b->Z = a->Z;
  3519.     b->Jump = a->Jump;
  3520.     b->Extend = a->Extend;
  3521.     b->TileWidth = a->TileWidth;
  3522.     b->TileHeight = a->TileHeight;
  3523.     b->HitWidth = a->HitWidth;
  3524.     b->HitHeight = a->HitHeight;
  3525.     b->HitZHeight = a->HitZHeight;
  3526.     b->HitXOffset = a->HitXOffset;
  3527.     b->HitYOffset = a->HitYOffset;
  3528.     b->DrawXOffset = a->DrawXOffset;
  3529.     b->DrawYOffset = a->DrawYOffset;
  3530.     b->DrawZOffset = a->DrawZOffset;
  3531.     b->Tile = a->Tile;
  3532.     b->CSet = a->CSet;
  3533.     b->DrawStyle = a->DrawStyle;
  3534.     b->Dir = a->Dir;
  3535.     b->OriginalTile = a->OriginalTile;
  3536.     b->OriginalCSet = a->OriginalCSet;
  3537.     b->FlashCSet = a->FlashCSet;
  3538.     b->NumFrames = a->NumFrames;
  3539.     b->Frame = a->Frame;
  3540.     b->ASpeed = a->ASpeed;
  3541.     b->Damage = a->Damage;
  3542.     b->Step = a->Step;
  3543.     b->Angle = a->Angle;
  3544.     b->Angular = a->Angular;
  3545.     b->CollDetection = a->CollDetection;
  3546.     b->DeadState = a->DeadState;
  3547.     b->Flash = a->Flash;
  3548.     b->Flip = a->Flip;
  3549.     for (int i = 0; i < 16; i++)
  3550.         b->Misc[i] = a->Misc[i];
  3551.     return b;
  3552. }
  3553.  
  3554.  
  3555.  
  3556. //Copy the attributes of a given lweapon to a new eweapon.
  3557. //Returns -1 on error, including if the type (weap->ID) conversion is illegal.
  3558. eweapon LWeaponToEWeapon(lweapon a){
  3559.     int type = LWeaponToEWeaponID(a->ID);
  3560. //  if ( type == -1 ) return type;
  3561.     eweapon b = Screen->CreateEWeapon(type);
  3562.     b->X = a->X;
  3563.     b->Y = a->Y;
  3564.     b->Z = a->Z;
  3565.     b->Jump = a->Jump;
  3566.     b->Extend = a->Extend;
  3567.     b->TileWidth = a->TileWidth;
  3568.     b->TileHeight = a->TileHeight;
  3569.     b->HitWidth = a->HitWidth;
  3570.     b->HitHeight = a->HitHeight;
  3571.     b->HitZHeight = a->HitZHeight;
  3572.     b->HitXOffset = a->HitXOffset;
  3573.     b->HitYOffset = a->HitYOffset;
  3574.     b->DrawXOffset = a->DrawXOffset;
  3575.     b->DrawYOffset = a->DrawYOffset;
  3576.     b->DrawZOffset = a->DrawZOffset;
  3577.     b->Tile = a->Tile;
  3578.     b->CSet = a->CSet;
  3579.     b->DrawStyle = a->DrawStyle;
  3580.     b->Dir = a->Dir;
  3581.     b->OriginalTile = a->OriginalTile;
  3582.     b->OriginalCSet = a->OriginalCSet;
  3583.     b->FlashCSet = a->FlashCSet;
  3584.     b->NumFrames = a->NumFrames;
  3585.     b->Frame = a->Frame;
  3586.     b->ASpeed = a->ASpeed;
  3587.     b->Damage = a->Damage;
  3588.     b->Step = a->Step;
  3589.     b->Angle = a->Angle;
  3590.     b->Angular = a->Angular;
  3591.     b->CollDetection = a->CollDetection;
  3592.     b->DeadState = a->DeadState;
  3593.     b->Flash = a->Flash;
  3594.     b->Flip = a->Flip;
  3595.     for (int i = 0; i < 16; i++)
  3596.         b->Misc[i] = a->Misc[i];
  3597.     return b;
  3598. }
  3599.  
  3600. lweapon EWeaponToLWeapon(lweapon b, eweapon a) { return EWeaponToLWeapon(a,b);}
  3601. eweapon LWeaponToEWeapon(eweapon b, lweapon a) { return LWeaponToEWeapon(a,b);}
  3602. lweapon EToLWeapon(lweapon b, eweapon a) { return EWeaponToLWeapon(a,b);}
  3603. eweapon LtoEWeapon(eweapon b, lweapon a) { return LWeaponToEWeapon(a,b);}
  3604.  
  3605. lweapon EToLWeapon(eweapon a, lweapon b) { return EWeaponToLWeapon(a,b);}
  3606. eweapon LtoEWeapon(lweapon a, eweapon b) { return LWeaponToEWeapon(a,b);}
  3607.  
  3608.  
  3609. eweapon LtoEWeapon(lweapon a){return LtoEWeapon(a);}
  3610. lweapon EtoLWeapon(eweapon a){return EtoLWeapon(a);}
  3611.  
  3612. //Copy the attributes of a given eweapon to a new lweapon.
  3613. //Returns -1 on error, including if the type (weap->ID) conversion is illegal.
  3614. lweapon EWeaponToLWeapon(eweapon a){
  3615.     int type = EWeaponToLWeaponID(a->ID);
  3616.     //if ( type == -1 ) return type;
  3617.     lweapon b = Screen->CreateLWeapon(type);
  3618.     b->X = a->X;
  3619.     b->Y = a->Y;
  3620.     b->Z = a->Z;
  3621.     b->Jump = a->Jump;
  3622.     b->Extend = a->Extend;
  3623.     b->TileWidth = a->TileWidth;
  3624.     b->TileHeight = a->TileHeight;
  3625.     b->HitWidth = a->HitWidth;
  3626.     b->HitHeight = a->HitHeight;
  3627.     b->HitZHeight = a->HitZHeight;
  3628.     b->HitXOffset = a->HitXOffset;
  3629.     b->HitYOffset = a->HitYOffset;
  3630.     b->DrawXOffset = a->DrawXOffset;
  3631.     b->DrawYOffset = a->DrawYOffset;
  3632.     b->DrawZOffset = a->DrawZOffset;
  3633.     b->Tile = a->Tile;
  3634.     b->CSet = a->CSet;
  3635.     b->DrawStyle = a->DrawStyle;
  3636.     b->Dir = a->Dir;
  3637.     b->OriginalTile = a->OriginalTile;
  3638.     b->OriginalCSet = a->OriginalCSet;
  3639.     b->FlashCSet = a->FlashCSet;
  3640.     b->NumFrames = a->NumFrames;
  3641.     b->Frame = a->Frame;
  3642.     b->ASpeed = a->ASpeed;
  3643.     b->Damage = a->Damage;
  3644.     b->Step = a->Step;
  3645.     b->Angle = a->Angle;
  3646.     b->Angular = a->Angular;
  3647.     b->CollDetection = a->CollDetection;
  3648.     b->DeadState = a->DeadState;
  3649.     b->Flash = a->Flash;
  3650.     b->Flip = a->Flip;
  3651.     for (int i = 0; i < 16; i++)
  3652.         b->Misc[i] = a->Misc[i];
  3653.     return b;
  3654. }
  3655.  
  3656.  
  3657. //Copy the attributes of a given eweapon to an lweapon.
  3658. //Returns -1 on error, including if the type (weap->ID) conversion is illegal.
  3659. lweapon EWeaponToLWeapon(eweapon a, lweapon b){
  3660.     int type = EWeaponToLWeaponID(a->ID);
  3661.     //if ( type == -1 ) return type;
  3662.     b->ID = type;
  3663.     b->X = a->X;
  3664.     b->Y = a->Y;
  3665.     b->Z = a->Z;
  3666.     b->Jump = a->Jump;
  3667.     b->Extend = a->Extend;
  3668.     b->TileWidth = a->TileWidth;
  3669.     b->TileHeight = a->TileHeight;
  3670.     b->HitWidth = a->HitWidth;
  3671.     b->HitHeight = a->HitHeight;
  3672.     b->HitZHeight = a->HitZHeight;
  3673.     b->HitXOffset = a->HitXOffset;
  3674.     b->HitYOffset = a->HitYOffset;
  3675.     b->DrawXOffset = a->DrawXOffset;
  3676.     b->DrawYOffset = a->DrawYOffset;
  3677.     b->DrawZOffset = a->DrawZOffset;
  3678.     b->Tile = a->Tile;
  3679.     b->CSet = a->CSet;
  3680.     b->DrawStyle = a->DrawStyle;
  3681.     b->Dir = a->Dir;
  3682.     b->OriginalTile = a->OriginalTile;
  3683.     b->OriginalCSet = a->OriginalCSet;
  3684.     b->FlashCSet = a->FlashCSet;
  3685.     b->NumFrames = a->NumFrames;
  3686.     b->Frame = a->Frame;
  3687.     b->ASpeed = a->ASpeed;
  3688.     b->Damage = a->Damage;
  3689.     b->Step = a->Step;
  3690.     b->Angle = a->Angle;
  3691.     b->Angular = a->Angular;
  3692.     b->CollDetection = a->CollDetection;
  3693.     b->DeadState = a->DeadState;
  3694.     b->Flash = a->Flash;
  3695.     b->Flip = a->Flip;
  3696.     for (int i = 0; i < 16; i++)
  3697.         b->Misc[i] = a->Misc[i];
  3698.     return b;
  3699. }
  3700.  
  3701.  
  3702. int EtoLWeaponID(int type){
  3703.     return EWeaponToLWeaponID(type);
  3704. }
  3705.  
  3706. int LtoEWeaponID(int type){
  3707.     return LWeaponToEWeaponID(type);
  3708. }
  3709.    
  3710.    
  3711. //Returns the centre of a given hitbox.
  3712. int CenterHitX(){}
  3713. int CenterHitY(){}
  3714.    
  3715.    
  3716.  
  3717. //Xor comparison of two calculations. ( e.g. Xor(n-x, n+y) )
  3718. //Returns true if they do not match.
  3719. bool Xor(float calcA, float calcB){
  3720.     if ( calcA != calcB ) return true;
  3721.     return false;
  3722. }
  3723.  
  3724.  
  3725. //Randomly return true or false.
  3726. int Chance(){
  3727.     return Rand(0,1);
  3728. }
  3729.  
  3730. //Randomly returns true, or false, using input 'percentChance' to determine the percentage change of a 'true return'
  3731. bool Chance(int percentChance){
  3732.     return RandB(percentChance);
  3733. }
  3734.  
  3735. int ProximityX(ffc a, ffc b) {
  3736.     if ( a->X > b->X ) return a->X - b->X;
  3737.     else return b->X - a->X;
  3738. }
  3739.  
  3740.  
  3741. int ProximityX(ffc a, lweapon b) {
  3742.     if ( a->X > b->X ) return a->X - b->X;
  3743.     else return b->X - a->X;
  3744. }
  3745.  
  3746.  
  3747. int ProximityX(ffc a, eweapon b) {
  3748.     if ( a->X > b->X ) return a->X - b->X;
  3749.     else return b->X - a->X;
  3750. }
  3751.    
  3752.  
  3753. int ProximityX(ffc a, npc b) {
  3754.     if ( a->X > b->X ) return a->X - b->X;
  3755.     else return b->X - a->X;
  3756. }
  3757.  
  3758.  
  3759. int ProximityX(ffc a, item b) {
  3760.     if ( a->X > b->X ) return a->X - b->X;
  3761.     else return b->X - a->X;
  3762. }
  3763.  
  3764.  
  3765. int ProximityX(lweapon a, ffc b) {
  3766.     if ( a->X > b->X ) return a->X - b->X;
  3767.     else return b->X - a->X;
  3768. }
  3769.  
  3770. int ProximityX(lweapon a, lweapon b) {
  3771.     if ( a->X > b->X ) return a->X - b->X;
  3772.     else return b->X - a->X;
  3773. }
  3774.  
  3775. int ProximityX(lweapon a, eweapon b) {
  3776.     if ( a->X > b->X ) return a->X - b->X;
  3777.     else return b->X - a->X;
  3778. }
  3779.  
  3780. int ProximityX(lweapon a, npc b) {
  3781.     if ( a->X > b->X ) return a->X - b->X;
  3782.     else return b->X - a->X;
  3783. }
  3784.  
  3785. int ProximityX(lweapon a, item b) {
  3786.     if ( a->X > b->X ) return a->X - b->X;
  3787.     else return b->X - a->X;
  3788. }
  3789.  
  3790. int ProximityX(eweapon a, ffc b) {
  3791.     if ( a->X > b->X ) return a->X - b->X;
  3792.     else return b->X - a->X;
  3793. }
  3794.  
  3795. int ProximityX(eweapon a, lweapon b) {
  3796.     if ( a->X > b->X ) return a->X - b->X;
  3797.     else return b->X - a->X;
  3798. }
  3799.  
  3800. int ProximityX(eweapon a, eweapon b) {
  3801.     if ( a->X > b->X ) return a->X - b->X;
  3802.     else return b->X - a->X;
  3803. }
  3804.  
  3805. int ProximityX(eweapon a, npc b) {
  3806.     if ( a->X > b->X ) return a->X - b->X;
  3807.     else return b->X - a->X;
  3808. }
  3809.  
  3810. int ProximityX(eweapon a, item b) {
  3811.     if ( a->X > b->X ) return a->X - b->X;
  3812.     else return b->X - a->X;
  3813. }
  3814.  
  3815. int ProximityX(npc a, ffc b) {
  3816.     if ( a->X > b->X ) return a->X - b->X;
  3817.     else return b->X - a->X;
  3818. }
  3819.  
  3820. int ProximityX(npc a, lweapon b) {
  3821.     if ( a->X > b->X ) return a->X - b->X;
  3822.     else return b->X - a->X;
  3823. }
  3824.  
  3825. int ProximityX(npc a, eweapon b) {
  3826.     if ( a->X > b->X ) return a->X - b->X;
  3827.     else return b->X - a->X;
  3828. }
  3829.  
  3830. int ProximityX(npc a, npc b) {
  3831.     if ( a->X > b->X ) return a->X - b->X;
  3832.     else return b->X - a->X;
  3833. }
  3834.  
  3835. int ProximityX(npc a, item b) {
  3836.     if ( a->X > b->X ) return a->X - b->X;
  3837.     else return b->X - a->X;
  3838. }
  3839.  
  3840.  
  3841. int ProximityX(item a, ffc b) {
  3842.     if ( a->X > b->X ) return a->X - b->X;
  3843.     else return b->X - a->X;
  3844. }
  3845.  
  3846. int ProximityX(item a, lweapon b) {
  3847.     if ( a->X > b->X ) return a->X - b->X;
  3848.     else return b->X - a->X;
  3849. }
  3850.  
  3851. int ProximityX(item a, eweapon b) {
  3852.     if ( a->X > b->X ) return a->X - b->X;
  3853.     else return b->X - a->X;
  3854. }
  3855.  
  3856. int ProximityX(item a, npc b) {
  3857.     if ( a->X > b->X ) return a->X - b->X;
  3858.     else return b->X - a->X;
  3859. }
  3860.  
  3861. int ProximityX(item a, item b) {
  3862.     if ( a->X > b->X ) return a->X - b->X;
  3863.     else return b->X - a->X;
  3864. }
  3865.  
  3866. int ProximityX(int b, ffc a) {
  3867.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3868.     else return ComboX(b) - a->X;
  3869. }
  3870.  
  3871.  
  3872. int ProximityX(int b, lweapon a) {
  3873.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3874.     else return ComboX(b) - a->X;
  3875. }
  3876.  
  3877.  
  3878. int ProximityX(int b, eweapon a) {
  3879.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3880.     else return ComboX(b) - a->X;
  3881. }
  3882.    
  3883.  
  3884. int ProximityX(int b, npc a) {
  3885.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3886.     else return ComboX(b) - a->X;
  3887. }
  3888.  
  3889.  
  3890. int ProximityX(int b, item a) {
  3891.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3892.     else return ComboX(b) - a->X;
  3893. }
  3894.  
  3895. int ProximityX(ffc a, int b) {
  3896.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3897.     else return ComboX(b) - a->X;
  3898. }
  3899.  
  3900.  
  3901. int ProximityX(lweapon a, int b) {
  3902.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3903.     else return ComboX(b) - a->X;
  3904. }
  3905.  
  3906.  
  3907. int ProximityX(eweapon a, int b) {
  3908.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3909.     else return ComboX(b) - a->X;
  3910. }
  3911.    
  3912.  
  3913. int ProximityX(npc a, int b) {
  3914.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3915.     else return ComboX(b) - a->X;
  3916. }
  3917.  
  3918.  
  3919. int ProximityX(item a, int b) {
  3920.     if ( a->X > ComboX(b) ) return a->X - ComboX(b);
  3921.     else return ComboX(b) - a->X;
  3922. }
  3923.  
  3924. int ProximityX(int b, int a) {
  3925.     if ( ComboX(a) > ComboX(b) ) return ComboX(a) - ComboX(b);
  3926.     else return ComboX(b) - ComboX(a);
  3927. }
  3928.  
  3929. int ProximityX(ffc a) {
  3930.     if ( a->X > Link->X ) return a->X - Link->X;
  3931.     else return Link->X - a->X;
  3932. }
  3933.  
  3934. int ProximityX(lweapon a) {
  3935.     if ( a->X > Link->X ) return a->X - Link->X;
  3936.     else return Link->X - a->X;
  3937. }
  3938.  
  3939. int ProximityX(eweapon a) {
  3940.     if ( a->X > Link->X ) return a->X - Link->X;
  3941.     else return Link->X - a->X;
  3942. }
  3943.  
  3944. int ProximityX(npc a) {
  3945.     if ( a->X > Link->X ) return a->X - Link->X;
  3946.     else return Link->X - a->X;
  3947. }
  3948.  
  3949. int ProximityX(item a) {
  3950.     if ( a->X > Link->X ) return a->X - Link->X;
  3951.     else return Link->X - a->X;
  3952. }
  3953.  
  3954. int ProximityX(int a) {
  3955.     int ax = ComboX(a);
  3956.     if ( ax > Link->X ) return ax - Link->X;
  3957.     else return Link->X - ax;
  3958. }
  3959.  
  3960. int ProximityY(ffc a, ffc b) {
  3961.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3962.     else return b->Y - a->Y;
  3963. }
  3964.  
  3965.  
  3966. int ProximityY(ffc a, lweapon b) {
  3967.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3968.     else return b->Y - a->Y;
  3969. }
  3970.  
  3971.  
  3972. int ProximityY(ffc a, eweapon b) {
  3973.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3974.     else return b->Y - a->Y;
  3975. }
  3976.    
  3977.  
  3978. int ProximityY(ffc a, npc b) {
  3979.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3980.     else return b->Y - a->Y;
  3981. }
  3982.  
  3983.  
  3984. int ProximityY(ffc a, item b) {
  3985.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3986.     else return b->Y - a->Y;
  3987. }
  3988.  
  3989.  
  3990. int ProximityY(lweapon a, ffc b) {
  3991.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3992.     else return b->Y - a->Y;
  3993. }
  3994.  
  3995. int ProximityY(lweapon a, lweapon b) {
  3996.     if ( a->Y > b->Y ) return a->Y - b->Y;
  3997.     else return b->Y - a->Y;
  3998. }
  3999.  
  4000. int ProximityY(lweapon a, eweapon b) {
  4001.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4002.     else return b->Y - a->Y;
  4003. }
  4004.  
  4005. int ProximityY(lweapon a, npc b) {
  4006.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4007.     else return b->Y - a->Y;
  4008. }
  4009.  
  4010. int ProximityY(lweapon a, item b) {
  4011.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4012.     else return b->Y - a->Y;
  4013. }
  4014.  
  4015. int ProximityY(eweapon a, ffc b) {
  4016.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4017.     else return b->Y - a->Y;
  4018. }
  4019.  
  4020. int ProximityY(eweapon a, lweapon b) {
  4021.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4022.     else return b->Y - a->Y;
  4023. }
  4024.  
  4025. int ProximityY(eweapon a, eweapon b) {
  4026.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4027.     else return b->Y - a->Y;
  4028. }
  4029.  
  4030. int ProximityY(eweapon a, npc b) {
  4031.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4032.     else return b->Y - a->Y;
  4033. }
  4034.  
  4035. int ProximityY(eweapon a, item b) {
  4036.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4037.     else return b->Y - a->Y;
  4038. }
  4039.  
  4040. int ProximityY(npc a, ffc b) {
  4041.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4042.     else return b->Y - a->Y;
  4043. }
  4044.  
  4045. int ProximityY(npc a, lweapon b) {
  4046.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4047.     else return b->Y - a->Y;
  4048. }
  4049.  
  4050. int ProximityY(npc a, eweapon b) {
  4051.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4052.     else return b->Y - a->Y;
  4053. }
  4054.  
  4055. int ProximityY(npc a, npc b) {
  4056.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4057.     else return b->Y - a->Y;
  4058. }
  4059.  
  4060. int ProximityY(npc a, item b) {
  4061.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4062.     else return b->Y - a->Y;
  4063. }
  4064.  
  4065.  
  4066. int ProximityY(item a, ffc b) {
  4067.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4068.     else return b->Y - a->Y;
  4069. }
  4070.  
  4071. int ProximityY(item a, lweapon b) {
  4072.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4073.     else return b->Y - a->Y;
  4074. }
  4075.  
  4076. int ProximityY(item a, eweapon b) {
  4077.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4078.     else return b->Y - a->Y;
  4079. }
  4080.  
  4081. int ProximityY(item a, npc b) {
  4082.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4083.     else return b->Y - a->Y;
  4084. }
  4085.  
  4086. int ProximityY(item a, item b) {
  4087.     if ( a->Y > b->Y ) return a->Y - b->Y;
  4088.     else return b->Y - a->Y;
  4089. }
  4090.  
  4091. int ProximityY(int b, ffc a) {
  4092.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4093.     else return ComboY(b) - a->Y;
  4094. }
  4095.  
  4096.  
  4097. int ProximityY(int b, lweapon a) {
  4098.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4099.     else return ComboY(b) - a->Y;
  4100. }
  4101.  
  4102.  
  4103. int ProximityY(int b, eweapon a) {
  4104.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4105.     else return ComboY(b) - a->Y;
  4106. }
  4107.    
  4108.  
  4109. int ProximityY(int b, npc a) {
  4110.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4111.     else return ComboY(b) - a->Y;
  4112. }
  4113.  
  4114.  
  4115. int ProximityY(int a, item b) {
  4116.     if ( b->Y > ComboY(a) ) return b->Y - ComboY(a);
  4117.     else return ComboY(a) - b->Y;
  4118. }
  4119.  
  4120. int ProximityY(ffc a, int b) {
  4121.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4122.     else return ComboY(b) - a->Y;
  4123. }
  4124.  
  4125.  
  4126. int ProximityY(lweapon a, int b) {
  4127.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4128.     else return ComboY(b) - a->Y;
  4129. }
  4130.  
  4131.  
  4132. int ProximityY(eweapon a, int b) {
  4133.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4134.     else return ComboY(b) - a->Y;
  4135. }
  4136.    
  4137.  
  4138. int ProximityY(npc a, int b) {
  4139.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4140.     else return ComboY(b) - a->Y;
  4141. }
  4142.  
  4143.  
  4144. int ProximityY(item a, int b) {
  4145.     if ( a->Y > ComboY(b) ) return a->Y - ComboY(b);
  4146.     else return ComboY(b) - a->Y;
  4147. }
  4148.  
  4149. int ProximityY(int b, int a) {
  4150.     if ( ComboY(a) > ComboY(b) ) return ComboY(a) - ComboY(b);
  4151.     else return ComboY(b) - ComboY(a);
  4152. }
  4153.  
  4154. int ProximityY(ffc a) {
  4155.     if ( a->Y > Link->Y ) return a->Y - Link->Y;
  4156.     else return Link->Y - a->Y;
  4157. }
  4158.  
  4159. int ProximityY(lweapon a) {
  4160.     if ( a->Y > Link->Y ) return a->Y - Link->Y;
  4161.     else return Link->Y - a->Y;
  4162. }
  4163.  
  4164. int ProximityY(eweapon a) {
  4165.     if ( a->Y > Link->Y ) return a->Y - Link->Y;
  4166.     else return Link->Y - a->Y;
  4167. }
  4168.  
  4169. int ProximityY(npc a) {
  4170.     if ( a->Y > Link->Y ) return a->Y - Link->Y;
  4171.     else return Link->Y - a->Y;
  4172. }
  4173.  
  4174. int ProximityY(item a) {
  4175.     if ( a->Y > Link->Y ) return a->Y - Link->Y;
  4176.     else return Link->Y - a->Y;
  4177. }
  4178.  
  4179. int ProximityY(int a) {
  4180.     int ay = ComboY(a);
  4181.     if ( ay > Link->Y ) return ay - Link->Y;
  4182.     else return Link->Y - ay;
  4183. }
  4184.  
  4185. //ProximityX also needs a precise variation.
  4186.  
  4187. //Proximity from centre of object's hitbox:
  4188. int ProximityX(ffc a, ffc b, bool fromcentre ) {
  4189.     if ( fromcentre ) {
  4190.         int ax = CenterX(a);
  4191.         int bx = CenterX(b);
  4192.         if ( ax > bx ) return ax - bx;
  4193.         else return bx - ax;
  4194.     }
  4195.     else {
  4196.         if ( a->X > b->X ) return a->X - b->X;
  4197.         else return b->X - a->X;
  4198.     }
  4199. }
  4200.  
  4201. //Rid these of varible declaration inefficiency?
  4202. int ProximityX(ffc a, lweapon b, bool fromcentre ) {
  4203.     if ( fromcentre ) {
  4204.         int ax = CenterX(a);
  4205.         int bx = CenterX(b,true);
  4206.         if ( ax > bx ) return ax - bx;
  4207.         else return bx - ax;
  4208.     }
  4209.     else {
  4210.         if ( a->X > b->X ) return a->X - b->X;
  4211.         else return b->X - a->X;
  4212.     }
  4213. }
  4214.  
  4215.  
  4216. int ProximityX(ffc a, eweapon b, bool fromcentre ) {
  4217.     if ( fromcentre ) {
  4218.         int ax = CenterX(a);
  4219.         int bx = CenterX(b,true);
  4220.         if ( ax > bx ) return ax - bx;
  4221.         else return bx - ax;
  4222.     }
  4223.     else {
  4224.         if ( a->X > b->X ) return a->X - b->X;
  4225.         else return b->X - a->X;
  4226.     }
  4227. }
  4228.    
  4229.  
  4230. int ProximityX(ffc a, npc b, bool fromcentre ) {
  4231.     if ( fromcentre ) {
  4232.         int ax = CenterX(a);
  4233.         int bx = CenterX(b,true);
  4234.         if ( ax > bx ) return ax - bx;
  4235.         else return bx - ax;
  4236.     }
  4237.     else {
  4238.         if ( a->X > b->X ) return a->X - b->X;
  4239.         else return b->X - a->X;
  4240.     }
  4241. }
  4242.  
  4243.  
  4244. int ProximityX(ffc a, item b, bool fromcentre ) {
  4245.     if ( fromcentre ) {
  4246.         int ax = CenterX(a);
  4247.         int bx = CenterX(b,true);
  4248.         if ( ax > bx ) return ax - bx;
  4249.         else return bx - ax;
  4250.     }
  4251.     else {
  4252.         if ( a->X > b->X ) return a->X - b->X;
  4253.         else return b->X - a->X;
  4254.     }
  4255. }
  4256.  
  4257.  
  4258. int ProximityX(lweapon a, ffc b, bool fromcentre ) {
  4259.     if ( fromcentre ) {
  4260.         int ax = CenterX(a,true);
  4261.         int bx = CenterX(b);
  4262.         if ( ax > bx ) return ax - bx;
  4263.         else return bx - ax;
  4264.     }
  4265.     else {
  4266.         if ( a->X > b->X ) return a->X - b->X;
  4267.         else return b->X - a->X;
  4268.     }
  4269. }
  4270.  
  4271. int ProximityX(lweapon a, lweapon b, bool fromcentre ) {
  4272.     if ( fromcentre ) {
  4273.         int ax = CenterX(a,true);
  4274.         int bx = CenterX(b,true);
  4275.         if ( ax > bx ) return ax - bx;
  4276.         else return bx - ax;
  4277.     }
  4278.     else {
  4279.         if ( a->X > b->X ) return a->X - b->X;
  4280.         else return b->X - a->X;
  4281.     }
  4282. }
  4283.  
  4284. int ProximityX(lweapon a, eweapon b, bool fromcentre ) {
  4285.     if ( fromcentre ) {
  4286.         int ax = CenterX(a,true);
  4287.         int bx = CenterX(b,true);
  4288.         if ( ax > bx ) return ax - bx;
  4289.         else return bx - ax;
  4290.     }
  4291.     else {
  4292.         if ( a->X > b->X ) return a->X - b->X;
  4293.         else return b->X - a->X;
  4294.     }
  4295. }
  4296.  
  4297. int ProximityX(lweapon a, npc b, bool fromcentre ) {
  4298.     if ( fromcentre ) {
  4299.         int ax = CenterX(a,true);
  4300.         int bx = CenterX(b,true);
  4301.         if ( ax > bx ) return ax - bx;
  4302.         else return bx - ax;
  4303.     }
  4304.     else {
  4305.         if ( a->X > b->X ) return a->X - b->X;
  4306.         else return b->X - a->X;
  4307.     }
  4308. }
  4309.  
  4310. int ProximityX(lweapon a, item b, bool fromcentre ) {
  4311.     if ( fromcentre ) {
  4312.         int ax = CenterX(a,true);
  4313.         int bx = CenterX(b,true);
  4314.         if ( ax > bx ) return ax - bx;
  4315.         else return bx - ax;
  4316.     }
  4317.     else {
  4318.         if ( a->X > b->X ) return a->X - b->X;
  4319.         else return b->X - a->X;
  4320.     }
  4321. }
  4322.  
  4323. int ProximityX(eweapon a, ffc b, bool fromcentre ) {
  4324.     if ( fromcentre ) {
  4325.         int ax = CenterX(a,true);
  4326.         int bx = CenterX(b);
  4327.         if ( ax > bx ) return ax - bx;
  4328.         else return bx - ax;
  4329.     }
  4330.     else {
  4331.         if ( a->X > b->X ) return a->X - b->X;
  4332.         else return b->X - a->X;
  4333.     }
  4334. }
  4335.  
  4336. int ProximityX(eweapon a, lweapon b, bool fromcentre ) {
  4337.     if ( fromcentre ) {
  4338.         int ax = CenterX(a,true);
  4339.         int bx = CenterX(b,true);
  4340.         if ( ax > bx ) return ax - bx;
  4341.         else return bx - ax;
  4342.     }
  4343.     else {
  4344.         if ( a->X > b->X ) return a->X - b->X;
  4345.         else return b->X - a->X;
  4346.     }
  4347. }
  4348.  
  4349. int ProximityX(eweapon a, eweapon b, bool fromcentre ) {
  4350.     if ( fromcentre ) {
  4351.         int ax = CenterX(a,true);
  4352.         int bx = CenterX(b,true);
  4353.         if ( ax > bx ) return ax - bx;
  4354.         else return bx - ax;
  4355.     }
  4356.     else {
  4357.         if ( a->X > b->X ) return a->X - b->X;
  4358.         else return b->X - a->X;
  4359.     }
  4360. }
  4361.  
  4362. int ProximityX(eweapon a, npc b, bool fromcentre ) {
  4363.     if ( fromcentre ) {
  4364.         int ax = CenterX(a,true);
  4365.         int bx = CenterX(b,true);
  4366.         if ( ax > bx ) return ax - bx;
  4367.         else return bx - ax;
  4368.     }
  4369.     else {
  4370.         if ( a->X > b->X ) return a->X - b->X;
  4371.         else return b->X - a->X;
  4372.     }
  4373. }
  4374.  
  4375. int ProximityX(eweapon a, item b, bool fromcentre ) {
  4376.     if ( fromcentre ) {
  4377.         int ax = CenterX(a,true);
  4378.         int bx = CenterX(b,true);
  4379.         if ( ax > bx ) return ax - bx;
  4380.         else return bx - ax;
  4381.     }
  4382.     else {
  4383.         if ( a->X > b->X ) return a->X - b->X;
  4384.         else return b->X - a->X;
  4385.     }
  4386. }
  4387.  
  4388. int ProximityX(npc a, ffc b, bool fromcentre ) {
  4389.     if ( fromcentre ) {
  4390.         int ax = CenterX(a,true);
  4391.         int bx = CenterX(b);
  4392.         if ( ax > bx ) return ax - bx;
  4393.         else return bx - ax;
  4394.     }
  4395.     else {
  4396.         if ( a->X > b->X ) return a->X - b->X;
  4397.         else return b->X - a->X;
  4398.     }
  4399. }
  4400.  
  4401. int ProximityX(npc a, lweapon b, bool fromcentre ) {
  4402.     if ( fromcentre ) {
  4403.         int ax = CenterX(a,true);
  4404.         int bx = CenterX(b,true);
  4405.         if ( ax > bx ) return ax - bx;
  4406.         else return bx - ax;
  4407.     }
  4408.     else {
  4409.         if ( a->X > b->X ) return a->X - b->X;
  4410.         else return b->X - a->X;
  4411.     }
  4412. }
  4413.  
  4414. int ProximityX(npc a, eweapon b, bool fromcentre ) {
  4415.     if ( fromcentre ) {
  4416.         int ax = CenterX(a,true);
  4417.         int bx = CenterX(b,true);
  4418.         if ( ax > bx ) return ax - bx;
  4419.         else return bx - ax;
  4420.     }
  4421.     else {
  4422.         if ( a->X > b->X ) return a->X - b->X;
  4423.         else return b->X - a->X;
  4424.     }
  4425. }
  4426.  
  4427. int ProximityX(npc a, npc b, bool fromcentre ) {
  4428.     if ( fromcentre ) {
  4429.         int ax = CenterX(a,true);
  4430.         int bx = CenterX(b,true);
  4431.         if ( ax > bx ) return ax - bx;
  4432.         else return bx - ax;
  4433.     }
  4434.     else {
  4435.         if ( a->X > b->X ) return a->X - b->X;
  4436.         else return b->X - a->X;
  4437.     }
  4438. }
  4439.  
  4440. int ProximityX(npc a, item b, bool fromcentre ) {
  4441.     if ( fromcentre ) {
  4442.         int ax = CenterX(a,true);
  4443.         int bx = CenterX(b,true);
  4444.         if ( ax > bx ) return ax - bx;
  4445.         else return bx - ax;
  4446.     }
  4447.     else {
  4448.         if ( a->X > b->X ) return a->X - b->X;
  4449.         else return b->X - a->X;
  4450.     }
  4451. }
  4452.  
  4453. int ProximityX(item a, ffc b, bool fromcentre ) {
  4454.     if ( fromcentre ) {
  4455.         int ax = CenterX(a,true);
  4456.         int bx = CenterX(b);
  4457.         if ( ax > bx ) return ax - bx;
  4458.         else return bx - ax;
  4459.     }
  4460.     else {
  4461.         if ( a->X > b->X ) return a->X - b->X;
  4462.         else return b->X - a->X;
  4463.     }
  4464. }
  4465. int ProximityX(item a, lweapon b, bool fromcentre ) {
  4466.     if ( fromcentre ) {
  4467.         int ax = CenterX(a,true);
  4468.         int bx = CenterX(b,true);
  4469.         if ( ax > bx ) return ax - bx;
  4470.         else return bx - ax;
  4471.     }
  4472.     else {
  4473.         if ( a->X > b->X ) return a->X - b->X;
  4474.         else return b->X - a->X;
  4475.     }
  4476. }
  4477.  
  4478. int ProximityX(item a, eweapon b, bool fromcentre ) {
  4479.     if ( fromcentre ) {
  4480.         int ax = CenterX(a,true);
  4481.         int bx = CenterX(b,true);
  4482.         if ( ax > bx ) return ax - bx;
  4483.         else return bx - ax;
  4484.     }
  4485.     else {
  4486.         if ( a->X > b->X ) return a->X - b->X;
  4487.         else return b->X - a->X;
  4488.     }
  4489. }
  4490.  
  4491. int ProximityX(item a, npc b, bool fromcentre ) {
  4492.     if ( fromcentre ) {
  4493.         int ax = CenterX(a,true);
  4494.         int bx = CenterX(b,true);
  4495.         if ( ax > bx ) return ax - bx;
  4496.         else return bx - ax;
  4497.     }
  4498.     else {
  4499.         if ( a->X > b->X ) return a->X - b->X;
  4500.         else return b->X - a->X;
  4501.     }
  4502. }
  4503.  
  4504. int ProximityX(item a, item b, bool fromcentre ) {
  4505.     if ( fromcentre ) {
  4506.         int ax = CenterX(a,true);
  4507.         int bx = CenterX(b,true);
  4508.         if ( ax > bx ) return ax - bx;
  4509.         else return bx - ax;
  4510.     }
  4511.     else {
  4512.         if ( a->X > b->X ) return a->X - b->X;
  4513.         else return b->X - a->X;
  4514.     }
  4515. }
  4516.  
  4517.  
  4518.  
  4519. //Are multiple function calls less efficient than setting these once as local vars?
  4520. //int ProximityX(ffc a) {
  4521. //  if ( CenterX(a) > CenterLinkX() ) return CenterX(a) - CenterLinkX();
  4522. //  else return CenterLinkX() - CenterX(a);
  4523. //}
  4524.  
  4525.  
  4526.  
  4527.  
  4528. int ProximityY(ffc a, ffc b, bool fromcentre ) {
  4529.     if ( fromcentre ) {
  4530.         int ax = CenterY(a);
  4531.         int bx = CenterY(b);
  4532.         if ( ax > bx ) return ax - bx;
  4533.         else return bx - ax;
  4534.     }
  4535.     else {
  4536.         if ( a->X > b->X ) return a->X - b->X;
  4537.         else return b->X - a->X;
  4538.     }
  4539. }
  4540.  
  4541.  
  4542. int ProximityY(ffc a, lweapon b, bool fromcentre ) {
  4543.     if ( fromcentre ) {
  4544.         int ax = CenterY(a);
  4545.         int bx = CenterY(b,true);
  4546.         if ( ax > bx ) return ax - bx;
  4547.         else return bx - ax;
  4548.     }
  4549.     else {
  4550.         if ( a->X > b->X ) return a->X - b->X;
  4551.         else return b->X - a->X;
  4552.     }
  4553. }
  4554.  
  4555.  
  4556. int ProximityY(ffc a, eweapon b, bool fromcentre ) {
  4557.     if ( fromcentre ) {
  4558.         int ax = CenterY(a);
  4559.         int bx = CenterY(b,true);
  4560.         if ( ax > bx ) return ax - bx;
  4561.         else return bx - ax;
  4562.     }
  4563.     else {
  4564.         if ( a->X > b->X ) return a->X - b->X;
  4565.         else return b->X - a->X;
  4566.     }
  4567. }
  4568.    
  4569.  
  4570. int ProximityY(ffc a, npc b, bool fromcentre ) {
  4571.     if ( fromcentre ) {
  4572.         int ax = CenterY(a);
  4573.         int bx = CenterY(b,true);
  4574.         if ( ax > bx ) return ax - bx;
  4575.         else return bx - ax;
  4576.     }
  4577.     else {
  4578.         if ( a->X > b->X ) return a->X - b->X;
  4579.         else return b->X - a->X;
  4580.     }
  4581. }
  4582.  
  4583. int ProximityY(ffc a, item b, bool fromcentre ) {
  4584.     if ( fromcentre ) {
  4585.         int ax = CenterY(a);
  4586.         int bx = CenterY(b,true);
  4587.         if ( ax > bx ) return ax - bx;
  4588.         else return bx - ax;
  4589.     }
  4590.     else {
  4591.         if ( a->X > b->X ) return a->X - b->X;
  4592.         else return b->X - a->X;
  4593.     }
  4594. }
  4595.  
  4596.  
  4597. int ProximityY(lweapon a, ffc b, bool fromcentre ) {
  4598.     if ( fromcentre ) {
  4599.         int ax = CenterY(a,true);
  4600.         int bx = CenterY(b);
  4601.         if ( ax > bx ) return ax - bx;
  4602.         else return bx - ax;
  4603.     }
  4604.     else {
  4605.         if ( a->X > b->X ) return a->X - b->X;
  4606.         else return b->X - a->X;
  4607.     }
  4608. }
  4609.  
  4610. int ProximityY(lweapon a, lweapon b, bool fromcentre ) {
  4611.     if ( fromcentre ) {
  4612.         int ax = CenterY(a,true);
  4613.         int bx = CenterY(b,true);
  4614.         if ( ax > bx ) return ax - bx;
  4615.         else return bx - ax;
  4616.     }
  4617.     else {
  4618.         if ( a->X > b->X ) return a->X - b->X;
  4619.         else return b->X - a->X;
  4620.     }
  4621. }
  4622.  
  4623. int ProximityY(lweapon a, eweapon b, bool fromcentre ) {
  4624.     if ( fromcentre ) {
  4625.         int ax = CenterY(a,true);
  4626.         int bx = CenterY(b,true);
  4627.         if ( ax > bx ) return ax - bx;
  4628.         else return bx - ax;
  4629.     }
  4630.     else {
  4631.         if ( a->X > b->X ) return a->X - b->X;
  4632.         else return b->X - a->X;
  4633.     }
  4634. }
  4635.  
  4636. int ProximityY(lweapon a, npc b, bool fromcentre ) {
  4637.     if ( fromcentre ) {
  4638.         int ax = CenterY(a,true);
  4639.         int bx = CenterY(b,true);
  4640.         if ( ax > bx ) return ax - bx;
  4641.         else return bx - ax;
  4642.     }
  4643.     else {
  4644.         if ( a->X > b->X ) return a->X - b->X;
  4645.         else return b->X - a->X;
  4646.     }
  4647. }
  4648.  
  4649. int ProximityY(lweapon a, item b, bool fromcentre ) {
  4650.     if ( fromcentre ) {
  4651.         int ax = CenterY(a,true);
  4652.         int bx = CenterY(b,true);
  4653.         if ( ax > bx ) return ax - bx;
  4654.         else return bx - ax;
  4655.     }
  4656.     else {
  4657.         if ( a->X > b->X ) return a->X - b->X;
  4658.         else return b->X - a->X;
  4659.     }
  4660. }
  4661.  
  4662. int ProximityY(eweapon a, ffc b, bool fromcentre ) {
  4663.     if ( fromcentre ) {
  4664.         int ax = CenterY(a,true);
  4665.         int bx = CenterY(b);
  4666.         if ( ax > bx ) return ax - bx;
  4667.         else return bx - ax;
  4668.     }
  4669.     else {
  4670.         if ( a->X > b->X ) return a->X - b->X;
  4671.         else return b->X - a->X;
  4672.     }
  4673. }
  4674.  
  4675. int ProximityY(eweapon a, lweapon b, bool fromcentre ) {
  4676.     if ( fromcentre ) {
  4677.         int ax = CenterY(a,true);
  4678.         int bx = CenterY(b,true);
  4679.         if ( ax > bx ) return ax - bx;
  4680.         else return bx - ax;
  4681.     }
  4682.     else {
  4683.         if ( a->X > b->X ) return a->X - b->X;
  4684.         else return b->X - a->X;
  4685.     }
  4686. }
  4687.  
  4688. int ProximityY(eweapon a, eweapon b, bool fromcentre ) {
  4689.     if ( fromcentre ) {
  4690.         int ax = CenterY(a,true);
  4691.         int bx = CenterY(b,true);
  4692.         if ( ax > bx ) return ax - bx;
  4693.         else return bx - ax;
  4694.     }
  4695.     else {
  4696.         if ( a->X > b->X ) return a->X - b->X;
  4697.         else return b->X - a->X;
  4698.     }
  4699. }
  4700.  
  4701. int ProximityY(eweapon a, npc b, bool fromcentre ) {
  4702.     if ( fromcentre ) {
  4703.         int ax = CenterY(a,true);
  4704.         int bx = CenterY(b,true);
  4705.         if ( ax > bx ) return ax - bx;
  4706.         else return bx - ax;
  4707.     }
  4708.     else {
  4709.         if ( a->X > b->X ) return a->X - b->X;
  4710.         else return b->X - a->X;
  4711.     }
  4712. }
  4713.  
  4714. int ProximityY(eweapon a, item b, bool fromcentre ) {
  4715.     if ( fromcentre ) {
  4716.         int ax = CenterY(a,true);
  4717.         int bx = CenterY(b,true);
  4718.         if ( ax > bx ) return ax - bx;
  4719.         else return bx - ax;
  4720.     }
  4721.     else {
  4722.         if ( a->X > b->X ) return a->X - b->X;
  4723.         else return b->X - a->X;
  4724.     }
  4725. }
  4726.  
  4727. int ProximityY(npc a, ffc b, bool fromcentre ) {
  4728.     if ( fromcentre ) {
  4729.         int ax = CenterY(a,true);
  4730.         int bx = CenterY(b);
  4731.         if ( ax > bx ) return ax - bx;
  4732.         else return bx - ax;
  4733.     }
  4734.     else {
  4735.         if ( a->X > b->X ) return a->X - b->X;
  4736.         else return b->X - a->X;
  4737.     }
  4738. }
  4739. int ProximityY(npc a, lweapon b, bool fromcentre ) {
  4740.     if ( fromcentre ) {
  4741.         int ax = CenterY(a,true);
  4742.         int bx = CenterY(b,true);
  4743.         if ( ax > bx ) return ax - bx;
  4744.         else return bx - ax;
  4745.     }
  4746.     else {
  4747.         if ( a->X > b->X ) return a->X - b->X;
  4748.         else return b->X - a->X;
  4749.     }
  4750. }
  4751.  
  4752. int ProximityY(npc a, eweapon b, bool fromcentre ) {
  4753.     if ( fromcentre ) {
  4754.         int ax = CenterY(a,true);
  4755.         int bx = CenterY(b,true);
  4756.         if ( ax > bx ) return ax - bx;
  4757.         else return bx - ax;
  4758.     }
  4759.     else {
  4760.         if ( a->X > b->X ) return a->X - b->X;
  4761.         else return b->X - a->X;
  4762.     }
  4763. }
  4764.  
  4765. int ProximityY(npc a, npc b, bool fromcentre ) {
  4766.     if ( fromcentre ) {
  4767.         int ax = CenterY(a,true);
  4768.         int bx = CenterY(b,true);
  4769.         if ( ax > bx ) return ax - bx;
  4770.         else return bx - ax;
  4771.     }
  4772.     else {
  4773.         if ( a->X > b->X ) return a->X - b->X;
  4774.         else return b->X - a->X;
  4775.     }
  4776. }
  4777. int ProximityY(npc a, item b, bool fromcentre ) {
  4778.     if ( fromcentre ) {
  4779.         int ax = CenterY(a,true);
  4780.         int bx = CenterY(b,true);
  4781.         if ( ax > bx ) return ax - bx;
  4782.         else return bx - ax;
  4783.     }
  4784.     else {
  4785.         if ( a->X > b->X ) return a->X - b->X;
  4786.         else return b->X - a->X;
  4787.     }
  4788. }
  4789.  
  4790.  
  4791. int ProximityY(item a, ffc b, bool fromcentre ) {
  4792.     if ( fromcentre ) {
  4793.         int ax = CenterY(a,true);
  4794.         int bx = CenterY(b);
  4795.         if ( ax > bx ) return ax - bx;
  4796.         else return bx - ax;
  4797.     }
  4798.     else {
  4799.         if ( a->X > b->X ) return a->X - b->X;
  4800.         else return b->X - a->X;
  4801.     }
  4802. }
  4803.  
  4804. int ProximityY(item a, lweapon b, bool fromcentre ) {
  4805.     if ( fromcentre ) {
  4806.         int ax = CenterY(a,true);
  4807.         int bx = CenterY(b,true);
  4808.         if ( ax > bx ) return ax - bx;
  4809.         else return bx - ax;
  4810.     }
  4811.     else {
  4812.         if ( a->X > b->X ) return a->X - b->X;
  4813.         else return b->X - a->X;
  4814.     }
  4815. }
  4816.  
  4817. int ProximityY(item a, eweapon b, bool fromcentre ) {
  4818.     if ( fromcentre ) {
  4819.         int ax = CenterY(a,true);
  4820.         int bx = CenterY(b,true);
  4821.         if ( ax > bx ) return ax - bx;
  4822.         else return bx - ax;
  4823.     }
  4824.     else {
  4825.         if ( a->X > b->X ) return a->X - b->X;
  4826.         else return b->X - a->X;
  4827.     }
  4828. }
  4829.  
  4830. int ProximityY(item a, npc b, bool fromcentre ) {
  4831.     if ( fromcentre ) {
  4832.         int ax = CenterY(a,true);
  4833.         int bx = CenterY(b,true);
  4834.         if ( ax > bx ) return ax - bx;
  4835.         else return bx - ax;
  4836.     }
  4837.     else {
  4838.         if ( a->X > b->X ) return a->X - b->X;
  4839.         else return b->X - a->X;
  4840.     }
  4841. }
  4842.  
  4843. int ProximityY(item a, item b, bool fromcentre ) {
  4844.     if ( fromcentre ) {
  4845.         int ax = CenterY(a,true);
  4846.         int bx = CenterY(b,true);
  4847.         if ( ax > bx ) return ax - bx;
  4848.         else return bx - ax;
  4849.     }
  4850.     else {
  4851.         if ( a->X > b->X ) return a->X - b->X;
  4852.         else return b->X - a->X;
  4853.     }
  4854. }
  4855.  
  4856. int ProximityX(ffc a, bool fromcentre) {
  4857.     int ax = CenterX(a);
  4858.     int lx = CenterLinkX();
  4859.     if ( fromcentre ) {
  4860.         if ( ax > lx ) return ax - lx;
  4861.         else return lx - ax;
  4862.     }
  4863.     else {
  4864.         if ( a->X > lx ) return a->X - lx;
  4865.         else return lx - a->X;
  4866.     }
  4867. }
  4868.  
  4869. int ProximityX(lweapon a, bool fromcentre) {
  4870.     int ax = CenterX(a);
  4871.     int lx = CenterLinkX();
  4872.     if ( fromcentre ) {
  4873.         if ( ax > lx ) return ax - lx;
  4874.         else return lx - ax;
  4875.     }
  4876.     else {
  4877.         if ( a->X > lx ) return a->X - lx;
  4878.         else return lx - a->X;
  4879.     }
  4880. }
  4881.  
  4882.  
  4883. int ProximityX(eweapon a, bool fromcentre) {
  4884.     int ax = CenterX(a);
  4885.     int lx = CenterLinkX();
  4886.     if ( fromcentre ) {
  4887.         if ( ax > lx ) return ax - lx;
  4888.         else return lx - ax;
  4889.     }
  4890.     else {
  4891.         if ( a->X > lx ) return a->X - lx;
  4892.         else return lx - a->X;
  4893.     }
  4894. }
  4895.  
  4896.  
  4897. int ProximityX(npc a, bool fromcentre) {
  4898.     int ax = CenterX(a);
  4899.     int lx = CenterLinkX();
  4900.     if ( fromcentre ) {
  4901.         if ( ax > lx ) return ax - lx;
  4902.         else return lx - ax;
  4903.     }
  4904.     else {
  4905.         if ( a->X > lx ) return a->X - lx;
  4906.         else return lx - a->X;
  4907.     }
  4908. }
  4909.  
  4910.  
  4911. int ProximityX(item a, bool fromcentre) {
  4912.     int ax = CenterX(a);
  4913.     int lx = CenterLinkX();
  4914.     if ( fromcentre ) {
  4915.         if ( ax > lx ) return ax - lx;
  4916.         else return lx - ax;
  4917.     }
  4918.     else {
  4919.         if ( a->X > lx ) return a->X - lx;
  4920.         else return lx - a->X;
  4921.     }
  4922. }
  4923.  
  4924.  
  4925.  
  4926. int ProximityY(ffc a, bool fromcentre) {
  4927.     int ay = CenterY(a);
  4928.     int ly = CenterLinkY();
  4929.     if ( fromcentre ) {
  4930.         if ( ay > ly ) return ay - ly;
  4931.         else return ly - ay;
  4932.     }
  4933.     else {
  4934.         if ( a->Y > ly ) return a->Y - ly;
  4935.         else return a->Y - ly;
  4936.     }
  4937. }
  4938.  
  4939. int ProximityY(lweapon a, bool fromcentre) {
  4940.     int ay = CenterY(a);
  4941.     int ly = CenterLinkY();
  4942.     if ( fromcentre ) {
  4943.         if ( ay > ly ) return ay - ly;
  4944.         else return ly - ay;
  4945.     }
  4946.     else {
  4947.         if ( a->Y > ly ) return a->Y - ly;
  4948.         else return a->Y - ly;
  4949.     }
  4950. }
  4951.  
  4952.  
  4953. int ProximityY(eweapon a, bool fromcentre) {
  4954.     int ay = CenterY(a);
  4955.     int ly = CenterLinkY();
  4956.     if ( fromcentre ) {
  4957.         if ( ay > ly ) return ay - ly;
  4958.         else return ly - ay;
  4959.     }
  4960.     else {
  4961.         if ( a->Y > ly ) return a->Y - ly;
  4962.         else return a->Y - ly;
  4963.     }
  4964. }
  4965.  
  4966.  
  4967. int ProximityY(npc a, bool fromcentre) {
  4968.     int ay = CenterY(a);
  4969.     int ly = CenterLinkY();
  4970.     if ( fromcentre ) {
  4971.         if ( ay > ly ) return ay - ly;
  4972.         else return ly - ay;
  4973.     }
  4974.     else {
  4975.         if ( a->Y > ly ) return a->Y - ly;
  4976.         else return a->Y - ly;
  4977.     }
  4978. }
  4979.  
  4980.  
  4981. int ProximityY(item a, bool fromcentre) {
  4982.     int ay = CenterY(a);
  4983.     int ly = CenterLinkY();
  4984.     if ( fromcentre ) {
  4985.         if ( ay > ly ) return ay - ly;
  4986.         else return ly - ay;
  4987.     }
  4988.     else {
  4989.         if ( a->Y > ly ) return a->Y - ly;
  4990.         else return a->Y - ly;
  4991.     }
  4992. }
  4993.  
  4994.  
  4995.  
  4996. ///Proximity between *ptr and combo.
  4997.  
  4998. int ProximityX(int a, ffc b, bool fromcentre ) {
  4999.     if ( fromcentre ) {
  5000.         int ax = CenterComboX(a);
  5001.         int bx = CenterX(b);
  5002.         if ( ax > bx ) return ax - bx;
  5003.         else return bx - ax;
  5004.     }
  5005.     else {
  5006.         if ( ComboX(a) > b->X ) return ComboX(a) - b->X;
  5007.         else return b->X - ComboX(a);
  5008.     }
  5009. }
  5010.  
  5011. int ProximityX(int a, lweapon b, bool fromcentre ) {
  5012.     if ( fromcentre ) {
  5013.         int ax = CenterComboX(a);
  5014.         int bx = CenterX(b,true);
  5015.         if ( ax > bx ) return ax - bx;
  5016.         else return bx - ax;
  5017.     }
  5018.     else {
  5019.         if ( ComboX(a) > b->X ) return ComboX(a) - b->X;
  5020.         else return b->X - ComboX(a);
  5021.     }
  5022. }
  5023.  
  5024. int ProximityX(int a, eweapon b, bool fromcentre ) {
  5025.     if ( fromcentre ) {
  5026.         int ax = CenterComboX(a);
  5027.         int bx = CenterX(b,true);
  5028.         if ( ax > bx ) return ax - bx;
  5029.         else return bx - ax;
  5030.     }
  5031.     else {
  5032.         if ( ComboX(a) > b->X ) return ComboX(a) - b->X;
  5033.         else return b->X - ComboX(a);
  5034.     }
  5035. }
  5036.  
  5037. int ProximityX(int a, npc b, bool fromcentre ) {
  5038.     if ( fromcentre ) {
  5039.         int ax = CenterComboX(a);
  5040.         int bx = CenterX(b,true);
  5041.         if ( ax > bx ) return ax - bx;
  5042.         else return bx - ax;
  5043.     }
  5044.     else {
  5045.         if ( ComboX(a) > b->X ) return ComboX(a) - b->X;
  5046.         else return b->X - ComboX(a);
  5047.     }
  5048. }
  5049.  
  5050. int ProximityX(int a, item b, bool fromcentre ) {
  5051.     if ( fromcentre ) {
  5052.         int ax = CenterComboX(a);
  5053.         int bx = CenterX(b,true);
  5054.         if ( ax > bx ) return ax - bx;
  5055.         else return bx - ax;
  5056.     }
  5057.     else {
  5058.         if ( ComboX