#pragma once

// @source: master/game/shared/cstrike15/gametypes.h
#pragma region valve_gametypes

enum EGameType : int
{
	GAMETYPE_UNKNOWN = -1,
	GAMETYPE_CLASSIC,
	GAMETYPE_GUNGAME,
	GAMETYPE_TRAINING,
	GAMETYPE_CUSTOM,
	GAMETYPE_COOPERATIVE,
	GAMETYPE_SKIRMISH,
	GAMETYPE_FREEFORALL
};

enum EGameMode : int
{
	GAMEMODE_UNKNOWN = -1,

	// GAMETYPE_CLASSIC
	GAMEMODE_CLASSIC_CASUAL = 0,
	GAMEMODE_CLASSIC_COMPETITIVE,
	GAMEMODE_CLASSIC_SCRIM_COMPETITIVE2V2,
	GAMEMODE_CLASSIC_SCRIM_COMPETITIVE5V5,

	// GAMETYPE_GUNGAME
	GAMEMODE_GUNGAME_PROGRESSIVE = 0,
	GAMEMODE_GUNGAME_BOMB,
	GAMEMODE_GUNGAME_DEATHMATCH,

	// GAMETYPE_TRAINING
	GAMEMODE_TRAINING_DEFAULT = 0,

	// GAMETYPE_CUSTOM
	GAMEMODE_CUSTOM_DEFAULT = 0,

	// GAMETYPE_COOPERATIVE
	GAMEMODE_COOPERATIVE_DEFAULT = 0,
	GAMEMODE_COOPERATIVE_MISSION,

	// GAMETYPE_SKIRMISH
	GAMEMODE_SKIRMISH_DEFAULT = 0,

	// GAMETYPE_FREEFORALL
	GAMEMODE_FREEFORALL_SURVIVAL = 0
};

#pragma endregion

enum ELifeState : int
{
	LIFE_ALIVE = 0,
	LIFE_DYING,
	LIFE_DEAD,
	LIFE_RESPAWNABLE,
	LIFE_DISCARDBODY
};

enum EFlags : int
{
	FL_ONGROUND = (1 << 0), // entity is at rest / on the ground
	FL_DUCKING = (1 << 1), // player is fully crouched/uncrouched
	FL_ANIMDUCKING = (1 << 2), // player is in the process of crouching or uncrouching but could be in transition
	FL_WATERJUMP = (1 << 3), // player is jumping out of water
	FL_ONTRAIN = (1 << 4), // player is controlling a train, so movement commands should be ignored on client during prediction
	FL_INRAIN = (1 << 5), // entity is standing in rain
	FL_FROZEN = (1 << 6), // player is frozen for 3rd-person camera
	FL_ATCONTROLS = (1 << 7), // player can't move, but keeps key inputs for controlling another entity
	FL_CLIENT = (1 << 8), // entity is a client (player)
	FL_FAKECLIENT = (1 << 9), // entity is a fake client, simulated server side; don't send network messages to them
	FL_INWATER = (1 << 10), // entity is in water
	FL_FLY = (1 << 11),
	FL_SWIM = (1 << 12),
	FL_CONVEYOR = (1 << 13),
	FL_NPC = (1 << 14),
	FL_GODMODE = (1 << 15),
	FL_NOTARGET = (1 << 16),
	FL_AIMTARGET = (1 << 17),
	FL_PARTIALGROUND = (1 << 18), // entity is standing on a place where not all corners are valid
	FL_STATICPROP = (1 << 19), // entity is a static property
	FL_GRAPHED = (1 << 20),
	FL_GRENADE = (1 << 21),
	FL_STEPMOVEMENT = (1 << 22),
	FL_DONTTOUCH = (1 << 23),
	FL_BASEVELOCITY = (1 << 24), // entity have applied base velocity this frame
	FL_WORLDBRUSH = (1 << 25), // entity is not moveable/removeable brush (part of the world, but represented as an entity for transparency or something)
	FL_OBJECT = (1 << 26),
	FL_KILLME = (1 << 27), // entity is marked for death and will be freed by the game
	FL_ONFIRE = (1 << 28),
	FL_DISSOLVING = (1 << 29),
	FL_TRANSRAGDOLL = (1 << 30), // entity is turning into client-side ragdoll
	FL_UNBLOCKABLE_BY_PLAYER = (1 << 31)
};

