#include <amxmod> 
#include <amxmisc> 
#include <string> 
#include <Vexd_Utilities> 

new beam, boom 

#define MAX_MINES   2 

new player_mines_ent[33][MAX_MINES] 
new player_mines_count[33] 




detonate_mine(iCurrent, iHit) { 

   new Float:vOrigin[3] 
   Entvars_Get_Vector(iCurrent, EV_VEC_origin, vOrigin) 

   message_begin(MSG_BROADCAST, SVC_TEMPENTITY) 
   write_byte(99) //99 = KillBeam 
   write_short(iCurrent) 
   message_end() 

   message_begin(MSG_BROADCAST, SVC_TEMPENTITY) 
   write_byte(3) 
   write_coord(floatround(vOrigin[0])) 
   write_coord(floatround(vOrigin[1])) 
   write_coord(floatround(vOrigin[2])) 
   write_short(boom) 
   write_byte(50) 
   write_byte(15) 
   write_byte(0) 
   message_end() 

   RadiusDamage(vOrigin, 1, 50) 

   new id,slot 
    
   //id = Entvars_Get_Edict(iCurrent, EV_ENT_owner) 
   RemoveEntity(iCurrent) 
    
    
    
    
    
   // clear this from the list of live tripmines 
   for (id=1;id<33;id++) { 
      for (slot=0;slot<MAX_MINES;slot++) { 
         if (player_mines_ent[id][slot] == iCurrent) { 
            player_mines_ent[id][slot] = -1 
            player_mines_count[id] = player_mines_count[id] - 1 
             
            if (iHit == -1) 
            { 
               client_print(id, print_chat, "[TripMines] Your mine has detonated.") 
            } else { 
               new szNetName[32] 
               Entvars_Get_String(iHit, EV_SZ_netname, szNetName, 32) 
               client_print(id, print_chat, "[TripMines] %s detonated your mine.",szNetName) 
            } 
             
            break 
         } 
      } 
   } 

} 




