Punish campers! xd

Version:

3.0

Added on:

04 Feb 2013 00:10

Tags:

Description:
Made a new version where you can define several rectangles to form one camp area (see id #3, the seekbox on semi).

Illustrating what tiles are marked:



It was a bit tricky to select the right ones, because when you jump into a tile above you your head (atleast as spaz) sticks into it a bit (the right outer side of the seekbox). I also made a small alteration to the comparison code, changing (xPos <= aCamp) to (xPos < aCamp). Not sure why it's better, but trial and error tells me that it is so.
/*
Punish campers xd! v2.0

changes v2.0:
-made non-rectangular camp areas possible

changes v1.1:
-had to recreate the onPlayer function, because it wouldn't work for clients :S
-moved a message out of isInCampArea()
-killed player with .kill() instead of .health=0 (thx cooba)

improvements needed:
-make it not needed to state maxcamp for every sub-area
-show time remaining in campspot (could be achieved with the timer functions, I assume)
-don't kill players if the game is stopped (the AngelScript implementation needs a new bool)
-the chat is sent as teamchat if the player last used teamchat
-you regain health if you die on purpose with flag xd
*/

/** script settings **/
const uint checkCampInterval=70;      //how often to check for camping (gameticks) 70 = one second
/*********************/

/** level settings: define camp areas **/
array<array<array<int>>> campArea = {
 /* A camparea is a rectangle referred to by its top left and bottom right corner
x,y -----------
    |         |
    |         |
    ----------- a,b                                                              */
//  camparea(x,y)  camparea(a,b)  allowed camp  id 
                                 // time(gameticks) (needed for new shapes)
  {{29,12},     {40,12},        {250},      {0}},        //camparea #0: on top of seek pu
  {{64,05},     {101,19},       {500},      {1}},        //camparea #1: the rf area
  {{30,49},     {64,56},     {250},      {2}},    //camparea #2: at carrot

  {{31,14},     {41,14},     {250},      {3}},     //camparea #3: rectangle1
  {{30,15},     {41,15},     {250},      {3}},     //camparea #3: rectangle2
  {{30,16},     {41,16},     {250},      {3}},     //camparea #3: rectangle3
  {{31,17},     {41,17},     {250},      {3}},     //camparea #3: rectangle4
  {{32,18},     {39,18},     {250},      {3}},     //camparea #3: rectangle5
  {{35,19},     {38,19},     {250},      {3}}     //camparea #3: rectangle6
};
//it doesn't seem like you can have mixed arrays in AS
//so we just put the strings in a separate array
array<string> campAreaName = {        
  "above seeks",              //camparea #0
  "in the rf area",              //camparea #1
  "at the carrot",              //camparea #2
  "in the seek box"              //camparea #3
};
/******** end of level settings ********/

/** script globals **/
uint campAreas = 0;
uint campAreasRealLength;
array<int> campTime;


void onLevelLoad() {
  campAreasRealLength = campArea.length();
  for (uint i=0; i < campAreasRealLength;i++) {
    campAreas = campArea[i][3][0];
  }
  campAreas++;
  campTime.resize(campAreas);
}

/********************/


/** This function checks if a player is in a certain camparea        **/
/** and returns two bools: 1) whether the player is in the camp area **/
/** and 2) whether they have been there for too long                 **/
array<bool> isInCampArea(int pID, int camparea) {  //use an array<bool> to return multiple bools
  //if (camparea == 3) jjDebug("checking area #" +  formatInt(camparea,"l"));
  array<bool> returnThis = {false, false};      //we assume that the player is not camping 
                                                                   //      (and not for too long)

  int maxCamp;
  int xPos = jjPlayers[pID].xPos / 32;
  int yPos = jjPlayers[pID].yPos / 32;
  campTime[camparea] += checkCampInterval;                  //update camptime
                          
  for (uint j=0; j < campAreasRealLength;j++) {        
    if (campArea[j][3][0] == camparea)  {      //all parts of the camp area
      //jjDebug("camp #" + formatInt(j,"l"));
      maxCamp = campArea[j][2][0];        //store a bunch of information in temporary                                  
      int xCamp = campArea[j][0][0];        //variables for easier reading
      int aCamp = campArea[j][1][0];
      int yCamp = campArea[j][0][1];
      int bCamp = campArea[j][1][1];
      
      if ((xPos >= xCamp)&&(xPos < aCamp)&&(yPos >= yCamp)&&(yPos <= bCamp)) {   //is player in camparea?
         returnThis[0] = true;                             //set bool is camping
      }
      
      }
  }
  
  
  if (!returnThis[0]) {
    campTime[camparea] = 0;                          //player not camping -> reset timer
    //if (camparea == 3) jjDebug("not camping #" + formatInt(camparea,"l"));
  }
  /*else {
    if (camparea == 3)jjDebug("is camping" + formatInt(camparea,"l"));
  }*/
  if (maxCamp < campTime[camparea]) {                                        
    returnThis[1] = true;                           //set bool camped for too long
  }
  
  
  
  
  
  return returnThis;                                //return the (possibly altered) bool
}

/** onPlayer wouldn't work for me ;S **/
void realOnPlayer(int pID) {
  if (jjGameTicks % checkCampInterval == 0) {                      //(thanks Artem/Foly)
    for (uint i=0; i < campAreas;i++) {                        //loop through all camp areas
        //^uint to avoid warning "Signed/Unsigned mismatch"
      array<bool> isCamping = isInCampArea(pID, i);                //check player and area, store result
      if (isCamping[0]) {                              //is current player in camparea #1?
        jjPlayers[pID].showText("You are camping " + campAreaName[i]);       //display text (looks stupid if
                                              // camping is checked too often)
        if (isCamping[1]) {                             //has current player been there for too long?
        
          /** WHAT SHOULD HAPPEN IF THE PLAYER CAMPS FOR TOO LONG??? **/
          jjChat("I camped for too long " + campAreaName[i] + ". Now I die :c");
          jjPlayers[pID].kill();                        //kill the player
          campTime[i] = 0;                          //reset timer
          /**                          ^-^                           **/ 
          
        }
      }
    }
  }
}
void onMain() {
  /** emulating onPlayer **/
  for (uint i=0; i < 32;i++) {
    if ((jjPlayers[i].isActive)&&(jjPlayers[i].isLocal)) realOnPlayer(i);
  }
  /************************/
}