enum EEFlags : int
{
	EFL_KILLME = (1 << 0),
	EFL_DORMANT = (1 << 1),
	EFL_NOCLIP_ACTIVE = (1 << 2),
	EFL_SETTING_UP_BONES = (1 << 3),
	EFL_KEEP_ON_RECREATE_ENTITIES = (1 << 4),
	EFL_DIRTY_SHADOWUPDATE = (1 << 5),
	EFL_NOTIFY = (1 << 6),
	EFL_FORCE_CHECK_TRANSMIT = (1 << 7),
	EFL_BOT_FROZEN = (1 << 8),
	EFL_SERVER_ONLY = (1 << 9),
	EFL_NO_AUTO_EDICT_ATTACH = (1 << 10),
	EFL_DIRTY_ABSTRANSFORM = (1 << 11),
	EFL_DIRTY_ABSVELOCITY = (1 << 12),
	EFL_DIRTY_ABSANGVELOCITY = (1 << 13),
	EFL_DIRTY_SURROUNDING_COLLISION_BOUNDS = (1 << 14),
	EFL_DIRTY_SPATIAL_PARTITION = (1 << 15),
	EFL_HAS_PLAYER_CHILD = (1 << 16),
	EFL_IN_SKYBOX = (1 << 17),
	EFL_USE_PARTITION_WHEN_NOT_SOLID = (1 << 18),
	EFL_TOUCHING_FLUID = (1 << 19),
	EFL_IS_BEING_LIFTED_BY_BARNACLE = (1 << 20),
	EFL_NO_ROTORWASH_PUSH = (1 << 21),
	EFL_NO_THINK_FUNCTION = (1 << 22),
	EFL_NO_GAME_PHYSICS_SIMULATION = (1 << 23),
	EFL_CHECK_UNTOUCH = (1 << 24),
	EFL_DONTBLOCKLOS = (1 << 25),
	EFL_DONTWALKON = (1 << 26),
	EFL_NO_DISSOLVE = (1 << 27),
	EFL_NO_MEGAPHYSCANNON_RAGDOLL = (1 << 28),
	EFL_NO_WATER_VELOCITY_CHANGE = (1 << 29),
	EFL_NO_PHYSCANNON_INTERACTION = (1 << 30),
	EFL_NO_DAMAGE_FORCES = (1 << 31)
};

enum EMoveType : int
{
	MOVETYPE_NONE = 0,
	MOVETYPE_ISOMETRIC,
	MOVETYPE_WALK,
	MOVETYPE_STEP,
	MOVETYPE_FLY, // no gravity, but still collides with stuff
	MOVETYPE_FLYGRAVITY, // flies through the air and is affected by gravity
	MOVETYPE_VPHYSICS,
	MOVETYPE_PUSH, // no clip to world, push and crush
	MOVETYPE_NOCLIP, // no gravity, no collisions, still do velocity/absvelocity
	MOVETYPE_LADDER,
	MOVETYPE_OBSERVER, // observer movement, depends on player's observer mode
	MOVETYPE_CUSTOM,
	MOVETYPE_LAST = MOVETYPE_CUSTOM,
	MOVETYPE_MAX_BITS = 4
};

// identifies how submerged in water a player is
enum : int
{
	WL_NOTINWATER = 0,
	WL_FEET,
	WL_WAIST,
	WL_EYES
};

enum ETeamID : int
{
	TEAM_UNK,
	TEAM_SPECTATOR,
	TEAM_TT,
	TEAM_CT
};