public Vexd_CreateMine(id,level,cid){ 


   new Status = get_cvar_num( "amx_tripmine" ) 
    
   if ( Status != 1  ){ 
      client_print(id, print_chat, "[Tripmines] Tripmines are not currently active.") 
      return PLUGIN_HANDLED 
   } 

    

   if(Entvars_Get_Int(id, EV_INT_deadflag) != 0) 
      return PLUGIN_HANDLED 
       
   if (is_user_alive(id) == 0) 
      return PLUGIN_HANDLED 
       
    
   if (player_mines_count[id] >= MAX_MINES) { 
      client_print(id, print_chat, "[Tripmines] Maximum mines have been deployed.") 
      return PLUGIN_HANDLED 
   } 

   new Float:vOrigin[3] 
   new Float:vAngles[3] 
   Entvars_Get_Vector(id, EV_VEC_origin, vOrigin) 
   Entvars_Get_Vector(id, EV_VEC_v_angle, vAngles) 

        new NewEnt 
        NewEnt = CreateEntity("info_target") 

        if(NewEnt == 0) { 
            return PLUGIN_HANDLED_MAIN 
        } 
        
        
        

   Entvars_Set_String(NewEnt, EV_SZ_classname, "vexd_tripmine") 
    
    
   Entvars_Set_Int(NewEnt, EV_INT_movetype, 5) //5 = movetype_fly, No grav, but collides. 
   Entvars_Set_Int(NewEnt, EV_INT_solid, 0) 

        ENT_SetModel(NewEnt, "models/v_tripmine.mdl") 
        
        
        Entvars_Set_Float(NewEnt, EV_FL_frame, 0.0) 
   Entvars_Set_Int(NewEnt, EV_INT_body, 3) 
   Entvars_Set_Int(NewEnt, EV_INT_sequence, 7)   // 7 = TRIPMINE_WORLD 
   Entvars_Set_Float(NewEnt, EV_FL_framerate, 0.0) 
    
   Entvars_Set_Float(NewEnt, EV_FL_takedamage, 1.0) 
   Entvars_Set_Float(NewEnt, EV_FL_dmg, 100.0) 
   Entvars_Set_Float(NewEnt, EV_FL_health, 5000.0) 
    
   Entvars_Set_Int(NewEnt, EV_INT_iuser2, 0) //0 Will be for inactive. 
    

   new Float:MinBox[3] 
   new Float:MaxBox[3] 

   MinBox[0] = -8.0 
   MinBox[1] = -8.0 
   MinBox[2] = -8.0 
   MaxBox[0] = 8.0 
   MaxBox[1] = 8.0 
   MaxBox[2] = 8.0 

   Entvars_Set_Vector(NewEnt, EV_VEC_mins, MinBox) 
   Entvars_Set_Vector(NewEnt, EV_VEC_maxs, MaxBox) 

   new Float:vNewOrigin[3] 
   new Float:vNormal[3] 
   new Float:vTraceDirection[3] 
   new Float:vTraceEnd[3] 
   new Float:vTraceResult[3] 
   new Float:vEntAngles[3] 

   VelocityByAim(id, 64, vTraceDirection) 
    
   vTraceEnd[0] = vTraceDirection[0] + vOrigin[0] 
   vTraceEnd[1] = vTraceDirection[1] + vOrigin[1] 
   vTraceEnd[2] = vTraceDirection[2] + vOrigin[2] 

   TraceLn(id, vOrigin, vTraceEnd, vTraceResult) 

   if(TraceNormal(id, vOrigin, vTraceEnd, vNormal) == 0) { 
      RemoveEntity(NewEnt) 
      client_print(id, print_chat, "[Tripmines] You must plant the tripmine on a wall!") 
      return PLUGIN_HANDLED_MAIN 
   } 
    
    
   new slot = 0; 
   for (slot = 0; slot < MAX_MINES; slot++) { 
      if (player_mines_ent[id][slot] == -1) 
         break; 
   } 
   if (slot >= MAX_MINES)  //unhandled error 
      return PLUGIN_HANDLED_MAIN 
       
        player_mines_ent[id][slot] = NewEnt 
   player_mines_count[id] = player_mines_count[id] + 1 

   vNewOrigin[0] = vTraceResult[0] + (vNormal[0] * 8.0) 
   vNewOrigin[1] = vTraceResult[1] + (vNormal[1] * 8.0) 
   vNewOrigin[2] = vTraceResult[2] + (vNormal[2] * 8.0) 

   ENT_SetOrigin(NewEnt, vNewOrigin) 
   VecToAngles(vNormal, vEntAngles) 

   Entvars_Set_Vector(NewEnt, EV_VEC_angles, vEntAngles) 


   new Float:vBeamEnd[3] 
   new Float:vTracedBeamEnd[3] 
   vBeamEnd[0] = vNewOrigin[0] + (vNormal[0] * 8192) 
   vBeamEnd[1] = vNewOrigin[1] + (vNormal[1] * 8192) 
   vBeamEnd[2] = vNewOrigin[2] + (vNormal[2] * 8192) 
   TraceLn(-1, vNewOrigin, vBeamEnd, vTracedBeamEnd) 
   Entvars_Set_Vector(NewEnt, EV_VEC_vuser1, vTracedBeamEnd) 

    
    
    

   emit_sound(NewEnt, CHAN_WEAPON, "weapons/mine_deploy.wav", 1.0, ATTN_NORM, 0, PITCH_NORM) 
   emit_sound(NewEnt, CHAN_VOICE, "weapons/mine_charge.wav", 1.0, ATTN_NORM, 0, PITCH_NORM) 

   new args[4] 
   num_to_str(NewEnt, args, 4) 

   set_task(3.0, "TripMineActivate", 0, args, 4) 

   return PLUGIN_HANDLED_MAIN 
} 

public TripMineActivate(MineID[]) { 
   new EntID = str_to_num(MineID) 
    
   new Float:vOrigin[3] 
   Entvars_Get_Vector(EntID, EV_VEC_origin, vOrigin) 

   new Float:vEnd[3] 
   Entvars_Get_Vector(EntID, EV_VEC_vuser1, vEnd) 

   message_begin(MSG_BROADCAST,SVC_TEMPENTITY) 
   write_byte(0) 
   write_coord(floatround(vOrigin[0])) 
   write_coord(floatround(vOrigin[1])) 
   write_coord(floatround(vOrigin[2])) 
   write_coord(floatround(vEnd[0])) //Random 
   write_coord(floatround(vEnd[1])) //Random 
   write_coord(floatround(vEnd[2])) //Random 
   write_short(beam) 
   write_byte(0) 
   write_byte(0) 
   write_byte(10) //Life 
   write_byte(5) //Width 
   write_byte(0) 
   write_byte(255) // r 
   write_byte(0) // g 
   write_byte(0) // b 
   write_byte(200) 
   write_byte(0) 
   message_end() 

   Entvars_Set_Int(EntID, EV_INT_iuser2, 1) //1 Will be for active. 
   Entvars_Set_Int(EntID, EV_INT_solid, 2) //1 Will be for active. 
    
   emit_sound(EntID, CHAN_VOICE, "weapons/mine_activate.wav", 1.0, ATTN_NORM, 0, PITCH_NORM) 
} 

