/* Plugin generated by AMXX-Studio */

#include <amxmodx>
#include <fakemeta>
#include <engine>
#include <hamsandwich>
#include <zombieplague>


#define PLUGIN "FG-Launcher"
#define VERSION "0.1"
#define AUTHOR "Barney"

#define bpammo 40
#define clipammo 10
#define damage 80
#define fgl "weapon_mp5navy"
#define CSW_FGLAUNCHER CSW_MP5NAVY
#define v_model "models/v_fglauncher.mdl"
#define p_model "models/p_fglauncher.mdl"
#define w_model "models/w_fglauncher.mdl"
#define s_model "models/s_fglauncher.mdl"
#define spark_sprite1 "sprites/spark2.spr"
#define spark_sprite2 "sprites/spark3.spr"
#define shoot_sound "weapons/fglauncher-1.wav"

/*	natives	*/
native give_item(index, const item[]);
native cs_get_user_bpammo(index, weapon);
native cs_set_user_bpammo(index, weapon, amount);
native cs_get_weapon_ammo(index);
native cs_set_weapon_ammo(index, newammo);
/*	---	*/


new bool:gHasFg[33], sTrail, sExplo, gmsgWeaponList, gItem;

public plugin_init() {
	register_plugin(PLUGIN, VERSION, AUTHOR);
	RegisterHam(Ham_Weapon_PrimaryAttack, fgl, "fgl_Pattack");
	RegisterHam(Ham_Item_AddToPlayer, fgl, "fgl_atp");
	register_forward(FM_SetModel, "fgl_setmodel");
	register_forward(FM_UpdateClientData, "client_data_post", 1);
	register_event("CurWeapon","CurrentWeapon","be","1=1")
	RegisterHam(Ham_Item_PostFrame, fgl, "fgl_PostFrame");
	RegisterHam(Ham_Weapon_Reload, fgl, "fgl_Reload");
	RegisterHam(Ham_Weapon_Reload, fgl, "fgl_Reload_Post", 1);
	
	register_clcmd("weapon_fglauncher_cso", "Hook_Select");
	
	register_touch("fgl_grenade", "*", "fgl_touch");
	
	gmsgWeaponList = get_user_msgid("WeaponList");
	
	gItem = zp_register_extra_item("FG-LAUNCHER", 15, ZP_TEAM_HUMAN);
}

public plugin_precache(){
	precache_model(v_model);
	precache_model(p_model);
	precache_model(w_model);
	precache_model(s_model);
	precache_generic( "sprites/weapon_fglauncher_cso.txt" );
	precache_generic( "sprites/cso/640hud86.spr" );
	precache_generic( "sprites/cso/640hud7x.spr" );
	precache_generic( "sprites/cso/scope_vip_grenade.spr" );
	sTrail = precache_model(spark_sprite2);
	sExplo = precache_model(spark_sprite1);
	precache_sound(shoot_sound);
}

public zp_extra_item_selected(id, itemid){
	if(itemid == gItem) {
		fgl_Give(id);
	}
}

public Hook_Select(id)
{
	engclient_cmd(id, fgl);
	return PLUGIN_HANDLED;
}

public CurrentWeapon(id){
	static lastweapon[33];
	if(gHasFg[id] && get_user_weapon(id) == CSW_FGLAUNCHER){
		if(lastweapon[id] != CSW_FGLAUNCHER) set_pev(id, pev_weaponanim, 3);
		set_pev(id, pev_viewmodel2, v_model);
		set_pev(id, pev_weaponmodel2, p_model);
	}
	lastweapon[id] = get_user_weapon(id);
}

public fgl_Pattack(weapon){
	new owner = pev(weapon, pev_owner);
	
	if(gHasFg[owner] && cs_get_weapon_ammo(weapon)>0){
		fakeshoot(owner, weapon);

		return HAM_SUPERCEDE;
	}
	return HAM_IGNORED;
}

public fgl_atp(fg, id) {
	if(!is_valid_ent(fg) || !is_user_connected(id)) return HAM_IGNORED;
        
	if(entity_get_int(fg, EV_INT_impulse) == 1431)
	{
		gHasFg[id] = true;
		entity_set_int(fg, EV_INT_impulse, 0);
		Sprite(id);
		return HAM_HANDLED;
	}
	else Sprite(id,0);
	
	return HAM_IGNORED;
}