using ItemDefinitionIndex_t = std::uint16_t;
enum EItemDefinitionIndexes : ItemDefinitionIndex_t
{
	WEAPON_NONE,
	WEAPON_DESERT_EAGLE,
	WEAPON_DUAL_BERETTAS,
	WEAPON_FIVE_SEVEN,
	WEAPON_GLOCK_18,
	WEAPON_AK_47 = 7,
	WEAPON_AUG,
	WEAPON_AWP,
	WEAPON_FAMAS,
	WEAPON_G3SG1,
	WEAPON_GALIL_AR = 13,
	WEAPON_M249,
	WEAPON_M4A4 = 16,
	WEAPON_MAC_10,
	WEAPON_P90 = 19,
	WEAPON_REPULSOR_DEVICE,
	WEAPON_MP5_SD = 23,
	WEAPON_UMP_45,
	WEAPON_XM1014,
	WEAPON_PP_BIZON,
	WEAPON_MAG_7,
	WEAPON_NEGEV,
	WEAPON_SAWED_OFF,
	WEAPON_TEC_9,
	WEAPON_ZEUS_X27,
	WEAPON_P2000,
	WEAPON_MP7,
	WEAPON_MP9,
	WEAPON_NOVA,
	WEAPON_P250,
	WEAPON_RIOT_SHIELD,
	WEAPON_SCAR_20,
	WEAPON_SG_553,
	WEAPON_SSG_08,
	WEAPON_KNIFE0,
	WEAPON_KNIFE1,
	WEAPON_FLASHBANG,
	WEAPON_HIGH_EXPLOSIVE_GRENADE,
	WEAPON_SMOKE_GRENADE,
	WEAPON_MOLOTOV,
	WEAPON_DECOY_GRENADE,
	WEAPON_INCENDIARY_GRENADE,
	WEAPON_C4_EXPLOSIVE,
	WEAPON_KEVLAR_VEST,
	WEAPON_KEVLAR_and_HELMET,
	WEAPON_HEAVY_ASSAULT_SUIT,
	WEAPON_NO_LOCALIZED_NAME0 = 54,
	WEAPON_DEFUSE_KIT,
	WEAPON_RESCUE_KIT,
	WEAPON_MEDI_SHOT,
	WEAPON_MUSIC_KIT,
	WEAPON_KNIFE2,
	WEAPON_M4A1_S,
	WEAPON_USP_S,
	WEAPON_TRADE_UP_CONTRACT,
	WEAPON_CZ75_AUTO,
	WEAPON_R8_REVOLVER,
	WEAPON_TACTICAL_AWARENESS_GRENADE = 68,
	WEAPON_BARE_HANDS,
	WEAPON_BREACH_CHARGE,
	WEAPON_TABLET = 72,
	WEAPON_KNIFE3 = 74,
	WEAPON_AXE,
	WEAPON_HAMMER,
	WEAPON_WRENCH = 78,
	WEAPON_SPECTRAL_SHIV = 80,
	WEAPON_FIRE_BOMB,
	WEAPON_DIVERSION_DEVICE,
	WEAPON_FRAG_GRENADE,
	WEAPON_SNOWBALL,
	WEAPON_BUMP_MINE,
	WEAPON_BAYONET = 500,
	WEAPON_CLASSIC_KNIFE = 503,
	WEAPON_FLIP_KNIFE = 505,
	WEAPON_GUT_KNIFE,
	WEAPON_KARAMBIT,
	WEAPON_M9_BAYONET,
	WEAPON_HUNTSMAN_KNIFE,
	WEAPON_FALCHION_KNIFE = 512,
	WEAPON_BOWIE_KNIFE = 514,
	WEAPON_BUTTERFLY_KNIFE,
	WEAPON_SHADOW_DAGGERS,
	WEAPON_PARACORD_KNIFE,
	WEAPON_SURVIVAL_KNIFE,
	WEAPON_URSUS_KNIFE,
	WEAPON_NAVAJA_KNIFE,
	WEAPON_NOMAD_KNIFE,
	WEAPON_STILETTO_KNIFE,
	WEAPON_TALON_KNIFE,
	WEAPON_SKELETON_KNIFE = 525,
};

enum EWeaponType : std::uint32_t
{
	WEAPONTYPE_KNIFE = 0,
	WEAPONTYPE_PISTOL = 1,
	WEAPONTYPE_SUBMACHINEGUN = 2,
	WEAPONTYPE_RIFLE = 3,
	WEAPONTYPE_SHOTGUN = 4,
	WEAPONTYPE_SNIPER_RIFLE = 5,
	WEAPONTYPE_MACHINEGUN = 6,
	WEAPONTYPE_C4 = 7,
	WEAPONTYPE_TASER = 8,
	WEAPONTYPE_GRENADE = 9,
	WEAPONTYPE_EQUIPMENT = 10,
	WEAPONTYPE_STACKABLEITEM = 11,
	WEAPONTYPE_FISTS = 12,
	WEAPONTYPE_BREACHCHARGE = 13,
	WEAPONTYPE_BUMPMINE = 14,
	WEAPONTYPE_TABLET = 15,
	WEAPONTYPE_MELEE = 16,
	WEAPONTYPE_SHIELD = 17,
	WEAPONTYPE_ZONE_REPULSOR = 18,
	WEAPONTYPE_UNKNOWN = 19
};
