mirror of
https://github.com/lifestorm/wnsrc.git
synced 2025-12-17 05:43:46 +03:00
Upload
This commit is contained in:
278
lua/weapons/weapon_medkit.lua
Normal file
278
lua/weapons/weapon_medkit.lua
Normal file
@@ -0,0 +1,278 @@
|
||||
--[[
|
||||
| This file was obtained through the combined efforts
|
||||
| of Madbluntz & Plymouth Antiquarian Society.
|
||||
|
|
||||
| Credits: lifestorm, Gregory Wayne Rossel JR.,
|
||||
| Maloy, DrPepper10 @ RIP, Atle!
|
||||
|
|
||||
| Visit for more: https://plymouth.thetwilightzone.ru/
|
||||
--]]
|
||||
|
||||
|
||||
AddCSLuaFile()
|
||||
|
||||
SWEP.PrintName = "#GMOD_MedKit"
|
||||
SWEP.Author = "robotboy655, MaxOfS2D, code_gs"
|
||||
SWEP.Purpose = "Heal other people with primary attack, heal yourself with secondary attack."
|
||||
|
||||
SWEP.Slot = 5
|
||||
SWEP.SlotPos = 3
|
||||
|
||||
SWEP.Spawnable = true
|
||||
|
||||
SWEP.ViewModel = Model( "models/weapons/c_medkit.mdl" )
|
||||
SWEP.WorldModel = Model( "models/weapons/w_medkit.mdl" )
|
||||
SWEP.ViewModelFOV = 54
|
||||
SWEP.UseHands = true
|
||||
|
||||
SWEP.Primary.ClipSize = 100
|
||||
SWEP.Primary.DefaultClip = SWEP.Primary.ClipSize
|
||||
SWEP.Primary.Automatic = false
|
||||
SWEP.Primary.Ammo = ""
|
||||
|
||||
SWEP.Secondary.ClipSize = -1
|
||||
SWEP.Secondary.DefaultClip = -1
|
||||
SWEP.Secondary.Automatic = false
|
||||
SWEP.Secondary.Ammo = ""
|
||||
|
||||
SWEP.HoldType = "slam"
|
||||
|
||||
SWEP.HealSound = Sound( "HealthKit.Touch" )
|
||||
SWEP.DenySound = Sound( "WallHealth.Deny" )
|
||||
|
||||
SWEP.HealCooldown = 0.5 -- Time between successful heals
|
||||
SWEP.DenyCooldown = 1 -- Time between unsuccessful heals
|
||||
|
||||
SWEP.HealAmount = 20 -- Maximum heal amount per use
|
||||
SWEP.HealRange = 64 -- Range in units at which healing works
|
||||
|
||||
SWEP.AmmoRegenRate = 1 -- Number of seconds before each ammo regen
|
||||
SWEP.AmmoRegenAmount = 2 -- Amount of ammo refilled every AmmoRegenRate seconds
|
||||
|
||||
function SWEP:Initialize()
|
||||
|
||||
self:SetHoldType( self.HoldType )
|
||||
|
||||
-- Prevent large ammo jumps on-creation
|
||||
-- if DefaultClip < ClipSize
|
||||
self:SetLastAmmoRegen( CurTime() )
|
||||
|
||||
if ( CLIENT ) then
|
||||
self.AmmoDisplay = {
|
||||
Draw = true,
|
||||
PrimaryClip = 0
|
||||
}
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
function SWEP:Deploy()
|
||||
|
||||
-- Regen what we've gained since we've holstered
|
||||
-- and realign the timer
|
||||
self:Regen( false )
|
||||
|
||||
return true
|
||||
|
||||
end
|
||||
|
||||
function SWEP:SetupDataTables()
|
||||
|
||||
self:NetworkVar( "Float", 0, "LastAmmoRegen" )
|
||||
self:NetworkVar( "Float", 1, "NextIdle" )
|
||||
|
||||
end
|
||||
|
||||
function SWEP:PrimaryAttack()
|
||||
|
||||
local owner = self:GetOwner()
|
||||
local dolagcomp = SERVER and owner:IsPlayer()
|
||||
|
||||
if ( dolagcomp ) then
|
||||
owner:LagCompensation( true )
|
||||
end
|
||||
|
||||
local startpos = owner:GetShootPos()
|
||||
local tr = util.TraceLine( {
|
||||
start = startpos,
|
||||
endpos = startpos + owner:GetAimVector() * self.HealRange,
|
||||
filter = owner
|
||||
} )
|
||||
|
||||
if ( dolagcomp ) then
|
||||
owner:LagCompensation( false )
|
||||
end
|
||||
|
||||
self:DoHeal( tr.Entity )
|
||||
|
||||
end
|
||||
|
||||
function SWEP:SecondaryAttack()
|
||||
|
||||
self:DoHeal( self:GetOwner() )
|
||||
|
||||
end
|
||||
|
||||
function SWEP:Reload()
|
||||
end
|
||||
|
||||
local DAMAGE_YES = 2
|
||||
|
||||
-- Basic black/whitelist function
|
||||
-- Checking if the entity's health is below its max is done in SWEP:DoHeal
|
||||
function SWEP:CanHeal( ent )
|
||||
|
||||
-- ent may be NULL here, but these functions return false for it
|
||||
if ( ent:IsPlayer() or ent:IsNPC() ) then
|
||||
local takedamage = ent:GetInternalVariable( "m_takedamage" )
|
||||
|
||||
-- Don't heal turrets and helicopters
|
||||
return takedamage == nil or takedamage == DAMAGE_YES
|
||||
end
|
||||
|
||||
return false
|
||||
|
||||
end
|
||||
|
||||
function SWEP:DoHeal( ent )
|
||||
|
||||
local amount = self.HealAmount
|
||||
|
||||
if ( !self:CanHeal( ent ) ) then self:HealFail( ent ) return false end
|
||||
|
||||
local health, maxhealth = ent:Health(), ent:GetMaxHealth()
|
||||
if ( health >= maxhealth ) then self:HealFail( ent ) return false end
|
||||
|
||||
-- Check regen right before we access the clip
|
||||
-- to make sure we're up to date
|
||||
self:Regen( true )
|
||||
|
||||
local healamount = self.HealAmount
|
||||
|
||||
-- No support for "damage kits"
|
||||
if ( healamount > 0 ) then
|
||||
healamount = math.min( maxhealth - health, healamount )
|
||||
local ammo = self:Clip1()
|
||||
if ( ammo < healamount ) then self:HealFail( ent ) return false end
|
||||
|
||||
-- Heal ent
|
||||
self:SetClip1( ammo - healamount )
|
||||
ent:SetHealth( health + healamount )
|
||||
else
|
||||
healamount = 0
|
||||
end
|
||||
|
||||
self:HealSuccess( ent, healamount )
|
||||
|
||||
return true
|
||||
|
||||
end
|
||||
|
||||
function SWEP:HealSuccess( ent, healamount )
|
||||
|
||||
-- Do effects
|
||||
self:EmitSound( self.HealSound )
|
||||
self:SendWeaponAnim( ACT_VM_PRIMARYATTACK )
|
||||
|
||||
local owner = self:GetOwner()
|
||||
|
||||
if ( owner:IsValid() ) then
|
||||
owner:SetAnimation( PLAYER_ATTACK1 )
|
||||
end
|
||||
|
||||
local curtime = CurTime()
|
||||
|
||||
-- Reset regen time
|
||||
self:SetLastAmmoRegen( curtime )
|
||||
|
||||
-- Set next idle time
|
||||
local endtime = curtime + self:SequenceDuration()
|
||||
self:SetNextIdle( endtime )
|
||||
|
||||
-- Set next firing time
|
||||
endtime = endtime + self.HealCooldown
|
||||
self:SetNextPrimaryFire( endtime )
|
||||
self:SetNextSecondaryFire( endtime )
|
||||
|
||||
end
|
||||
|
||||
function SWEP:HealFail( ent )
|
||||
|
||||
-- Do effects
|
||||
self:EmitSound( self.DenySound )
|
||||
|
||||
-- Setup next firing time
|
||||
local endtime = CurTime() + self.DenyCooldown
|
||||
self:SetNextPrimaryFire( endtime )
|
||||
self:SetNextSecondaryFire( endtime )
|
||||
|
||||
end
|
||||
|
||||
function SWEP:Think()
|
||||
|
||||
-- Try ammo regen
|
||||
-- but keep it aligned to the last action time
|
||||
self:Regen( true )
|
||||
|
||||
-- Do idle anim
|
||||
self:Idle()
|
||||
|
||||
end
|
||||
|
||||
function SWEP:Regen( keepaligned )
|
||||
|
||||
local curtime = CurTime()
|
||||
local lastregen = self:GetLastAmmoRegen()
|
||||
local timepassed = curtime - lastregen
|
||||
local regenrate = self.AmmoRegenRate
|
||||
|
||||
-- Not ready to regenerate
|
||||
if ( timepassed < regenrate ) then return false end
|
||||
|
||||
local ammo = self:Clip1()
|
||||
local maxammo = self.Primary.ClipSize
|
||||
|
||||
-- Already at/over max ammo
|
||||
if ( ammo >= maxammo ) then return false end
|
||||
|
||||
if ( regenrate > 0 ) then
|
||||
self:SetClip1( math.min( ammo + math.floor( timepassed / regenrate ) * self.AmmoRegenAmount, maxammo ) )
|
||||
|
||||
-- If we are setting the last regen time from the Think function,
|
||||
-- keep it aligned with the last action time to prevent late Thinks from
|
||||
-- creating hiccups in the rate
|
||||
self:SetLastAmmoRegen( keepaligned == true and curtime + timepassed % regenrate or curtime )
|
||||
else
|
||||
self:SetClip1( maxammo )
|
||||
self:SetLastAmmoRegen( curtime )
|
||||
end
|
||||
|
||||
return true
|
||||
|
||||
end
|
||||
|
||||
function SWEP:Idle()
|
||||
|
||||
-- Update idle anim
|
||||
local curtime = CurTime()
|
||||
|
||||
if ( curtime < self:GetNextIdle() ) then return false end
|
||||
|
||||
self:SendWeaponAnim( ACT_VM_IDLE )
|
||||
self:SetNextIdle( curtime + self:SequenceDuration() )
|
||||
|
||||
return true
|
||||
|
||||
end
|
||||
|
||||
-- The following code does not need to exist on the server, so bail
|
||||
if ( SERVER ) then return end
|
||||
|
||||
function SWEP:CustomAmmoDisplay()
|
||||
|
||||
local display = self.AmmoDisplay
|
||||
display.PrimaryClip = self:Clip1()
|
||||
|
||||
return display
|
||||
|
||||
end
|
||||
Reference in New Issue
Block a user