public fgl_setmodel(entity, model[])
{
	if(!is_valid_ent(entity))
		return FMRES_IGNORED;
	
	new cn[33];
	pev(entity, pev_classname, cn, 32);
	
	if(equal(cn, "weaponbox")) {
	
		new owner = pev(entity, pev_owner);
	
		if(equal(model, "models/w_mp5.mdl"))
		{
			static iStoredFGID;
			iStoredFGID = find_ent_by_owner(-1, "weapon_mp5navy", entity);
			
			if(gHasFg[owner] && is_valid_ent(iStoredFGID))
			{
				entity_set_int(iStoredFGID, EV_INT_impulse, 1431);
				gHasFg[owner] = false;
				
				entity_set_model(entity, w_model);
				return FMRES_SUPERCEDE;
			}
		}
	}
	
	return FMRES_IGNORED;
}

public fakeshoot(id, weapon){
	new Float:f[3];
	cs_set_weapon_ammo(weapon, cs_get_weapon_ammo(weapon)-1);
	set_pev(id, pev_punchangle, Float:{ -10.0, 0.0, 0.0 });
	UTIL_PlayWeaponAnimation(id, 1);
	emit_sound(id, CHAN_WEAPON, shoot_sound, 1.0, ATTN_NORM, 0, PITCH_NORM);
	set_pdata_float(id, 83, 1.5);
	pev(id, pev_origin, f);
	f[2]+=3.0;
	set_pev(id, pev_origin, f);
	set_task(0.1, "check_stuck", id+121);
	
	create_grenade(id);
}

public create_grenade(id){
	new grenade = create_entity("info_target"), Float:fOrigin[3], Float:fVelocity[3], Float:fAngles[3];
	
	engfunc(EngFunc_GetAttachment, id, 1, fOrigin, fAngles);
	
	velocity_by_aim(id, 1000, fVelocity);
	fVelocity[2]+=100.0;
	
	pev(id, pev_v_angle, fAngles);
	
	set_pev(grenade, pev_classname, "fgl_grenade");
	set_pev(grenade, pev_origin, fOrigin);
	set_pev(grenade, pev_velocity, fVelocity);
	set_pev(grenade, pev_angles, fAngles);
	set_pev(grenade, pev_movetype, MOVETYPE_TOSS);
	set_pev(grenade, pev_solid, SOLID_BBOX);
	set_pev(grenade, pev_owner, id);
	
	entity_set_model(grenade, s_model);
	
	message_begin(MSG_BROADCAST, SVC_TEMPENTITY);
	write_byte(TE_BEAMFOLLOW);
	write_short(grenade);
	write_short(sTrail);
	write_byte(10);
	write_byte(3);
	write_byte(255);
	write_byte(255);
	write_byte(255);
	write_byte(250);
	message_end();
	
}

public fgl_touch(ent){
	new Float:originF[3];
	pev(ent, pev_origin, originF);
	
	engfunc(EngFunc_MessageBegin, MSG_PAS, SVC_TEMPENTITY, originF, 0);
	write_byte(TE_WORLDDECAL);
	engfunc(EngFunc_WriteCoord, originF[0]);
	engfunc(EngFunc_WriteCoord, originF[1]);
	engfunc(EngFunc_WriteCoord, originF[2]);
	write_byte(engfunc(EngFunc_DecalIndex,"{scorch3"));
	message_end();
	
	message_begin(MSG_BROADCAST, SVC_TEMPENTITY);
	write_byte(TE_EXPLOSION);
	engfunc(EngFunc_WriteCoord, originF[0]);
	engfunc(EngFunc_WriteCoord, originF[1]);
	engfunc(EngFunc_WriteCoord, originF[2]+60.0);
	write_short(sTrail);
	write_byte(10);
	write_byte(15);
	write_byte(0);
	message_end();
	
	message_begin(MSG_BROADCAST, SVC_TEMPENTITY);
	write_byte(TE_SPRITE);
	engfunc(EngFunc_WriteCoord, originF[0]+random_float(-5.0, 5.0));
	engfunc(EngFunc_WriteCoord, originF[1]+random_float(-5.0, 5.0));
	engfunc(EngFunc_WriteCoord, originF[2]+200.0);
	write_short(sExplo);
	write_byte(15);
	write_byte(200);
	message_end();
			
	new owner = pev(ent, pev_owner);
	new a = FM_NULLENT;

	while((a = find_ent_in_sphere(a,originF,300.0)) != 0) {
		
		if(a!=owner && a!=ent && pev(a,pev_takedamage)!=DAMAGE_NO && is_user_connected(a) && zp_get_user_zombie(a)) {
			ExecuteHamB( Ham_TakeDamage, a ,owner,owner, (damage*60/entity_range(ent,a)), DMG_BULLET);
		}
	}
	remove_entity(ent);
}