public TripMineThink() { 
   new iCurrent 
   iCurrent = FindEntity(-1, "vexd_tripmine") 

   while(iCurrent != -1) { 
      if(Entvars_Get_Int(iCurrent, EV_INT_iuser2) == 1) { 
         new Float:vOrigin[3] 
         Entvars_Get_Vector(iCurrent, EV_VEC_origin, vOrigin) 

         new Float:vEnd[3] 
         Entvars_Get_Vector(iCurrent, EV_VEC_vuser1, vEnd) 

         new Float:vTrace[3] 
         new iHit 
         iHit = TraceLn(iCurrent, vOrigin, vEnd, vTrace) 
          
         new Float:health[1] 
          
         health[0] = Entvars_Get_Float(iCurrent, EV_FL_health) 
          
         if (health[0] < 5000) { 
            detonate_mine(iCurrent,-1) 
         } else { 

            if(iHit > 0 ) { 
               new szClassName[32] 
               Entvars_Get_String(iHit, EV_SZ_classname, szClassName, 32) 
                
               if(equal(szClassName, "player")) { 
                  detonate_mine(iCurrent,iHit) 
               } 
            } 
         } 
      } 

      iCurrent =  FindEntity(iCurrent, "vexd_tripmine") 
   } 
} 

public LaserThink() { 
   new iCurrent 
   iCurrent = FindEntity(-1, "vexd_tripmine") 

   while(iCurrent != -1) { 
      if(Entvars_Get_Int(iCurrent, EV_INT_iuser2) == 1) { 
         new Float:vOrigin[3] 
         Entvars_Get_Vector(iCurrent, EV_VEC_origin, vOrigin) 

         new Float:vEnd[3] 
         Entvars_Get_Vector(iCurrent, EV_VEC_vuser1, vEnd) 

         message_begin(MSG_BROADCAST,SVC_TEMPENTITY) 
         write_byte(0) 
         write_coord(floatround(vOrigin[0])) 
         write_coord(floatround(vOrigin[1])) 
         write_coord(floatround(vOrigin[2])) 
         write_coord(floatround(vEnd[0])) //Random 
         write_coord(floatround(vEnd[1])) //Random 
         write_coord(floatround(vEnd[2])) //Random 
         write_short(beam) 
         write_byte(0) 
         write_byte(0) 
         write_byte(10) //Life 
         write_byte(5) //Width 
         write_byte(0) 
         write_byte(255) // r 
         write_byte(0) // g 
         write_byte(0) // b 
         write_byte(50) 
         write_byte(0) 
         message_end() 
      } 

      iCurrent =  FindEntity(iCurrent, "vexd_tripmine") 
   } 
} 

public plugin_init(){ 
    register_plugin("Vexd Entity demo (TripMine)","1.01","default") 
    register_clcmd("amx_setmine","Vexd_CreateMine",0,"") 
    
    register_cvar( "amx_tripmine", "0", FCVAR_UNLOGGED ) 
    
    set_task(0.01, "TripMineThink", 0, "", 0, "b") 
    set_task(1.0, "LaserThink", 0, "", 0, "b") 
    
    return PLUGIN_CONTINUE 
} 

public client_connect(id){ 
    
   new j 
   for (j=0;j<MAX_MINES;j++) { 
      player_mines_ent[id][j] = -1 
      player_mines_count[id] = 0 
   } 
    
    
   return PLUGIN_CONTINUE 
} 

public client_disconnect(id){ 

   new j, iCurrent 
   player_mines_count[id] = 0 
    
   for (j=0;j<MAX_MINES;j++) { 
      if (player_mines_ent[id][j] != -1) { 
       
         iCurrent = player_mines_ent[id][j] 
       
         new Float:vOrigin[3] 
         Entvars_Get_Vector(iCurrent, EV_VEC_origin, vOrigin) 
          
         message_begin(MSG_BROADCAST, SVC_TEMPENTITY) 
         write_byte(99) //99 = KillBeam 
         write_short(iCurrent) 
         message_end() 
       
         message_begin(MSG_BROADCAST, SVC_TEMPENTITY) 
         write_byte(3) 
         write_coord(floatround(vOrigin[0])) 
         write_coord(floatround(vOrigin[1])) 
         write_coord(floatround(vOrigin[2])) 
         write_short(boom) 
         write_byte(50) 
         write_byte(15) 
         write_byte(0) 
         message_end() 
       
         RadiusDamage(vOrigin, 1, 50) 
       
         RemoveEntity(iCurrent) 
          
         player_mines_ent[id][j] = -1 
          
      } 
   } 
    
   return PLUGIN_CONTINUE 
} 

public plugin_precache() { 
   precache_sound("weapons/mine_deploy.wav") 
   precache_sound("weapons/mine_charge.wav") 
   precache_sound("weapons/mine_activate.wav") 
   precache_model("models/v_tripmine.mdl") 
   beam = precache_model("sprites/laserbeam.spr") 
   boom = precache_model("sprites/zerogxplode.spr") 

   return PLUGIN_CONTINUE 
}