public check_stuck(id){
	id-=121;
	new Float:f[3];
	if(is_player_stuck(id)){
		pev(id, pev_origin, f);
		f[2]-=3.0;
		set_pev(id, pev_origin, f);
	}
}

public client_data_post(id, SendWeapons, CD_Handle)
{
	if(is_user_alive(id) && get_user_weapon(id) == CSW_FGLAUNCHER && gHasFg[id])
		set_cd(CD_Handle, CD_flNextAttack, halflife_time () + 0.00001);
}

public fgl_PostFrame(weapon_entity) {
	new id = pev(weapon_entity, pev_owner);
	if (!is_user_connected(id) || !gHasFg[id])
		return HAM_IGNORED;

	new Float:flNextAttack = get_pdata_float(id, 83, 4);

	new iClip = get_pdata_int(weapon_entity, 51, 4);

	new fInReload = get_pdata_int(weapon_entity, 54, 4) ;

	if( fInReload && flNextAttack <= 0.0 )
	{
		new j = min(clipammo - iClip, cs_get_user_bpammo(id, CSW_FGLAUNCHER));
	
		set_pdata_int(weapon_entity, 51, iClip + j, 4);
		cs_set_user_bpammo(id, CSW_FGLAUNCHER, cs_get_user_bpammo(id, CSW_FGLAUNCHER)-j);
		
		set_pdata_int(weapon_entity, 54, 0, 4);
		fInReload = 0;
	}

	return HAM_IGNORED;
}

public fgl_Reload(weapon_entity) {
	new id = pev(weapon_entity, pev_owner);
	if (!is_user_connected(id) || !gHasFg[id])
		return HAM_IGNORED;

	new iBpAmmo = cs_get_user_bpammo(id, CSW_FGLAUNCHER);
	new iClip = get_pdata_int(weapon_entity, 51, 4);

	if (iBpAmmo <= 0 || iClip >= 10)
		return HAM_SUPERCEDE;


	return HAM_IGNORED;
}

public fgl_Reload_Post(weapon_entity) {
	new id = pev(weapon_entity, pev_owner);
	
	if (!is_user_connected(id))
		return HAM_IGNORED;

	if (!gHasFg[id])
		return HAM_IGNORED;

	set_pdata_float(weapon_entity, 48, 6.0, 4);

	set_pdata_float(id, 83, 6.0, 5);

	set_pdata_int(weapon_entity, 54, 1, 4);

	UTIL_PlayWeaponAnimation(id, 2);

	return HAM_IGNORED;
}

public fgl_Give(id){
	
	gHasFg[id] = true;
	new weapon = give_item(id, fgl);
	cs_set_user_bpammo(id, CSW_FGLAUNCHER, 40);
	cs_set_weapon_ammo(weapon, 10);
	ExecuteHamB(Ham_Item_Deploy, weapon);
	Sprite(id);
	
}

stock Sprite(id, type=1)
{
	
	message_begin(MSG_ONE, gmsgWeaponList, {0,0,0}, id);
	write_string(type?"weapon_fglauncher_cso":fgl);
	write_byte(10);
	write_byte(40);
	write_byte(-1);
	write_byte(-1);
	write_byte(0);
	write_byte(7);
	write_byte(19);
	write_byte(0);
	message_end();
	
}

stock is_player_stuck(id)
{
	static Float:originF[3];
	pev(id, pev_origin, originF);
	
	engfunc(EngFunc_TraceHull, originF, originF, 0, (pev(id, pev_flags) & FL_DUCKING) ? HULL_HEAD : HULL_HUMAN, id, 0);
	
	if (get_tr2(0, TR_StartSolid) || get_tr2(0, TR_AllSolid) || !get_tr2(0, TR_InOpen))
		return true;
	
	return false;
}

stock UTIL_PlayWeaponAnimation(const Player, const Sequence)
{
	set_pev(Player, pev_weaponanim, Sequence);
        
	message_begin(MSG_ONE_UNRELIABLE, SVC_WEAPONANIM, .player = Player);
	write_byte(Sequence);
	write_byte(2);
	message_end();
}
/* AMXX-Studio Notes - DO NOT MODIFY BELOW HERE
*{\\ rtf1\\ ansi\\ deff0{\\ fonttbl{\\ f0\\ fnil Tahoma;}}\n\\ viewkind4\\ uc1\\ pard\\ lang1049\\ f0\\ fs16 \n\\ par }
*/
